Skip to content

Commit de19227

Browse files
committed
fix(talk/settings): new design
Signed-off-by: Grigorii K. Shartsev <[email protected]>
1 parent 20e517c commit de19227

File tree

2 files changed

+134
-124
lines changed

2 files changed

+134
-124
lines changed

src/talk/renderer/Settings/DesktopSettingsSection.vue

Lines changed: 85 additions & 124 deletions
Original file line numberDiff line numberDiff line change
@@ -10,21 +10,18 @@ import { t } from '@nextcloud/l10n'
1010
import { storeToRefs } from 'pinia'
1111
import { computed, ref } from 'vue'
1212
import NcButton from '@nextcloud/vue/components/NcButton'
13-
import NcCheckboxRadioSwitch from '@nextcloud/vue/components/NcCheckboxRadioSwitch'
13+
import NcFormBox from '@nextcloud/vue/components/NcFormBox'
14+
import NcFormBoxSwitch from '@nextcloud/vue/components/NcFormBoxSwitch'
15+
import NcFormGroup from '@nextcloud/vue/components/NcFormGroup'
1416
import NcNoteCard from '@nextcloud/vue/components/NcNoteCard'
15-
import NcTextField from '@nextcloud/vue/components/NcTextField'
16-
import IconBellRingOutline from 'vue-material-design-icons/BellRingOutline.vue'
17-
import IconCardAccountPhoneOutline from 'vue-material-design-icons/CardAccountPhoneOutline.vue'
18-
import IconMagnify from 'vue-material-design-icons/Magnify.vue'
19-
import IconMinus from 'vue-material-design-icons/Minus.vue'
20-
import IconPhoneRingOutline from 'vue-material-design-icons/PhoneRingOutline.vue'
21-
import IconPlus from 'vue-material-design-icons/Plus.vue'
17+
import NcRadioGroup from '@nextcloud/vue/components/NcRadioGroup'
18+
import NcRadioGroupButton from '@nextcloud/vue/components/NcRadioGroupButton'
19+
import NcSelect from '@nextcloud/vue/components/NcSelect'
2220
import IconRestore from 'vue-material-design-icons/Restore.vue'
2321
import IconThemeLightDark from 'vue-material-design-icons/ThemeLightDark.vue'
24-
import IconVolumeHigh from 'vue-material-design-icons/VolumeHigh.vue'
25-
import SettingsFormGroup from './components/SettingsFormGroup.vue'
26-
import SettingsSelect from './components/SettingsSelect.vue'
27-
import SettingsSubsection from './components/SettingsSubsection.vue'
22+
import IconWeatherNight from 'vue-material-design-icons/WeatherNight.vue'
23+
import IconWeatherSunny from 'vue-material-design-icons/WeatherSunny.vue'
24+
import UiFormBoxNumber from './components/UiFormBoxNumber.vue'
2825
import { ZOOM_MAX, ZOOM_MIN } from '../../../constants.js'
2926
import { useNcSelectModel } from '../composables/useNcSelectModel.ts'
3027
import { useAppConfigStore } from './appConfig.store.ts'
@@ -37,12 +34,6 @@ const { isRelaunchRequired } = storeToRefs(useAppConfigStore())
3734
const launchAtStartup = useAppConfigValue('launchAtStartup')
3835
3936
const theme = useAppConfigValue('theme')
40-
const themeOptions = [
41-
{ label: t('talk_desktop', 'System default'), value: 'default' } as const,
42-
{ label: t('talk_desktop', 'Light'), value: 'light' } as const,
43-
{ label: t('talk_desktop', 'Dark'), value: 'dark' } as const,
44-
]
45-
const themeOption = useNcSelectModel(theme, themeOptions)
4637
4738
const systemTitleBar = useAppConfigValue('systemTitleBar')
4839
const monochromeTrayIcon = useAppConfigValue('monochromeTrayIcon')
@@ -55,9 +46,9 @@ const zoomFactor = computed({
5546
},
5647
})
5748
const zoomFactorPercentage = computed({
58-
get: () => Math.round(zoomFactor.value * 100).toString(),
59-
set: (value: string) => {
60-
zoomFactor.value = parseFloat(value) / 100
49+
get: () => Math.round(zoomFactor.value * 100),
50+
set: (value: number) => {
51+
zoomFactor.value = value / 100
6152
},
6253
})
6354
const ZOOM_STEP = Math.sqrt(1.2)
@@ -67,20 +58,10 @@ const zoomHint = t('talk_desktop', 'Zoom can be also changed by {key} or mouse w
6758
resetKey: `<kbd>${ctrl} + 0</kbd>`,
6859
}, undefined, { escape: false })
6960
70-
const generalNotificationOptions = [
71-
{ label: t('talk_desktop', 'Always'), value: 'always' } as const,
72-
{ label: t('talk_desktop', 'When not in "Do not disturb"'), value: 'respect-dnd' } as const,
73-
{ label: t('talk_desktop', 'Never'), value: 'never' } as const,
74-
]
75-
7661
const playSoundChat = useAppConfigValue('playSoundChat')
77-
const playSoundChatOption = useNcSelectModel(playSoundChat, generalNotificationOptions)
78-
7962
const playSoundCall = useAppConfigValue('playSoundCall')
80-
const playSoundCallOption = useNcSelectModel(playSoundCall, generalNotificationOptions)
81-
8263
const enableCallbox = useAppConfigValue('enableCallbox')
83-
const enableCallboxOption = useNcSelectModel(enableCallbox, generalNotificationOptions)
64+
const whenNodInDndLabel = t('talk_desktop', 'When not in "Do not disturb"')
8465
8566
const secondarySpeaker = useAppConfigValue('secondarySpeaker')
8667
@@ -122,7 +103,7 @@ function relaunch() {
122103
</script>
123104

124105
<template>
125-
<div>
106+
<div style="display: flex; flex-direction: column; justify-content: stretch; gap: 12px">
126107
<NcNoteCard v-if="isRelaunchRequired" type="info" class="relaunch-require-note-card">
127108
<div class="relaunch-require-note-card__content">
128109
<span>{{ t('talk_desktop', 'Some changes require a relaunch to take effect') }}</span>
@@ -136,106 +117,90 @@ function relaunch() {
136117
</div>
137118
</NcNoteCard>
138119

139-
<SettingsSubsection v-if="!isLinux" :name="t('talk_desktop', 'General')">
140-
<NcCheckboxRadioSwitch v-model="launchAtStartup" type="switch">
141-
{{ t('talk_desktop', 'Launch at startup') }}
142-
</NcCheckboxRadioSwitch>
143-
</SettingsSubsection>
120+
<NcFormBox v-if="!isLinux">
121+
<NcFormBoxSwitch v-model="launchAtStartup" :label="t('talk_desktop', 'Launch at startup')" />
122+
</NcFormBox>
144123

145-
<SettingsSubsection :name="t('talk_desktop', 'Appearance')">
146-
<SettingsSelect v-model="themeOption" :options="themeOptions" :label="t('talk_desktop', 'Theme')">
147-
<template #icon="{ size }">
148-
<IconThemeLightDark :size="size" />
124+
<NcRadioGroup v-model="theme" :label="t('talk_desktop', 'Theme')">
125+
<NcRadioGroupButton :label="t('talk_desktop', 'System default')" value="default">
126+
<template #icon>
127+
<IconThemeLightDark :size="20" />
149128
</template>
150-
</SettingsSelect>
151-
152-
<NcCheckboxRadioSwitch v-model="monochromeTrayIcon" type="switch">
153-
{{ t('talk_desktop', 'Use monochrome tray icon') }}
154-
</NcCheckboxRadioSwitch>
129+
</NcRadioGroupButton>
130+
<NcRadioGroupButton :label="t('talk_desktop', 'Light')" value="light">
131+
<template #icon>
132+
<IconWeatherSunny :size="20" />
133+
</template>
134+
</NcRadioGroupButton>
135+
<NcRadioGroupButton :label="t('talk_desktop', 'Dark')" value="dark">
136+
<template #icon>
137+
<IconWeatherNight :size="20" />
138+
</template>
139+
</NcRadioGroupButton>
140+
</NcRadioGroup>
155141

156-
<NcCheckboxRadioSwitch v-model="systemTitleBar" type="switch">
157-
{{ t('talk_desktop', 'Use system title bar') }}
158-
</NcCheckboxRadioSwitch>
142+
<NcFormGroup :label="t('talk_desktop', 'Appearance')">
143+
<NcFormBox>
144+
<NcFormBoxSwitch v-model="monochromeTrayIcon" :label="t('talk_desktop', 'Use monochrome tray icon')" />
145+
<NcFormBoxSwitch v-model="systemTitleBar" :label="t('talk_desktop', 'Use system title bar')" />
146+
</NcFormBox>
159147

160-
<SettingsFormGroup :label="t('talk_desktop', 'Zoom')">
161-
<template #icon="{ size }">
162-
<IconMagnify :size="size" />
163-
</template>
148+
<NcFormGroup :label="t('talk_desktop', 'Zoom')">
164149
<template #description>
165150
<!-- eslint-disable-next-line vue/no-v-html -->
166151
<span v-html="zoomHint" />
167152
</template>
168-
<template #default="{ inputId, descriptionId }">
169-
<NcButton :aria-label="t('talk_desktop', 'Zoom out')" variant="tertiary" @click="zoomFactor /= ZOOM_STEP">
170-
<template #icon>
171-
<IconMinus :size="20" />
172-
</template>
173-
</NcButton>
174-
<NcTextField
175-
:id="inputId"
176-
class="zoom-input"
177-
:aria-describedby="descriptionId"
178-
label-outside
179-
inputmode="number"
180-
:model-value="zoomFactorPercentage"
181-
@change="zoomFactorPercentage = $event.target.value"
182-
@blur="$event.target.value = zoomFactorPercentage" />
183-
<NcButton :aria-label="t('talk_desktop', 'Zoom in')" variant="tertiary" @click="zoomFactor *= ZOOM_STEP">
184-
<template #icon>
185-
<IconPlus :size="20" />
186-
</template>
187-
</NcButton>
188-
<NcButton @click="zoomFactor = 1">
153+
<NcFormBox>
154+
<UiFormBoxNumber v-model="zoomFactorPercentage" @decrease="zoomFactor /= ZOOM_STEP" @increase="zoomFactor *= ZOOM_STEP" />
155+
<NcButton wide @click="zoomFactor = 1">
189156
<template #icon>
190157
<IconRestore :size="20" />
191158
</template>
192159
{{ t('talk_desktop', 'Reset') }}
193160
</NcButton>
194-
</template>
195-
</SettingsFormGroup>
196-
</SettingsSubsection>
197-
198-
<SettingsSubsection :name="t('talk_desktop', 'Notifications and sounds')">
199-
<SettingsSelect v-model="playSoundChatOption" :options="generalNotificationOptions" :label="t('talk_desktop', 'Play chat notification sound')">
200-
<template #icon="{ size }">
201-
<IconBellRingOutline :size="size" />
202-
</template>
203-
</SettingsSelect>
204-
205-
<SettingsSelect v-model="playSoundCallOption" :options="generalNotificationOptions" :label="t('talk_desktop', 'Play call notification sound')">
206-
<template #icon="{ size }">
207-
<IconPhoneRingOutline :size="size" />
208-
</template>
209-
</SettingsSelect>
210-
211-
<SettingsSelect v-model="enableCallboxOption" :options="generalNotificationOptions" :label="t('talk_desktop', 'Show call notification popup')">
212-
<template #icon="{ size }">
213-
<IconCardAccountPhoneOutline :size="size" />
214-
</template>
215-
</SettingsSelect>
216-
217-
<NcCheckboxRadioSwitch v-model="secondarySpeaker" type="switch">
218-
{{ t('talk_desktop', 'Also repeat call notification on a secondary speaker') }}
219-
</NcCheckboxRadioSwitch>
220-
221-
<SettingsSelect
222-
v-if="secondarySpeaker"
223-
v-model="secondarySpeakerDeviceOption"
224-
:options="secondarySpeakerOptions"
225-
:disabled="secondarySpeakerOptions.length === 1"
226-
:label="t('talk_desktop', 'Secondary speaker')">
227-
<template #icon="{ size }">
228-
<IconVolumeHigh :size="size" />
229-
</template>
230-
<template #action>
231-
<NcButton variant="tertiary" @click="initializeDevices">
232-
<template #icon>
233-
<IconRestore :size="20" />
234-
</template>
235-
</NcButton>
236-
</template>
237-
</SettingsSelect>
238-
</SettingsSubsection>
161+
</NcFormBox>
162+
</NcFormGroup>
163+
</NcFormGroup>
164+
165+
<NcFormGroup :label="t('talk_desktop', 'Notifications and sounds')">
166+
<NcRadioGroup v-model="playSoundChat" :label="t('talk_desktop', 'Play chat notification sound')">
167+
<NcRadioGroupButton :label="t('talk_desktop', 'Always')" value="always" />
168+
<NcRadioGroupButton :label="whenNodInDndLabel" value="respect-dnd" />
169+
<NcRadioGroupButton :label="t('talk_desktop', 'Never')" value="never" />
170+
</NcRadioGroup>
171+
172+
<NcRadioGroup v-model="playSoundCall" :label="t('talk_desktop', 'Play call notification sound')">
173+
<NcRadioGroupButton :label="t('talk_desktop', 'Always')" value="always" />
174+
<NcRadioGroupButton :label="whenNodInDndLabel" value="respect-dnd" />
175+
<NcRadioGroupButton :label="t('talk_desktop', 'Never')" value="never" />
176+
</NcRadioGroup>
177+
178+
<NcRadioGroup v-model="enableCallbox" :label="t('talk_desktop', 'Show call notification popup')">
179+
<NcRadioGroupButton :label="t('talk_desktop', 'Always')" value="always" />
180+
<NcRadioGroupButton :label="whenNodInDndLabel" value="respect-dnd" />
181+
<NcRadioGroupButton :label="t('talk_desktop', 'Never')" value="never" />
182+
</NcRadioGroup>
183+
184+
<NcFormBoxSwitch v-model="secondarySpeaker" :label="t('talk_desktop', 'Also repeat call notification on a secondary speaker')" />
185+
186+
<div v-if="secondarySpeaker" style="display: flex; gap: 4px; align-items: flex-end;">
187+
<NcSelect
188+
v-model="secondarySpeakerDeviceOption"
189+
:input-label="t('talk_desktop', 'Secondary speaker')"
190+
:options="secondarySpeakerOptions"
191+
:disabled="secondarySpeakerOptions.length === 1"
192+
style="flex: 1; margin: 0" />
193+
<NcButton
194+
:aria-label="t('talk_desktop', 'Reload')"
195+
:title="t('talk_desktop', 'Reload')"
196+
variant="tertiary"
197+
@click="initializeDevices">
198+
<template #icon>
199+
<IconRestore :size="20" />
200+
</template>
201+
</NcButton>
202+
</div>
203+
</NcFormGroup>
239204
</div>
240205
</template>
241206

@@ -258,8 +223,4 @@ function relaunch() {
258223
margin-inline-start: auto;
259224
flex: 0 0 auto;
260225
}
261-
262-
.zoom-input {
263-
width: 50px !important;
264-
}
265226
</style>
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
<!--
2+
- SPDX-FileCopyrightText: 2025 Nextcloud GmbH and Nextcloud contributors
3+
- SPDX-License-Identifier: AGPL-3.0-or-later
4+
-->
5+
6+
<script setup lang="ts">
7+
import { t } from '@nextcloud/l10n'
8+
import NcButton from '@nextcloud/vue/components/NcButton'
9+
import NcFormBox from '@nextcloud/vue/components/NcFormBox'
10+
import NcTextField from '@nextcloud/vue/components/NcTextField'
11+
import IconMinus from 'vue-material-design-icons/Minus.vue'
12+
import IconPlus from 'vue-material-design-icons/Plus.vue'
13+
14+
const modelValue = defineModel<number>({ required: true })
15+
16+
const emit = defineEmits<{
17+
decrease: []
18+
increase: []
19+
}>()
20+
</script>
21+
22+
<template>
23+
<NcFormBox row>
24+
<NcButton
25+
:aria-label="t('talk_desktop', 'Zoom out')"
26+
variant="secondary"
27+
style="flex: 0 1"
28+
@click="emit('decrease')">
29+
<template #icon>
30+
<IconMinus :size="20" />
31+
</template>
32+
</NcButton>
33+
<NcTextField
34+
label-outside
35+
inputmode="number"
36+
:model-value="modelValue"
37+
@change="modelValue = $event.target.value"
38+
@blur="$event.target.value = modelValue" />
39+
<NcButton
40+
:aria-label="t('talk_desktop', 'Zoom in')"
41+
variant="secondary"
42+
style="flex: 0 1"
43+
@click="emit('increase')">
44+
<template #icon>
45+
<IconPlus :size="20" />
46+
</template>
47+
</NcButton>
48+
</NcFormBox>
49+
</template>

0 commit comments

Comments
 (0)