[AGS] Launcher: Prepare
This commit is contained in:
parent
02861efcae
commit
afe25a322a
@ -1,22 +1,23 @@
|
|||||||
import { Variable } from "astal";
|
import { Variable } from "astal";
|
||||||
import { App, Astal, Gdk, Gtk } from "astal/gtk4";
|
import { App, Astal, Gdk, Gtk, hook } from "astal/gtk4";
|
||||||
import AstalApps from "gi://AstalApps";
|
import AstalApps from "gi://AstalApps";
|
||||||
|
import AppList from "./modules/Apps";
|
||||||
|
|
||||||
const MAX_ITEMS = 8;
|
const prefixes = ['='];
|
||||||
|
|
||||||
function hide() {
|
function hide() {
|
||||||
App.get_window("launcher")!.hide();
|
App.get_window("launcher")!.hide();
|
||||||
}
|
}
|
||||||
|
|
||||||
const Launcher = () => {
|
const Launcher = () => {
|
||||||
const { CENTER } = Gtk.Align;
|
|
||||||
const apps = new AstalApps.Apps();
|
const apps = new AstalApps.Apps();
|
||||||
const width = Variable(1000);
|
const width = Variable(1000);
|
||||||
|
const height = Variable(1000);
|
||||||
|
|
||||||
const text = Variable("");
|
const text = Variable("");
|
||||||
const visible = Variable(false);
|
const visible = Variable(false);
|
||||||
const list = text((text) => apps.fuzzy_query(text).slice(0, MAX_ITEMS));
|
|
||||||
const onEnter = () => {
|
const onEnter = () => {
|
||||||
|
// TODO handle custom stuff
|
||||||
apps.fuzzy_query(text.get())?.[0].launch();
|
apps.fuzzy_query(text.get())?.[0].launch();
|
||||||
hide();
|
hide();
|
||||||
};
|
};
|
||||||
@ -29,13 +30,58 @@ const Launcher = () => {
|
|||||||
application={App}
|
application={App}
|
||||||
onShow={(self) => {
|
onShow={(self) => {
|
||||||
width.set(self.get_current_monitor().geometry.width);
|
width.set(self.get_current_monitor().geometry.width);
|
||||||
|
height.set(self.get_current_monitor().geometry.height);
|
||||||
}}
|
}}
|
||||||
onKeyPressed={(self, keyval) => {
|
onKeyPressed={(self, keyval) => {
|
||||||
if (keyval === Gdk.KEY_Escape) self.hide();
|
if (keyval === Gdk.KEY_Escape) self.hide();
|
||||||
}}
|
}}
|
||||||
child={
|
child={
|
||||||
<box></box>
|
<box
|
||||||
|
vertical
|
||||||
|
cssClasses={["app-launcher-wrapper"]}
|
||||||
|
widthRequest={width()}
|
||||||
|
heightRequest={height()}
|
||||||
|
valign={Gtk.Align.CENTER}
|
||||||
|
>
|
||||||
|
<button onClicked={hide} visible={false} />
|
||||||
|
<box
|
||||||
|
vertical
|
||||||
|
cssClasses={["app-launcher"]}
|
||||||
|
valign={Gtk.Align.CENTER}
|
||||||
|
halign={Gtk.Align.CENTER}
|
||||||
|
widthRequest={500}
|
||||||
|
>
|
||||||
|
<button onClicked={hide} visible={false}></button>
|
||||||
|
<box cssClasses={["search"]}>
|
||||||
|
<image iconName={"system-search-symbolic"}></image>
|
||||||
|
<entry
|
||||||
|
placeholderText={"Search..."}
|
||||||
|
text={text.get()}
|
||||||
|
setup={self => {
|
||||||
|
hook(self, App, 'window-toggled', (_, win) => {
|
||||||
|
if (win.name == 'launcher') {
|
||||||
|
self.set_text('');
|
||||||
|
self.grab_focus();
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}}
|
||||||
|
onNotifyText={self => text.set(self.text)}
|
||||||
|
primaryIconSensitive
|
||||||
|
onActivate={onEnter}
|
||||||
|
hexpand></entry>
|
||||||
|
</box>
|
||||||
|
<AppList
|
||||||
|
hide={hide}
|
||||||
|
query={text}
|
||||||
|
visible={text(v => {
|
||||||
|
return !prefixes.includes(v.slice(0, 1));
|
||||||
|
})}
|
||||||
|
></AppList>
|
||||||
|
</box>
|
||||||
|
</box>
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
</window>
|
</window>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export default Launcher;
|
||||||
|
16
config/astal/components/launcher/launcher.scss
Normal file
16
config/astal/components/launcher/launcher.scss
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
@use '../../util/colours.scss' as *;
|
||||||
|
|
||||||
|
window {
|
||||||
|
background: transparent;
|
||||||
|
}
|
||||||
|
|
||||||
|
box.app-launcher-wrapper {
|
||||||
|
background-color: $shadow-color;
|
||||||
|
|
||||||
|
>box.app-launcher {
|
||||||
|
background-color: $bg-color;
|
||||||
|
border-radius: 30px;
|
||||||
|
padding: 20px;
|
||||||
|
border: 1px solid $accent-color-2;
|
||||||
|
}
|
||||||
|
}
|
59
config/astal/components/launcher/modules/Apps.tsx
Normal file
59
config/astal/components/launcher/modules/Apps.tsx
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
import { Binding, Variable } from "astal";
|
||||||
|
import { Gtk } from "astal/gtk4";
|
||||||
|
import AstalApps from "gi://AstalApps";
|
||||||
|
import Pango from "gi://Pango?version=1.0";
|
||||||
|
|
||||||
|
const MAX_ITEMS = 8;
|
||||||
|
|
||||||
|
const AppList = ({ hide, query, visible }: { hide: () => void, query: Variable<string>, visible: Binding<Boolean> }) => {
|
||||||
|
const apps = new AstalApps.Apps();
|
||||||
|
const list = query((text) => apps.fuzzy_query(text).slice(0, MAX_ITEMS));
|
||||||
|
return <box>
|
||||||
|
<box
|
||||||
|
spacing={6}
|
||||||
|
vertical
|
||||||
|
cssClasses={["app-list"]}
|
||||||
|
visible={list.as(l => l.length > 0)}
|
||||||
|
>
|
||||||
|
{list.as(l => l.map(app => <AppButton app={app} hide={hide}></AppButton>))}
|
||||||
|
</box>
|
||||||
|
<box
|
||||||
|
halign={Gtk.Align.CENTER}
|
||||||
|
cssClasses={["list-empty"]}
|
||||||
|
vertical
|
||||||
|
visible={list.as(l => l.length === 0)}
|
||||||
|
>
|
||||||
|
<image iconName={"system-search-symbolic"}></image>
|
||||||
|
<label label={"No match found"}></label>
|
||||||
|
</box>
|
||||||
|
</box>
|
||||||
|
}
|
||||||
|
|
||||||
|
const AppButton = ({ app, hide }: { app: AstalApps.Application, hide: () => void }) => {
|
||||||
|
return <button
|
||||||
|
onClicked={() => {
|
||||||
|
hide();
|
||||||
|
app.launch();
|
||||||
|
}}
|
||||||
|
child={
|
||||||
|
<box>
|
||||||
|
<image iconName={app.iconName}></image>
|
||||||
|
<box valign={Gtk.Align.CENTER} vertical>
|
||||||
|
<label
|
||||||
|
cssClasses={["title-2"]}
|
||||||
|
ellipsize={Pango.EllipsizeMode.END}
|
||||||
|
maxWidthChars={40}
|
||||||
|
xalign={0}
|
||||||
|
label={app.name}
|
||||||
|
></label>
|
||||||
|
<label
|
||||||
|
wrap xalign={0}
|
||||||
|
label={app.description}
|
||||||
|
></label>
|
||||||
|
</box>
|
||||||
|
</box>
|
||||||
|
}>
|
||||||
|
</button>
|
||||||
|
}
|
||||||
|
|
||||||
|
export default AppList;
|
Loading…
x
Reference in New Issue
Block a user