Skip to content

Commit 73e0fe1

Browse files
authored
Merge pull request #2224 from nextcloud/backport/2223/stable29
[stable29] fix: style and template fixes
2 parents de5efba + a9346d9 commit 73e0fe1

8 files changed

Lines changed: 158 additions & 149 deletions

js/notifications-main.js

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

js/notifications-main.js.map

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

js/notifications-src_NotificationsApp_vue.js

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

js/notifications-src_NotificationsApp_vue.js.map

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 91 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,91 @@
1+
<!--
2+
- SPDX-FileCopyrightText: 2019 Nextcloud GmbH and Nextcloud contributors
3+
- SPDX-License-Identifier: AGPL-3.0-or-later
4+
-->
5+
<template>
6+
<span v-if="showDot || showWarning" class="notifications-button__icon">
7+
<!-- Modified IconBell from material design icons -->
8+
<svg xmlns="http://www.w3.org/2000/svg"
9+
xmlns:xlink="http://www.w3.org/1999/xlink"
10+
version="1.1"
11+
:width="size"
12+
:height="size"
13+
viewBox="0 0 24 24"
14+
fill="currentColor">
15+
<path d="M 19,11.79 C 18.5,11.92 18,12 17.5,12 14.47,12 12,9.53 12,6.5 12,5.03 12.58,3.7 13.5,2.71 13.15,2.28 12.61,2 12,2 10.9,2 10,2.9 10,4 V 4.29 C 7.03,5.17 5,7.9 5,11 v 6 l -2,2 v 1 H 21 V 19 L 19,17 V 11.79 M 12,23 c 1.11,0 2,-0.89 2,-2 h -4 c 0,1.11 0.9,2 2,2 z" />
16+
<path class="notification__dot"
17+
:class="{
18+
'notification__dot--warning': showWarning && !isOrangeThemed,
19+
'notification__dot--white': isRedThemed || (showWarning && isOrangeThemed),
20+
}"
21+
d="M 21,6.5 C 21,8.43 19.43,10 17.5,10 15.57,10 14,8.43 14,6.5 14,4.57 15.57,3 17.5,3 19.43,3 21,4.57 21,6.5" />
22+
</svg>
23+
</span>
24+
<IconBell v-else class="notifications-button__icon" :size="size" />
25+
</template>
26+
27+
<script setup>
28+
import IconBell from 'vue-material-design-icons/Bell.vue'
29+
30+
import { computed } from 'vue'
31+
import { getCapabilities } from '@nextcloud/capabilities'
32+
33+
const theming = getCapabilities()?.theming
34+
35+
defineProps({
36+
showDot: {
37+
type: Boolean,
38+
default: false,
39+
},
40+
showWarning: {
41+
type: Boolean,
42+
default: false,
43+
},
44+
size: {
45+
type: Number,
46+
default: 20,
47+
},
48+
})
49+
50+
const hexRegex = /^#(?:[0-9a-fA-F]{3}|[0-9a-fA-F]{6})$/
51+
const hexToHSL = (hexColor) => {
52+
const r = parseInt(hexColor.substring(1, 3), 16) / 255
53+
const g = parseInt(hexColor.substring(3, 5), 16) / 255
54+
const b = parseInt(hexColor.substring(5, 7), 16) / 255
55+
56+
const max = Math.max(r, g, b)
57+
const min = Math.min(r, g, b)
58+
let hue = 0
59+
let sat = 0
60+
const lum = (max + min) / 2
61+
62+
if (max !== min) {
63+
const d = max - min
64+
sat = lum > 0.5 ? d / (2 - max - min) : d / (max + min)
65+
switch (max) {
66+
case r: hue = (g - b) / d + (g < b ? 6 : 0); break
67+
case g: hue = (b - r) / d + 2; break
68+
case b: hue = (r - g) / d + 4; break
69+
}
70+
hue *= 60
71+
}
72+
73+
return [hue, sat, lum]
74+
}
75+
76+
const isRedThemed = computed(() => {
77+
if (!theming?.color || !hexRegex.test(theming?.color)) {
78+
return false
79+
}
80+
const [hue, sat, lum] = hexToHSL(theming.color)
81+
return (hue >= 330 || hue <= 15) && sat > 0.4 && (lum > 0.1 || lum < 0.6)
82+
})
83+
84+
const isOrangeThemed = computed(() => {
85+
if (!theming?.color || !hexRegex.test(theming?.color)) {
86+
return false
87+
}
88+
const [hue, sat, lum] = hexToHSL(theming.color)
89+
return (hue >= 305 || hue <= 64) && sat > 0.7 && (lum > 0.1 || lum < 0.6)
90+
})
91+
</script>

