ags: finish center-window widget with big-media and calendar
This commit is contained in:
@@ -1,29 +1,30 @@
|
||||
import AstalNotifd from "gi://AstalNotifd";
|
||||
import { timeout } from "astal/time";
|
||||
import { Connectable } from "astal/binding";
|
||||
import { GObject, register, signal } from "astal";
|
||||
import { Subscribable } from "astal/binding";
|
||||
import { GObject, property, register, Variable } from "astal";
|
||||
import { Windows } from "../windows";
|
||||
import { FloatingNotifications } from "../window/FloatingNotifications";
|
||||
|
||||
@register({ GTypeName: "Notifications" })
|
||||
class NotificationsClass extends GObject.Object implements Connectable {
|
||||
class NotificationsClass extends GObject.Object implements Subscribable {
|
||||
|
||||
private static instance: NotificationsClass;
|
||||
|
||||
@property(AstalNotifd.Notifd)
|
||||
private notifd: AstalNotifd.Notifd;
|
||||
|
||||
public notifications: Array<AstalNotifd.Notification> = [];
|
||||
@property(Boolean)
|
||||
private doNotDisturb: boolean = false;
|
||||
|
||||
@property()
|
||||
public notificationHistory: Array<AstalNotifd.Notification> = [];
|
||||
|
||||
@signal(AstalNotifd.Notification)
|
||||
declare notificationAdded: (added: AstalNotifd.Notification) => void;
|
||||
|
||||
@signal(Number)
|
||||
declare notificationRemoved: (id: number) => void;
|
||||
|
||||
@property()
|
||||
public notifications: Variable<Array<AstalNotifd.Notification>> = new Variable<Array<AstalNotifd.Notification>>([]);
|
||||
|
||||
public static getDefault(): NotificationsClass {
|
||||
if(!NotificationsClass.instance) {
|
||||
NotificationsClass.instance = new NotificationsClass();
|
||||
this.instance._init();
|
||||
}
|
||||
|
||||
return NotificationsClass.instance;
|
||||
@@ -36,13 +37,28 @@ class NotificationsClass extends GObject.Object implements Connectable {
|
||||
dontDisturb: false
|
||||
} as AstalNotifd.Notifd.ConstructorProps);
|
||||
|
||||
this.getNotifd().connect("notified", (_source: AstalNotifd.Notifd, id: number, _replaced: boolean) => {
|
||||
this.addNotification(this.getNotifd().get_notification(id));
|
||||
this.getNotifd().connect("notified", (daemon: AstalNotifd.Notifd, id: number) => {
|
||||
const notification: (AstalNotifd.Notification|null) = daemon.get_notification(id);
|
||||
if(!notification) {
|
||||
console.log("[LOG] Notification is null, ignoring");
|
||||
return;
|
||||
}
|
||||
|
||||
if(!this.doNotDisturb) {
|
||||
this.handleNotification(notification);
|
||||
return;
|
||||
}
|
||||
|
||||
this.addHistory(notification);
|
||||
});
|
||||
}
|
||||
|
||||
public addNotification(notification: AstalNotifd.Notification) {
|
||||
this.prependArray(this.notifications, this.getNotifd().get_notification(notification.id));
|
||||
public handleNotification(notification: AstalNotifd.Notification): void {
|
||||
Windows.open(FloatingNotifications);
|
||||
|
||||
let tmpArray = this.notifications.get().reverse();
|
||||
tmpArray.push(notification);
|
||||
this.notifications.set(tmpArray.reverse());
|
||||
|
||||
// default timeout if undefined
|
||||
let notificationTimeout = 4000;
|
||||
@@ -56,47 +72,38 @@ class NotificationsClass extends GObject.Object implements Connectable {
|
||||
break;
|
||||
}
|
||||
|
||||
notification.urgency !== AstalNotifd.Urgency.CRITICAL ?
|
||||
notification.urgency !== AstalNotifd.Urgency.CRITICAL &&
|
||||
timeout(notificationTimeout, () => {
|
||||
this.notifications.map((item: AstalNotifd.Notification) =>
|
||||
item.id === notification.id && (() => {
|
||||
this.removeNotification(notification.id);
|
||||
this.addToNotificationHistory(notification);
|
||||
})())
|
||||
})
|
||||
: this.addToNotificationHistory(notification);
|
||||
notification.dismiss();
|
||||
this.notifications.set(this.notifications.get().filter((item) => item.id !== notification.id));
|
||||
this.addHistory(notification);
|
||||
});
|
||||
|
||||
this.emit("notification-added", notification);
|
||||
}
|
||||
|
||||
public removeNotification(notificationId: number) {
|
||||
if(this.notifications.length === 1)
|
||||
Windows.close(Windows.getWindow("floating-notifications")!);
|
||||
|
||||
this.notifications = this.notifications.filter((notification: AstalNotifd.Notification) =>
|
||||
notification.id !== notificationId);
|
||||
|
||||
this.emit("notification-removed", notificationId);
|
||||
public addHistory(notification: AstalNotifd.Notification): void {
|
||||
let tmpArray: Array<AstalNotifd.Notification> = this.notificationHistory.reverse()
|
||||
.filter((item: AstalNotifd.Notification) => item.id !== notification.id);
|
||||
tmpArray.push(notification);
|
||||
this.notificationHistory = tmpArray.reverse();
|
||||
}
|
||||
|
||||
public addToNotificationHistory(notification: AstalNotifd.Notification) {
|
||||
this.prependArray(this.notificationHistory, notification);
|
||||
}
|
||||
|
||||
public removeFromNotificationHistory(notificationId: number) {
|
||||
public removeHistory(notification: AstalNotifd.Notification) {
|
||||
this.notificationHistory = this.notificationHistory.filter((curNotification: AstalNotifd.Notification) =>
|
||||
curNotification.id !== notificationId);
|
||||
}
|
||||
|
||||
private prependArray(array: Array<any>, item: any): Array<any> {
|
||||
let tmpArray = array.reverse();
|
||||
tmpArray.push(item);
|
||||
return tmpArray.reverse();
|
||||
curNotification.id !== notification.id);
|
||||
}
|
||||
|
||||
public getNotifd(): AstalNotifd.Notifd {
|
||||
return this.notifd;
|
||||
}
|
||||
|
||||
get() {
|
||||
return this.notifications.get();
|
||||
}
|
||||
|
||||
subscribe(callback: (list: Array<AstalNotifd.Notification>) => void) {
|
||||
return this.notifications.subscribe(callback);
|
||||
}
|
||||
}
|
||||
|
||||
export const Notifications = new NotificationsClass();
|
||||
|
||||
@@ -2,11 +2,13 @@
|
||||
|
||||
@use "./style/wal";
|
||||
@use "./style/mixins";
|
||||
@use "./style/colors";
|
||||
|
||||
@use "./style/bar";
|
||||
@use "./style/osd";
|
||||
@use "./style/control-center";
|
||||
@use "./style/center-window";
|
||||
@use "./style/float-notifications";
|
||||
|
||||
|
||||
* {
|
||||
@@ -16,3 +18,17 @@
|
||||
window * {
|
||||
@include mixins.default-styles;
|
||||
}
|
||||
|
||||
tooltip {
|
||||
padding: 16px;
|
||||
|
||||
& > box {
|
||||
padding: 7px 8px;
|
||||
border-radius: 10px;
|
||||
background: rgba(colors.$bg-primary, .98);
|
||||
font-size: 13.1px;
|
||||
font-weight: 500;
|
||||
color: colors.$fg-primary;
|
||||
box-shadow: 0 1px 4px 1px rgba(colors.$bg-primary, .6);
|
||||
}
|
||||
}
|
||||
|
||||
+17
-3
@@ -91,6 +91,10 @@
|
||||
}
|
||||
}
|
||||
|
||||
.clock.open > button {
|
||||
background-color: colors.$bg-primary;
|
||||
}
|
||||
|
||||
.media-eventbox {
|
||||
& > .media {
|
||||
border-radius: 12px;
|
||||
@@ -98,6 +102,10 @@
|
||||
padding: 0 8px;
|
||||
}
|
||||
|
||||
&:hover > .media {
|
||||
box-shadow: inset 0 0 0 300px rgba(colors.$fg-primary, .2);
|
||||
}
|
||||
|
||||
& .nf {
|
||||
margin-right: 4px;
|
||||
font-size: 14px;
|
||||
@@ -105,10 +113,9 @@
|
||||
|
||||
& .media-controls {
|
||||
transition: none;
|
||||
padding-left: 6px;
|
||||
padding: 0 6px;
|
||||
border-top-right-radius: 12px;
|
||||
border-bottom-right-radius: 12px;
|
||||
background: linear-gradient(to left, colors.$bg-primary 45px, colors.$bg-primary);
|
||||
|
||||
& > button {
|
||||
margin: 4px 1px;
|
||||
@@ -124,6 +131,12 @@
|
||||
& .media > box {
|
||||
border-top-right-radius: 0;
|
||||
border-bottom-right-radius: 0;
|
||||
padding: 0 6px;
|
||||
}
|
||||
|
||||
& .media {
|
||||
padding-left: 0;
|
||||
padding-right: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -154,7 +167,8 @@
|
||||
.audio {
|
||||
@include mixins.reset-props;
|
||||
|
||||
&:hover > box {
|
||||
&:hover > box,
|
||||
&.open > box {
|
||||
background: colors.$bg-primary;
|
||||
}
|
||||
|
||||
|
||||
@@ -8,24 +8,8 @@
|
||||
border-radius: 18px;
|
||||
padding: 12px;
|
||||
|
||||
& .left {
|
||||
& > .top {
|
||||
padding-bottom: 10px;
|
||||
|
||||
& .time {
|
||||
font-size: 28px;
|
||||
font-weight: 800;
|
||||
}
|
||||
|
||||
& .date {
|
||||
font-size: 14px;
|
||||
font-weight: 500;
|
||||
color: colors.$fg-disabled;
|
||||
}
|
||||
}
|
||||
|
||||
& .big-media {
|
||||
padding: 6px 16px;
|
||||
padding: 6px;
|
||||
|
||||
& > box > .image {
|
||||
background-size: cover;
|
||||
@@ -51,26 +35,90 @@
|
||||
}
|
||||
}
|
||||
|
||||
& > .controls {
|
||||
padding: 8px 0;
|
||||
& slider {
|
||||
background: transparent;
|
||||
min-height: .6em;
|
||||
}
|
||||
|
||||
& trough {
|
||||
border-radius: 4px;
|
||||
min-height: .6em;
|
||||
}
|
||||
|
||||
& trough highlight {
|
||||
border-radius: 4px;
|
||||
min-height: .6em;
|
||||
}
|
||||
|
||||
& .bottom {
|
||||
& .controls {
|
||||
margin-top: 5px;
|
||||
& button {
|
||||
padding: 7px;
|
||||
& label {
|
||||
font-size: 10px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
& .right {
|
||||
& .elapsed,
|
||||
& .length {
|
||||
font-size: 12px;
|
||||
color: colors.$fg-disabled;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
& .left .top {
|
||||
padding-bottom: 10px;
|
||||
|
||||
& .time {
|
||||
font-size: 28px;
|
||||
font-weight: 800;
|
||||
}
|
||||
|
||||
& .date {
|
||||
font-size: 14px;
|
||||
font-weight: 500;
|
||||
color: colors.$fg-disabled;
|
||||
}
|
||||
}
|
||||
|
||||
& .calendar-box {
|
||||
padding: 5px;
|
||||
& calendar {
|
||||
border-radius: 6px;
|
||||
padding: 2px;
|
||||
$border-radius: 10px;
|
||||
font-weight: 600;
|
||||
padding-bottom: 2px;
|
||||
|
||||
&.view {
|
||||
background: funs.toRGB(color.adjust($color: wal.$color1, $lightness: -35%));
|
||||
background: colors.$bg-primary;
|
||||
border-radius: $border-radius;
|
||||
}
|
||||
|
||||
& header {
|
||||
background: funs.toRGB(color.adjust($color: wal.$background, $lightness: -20%));
|
||||
&.header {
|
||||
background: colors.$bg-secondary;
|
||||
border-top-left-radius: $border-radius;
|
||||
border-top-right-radius: $border-radius;
|
||||
padding: 4px;
|
||||
}
|
||||
|
||||
&.button {
|
||||
transition: 80ms linear;
|
||||
border-radius: 6px;
|
||||
|
||||
&:hover {
|
||||
background-color: colors.$bg-tertiary;
|
||||
}
|
||||
}
|
||||
|
||||
&:selected {
|
||||
background: colors.$bg-secondary;
|
||||
border-radius: 6px;
|
||||
}
|
||||
|
||||
&.highlight {
|
||||
background: transparent;
|
||||
box-shadow: 0 2px 0 -1px rgba(colors.$bg-secondary, .5);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,41 @@
|
||||
@use "./colors";
|
||||
|
||||
.floating-notifications-container {
|
||||
padding: {
|
||||
right: 6px;
|
||||
top: 6px;
|
||||
};
|
||||
|
||||
& > .notification {
|
||||
background: colors.$bg-primary;
|
||||
border-radius: 16px;
|
||||
padding: 12px;
|
||||
margin: 6px 0;
|
||||
|
||||
& > .top {
|
||||
& .app-name {
|
||||
font-size: 12px;
|
||||
color: colors.$fg-disabled;
|
||||
}
|
||||
}
|
||||
|
||||
& .content {
|
||||
& .image {
|
||||
$size: 78px;
|
||||
min-width: $size;
|
||||
min-height: $size;
|
||||
background-size: cover;
|
||||
background-position: center 0;
|
||||
margin: 6px;
|
||||
}
|
||||
}
|
||||
|
||||
&:first-child {
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
&:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -69,16 +69,6 @@
|
||||
}
|
||||
}
|
||||
|
||||
& tooltip {
|
||||
padding: 8px;
|
||||
border-radius: 14px;
|
||||
|
||||
& label {
|
||||
font-size: 14px;
|
||||
color: colors.$fg-primary;
|
||||
}
|
||||
}
|
||||
|
||||
& trough {
|
||||
background: funs.toRGB(color.adjust($color: wal.$color1, $lightness: -20%));
|
||||
border-radius: 8px;
|
||||
|
||||
+20
-20
@@ -1,26 +1,26 @@
|
||||
// SCSS Variables
|
||||
// Generated by 'wal'
|
||||
$wallpaper: "/home/joaov/wallpapers/Miku, Rin and Luka Chibi.jpg";
|
||||
$wallpaper: "/home/joaov/wallpapers/Miku Bush.jpg";
|
||||
|
||||
// Special
|
||||
$background: #3d2217;
|
||||
$foreground: #cec7c5;
|
||||
$cursor: #cec7c5;
|
||||
$background: #0f1b06;
|
||||
$foreground: #c3c6c0;
|
||||
$cursor: #c3c6c0;
|
||||
|
||||
// Colors
|
||||
$color0: #3d2217;
|
||||
$color1: #b38678;
|
||||
$color2: #a4998a;
|
||||
$color3: #b39e8a;
|
||||
$color4: #a5a09b;
|
||||
$color5: #aea299;
|
||||
$color6: #b4aea2;
|
||||
$color7: #a39c99;
|
||||
$color8: #7f6f68;
|
||||
$color9: #EFB3A1;
|
||||
$color10: #DBCCB9;
|
||||
$color11: #EFD3B9;
|
||||
$color12: #DDD6CF;
|
||||
$color13: #E8D8CD;
|
||||
$color14: #F1E8D9;
|
||||
$color15: #cec7c5;
|
||||
$color0: #0f1b06;
|
||||
$color1: #4e7278;
|
||||
$color2: #5b7b94;
|
||||
$color3: #71807c;
|
||||
$color4: #7b9882;
|
||||
$color5: #a3a881;
|
||||
$color6: #778591;
|
||||
$color7: #93988d;
|
||||
$color8: #626d59;
|
||||
$color9: #6898A1;
|
||||
$color10: #7AA5C6;
|
||||
$color11: #97ABA6;
|
||||
$color12: #A5CBAE;
|
||||
$color13: #DAE0AC;
|
||||
$color14: #9FB2C2;
|
||||
$color15: #c3c6c0;
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
//TODO
|
||||
@@ -1,3 +1,4 @@
|
||||
import { Binding } from "astal";
|
||||
import { Gtk, Widget } from "astal/gtk3";
|
||||
|
||||
export interface SeparatorProps {
|
||||
@@ -6,21 +7,23 @@ export interface SeparatorProps {
|
||||
cssColor?: string;
|
||||
orientation?: Gtk.Orientation;
|
||||
size?: number;
|
||||
visible?: boolean | Binding<boolean | undefined>;
|
||||
}
|
||||
|
||||
export function Separator(props: SeparatorProps) {
|
||||
return new Widget.Box({
|
||||
className: `separator separator-${ props.orientation == Gtk.Orientation.VERTICAL ? "vertical" : "horizontal" } ${ props.class && props.class }`,
|
||||
visible: props.visible,
|
||||
css: `.separator {
|
||||
background: ${ props.cssColor || "lightgray" };
|
||||
opacity: ${ props.alpha || 1 };
|
||||
}
|
||||
.separator-horizontal {
|
||||
padding-right: ${props.size || 1 }px;
|
||||
padding-bottom: ${props.size || 1 }px;
|
||||
margin: 7px 4px;
|
||||
}
|
||||
.separator-vertical {
|
||||
padding-bottom: ${props.size || 1 }px;
|
||||
padding-right: ${props.size || 1 }px;
|
||||
margin: 4px 7px;
|
||||
}`,
|
||||
} as Widget.BoxProps);
|
||||
|
||||
@@ -2,12 +2,14 @@ import { bind, Process } from "astal";
|
||||
import { Widget } from "astal/gtk3";
|
||||
import AstalWp from "gi://AstalWp";
|
||||
import { Wireplumber } from "../../scripts/volume";
|
||||
import { ControlCenter } from "../../window/ControlCenter";
|
||||
|
||||
const wp = AstalWp.get_default();
|
||||
|
||||
export function Audio() {
|
||||
return wp && new Widget.EventBox({
|
||||
className: "audio",
|
||||
className: bind(ControlCenter, "visible").as((visible: boolean) =>
|
||||
visible ? "audio open" : "audio"),
|
||||
onClick: () => Process.exec_async("astal toggle control-center", () => {}),
|
||||
child: new Widget.Box({
|
||||
children: [
|
||||
|
||||
@@ -1,12 +1,13 @@
|
||||
import { Widget } from "astal/gtk3";
|
||||
import { getDateTime } from "../../scripts/time";
|
||||
import { GLib } from "astal";
|
||||
import { bind, GLib } from "astal";
|
||||
import { Windows } from "../../windows";
|
||||
import { CenterWindow } from "../../window/CenterWindow";
|
||||
|
||||
export function Clock(): JSX.Element {
|
||||
return new Widget.Box({
|
||||
className: "clock",
|
||||
className: bind(CenterWindow, "visible").as((visible: boolean) =>
|
||||
visible ? "clock open" : "clock"),
|
||||
child: new Widget.Button({
|
||||
onClick: () => Windows.toggle(CenterWindow),
|
||||
label: getDateTime().as((dateTime: GLib.DateTime) => {
|
||||
|
||||
@@ -2,6 +2,8 @@ import { bind, GLib, Process } from "astal";
|
||||
import { Gtk, Widget } from "astal/gtk3";
|
||||
import AstalMpris from "gi://AstalMpris";
|
||||
import { Separator, SeparatorProps } from "../Separator";
|
||||
import { CenterWindow } from "../../window/CenterWindow";
|
||||
import { Windows } from "../../windows";
|
||||
|
||||
const mpris: AstalMpris.Mpris = AstalMpris.get_default();
|
||||
|
||||
@@ -66,7 +68,10 @@ export function Media(): Gtk.Widget {
|
||||
|
||||
const mediaWidget = new Widget.EventBox({
|
||||
className: "media-eventbox",
|
||||
visible: bind(mpris, "players").as((players: Array<AstalMpris.Player>) => players[0]).as(Boolean),
|
||||
visible: bind(mpris, "players").as((players: Array<AstalMpris.Player>) => {
|
||||
return players[0] && players[0].get_available() || CenterWindow.is_visible();
|
||||
}),
|
||||
onClick: () => Windows.toggle(CenterWindow),
|
||||
child: new Widget.Box({
|
||||
className: "media",
|
||||
children: [
|
||||
@@ -85,6 +90,7 @@ export function Media(): Gtk.Widget {
|
||||
label: bind(players[0], "title").as((title: string) => title || "No Title")
|
||||
} as Widget.LabelProps),
|
||||
Separator({
|
||||
orientation: Gtk.Orientation.VERTICAL,
|
||||
size: 2,
|
||||
cssColor: `rgb(180, 180, 180)`,
|
||||
alpha: 1
|
||||
|
||||
@@ -8,8 +8,11 @@ export const BigMedia: Gtk.Widget = new Widget.Box({
|
||||
className: "big-media",
|
||||
orientation: Gtk.Orientation.VERTICAL,
|
||||
homogeneous: false,
|
||||
width_request: 250,
|
||||
visible: bind(AstalMpris.get_default(), "players").as((players: Array<AstalMpris.Player>) =>
|
||||
players[0] ? true : false),
|
||||
children: bind(AstalMpris.get_default(), "players").as((players: Array<AstalMpris.Player>) =>
|
||||
players[0] ? [
|
||||
players[0] && [
|
||||
new Widget.Box({
|
||||
halign: Gtk.Align.CENTER,
|
||||
child: new Widget.Box({
|
||||
@@ -72,16 +75,29 @@ export const BigMedia: Gtk.Widget = new Widget.Box({
|
||||
})
|
||||
]
|
||||
}),
|
||||
new Widget.Box({
|
||||
className: "controls button-row",
|
||||
new Widget.CenterBox({
|
||||
className: "bottom",
|
||||
homogeneous: false,
|
||||
hexpand: true,
|
||||
halign: Gtk.Align.CENTER,
|
||||
startWidget: new Widget.Label({
|
||||
className: "elapsed",
|
||||
valign: Gtk.Align.START,
|
||||
halign: Gtk.Align.START,
|
||||
label: bind(players[0], "position").as((pos: number) => {
|
||||
const sec: number = Math.floor(pos % 60);
|
||||
return pos > 0 && players[0].length > 0 ?
|
||||
`${Math.floor(pos / 60)}:${sec < 10 ? "0" : ""}${sec}`
|
||||
: `0:00`;
|
||||
})
|
||||
} as Widget.LabelProps),
|
||||
centerWidget: new Widget.Box({
|
||||
className: "controls button-row",
|
||||
children: [
|
||||
new Widget.Button({
|
||||
className: "link nf",
|
||||
label: "",
|
||||
tooltipText: "Copy link to Clipboard",
|
||||
visible: bind(players[0], "metadata").as((_metadata: GLib.HashTable) =>
|
||||
visible: bind(players[0], "metadata").as((_meta: GLib.HashTable) =>
|
||||
players[0].get_meta("xesam:url") === null),
|
||||
onClick: () => Process.exec(`wl-copy ${players[0].get_meta("xesam:url")?.get_string()[0]}`)
|
||||
} as Widget.ButtonProps),
|
||||
@@ -111,6 +127,18 @@ export const BigMedia: Gtk.Widget = new Widget.Box({
|
||||
onClick: () => players[0].canGoNext && players[0].next()
|
||||
} as Widget.ButtonProps)
|
||||
]
|
||||
} as Widget.BoxProps),
|
||||
endWidget: new Widget.Label({
|
||||
className: "length",
|
||||
valign: Gtk.Align.START,
|
||||
halign: Gtk.Align.END,
|
||||
label: bind(players[0], "length").as((len/* bananananananana */: number) => {
|
||||
const sec: number = Math.floor(len % 60);
|
||||
return len > 0 ?
|
||||
`${Math.floor(len / 60)}:${sec < 10 ? "0" : ""}${sec}`
|
||||
: "0:00";
|
||||
})
|
||||
] : new Widget.Box({ className: "empty no-media" }))
|
||||
} as Widget.LabelProps)
|
||||
})
|
||||
])
|
||||
} as Widget.BoxProps);
|
||||
|
||||
+20
-10
@@ -1,8 +1,9 @@
|
||||
import { Astal, Gtk, Widget } from "astal/gtk3";
|
||||
import { GLib } from "astal";
|
||||
import { bind, GLib } from "astal";
|
||||
|
||||
import { getDateTime } from "../scripts/time";
|
||||
import { BigMedia } from "../widget/center-window/BigMedia";
|
||||
import { Separator, SeparatorProps } from "../widget/Separator";
|
||||
|
||||
export const CenterWindow: Widget.Window = new Widget.Window({
|
||||
className: "center-window",
|
||||
@@ -12,7 +13,6 @@ export const CenterWindow: Widget.Window = new Widget.Window({
|
||||
layer: Astal.Layer.OVERLAY,
|
||||
exclusivity: Astal.Exclusivity.NORMAL,
|
||||
visible: false,
|
||||
height_request: 400,
|
||||
margin_top: 10,
|
||||
anchor: Astal.WindowAnchor.TOP,
|
||||
child: new Widget.Box({
|
||||
@@ -21,7 +21,6 @@ export const CenterWindow: Widget.Window = new Widget.Window({
|
||||
new Widget.Box({
|
||||
className: "vertical left",
|
||||
orientation: Gtk.Orientation.VERTICAL,
|
||||
width_request: 300,
|
||||
children: [
|
||||
new Widget.Box({
|
||||
className: "top",
|
||||
@@ -36,18 +35,15 @@ export const CenterWindow: Widget.Window = new Widget.Window({
|
||||
new Widget.Label({
|
||||
className: "date",
|
||||
label: getDateTime().as((dateTime: GLib.DateTime) =>
|
||||
dateTime.format("%A, %B %d %Y"))
|
||||
dateTime.format("%A, %B %d"))
|
||||
} as Widget.LabelProps)
|
||||
]
|
||||
} as Widget.BoxProps),
|
||||
BigMedia
|
||||
]
|
||||
} as Widget.BoxProps),
|
||||
new Widget.Box({
|
||||
className: "vertical right",
|
||||
children: [
|
||||
new Widget.Box({
|
||||
className: "calendar-box",
|
||||
vexpand: false,
|
||||
hexpand: true,
|
||||
valign: Gtk.Align.START,
|
||||
child: new Gtk.Calendar({
|
||||
visible: true,
|
||||
show_heading: true,
|
||||
@@ -56,6 +52,20 @@ export const CenterWindow: Widget.Window = new Widget.Window({
|
||||
} as Gtk.Calendar.ConstructorProps)
|
||||
} as Widget.BoxProps)
|
||||
]
|
||||
} as Widget.BoxProps),
|
||||
Separator({
|
||||
visible: bind(BigMedia, "visible"),
|
||||
orientation: Gtk.Orientation.VERTICAL,
|
||||
alpha: .5,
|
||||
cssColor: "gray",
|
||||
size: 1
|
||||
} as SeparatorProps),
|
||||
new Widget.Box({
|
||||
className: "vertical right",
|
||||
orientation: Gtk.Orientation.VERTICAL,
|
||||
children: [
|
||||
BigMedia
|
||||
]
|
||||
} as Widget.BoxProps)
|
||||
]
|
||||
} as Widget.BoxProps)
|
||||
|
||||
@@ -16,14 +16,22 @@ function NotificationWidget(notification: AstalNotifd.Notification): Gtk.Widget
|
||||
hexpand: true,
|
||||
vexpand: false,
|
||||
children: [
|
||||
new Widget.Icon({
|
||||
className: "icon",
|
||||
visible: notification.appIcon !== "",
|
||||
icon: notification.appIcon || "image-missing",
|
||||
iconSize: Gtk.IconSize.DND,
|
||||
css: ".icon { font-size: 24px; }"
|
||||
}),
|
||||
new Widget.Label({
|
||||
className: "app-name",
|
||||
halign: Gtk.Align.START,
|
||||
label: notification.appName || "Unknown Application"
|
||||
} as Widget.LabelProps),
|
||||
new Widget.Button({
|
||||
className: "close-button",
|
||||
onClick: () => Notifications.removeNotification(notification.id)
|
||||
className: "close nf",
|
||||
onClick: () => notification.dismiss(),
|
||||
label: ""
|
||||
} as Widget.ButtonProps)
|
||||
]
|
||||
} as Widget.BoxProps),
|
||||
@@ -71,8 +79,8 @@ export const FloatingNotifications: Widget.Window = new Widget.Window({
|
||||
className: "floating-notifications-container",
|
||||
orientation: Gtk.Orientation.VERTICAL,
|
||||
homogeneous: false,
|
||||
children: bind(Notifications, "notifications").as((notifications: Array<AstalNotifd.Notification>) =>
|
||||
notifications.map((notification: AstalNotifd.Notification) =>
|
||||
NotificationWidget(notification)))
|
||||
children: Notifications.notifications().as((notifications: Array<AstalNotifd.Notification>) =>
|
||||
notifications.map((item: AstalNotifd.Notification) =>
|
||||
NotificationWidget(item)))
|
||||
} as Widget.BoxProps)
|
||||
} as Widget.WindowProps);
|
||||
|
||||
@@ -0,0 +1,37 @@
|
||||
import { Variable } from "astal";
|
||||
import { Astal, Gtk, Widget } from "astal/gtk3";
|
||||
|
||||
// TODO
|
||||
|
||||
export interface RunnerProps {
|
||||
anchor?: Astal.WindowAnchor;
|
||||
width?: number;
|
||||
height?: number;
|
||||
entryPlaceHolder?: string;
|
||||
resultsPlaceholder?: Array<Gtk.Widget>;
|
||||
}
|
||||
|
||||
export function Runner(props?: RunnerProps) {
|
||||
|
||||
const entryText: Variable<string> = new Variable<string>("");
|
||||
|
||||
const resultsBox: Widget.Box = new Widget.Box({
|
||||
className: "results",
|
||||
|
||||
} as Widget.BoxProps);
|
||||
|
||||
return new Widget.Window({
|
||||
namespace: "runner",
|
||||
widthRequest: props?.width || 600,
|
||||
heightRequest: props?.height || 500,
|
||||
child: new Widget.Box({
|
||||
className: "main",
|
||||
children: [
|
||||
new Widget.Entry({
|
||||
className: "search",
|
||||
onChanged: (entry) => entryText.set(entry.text),
|
||||
} as Widget.EntryProps),
|
||||
]
|
||||
} as Widget.BoxProps)
|
||||
} as Widget.WindowProps);
|
||||
}
|
||||
+2
-1
@@ -1,4 +1,4 @@
|
||||
import { Gtk, Widget } from "astal/gtk3";
|
||||
import { Gtk } from "astal/gtk3";
|
||||
|
||||
import { Bar } from "./window/Bar";
|
||||
import { OSD } from "./window/OSD";
|
||||
@@ -22,6 +22,7 @@ export const Windows = GObject.registerClass({
|
||||
WindowsClass.windowsMap.set("control-center", ControlCenter);
|
||||
WindowsClass.windowsMap.set("center-window", CenterWindow);
|
||||
WindowsClass.windowsMap.set("logout-menu", LogoutMenu);
|
||||
WindowsClass.windowsMap.set("floating-notifications", FloatingNotifications);
|
||||
}
|
||||
|
||||
public _init(...args: any[]) {
|
||||
|
||||
Reference in New Issue
Block a user