143 lines
4.9 KiB
JavaScript
143 lines
4.9 KiB
JavaScript
|
// This file is for the notification list on the sidebar
|
||
|
// For the popup notifications, see onscreendisplay.js
|
||
|
// The actual widget for each single notification is in lib/notification.js
|
||
|
import Widget from 'resource:///com/github/Aylur/ags/widget.js';
|
||
|
import Notifications from 'resource:///com/github/Aylur/ags/service/notifications.js';
|
||
|
const { Box, Button, Label, Scrollable, Stack } = Widget;
|
||
|
import { MaterialIcon } from "../../lib/materialicon.js";
|
||
|
import { setupCursorHover } from "../../lib/cursorhover.js";
|
||
|
import Notification from "../../lib/notification.js";
|
||
|
|
||
|
export default (props) => {
|
||
|
const notifEmptyContent = Box({
|
||
|
homogeneous: true,
|
||
|
children: [Box({
|
||
|
vertical: true,
|
||
|
vpack: 'center',
|
||
|
className: 'txt spacing-v-10',
|
||
|
children: [
|
||
|
Box({
|
||
|
vertical: true,
|
||
|
className: 'spacing-v-5',
|
||
|
children: [
|
||
|
MaterialIcon('notifications_active', 'gigantic'),
|
||
|
Label({ label: 'No notifications', className: 'txt-small' }),
|
||
|
]
|
||
|
}),
|
||
|
]
|
||
|
})]
|
||
|
});
|
||
|
const notificationList = Box({
|
||
|
vertical: true,
|
||
|
vpack: 'start',
|
||
|
className: 'spacing-v-5-revealer',
|
||
|
setup: (self) => self
|
||
|
.hook(Notifications, (box, id) => {
|
||
|
if (box.get_children().length == 0) { // On init there's no notif, or 1st notif
|
||
|
Notifications.notifications
|
||
|
.forEach(n => {
|
||
|
box.pack_end(Notification({
|
||
|
notifObject: n,
|
||
|
isPopup: false,
|
||
|
}), false, false, 0)
|
||
|
});
|
||
|
box.show_all();
|
||
|
return;
|
||
|
}
|
||
|
// 2nd or later notif
|
||
|
const notif = Notifications.getNotification(id);
|
||
|
const NewNotif = Notification({
|
||
|
notifObject: notif,
|
||
|
isPopup: false,
|
||
|
});
|
||
|
if (NewNotif) {
|
||
|
box.pack_end(NewNotif, false, false, 0);
|
||
|
box.show_all();
|
||
|
}
|
||
|
}, 'notified')
|
||
|
.hook(Notifications, (box, id) => {
|
||
|
if (!id) return;
|
||
|
for (const ch of box.children) {
|
||
|
if (ch._id === id) {
|
||
|
ch.attribute.destroyWithAnims();
|
||
|
}
|
||
|
}
|
||
|
}, 'closed')
|
||
|
,
|
||
|
});
|
||
|
const ListActionButton = (icon, name, action) => Button({
|
||
|
className: 'notif-listaction-btn',
|
||
|
onClicked: action,
|
||
|
child: Box({
|
||
|
className: 'spacing-h-5',
|
||
|
children: [
|
||
|
MaterialIcon(icon, 'norm'),
|
||
|
Label({
|
||
|
className: 'txt-small',
|
||
|
label: name,
|
||
|
})
|
||
|
]
|
||
|
}),
|
||
|
setup: setupCursorHover,
|
||
|
});
|
||
|
const silenceButton = ListActionButton('notifications_paused', 'Silence', (self) => {
|
||
|
Notifications.dnd = !Notifications.dnd;
|
||
|
self.toggleClassName('notif-listaction-btn-enabled', Notifications.dnd);
|
||
|
});
|
||
|
const clearButton = ListActionButton('clear_all', 'Clear', () => {
|
||
|
// Manual destruction is not necessary
|
||
|
// since Notifications.clear() sends destroy signals to every notif
|
||
|
Notifications.clear();
|
||
|
});
|
||
|
const listTitle = Box({
|
||
|
vpack: 'start',
|
||
|
className: 'sidebar-group-invisible txt spacing-h-5',
|
||
|
children: [
|
||
|
Label({
|
||
|
hexpand: true,
|
||
|
xalign: 0,
|
||
|
className: 'txt-title-small margin-left-10',
|
||
|
// ^ (extra margin on the left so that it looks similarly spaced
|
||
|
// when compared to borderless "Clear" button on the right)
|
||
|
label: 'Notifications',
|
||
|
}),
|
||
|
silenceButton,
|
||
|
clearButton,
|
||
|
]
|
||
|
});
|
||
|
const notifList = Scrollable({
|
||
|
hexpand: true,
|
||
|
hscroll: 'never',
|
||
|
vscroll: 'automatic',
|
||
|
child: Box({
|
||
|
vexpand: true,
|
||
|
// homogeneous: true,
|
||
|
children: [notificationList],
|
||
|
}),
|
||
|
setup: (self) => {
|
||
|
const vScrollbar = self.get_vscrollbar();
|
||
|
vScrollbar.get_style_context().add_class('sidebar-scrollbar');
|
||
|
}
|
||
|
});
|
||
|
const listContents = Stack({
|
||
|
transition: 'crossfade',
|
||
|
transitionDuration: 150,
|
||
|
children: {
|
||
|
'empty': notifEmptyContent,
|
||
|
'list': notifList,
|
||
|
},
|
||
|
setup: (self) => self
|
||
|
.hook(Notifications, (self) => self.shown = (Notifications.notifications.length > 0 ? 'list' : 'empty'))
|
||
|
,
|
||
|
});
|
||
|
return Box({
|
||
|
...props,
|
||
|
className: 'sidebar-group spacing-v-5',
|
||
|
vertical: true,
|
||
|
children: [
|
||
|
listTitle,
|
||
|
listContents,
|
||
|
]
|
||
|
});
|
||
|
}
|