[web] Refactor management of remotes and outputs

This commit is contained in:
Alain Nussbaumer
2025-04-27 16:10:30 +02:00
parent 95de42e6be
commit 786d8cbc09
16 changed files with 172 additions and 153 deletions

View File

@@ -0,0 +1,41 @@
<template>
<div class="field is-grouped">
<div class="control">
<input
ref="input"
v-model="value"
class="input"
inputmode="numeric"
pattern="[\d]{4}"
:placeholder="placeholder"
@input="validate"
/>
</div>
<slot />
</div>
</template>
<script>
export default {
name: 'ControlPinField',
props: {
placeholder: { required: true, type: String }
},
emits: ['input'],
data() {
return { value: '' }
},
mounted() {
setTimeout(() => {
this.$refs.input.focus()
}, 10)
},
methods: {
validate(event) {
const { validity } = event.target
const invalid = validity.patternMismatch || validity.valueMissing
this.$emit('input', this.value, invalid)
}
}
}
</script>

View File

@@ -29,10 +29,7 @@ export default {
},
emits: ['input'],
data() {
return {
disabled: true,
value: ''
}
return { value: '' }
},
mounted() {
setTimeout(() => {
@@ -42,8 +39,8 @@ export default {
methods: {
validate(event) {
const { validity } = event.target
this.disabled = validity.patternMismatch || validity.valueMissing
this.$emit('input', this.value, this.disabled)
const invalid = validity.patternMismatch || validity.valueMissing
this.$emit('input', this.value, invalid)
}
}
}

View File

@@ -7,32 +7,25 @@
>
<template #content>
<form @submit.prevent="pair">
<label class="label" v-text="pairing.remote" />
<div class="field">
<div class="control">
<input
ref="pin_field"
v-model="pairing_req.pin"
class="input"
inputmode="numeric"
pattern="[\d]{4}"
:placeholder="$t('dialog.remote-pairing.pairing-code')"
/>
</div>
</div>
<label class="label" v-text="remoteStore.remote" />
<control-pin-field
:placeholder="$t('dialog.remote-pairing.pairing-code')"
@input="onPinChange"
/>
</form>
</template>
</modal-dialog>
</template>
<script>
import ControlPinField from '@/components/ControlPinField.vue'
import ModalDialog from '@/components/ModalDialog.vue'
import { useRemotesStore } from '@/stores/remotes'
import webapi from '@/webapi'
export default {
name: 'ModalDialogRemotePairing',
components: { ModalDialog },
components: { ControlPinField, ModalDialog },
props: { show: Boolean },
emits: ['close'],
setup() {
@@ -40,38 +33,34 @@ export default {
},
data() {
return {
pairing_req: { pin: '' }
disabled: true,
pin: ''
}
},
computed: {
actions() {
return [
{ handler: this.cancel, icon: 'cancel', key: 'actions.cancel' },
{ handler: this.pair, icon: 'cellphone', key: 'actions.pair' }
{
disabled: this.disabled,
handler: this.pair,
icon: 'vector-link',
key: 'actions.pair'
}
]
},
pairing() {
return this.remoteStore.pairing
}
},
watch: {
show() {
if (this.show) {
this.loading = false
// Delay setting the focus on the input field until it is part of the DOM and visible
setTimeout(() => {
this.$refs.pin_field.focus()
}, 10)
}
}
},
methods: {
cancel() {
this.$emit('close')
},
onPinChange(pin, disabled) {
this.pin = pin
this.disabled = disabled
},
pair() {
webapi.pairing_kickoff(this.pairing_req).then(() => {
this.pairing_req.pin = ''
webapi.pairing_kickoff({ pin: this.pin }).then(() => {
this.pin = ''
})
}
}

View File

@@ -16,8 +16,8 @@ export default {
to: { name: 'settings-webinterface' }
},
{
key: 'page.settings.tabs.remotes-and-outputs',
to: { name: 'settings-remotes-outputs' }
key: 'page.settings.tabs.devices',
to: { name: 'settings-devices' }
},
{
key: 'page.settings.tabs.artwork',