src/Components/Notification.vue

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -297,8 +297,6 @@ export default {
297297

298298
<style lang="scss" scoped>
299299
.notification {
300-
background-color: var(--color-main-background);
301-
302300
:deep(img.notification-icon) {
303301
display: flex;
304302
width: 32px;

src/NotificationsApp.vue

Lines changed: 61 additions & 115 deletions
Original file line numberDiff line numberDiff line change
@@ -5,74 +5,43 @@
55
:exclude-click-outside-selectors="['.popover']"
66
:open.sync="open"
77
:aria-label="t('notifications', 'Notifications')"
8+
:title="t('notifications', 'Notifications')"
89
@open="onOpen">
910
<template #trigger>
10-
<Bell v-if="notifications.length === 0 && webNotificationsGranted !== null && !hasThrottledPushNotifications"
11-
class="notifications-button__icon"
12-
:size="20"
13-
:title="t('notifications', 'Notifications')" />
14-
<!-- From material design icons -->
15-
<svg v-else
16-
class="notifications-button__icon"
17-
xmlns="http://www.w3.org/2000/svg"
18-
xmlns:xlink="http://www.w3.org/1999/xlink"
19-
version="1.1"
20-
width="20"
21-
height="20"
22-
viewBox="0 0 24 24"
23-
fill="currentColor">
24-
<path d="M 19,11.79 C 18.5,11.92 18,12 17.5,12 14.47,12 12,9.53 12,6.5 12,5.03 12.58,3.7 13.5,2.71 13.15,2.28 12.61,2 12,2 10.9,2 10,2.9 10,4 V 4.29 C 7.03,5.17 5,7.9 5,11 v 6 l -2,2 v 1 H 21 V 19 L 19,17 V 11.79 M 12,23 c 1.11,0 2,-0.89 2,-2 h -4 c 0,1.11 0.9,2 2,2 z" />
25-
<path :class="isRedThemed ? 'notification__dot--white' : ''" class="notification__dot" d="M 21,6.5 C 21,8.43 19.43,10 17.5,10 15.57,10 14,8.43 14,6.5 14,4.57 15.57,3 17.5,3 19.43,3 21,4.57 21,6.5" />
26-
<path v-if="hasThrottledPushNotifications"
27-
:class="isOrangeThemed ? 'notification__dot--white' : ''"
28-
class="notification__dot notification__dot--warning"
29-
d="M 21,6.5 C 21,8.43 19.43,10 17.5,10 15.57,10 14,8.43 14,6.5 14,4.57 15.57,3 17.5,3 19.43,3 21,4.57 21,6.5" />
30-
</svg>
11+
<IconNotification :size="20"
12+
:show-dot="notifications.length !== 0 || webNotificationsGranted === null"
13+
:show-warning="hasThrottledPushNotifications" />
3114
</template>
3215

3316
<!-- Notifications list content -->
3417
<div ref="container" class="notification-container">
3518
<transition name="fade" mode="out-in">
36-
<div v-if="notifications.length > 0">
37-
<transition-group class="notification-wrapper"
38-
name="list"
39-
tag="ul">
40-
<Notification v-if="hasThrottledPushNotifications"
41-
:key="-2016"
42-
datetime="warning"
43-
app="core"
44-
:icon="warningIcon"
45-
external-link="https://nextcloud.com/fairusepolicy"
46-
:message="emptyContentDescription"
47-
:subject="emptyContentMessage"
48-
:index="2016" />
49-
<Notification v-for="(n, index) in notifications"
50-
:key="n.notificationId"
51-
v-bind="n"
52-
:index="index"
53-
@remove="onRemove" />
54-
</transition-group>
55-
56-
<!-- Dismiss all -->
57-
<span v-if="notifications.length > 0"
58-
class="dismiss-all"
59-
@click="onDismissAll">
60-
<NcButton type="tertiary"
61-
@click="onDismissAll">
62-
<template #icon>
63-
<Close :size="20" />
64-
</template>
65-
{{ t('notifications', 'Dismiss all notifications') }}
66-
</NcButton>
67-
</span>
68-
</div>
19+
<transition-group v-if="notifications.length > 0"
20+
class="notification-wrapper"
21+
name="list"
22+
tag="ul">
23+
<Notification v-if="hasThrottledPushNotifications"
24+
:key="-2016"
25+
datetime="warning"
26+
app="core"
27+
:icon="warningIcon"
28+
external-link="https://nextcloud.com/fairusepolicy"
29+
:message="emptyContentDescription"
30+
:subject="emptyContentMessage"
31+
:index="2016" />
32+
<Notification v-for="(n, index) in notifications"
33+
:key="n.notificationId"
34+
v-bind="n"
35+
:index="index"
36+
@remove="onRemove" />
37+
</transition-group>
6938

7039
<!-- No notifications -->
7140
<NcEmptyContent v-else
7241
:name="emptyContentMessage"
7342
:description="emptyContentDescription">
7443
<template #icon>
75-
<Bell v-if="!hasThrottledPushNotifications" />
44+
<IconBell v-if="!hasThrottledPushNotifications" />
7645
<span v-else class="icon icon-alert-outline" />
7746
</template>
7847

@@ -82,21 +51,36 @@
8251
target="_blank"
8352
rel="noreferrer noopener">
8453
<template #icon>
85-
<Message :size="20" />
54+
<IconMessage :size="20" />
8655
</template>
8756
{{ t('notifications', 'Contact Nextcloud GmbH') }} ↗
8857
</NcButton>
8958
</template>
9059
</NcEmptyContent>
9160
</transition>
61+
62+
<!-- Dismiss all -->
63+
<div v-if="notifications.length > 0" class="dismiss-all">
64+
<NcButton type="tertiary"
65+
wide
66+
@click="onDismissAll">
67+
<template #icon>
68+
<IconClose :size="20" />
69+
</template>
70+
{{ t('notifications', 'Dismiss all notifications') }}
71+
</NcButton>
72+
</div>
9273
</div>
9374
</NcHeaderMenu>
9475
</template>
9576

9677
<script>
78+
import IconBell from 'vue-material-design-icons/Bell.vue'
79+
import IconClose from 'vue-material-design-icons/Close.vue'
80+
import IconMessage from 'vue-material-design-icons/Message.vue'
81+
import IconNotification from './Components/IconNotification.vue'
9782
import Notification from './Components/Notification.vue'
9883
import NcButton from '@nextcloud/vue/dist/Components/NcButton.js'
99-
import Close from 'vue-material-design-icons/Close.vue'
10084
import axios from '@nextcloud/axios'
10185
import { getCurrentUser } from '@nextcloud/auth'
10286
import { emit, subscribe, unsubscribe } from '@nextcloud/event-bus'
@@ -108,21 +92,20 @@ import {
10892
} from '@nextcloud/router'
10993
import { getNotificationsData } from './services/notificationsService.js'
11094
import { listen } from '@nextcloud/notify_push'
111-
import Bell from 'vue-material-design-icons/Bell.vue'
112-
import Message from 'vue-material-design-icons/Message.vue'
95+
11396
import NcEmptyContent from '@nextcloud/vue/dist/Components/NcEmptyContent.js'
114-
import { getCapabilities } from '@nextcloud/capabilities'
11597
import NcHeaderMenu from '@nextcloud/vue/dist/Components/NcHeaderMenu.js'
11698
import { createWebNotification } from './services/webNotificationsService.js'
11799
118100
export default {
119101
name: 'NotificationsApp',
120102
121103
components: {
104+
IconBell,
105+
IconClose,
106+
IconMessage,
107+
IconNotification,
122108
NcButton,
123-
Close,
124-
Bell,
125-
Message,
126109
NcEmptyContent,
127110
NcHeaderMenu,
128111
Notification,
@@ -134,7 +117,6 @@ export default {
134117
backgroundFetching: false,
135118
hasNotifyPush: false,
136119
shutdown: false,
137-
theming: getCapabilities()?.theming || {},
138120
hasThrottledPushNotifications: loadState('notifications', 'throttled_push_notifications'),
139121
notifications: [],
140122
lastETag: null,
@@ -175,27 +157,6 @@ export default {
175157
_$icon: null,
176158
177159
computed: {
178-
isRedThemed() {
179-
if (this.theming?.color) {
180-
const hsl = this.rgbToHsl(this.theming.color.substring(1, 3),
181-
this.theming.color.substring(3, 5),
182-
this.theming.color.substring(5, 7))
183-
const h = hsl[0] * 360
184-
return (h >= 330 || h <= 15) && hsl[1] > 0.4 && (hsl[2] > 0.1 || hsl[2] < 0.6)
185-
}
186-
return false
187-
},
188-
isOrangeThemed() {
189-
if (this.theming?.color) {
190-
const hsl = this.rgbToHsl(this.theming.color.substring(1, 3),
191-
this.theming.color.substring(3, 5),
192-
this.theming.color.substring(5, 7))
193-
const h = hsl[0] * 360
194-
return (h >= 305 || h <= 64) && hsl[1] > 0.7 && (hsl[2] > 0.1 || hsl[2] < 0.6)
195-
}
196-
return false
197-
},
198-
199160
showBrowserNotifications() {
200161
return this.backgroundFetching
201162
&& this.webNotificationsGranted
@@ -311,27 +272,6 @@ export default {
311272
this.notifications.splice(index, 1)
312273
},
313274
314-
rgbToHsl(r, g, b) {
315-
r = parseInt(r, 16) / 255; g = parseInt(g, 16) / 255; b = parseInt(b, 16) / 255
316-
const max = Math.max(r, g, b); const min = Math.min(r, g, b)
317-
let h; let s; const l = (max + min) / 2
318-
319-
if (max === min) {
320-
h = s = 0
321-
} else {
322-
const d = max - min
323-
s = l > 0.5 ? d / (2 - max - min) : d / (max + min)
324-
switch (max) {
325-
case r: h = (g - b) / d + (g < b ? 6 : 0); break
326-
case g: h = (b - r) / d + 2; break
327-
case b: h = (r - g) / d + 4; break
328-
}
329-
h /= 6
330-
}
331-
332-
return [h, s, l]
333-
},
334-
335275
/**
336276
* Update the title to show * if there are new notifications
337277
*
@@ -535,18 +475,24 @@ export default {
535475
.notification-container {
536476
/* Prevent slide animation to go out of the div */
537477
overflow: hidden;
538-
}
539478
540-
.notification-wrapper {
541-
max-height: calc(100vh - 50px * 4);
542-
overflow: auto;
543-
}
479+
&,
480+
& :deep(*),
481+
& :deep(*::before),
482+
& :deep(*::after) {
483+
box-sizing: border-box;
484+
}
544485
545-
::v-deep .empty-content {
546-
margin: 12vh 10px;
486+
.notification-wrapper {
487+
display: flex;
488+
flex-direction: column;
489+
max-height: calc(100vh - 50px * 5);
490+
overflow: auto;
491+
}
547492
548-
p {
549-
color: var(--color-text-maxcontrast);
493+
.dismiss-all {
494+
padding: calc(2 * var(--default-grid-baseline));
495+
border-top: 1px solid var(--color-border);
550496
}
551497
}
552498

0 commit comments

Comments
 (0)