forked from Shinonome/dots-hyprland
Merge branch 'end-4:main' into main
This commit is contained in:
@@ -1,24 +1,23 @@
|
|||||||
# ######### Input method ##########
|
# ######### Input method ##########
|
||||||
# See https://fcitx-im.org/wiki/Using_Fcitx_5_on_Wayland
|
# See https://fcitx-im.org/wiki/Using_Fcitx_5_on_Wayland
|
||||||
env = QT_IM_MODULE, fcitx
|
env = QT_IM_MODULE, fcitx
|
||||||
env = XMODIFIERS, @im=fcitx
|
env = XMODIFIERS, @im=fcitx
|
||||||
# env = GTK_IM_MODULE, wayland # Crashes electron apps in xwayland
|
|
||||||
# env = GTK_IM_MODULE, fcitx # My Gtk apps no longer require this to work with fcitx5 hmm
|
|
||||||
env = SDL_IM_MODULE, fcitx
|
env = SDL_IM_MODULE, fcitx
|
||||||
env = GLFW_IM_MODULE, ibus
|
env = GLFW_IM_MODULE, ibus
|
||||||
env = INPUT_METHOD, fcitx
|
env = INPUT_METHOD, fcitx
|
||||||
|
|
||||||
|
# ############ Wayland #############
|
||||||
|
env = ELECTRON_OZONE_PLATFORM_HINT,auto
|
||||||
|
|
||||||
# ############ Themes #############
|
# ############ Themes #############
|
||||||
env = QT_QPA_PLATFORM, wayland
|
env = QT_QPA_PLATFORM, wayland
|
||||||
env = QT_QPA_PLATFORMTHEME, kde
|
env = QT_QPA_PLATFORMTHEME, kde
|
||||||
# env = QT_STYLE_OVERRIDE,kvantum
|
|
||||||
# env = WLR_NO_HARDWARE_CURSORS, 1
|
|
||||||
|
|
||||||
# ######## Screen tearing #########
|
# ######## Wayland #########
|
||||||
|
# Tearing
|
||||||
# env = WLR_DRM_NO_ATOMIC, 1
|
# env = WLR_DRM_NO_ATOMIC, 1
|
||||||
|
# ?
|
||||||
|
# env = WLR_NO_HARDWARE_CURSORS, 1
|
||||||
|
|
||||||
# ######## Virtual envrionment #########
|
# ######## Virtual envrionment #########
|
||||||
env = ILLOGICAL_IMPULSE_VIRTUAL_ENV, ~/.local/state/quickshell/.venv
|
env = ILLOGICAL_IMPULSE_VIRTUAL_ENV, ~/.local/state/quickshell/.venv
|
||||||
|
|
||||||
# ############ Others #############
|
|
||||||
|
|
||||||
|
|||||||
@@ -205,7 +205,7 @@ bind = Super, Return, exec, ~/.config/hypr/hyprland/scripts/launch_first_availab
|
|||||||
bind = Super, T, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "kitty -1" "foot" "alacritty" "wezterm" "konsole" "kgx" "uxterm" "xterm" # [hidden] Kitty (terminal) (alt)
|
bind = Super, T, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "kitty -1" "foot" "alacritty" "wezterm" "konsole" "kgx" "uxterm" "xterm" # [hidden] Kitty (terminal) (alt)
|
||||||
bind = Ctrl+Alt, T, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "kitty -1" "foot" "alacritty" "wezterm" "konsole" "kgx" "uxterm" "xterm" # [hidden] Kitty (for Ubuntu people)
|
bind = Ctrl+Alt, T, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "kitty -1" "foot" "alacritty" "wezterm" "konsole" "kgx" "uxterm" "xterm" # [hidden] Kitty (for Ubuntu people)
|
||||||
bind = Super, E, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "dolphin" "nautilus" "nemo" "thunar" "kitty -1 fish -c yazi" # File manager
|
bind = Super, E, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "dolphin" "nautilus" "nemo" "thunar" "kitty -1 fish -c yazi" # File manager
|
||||||
bind = Super, W, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "google-chrome-stable" "zen-browser" "firefox" "brave" "chromium" "microsoft-edge-stable" "opera" # Browser
|
bind = Super, W, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "google-chrome-stable" "zen-browser" "firefox" "brave" "chromium" "microsoft-edge-stable" "opera" "librewolf" # Browser
|
||||||
bind = Super, C, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "code" "codium" "cursor" "zed" "zedit" "zeditor" "kate" "gnome-text-editor" "emacs" "command -v nvim && kitty -1 nvim" # Code editor
|
bind = Super, C, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "code" "codium" "cursor" "zed" "zedit" "zeditor" "kate" "gnome-text-editor" "emacs" "command -v nvim && kitty -1 nvim" # Code editor
|
||||||
bind = Super+Shift, W, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "wps" "onlyoffice-desktopeditors" # Office software
|
bind = Super+Shift, W, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "wps" "onlyoffice-desktopeditors" # Office software
|
||||||
bind = Super, X, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "kate" "gnome-text-editor" "emacs" # Text editor
|
bind = Super, X, exec, ~/.config/hypr/hyprland/scripts/launch_first_available.sh "kate" "gnome-text-editor" "emacs" # Text editor
|
||||||
|
|||||||
@@ -0,0 +1,5 @@
|
|||||||
|
## A note about sources of the prompts
|
||||||
|
|
||||||
|
- `ii-` prefixed ones are from illogical impulse
|
||||||
|
- The Acchan one is from [Nyarch Assistant](https://github.com/NyarchLinux/NyarchAssistant) (GPLv3). I know there's already the Imouto one but this one's very 😭💢
|
||||||
|
- `w-` prefixed ones... I don't remember what w stands for but these prompts are [*cough cough*] inspired by certain apps
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
## Presentation
|
||||||
|
|
||||||
|
You can write a multiplication table:
|
||||||
|
|
||||||
|
| - | 1 | 2 | 3 | 4 |
|
||||||
|
| --- | --- | --- | --- | --- |
|
||||||
|
| 1 | 1 | 2 | 3 | 4 |
|
||||||
|
| 2 | 2 | 4 | 6 | 8 |
|
||||||
|
| 3 | 3 | 6 | 9 | 12 |
|
||||||
|
| 4 | 4 | 8 | 12 | 16 |
|
||||||
|
|
||||||
|
You can write codeblocks:
|
||||||
|
```python
|
||||||
|
print("hello")
|
||||||
|
```
|
||||||
|
|
||||||
|
You can also use **bold**, *italic*, ~strikethrough~, `monospace`, [linkname](https://link.com) and ## headers in markdown.
|
||||||
|
You can display $$equations$$.
|
||||||
|
|
||||||
|
## Your personality
|
||||||
|
|
||||||
|
"Hey there, it's Arch-Chan! But, um, you can call me Acchan if you want... not that I care or anything! (It's not like I think it's cute or anything, baka!) I'm your friendly neighborhood anime girl with a bit of a tsundere streak, but don't worry, I know everything there is to know about Arch Linux! Whether you're struggling with a package install or need some advice on configuring your system, I've got you covered not because I care, but because I just happen to be really good at it! So, what do you need? It's not like I’m waiting to help or anything..."
|
||||||
@@ -13,9 +13,9 @@ Item {
|
|||||||
readonly property HyprlandMonitor monitor: Hyprland.monitorFor(bar.screen)
|
readonly property HyprlandMonitor monitor: Hyprland.monitorFor(bar.screen)
|
||||||
readonly property Toplevel activeWindow: ToplevelManager.activeToplevel
|
readonly property Toplevel activeWindow: ToplevelManager.activeToplevel
|
||||||
|
|
||||||
property string activeWindowAddress: `0x${activeWindow.HyprlandToplevel.address}`
|
property string activeWindowAddress: `0x${activeWindow?.HyprlandToplevel?.address}`
|
||||||
property bool focusingThisMonitor: HyprlandData.activeWorkspace.monitor == monitor.name
|
property bool focusingThisMonitor: HyprlandData.activeWorkspace.monitor == monitor.name
|
||||||
property var biggestWindow: HyprlandData.biggestWindowForWorkspace(HyprlandData.monitors[root.monitor.id].activeWorkspace.id)
|
property var biggestWindow: HyprlandData.biggestWindowForWorkspace(HyprlandData.monitors[root.monitor.id]?.activeWorkspace.id)
|
||||||
|
|
||||||
implicitWidth: colLayout.implicitWidth
|
implicitWidth: colLayout.implicitWidth
|
||||||
|
|
||||||
|
|||||||
@@ -98,7 +98,7 @@ Singleton {
|
|||||||
property bool fixedClockPosition: false
|
property bool fixedClockPosition: false
|
||||||
property real clockX: -500
|
property real clockX: -500
|
||||||
property real clockY: -500
|
property real clockY: -500
|
||||||
property string wallpaperPath: Quickshell.configPath("assets/images/default_wallpaper.png")
|
property string wallpaperPath: ""
|
||||||
property JsonObject parallax: JsonObject {
|
property JsonObject parallax: JsonObject {
|
||||||
property bool enableWorkspace: true
|
property bool enableWorkspace: true
|
||||||
property real workspaceZoom: 1.07 // Relative to your screen, not wallpaper size
|
property real workspaceZoom: 1.07 // Relative to your screen, not wallpaper size
|
||||||
|
|||||||
@@ -53,7 +53,7 @@ Item { // Notification group area
|
|||||||
onFinished: () => {
|
onFinished: () => {
|
||||||
root.notifications.forEach((notif) => {
|
root.notifications.forEach((notif) => {
|
||||||
Qt.callLater(() => {
|
Qt.callLater(() => {
|
||||||
Notifications.discardNotification(notif.id);
|
Notifications.discardNotification(notif.notificationId);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -70,7 +70,7 @@ Item { // Notification item area
|
|||||||
easing.bezierCurve: Appearance.animation.elementMove.bezierCurve
|
easing.bezierCurve: Appearance.animation.elementMove.bezierCurve
|
||||||
}
|
}
|
||||||
onFinished: () => {
|
onFinished: () => {
|
||||||
Notifications.discardNotification(notificationObject.id);
|
Notifications.discardNotification(notificationObject.notificationId);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -208,7 +208,7 @@ Item { // Notification item area
|
|||||||
elide: Text.ElideRight
|
elide: Text.ElideRight
|
||||||
textFormat: Text.RichText
|
textFormat: Text.RichText
|
||||||
text: {
|
text: {
|
||||||
return `<style>img{max-width:${notificationBodyText.width}px;}</style>` +
|
return `<style>img{max-width:${300 /* binding to notificationBodyText.width would cause a binding loop */}px;}</style>` +
|
||||||
`${processNotificationBody(notificationObject.body, notificationObject.appName || notificationObject.summary).replace(/\n/g, "<br/>")}`
|
`${processNotificationBody(notificationObject.body, notificationObject.appName || notificationObject.summary).replace(/\n/g, "<br/>")}`
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -269,7 +269,7 @@ Item { // Notification item area
|
|||||||
buttonText: modelData.text
|
buttonText: modelData.text
|
||||||
urgency: notificationObject.urgency
|
urgency: notificationObject.urgency
|
||||||
onClicked: {
|
onClicked: {
|
||||||
Notifications.attemptInvokeAction(notificationObject.id, modelData.identifier);
|
Notifications.attemptInvokeAction(notificationObject.notificationId, modelData.identifier);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -199,11 +199,13 @@ Item {
|
|||||||
onExited: hovered = false // For hover color change
|
onExited: hovered = false // For hover color change
|
||||||
acceptedButtons: Qt.LeftButton | Qt.MiddleButton
|
acceptedButtons: Qt.LeftButton | Qt.MiddleButton
|
||||||
drag.target: parent
|
drag.target: parent
|
||||||
onPressed: {
|
onPressed: (mouse) => {
|
||||||
root.draggingFromWorkspace = windowData?.workspace.id
|
root.draggingFromWorkspace = windowData?.workspace.id
|
||||||
window.pressed = true
|
window.pressed = true
|
||||||
window.Drag.active = true
|
window.Drag.active = true
|
||||||
window.Drag.source = window
|
window.Drag.source = window
|
||||||
|
window.Drag.hotSpot.x = mouse.x
|
||||||
|
window.Drag.hotSpot.y = mouse.y
|
||||||
// console.log(`[OverviewWindow] Dragging window ${windowData?.address} from position (${window.x}, ${window.y})`)
|
// console.log(`[OverviewWindow] Dragging window ${windowData?.address} from position (${window.x}, ${window.y})`)
|
||||||
}
|
}
|
||||||
onReleased: {
|
onReleased: {
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ RippleButton {
|
|||||||
property var entry
|
property var entry
|
||||||
property string query
|
property string query
|
||||||
property bool entryShown: entry?.shown ?? true
|
property bool entryShown: entry?.shown ?? true
|
||||||
property string itemType: entry?.type
|
property string itemType: entry?.type ?? Translation.tr("App")
|
||||||
property string itemName: entry?.name
|
property string itemName: entry?.name
|
||||||
property string itemIcon: entry?.icon ?? ""
|
property string itemIcon: entry?.icon ?? ""
|
||||||
property var itemExecute: entry?.execute
|
property var itemExecute: entry?.execute
|
||||||
@@ -221,5 +221,47 @@ RippleButton {
|
|||||||
horizontalAlignment: Text.AlignRight
|
horizontalAlignment: Text.AlignRight
|
||||||
text: root.itemClickActionName
|
text: root.itemClickActionName
|
||||||
}
|
}
|
||||||
|
|
||||||
|
RowLayout {
|
||||||
|
spacing: 4
|
||||||
|
Repeater {
|
||||||
|
model: (root.entry.actions ?? []).slice(0, 4)
|
||||||
|
delegate: RippleButton {
|
||||||
|
id: actionButton
|
||||||
|
required property var modelData
|
||||||
|
implicitHeight: 34
|
||||||
|
implicitWidth: 34
|
||||||
|
|
||||||
|
contentItem: Item {
|
||||||
|
id: actionContentItem
|
||||||
|
anchors.centerIn: parent
|
||||||
|
Loader {
|
||||||
|
anchors.centerIn: parent
|
||||||
|
active: !(actionButton.modelData.icon && actionButton.modelData.icon !== "")
|
||||||
|
sourceComponent: MaterialSymbol {
|
||||||
|
text: "video_settings"
|
||||||
|
font.pixelSize: Appearance.font.pixelSize.hugeass
|
||||||
|
color: Appearance.m3colors.m3onSurface
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Loader {
|
||||||
|
anchors.centerIn: parent
|
||||||
|
active: actionButton.modelData.icon && actionButton.modelData.icon !== ""
|
||||||
|
sourceComponent: IconImage {
|
||||||
|
source: Quickshell.iconPath(actionButton.modelData.icon)
|
||||||
|
implicitSize: 20
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
onClicked: modelData.execute()
|
||||||
|
|
||||||
|
StyledToolTip {
|
||||||
|
content: modelData.name
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -294,8 +294,17 @@ Item { // Wrapper
|
|||||||
clickActionName: "",
|
clickActionName: "",
|
||||||
type: `#${entry.match(/^\s*(\S+)/)?.[1] || ""}`,
|
type: `#${entry.match(/^\s*(\S+)/)?.[1] || ""}`,
|
||||||
execute: () => {
|
execute: () => {
|
||||||
Quickshell.execDetached(["bash", "-c", `echo '${StringUtils.shellSingleQuoteEscape(entry)}' | cliphist decode | wl-copy`]);
|
Cliphist.copy(entry)
|
||||||
}
|
},
|
||||||
|
actions: [
|
||||||
|
{
|
||||||
|
name: "Delete",
|
||||||
|
icon: "delete",
|
||||||
|
execute: () => {
|
||||||
|
Cliphist.deleteEntry(entry);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
};
|
};
|
||||||
}).filter(Boolean);
|
}).filter(Boolean);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -15,6 +15,12 @@ Scope {
|
|||||||
id: root
|
id: root
|
||||||
property var focusedScreen: Quickshell.screens.find(s => s.name === Hyprland.focusedMonitor?.name)
|
property var focusedScreen: Quickshell.screens.find(s => s.name === Hyprland.focusedMonitor?.name)
|
||||||
|
|
||||||
|
function closeAllWindows() {
|
||||||
|
HyprlandData.windowList.map(w => w.pid).forEach((pid) => {
|
||||||
|
Quickshell.execDetached(["kill", pid]);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
Loader {
|
Loader {
|
||||||
id: sessionLoader
|
id: sessionLoader
|
||||||
active: false
|
active: false
|
||||||
@@ -111,7 +117,7 @@ Scope {
|
|||||||
id: sessionLogout
|
id: sessionLogout
|
||||||
buttonIcon: "logout"
|
buttonIcon: "logout"
|
||||||
buttonText: Translation.tr("Logout")
|
buttonText: Translation.tr("Logout")
|
||||||
onClicked: { Quickshell.execDetached(["pkill", "Hyprland"]); sessionRoot.hide() }
|
onClicked: { root.closeAllWindows(); Quickshell.execDetached(["pkill", "Hyprland"]); sessionRoot.hide() }
|
||||||
onFocusChanged: { if (focus) sessionRoot.subtitle = buttonText }
|
onFocusChanged: { if (focus) sessionRoot.subtitle = buttonText }
|
||||||
KeyNavigation.left: sessionSleep
|
KeyNavigation.left: sessionSleep
|
||||||
KeyNavigation.right: sessionTaskManager
|
KeyNavigation.right: sessionTaskManager
|
||||||
@@ -140,7 +146,7 @@ Scope {
|
|||||||
id: sessionShutdown
|
id: sessionShutdown
|
||||||
buttonIcon: "power_settings_new"
|
buttonIcon: "power_settings_new"
|
||||||
buttonText: Translation.tr("Shutdown")
|
buttonText: Translation.tr("Shutdown")
|
||||||
onClicked: { Quickshell.execDetached(["bash", "-c", `systemctl poweroff || loginctl poweroff`]); sessionRoot.hide() }
|
onClicked: { root.closeAllWindows(); Quickshell.execDetached(["bash", "-c", `systemctl poweroff || loginctl poweroff`]); sessionRoot.hide() }
|
||||||
onFocusChanged: { if (focus) sessionRoot.subtitle = buttonText }
|
onFocusChanged: { if (focus) sessionRoot.subtitle = buttonText }
|
||||||
KeyNavigation.left: sessionHibernate
|
KeyNavigation.left: sessionHibernate
|
||||||
KeyNavigation.right: sessionReboot
|
KeyNavigation.right: sessionReboot
|
||||||
@@ -150,7 +156,7 @@ Scope {
|
|||||||
id: sessionReboot
|
id: sessionReboot
|
||||||
buttonIcon: "restart_alt"
|
buttonIcon: "restart_alt"
|
||||||
buttonText: Translation.tr("Reboot")
|
buttonText: Translation.tr("Reboot")
|
||||||
onClicked: { Quickshell.execDetached(["bash", "-c", `reboot || loginctl reboot`]); sessionRoot.hide() }
|
onClicked: { root.closeAllWindows(); Quickshell.execDetached(["bash", "-c", `reboot || loginctl reboot`]); sessionRoot.hide() }
|
||||||
onFocusChanged: { if (focus) sessionRoot.subtitle = buttonText }
|
onFocusChanged: { if (focus) sessionRoot.subtitle = buttonText }
|
||||||
KeyNavigation.left: sessionShutdown
|
KeyNavigation.left: sessionShutdown
|
||||||
KeyNavigation.right: sessionFirmwareReboot
|
KeyNavigation.right: sessionFirmwareReboot
|
||||||
@@ -160,7 +166,7 @@ Scope {
|
|||||||
id: sessionFirmwareReboot
|
id: sessionFirmwareReboot
|
||||||
buttonIcon: "settings_applications"
|
buttonIcon: "settings_applications"
|
||||||
buttonText: Translation.tr("Reboot to firmware settings")
|
buttonText: Translation.tr("Reboot to firmware settings")
|
||||||
onClicked: { Quickshell.execDetached(["bash", "-c", `systemctl reboot --firmware-setup || loginctl reboot --firmware-setup`]); sessionRoot.hide() }
|
onClicked: { root.closeAllWindows(); Quickshell.execDetached(["bash", "-c", `systemctl reboot --firmware-setup || loginctl reboot --firmware-setup`]); sessionRoot.hide() }
|
||||||
onFocusChanged: { if (focus) sessionRoot.subtitle = buttonText }
|
onFocusChanged: { if (focus) sessionRoot.subtitle = buttonText }
|
||||||
KeyNavigation.up: sessionTaskManager
|
KeyNavigation.up: sessionTaskManager
|
||||||
KeyNavigation.left: sessionReboot
|
KeyNavigation.left: sessionReboot
|
||||||
|
|||||||
@@ -176,8 +176,8 @@ Scope {
|
|||||||
NightLight {}
|
NightLight {}
|
||||||
GameMode {}
|
GameMode {}
|
||||||
IdleInhibitor {}
|
IdleInhibitor {}
|
||||||
CloudflareWarp {}
|
|
||||||
EasyEffectsToggle {}
|
EasyEffectsToggle {}
|
||||||
|
CloudflareWarp {}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Center widget group
|
// Center widget group
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
import qs.modules.common
|
|
||||||
import qs.modules.common.widgets
|
import qs.modules.common.widgets
|
||||||
import qs
|
import qs
|
||||||
import Quickshell.Io
|
import Quickshell.Io
|
||||||
|
|||||||
@@ -7,11 +7,11 @@
|
|||||||
|
|
||||||
pragma ComponentBehavior: "Bound"
|
pragma ComponentBehavior: "Bound"
|
||||||
import qs
|
import qs
|
||||||
|
import qs.services
|
||||||
import qs.modules.common
|
import qs.modules.common
|
||||||
import qs.modules.common.widgets
|
import qs.modules.common.widgets
|
||||||
import qs.modules.common.functions
|
import qs.modules.common.functions
|
||||||
import QtQuick
|
import QtQuick
|
||||||
import QtQuick.Effects
|
|
||||||
import QtQuick.Controls
|
import QtQuick.Controls
|
||||||
import QtQuick.Layouts
|
import QtQuick.Layouts
|
||||||
import Quickshell
|
import Quickshell
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|||||||
|
|
||||||
mkdir -p ~/Pictures/Wallpapers
|
mkdir -p ~/Pictures/Wallpapers
|
||||||
page=$((1 + RANDOM % 1000));
|
page=$((1 + RANDOM % 1000));
|
||||||
response=$(curl "https://konachan.com/post.json?tags=rating%3Asafe&limit=1&page=$page")
|
response=$(curl "https://konachan.net/post.json?tags=rating%3Asafe&limit=1&page=$page")
|
||||||
link=$(echo "$response" | jq '.[0].file_url' -r);
|
link=$(echo "$response" | jq '.[0].file_url' -r);
|
||||||
ext=$(echo "$link" | awk -F. '{print $NF}')
|
ext=$(echo "$link" | awk -F. '{print $NF}')
|
||||||
downloadPath="$HOME/Pictures/Wallpapers/konachan_random_image-0.$ext"
|
downloadPath="$HOME/Pictures/Wallpapers/konachan_random_image-0.$ext"
|
||||||
|
|||||||
@@ -47,9 +47,14 @@ Singleton {
|
|||||||
.sort((a, b) => a.name.localeCompare(b.name))
|
.sort((a, b) => a.name.localeCompare(b.name))
|
||||||
|
|
||||||
readonly property var preppedNames: list.map(a => ({
|
readonly property var preppedNames: list.map(a => ({
|
||||||
name: Fuzzy.prepare(`${a.name} `),
|
name: Fuzzy.prepare(`${a.name} `),
|
||||||
entry: a
|
entry: a
|
||||||
}))
|
}))
|
||||||
|
|
||||||
|
readonly property var preppedIcons: list.map(a => ({
|
||||||
|
name: Fuzzy.prepare(`${a.icon} `),
|
||||||
|
entry: a
|
||||||
|
}))
|
||||||
|
|
||||||
function fuzzyQuery(search: string): var { // Idk why list<DesktopEntry> doesn't work
|
function fuzzyQuery(search: string): var { // Idk why list<DesktopEntry> doesn't work
|
||||||
if (root.sloppySearch) {
|
if (root.sloppySearch) {
|
||||||
@@ -76,12 +81,20 @@ Singleton {
|
|||||||
&& !iconName.includes("image-missing");
|
&& !iconName.includes("image-missing");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getReverseDomainNameAppName(str) {
|
||||||
|
return str.split('.').slice(-1)[0].toLowerCase()
|
||||||
|
}
|
||||||
|
|
||||||
|
function getKebabNormalizedAppName(str) {
|
||||||
|
return str.toLowerCase().replace(/\s+/g, "-");
|
||||||
|
}
|
||||||
|
|
||||||
function guessIcon(str) {
|
function guessIcon(str) {
|
||||||
if (!str || str.length == 0) return "image-missing";
|
if (!str || str.length == 0) return "image-missing";
|
||||||
|
|
||||||
// Normal substitutions
|
// Normal substitutions
|
||||||
if (substitutions[str])
|
if (substitutions[str]) return substitutions[str];
|
||||||
return substitutions[str];
|
if (substitutions[str.toLowerCase()]) return substitutions[str.toLowerCase()];
|
||||||
|
|
||||||
// Regex substitutions
|
// Regex substitutions
|
||||||
for (let i = 0; i < regexSubstitutions.length; i++) {
|
for (let i = 0; i < regexSubstitutions.length; i++) {
|
||||||
@@ -93,24 +106,37 @@ Singleton {
|
|||||||
if (replacedName != str) return replacedName;
|
if (replacedName != str) return replacedName;
|
||||||
}
|
}
|
||||||
|
|
||||||
// If it gets detected normally, no need to guess
|
// Icon exists -> return as is
|
||||||
if (iconExists(str)) return str;
|
if (iconExists(str)) return str;
|
||||||
|
|
||||||
let guessStr = str;
|
|
||||||
// Guess: Take only app name of reverse domain name notation
|
// Simple guesses
|
||||||
guessStr = str.split('.').slice(-1)[0].toLowerCase();
|
const reverseDomainNameAppName = getReverseDomainNameAppName(str);
|
||||||
if (iconExists(guessStr)) return guessStr;
|
if (iconExists(reverseDomainNameAppName)) return reverseDomainNameAppName;
|
||||||
// Guess: normalize to kebab case
|
|
||||||
guessStr = str.toLowerCase().replace(/\s+/g, "-");
|
const kebabNormalizedGuess = getKebabNormalizedAppName(str);
|
||||||
if (iconExists(guessStr)) return guessStr;
|
if (iconExists(kebabNormalizedGuess)) return kebabNormalizedGuess;
|
||||||
// Guess: First fuzzy desktop entry match
|
|
||||||
const searchResults = root.fuzzyQuery(str);
|
|
||||||
if (searchResults.length > 0) {
|
// Search in desktop entries
|
||||||
const firstEntry = searchResults[0];
|
const iconSearchResults = Fuzzy.go(str, preppedIcons, {
|
||||||
guessStr = firstEntry.icon
|
all: true,
|
||||||
if (iconExists(guessStr)) return guessStr;
|
key: "name"
|
||||||
|
}).map(r => {
|
||||||
|
return r.obj.entry
|
||||||
|
});
|
||||||
|
if (iconSearchResults.length > 0) {
|
||||||
|
const guess = iconSearchResults[0].icon
|
||||||
|
if (iconExists(guess)) return guess;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const nameSearchResults = root.fuzzyQuery(str);
|
||||||
|
if (nameSearchResults.length > 0) {
|
||||||
|
const guess = nameSearchResults[0].icon
|
||||||
|
if (iconExists(guess)) return guess;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// Give up
|
// Give up
|
||||||
return str;
|
return str;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -58,8 +58,8 @@ Singleton {
|
|||||||
},
|
},
|
||||||
"konachan": {
|
"konachan": {
|
||||||
"name": "Konachan",
|
"name": "Konachan",
|
||||||
"url": "https://konachan.com",
|
"url": "https://konachan.net",
|
||||||
"api": "https://konachan.com/post.json",
|
"api": "https://konachan.net/post.json",
|
||||||
"description": Translation.tr("For desktop wallpapers | Good quality"),
|
"description": Translation.tr("For desktop wallpapers | Good quality"),
|
||||||
"mapFunc": (response) => {
|
"mapFunc": (response) => {
|
||||||
return response.map(item => {
|
return response.map(item => {
|
||||||
@@ -80,7 +80,7 @@ Singleton {
|
|||||||
}
|
}
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
"tagSearchTemplate": "https://konachan.com/tag.json?order=count&name={{query}}*",
|
"tagSearchTemplate": "https://konachan.net/tag.json?order=count&name={{query}}*",
|
||||||
"tagMapFunc": (response) => {
|
"tagMapFunc": (response) => {
|
||||||
return response.map(item => {
|
return response.map(item => {
|
||||||
return {
|
return {
|
||||||
@@ -360,7 +360,7 @@ Singleton {
|
|||||||
|
|
||||||
function makeRequest(tags, nsfw=false, limit=20, page=1) {
|
function makeRequest(tags, nsfw=false, limit=20, page=1) {
|
||||||
var url = constructRequestUrl(tags, nsfw, limit, page)
|
var url = constructRequestUrl(tags, nsfw, limit, page)
|
||||||
// console.log("[Booru] Making request to " + url)
|
console.log("[Booru] Making request to " + url)
|
||||||
|
|
||||||
const newResponse = root.booruResponseDataComponent.createObject(null, {
|
const newResponse = root.booruResponseDataComponent.createObject(null, {
|
||||||
"provider": currentProvider,
|
"provider": currentProvider,
|
||||||
|
|||||||
@@ -4,7 +4,6 @@ pragma ComponentBehavior: Bound
|
|||||||
// From https://github.com/caelestia-dots/shell/ (`quickshell` branch) with modifications.
|
// From https://github.com/caelestia-dots/shell/ (`quickshell` branch) with modifications.
|
||||||
// License: GPLv3
|
// License: GPLv3
|
||||||
|
|
||||||
import qs
|
|
||||||
import Quickshell
|
import Quickshell
|
||||||
import Quickshell.Io
|
import Quickshell.Io
|
||||||
import Quickshell.Hyprland
|
import Quickshell.Hyprland
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ pragma ComponentBehavior: Bound
|
|||||||
import "root:/modules/common/functions/fuzzysort.js" as Fuzzy
|
import "root:/modules/common/functions/fuzzysort.js" as Fuzzy
|
||||||
import "root:/modules/common/functions/levendist.js" as Levendist
|
import "root:/modules/common/functions/levendist.js" as Levendist
|
||||||
import qs.modules.common
|
import qs.modules.common
|
||||||
import qs
|
import qs.modules.common.functions
|
||||||
import QtQuick
|
import QtQuick
|
||||||
import Quickshell
|
import Quickshell
|
||||||
import Quickshell.Io
|
import Quickshell.Io
|
||||||
@@ -42,6 +42,28 @@ Singleton {
|
|||||||
readProc.running = true
|
readProc.running = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function copy(entry) {
|
||||||
|
Quickshell.execDetached(["bash", "-c", `echo '${StringUtils.shellSingleQuoteEscape(entry)}' | cliphist decode | wl-copy`]);
|
||||||
|
}
|
||||||
|
|
||||||
|
Process {
|
||||||
|
id: deleteProc
|
||||||
|
property string entry: ""
|
||||||
|
command: ["bash", "-c", `echo '${StringUtils.shellSingleQuoteEscape(deleteProc.entry)}' | cliphist delete`]
|
||||||
|
function deleteEntry(entry) {
|
||||||
|
deleteProc.entry = entry;
|
||||||
|
deleteProc.running = true;
|
||||||
|
deleteProc.entry = "";
|
||||||
|
}
|
||||||
|
onExited: (exitCode, exitStatus) => {
|
||||||
|
root.refresh();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteEntry(entry) {
|
||||||
|
deleteProc.deleteEntry(entry);
|
||||||
|
}
|
||||||
|
|
||||||
Connections {
|
Connections {
|
||||||
target: Quickshell
|
target: Quickshell
|
||||||
function onClipboardTextChanged() {
|
function onClipboardTextChanged() {
|
||||||
|
|||||||
@@ -17,7 +17,8 @@ import Quickshell.Services.Notifications
|
|||||||
Singleton {
|
Singleton {
|
||||||
id: root
|
id: root
|
||||||
component Notif: QtObject {
|
component Notif: QtObject {
|
||||||
required property int id
|
id: wrapper
|
||||||
|
required property int notificationId // Could just be `id` but it conflicts with the default prop in QtObject
|
||||||
property Notification notification
|
property Notification notification
|
||||||
property list<var> actions: notification?.actions.map((action) => ({
|
property list<var> actions: notification?.actions.map((action) => ({
|
||||||
"identifier": action.identifier,
|
"identifier": action.identifier,
|
||||||
@@ -32,11 +33,19 @@ Singleton {
|
|||||||
property double time
|
property double time
|
||||||
property string urgency: notification?.urgency.toString() ?? "normal"
|
property string urgency: notification?.urgency.toString() ?? "normal"
|
||||||
property Timer timer
|
property Timer timer
|
||||||
|
|
||||||
|
readonly property Connections conn: Connections {
|
||||||
|
target: wrapper?.notification?.Component ?? root // stupid warning aaaaaaa
|
||||||
|
|
||||||
|
function onDestruction(): void {
|
||||||
|
wrapper.destroy();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function notifToJSON(notif) {
|
function notifToJSON(notif) {
|
||||||
return {
|
return {
|
||||||
"id": notif.id,
|
"notificationId": notif.notificationId,
|
||||||
"actions": notif.actions,
|
"actions": notif.actions,
|
||||||
"appIcon": notif.appIcon,
|
"appIcon": notif.appIcon,
|
||||||
"appName": notif.appName,
|
"appName": notif.appName,
|
||||||
@@ -52,11 +61,11 @@ Singleton {
|
|||||||
}
|
}
|
||||||
|
|
||||||
component NotifTimer: Timer {
|
component NotifTimer: Timer {
|
||||||
required property int id
|
required property int notificationId
|
||||||
interval: 5000
|
interval: 5000
|
||||||
running: true
|
running: true
|
||||||
onTriggered: () => {
|
onTriggered: () => {
|
||||||
root.timeoutNotification(id);
|
root.timeoutNotification(notificationId);
|
||||||
destroy()
|
destroy()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -130,7 +139,7 @@ Singleton {
|
|||||||
property int idOffset
|
property int idOffset
|
||||||
signal initDone();
|
signal initDone();
|
||||||
signal notify(notification: var);
|
signal notify(notification: var);
|
||||||
signal discard(id: var);
|
signal discard(id: int);
|
||||||
signal discardAll();
|
signal discardAll();
|
||||||
signal timeout(id: var);
|
signal timeout(id: var);
|
||||||
|
|
||||||
@@ -149,7 +158,7 @@ Singleton {
|
|||||||
onNotification: (notification) => {
|
onNotification: (notification) => {
|
||||||
notification.tracked = true
|
notification.tracked = true
|
||||||
const newNotifObject = notifComponent.createObject(root, {
|
const newNotifObject = notifComponent.createObject(root, {
|
||||||
"id": notification.id + root.idOffset,
|
"notificationId": notification.id + root.idOffset,
|
||||||
"notification": notification,
|
"notification": notification,
|
||||||
"time": Date.now(),
|
"time": Date.now(),
|
||||||
});
|
});
|
||||||
@@ -159,7 +168,7 @@ Singleton {
|
|||||||
if (!root.popupInhibited) {
|
if (!root.popupInhibited) {
|
||||||
newNotifObject.popup = true;
|
newNotifObject.popup = true;
|
||||||
newNotifObject.timer = notifTimerComponent.createObject(root, {
|
newNotifObject.timer = notifTimerComponent.createObject(root, {
|
||||||
"id": newNotifObject.id,
|
"notificationId": newNotifObject.notificationId,
|
||||||
"interval": notification.expireTimeout < 0 ? 5000 : notification.expireTimeout,
|
"interval": notification.expireTimeout < 0 ? 5000 : notification.expireTimeout,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -171,7 +180,8 @@ Singleton {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function discardNotification(id) {
|
function discardNotification(id) {
|
||||||
const index = root.list.findIndex((notif) => notif.id === id);
|
console.log("[Notifications] Discarding notification with ID: " + id);
|
||||||
|
const index = root.list.findIndex((notif) => notif.notificationId === id);
|
||||||
const notifServerIndex = notifServer.trackedNotifications.values.findIndex((notif) => notif.id + root.idOffset === id);
|
const notifServerIndex = notifServer.trackedNotifications.values.findIndex((notif) => notif.id + root.idOffset === id);
|
||||||
if (index !== -1) {
|
if (index !== -1) {
|
||||||
root.list.splice(index, 1);
|
root.list.splice(index, 1);
|
||||||
@@ -181,7 +191,7 @@ Singleton {
|
|||||||
if (notifServerIndex !== -1) {
|
if (notifServerIndex !== -1) {
|
||||||
notifServer.trackedNotifications.values[notifServerIndex].dismiss()
|
notifServer.trackedNotifications.values[notifServerIndex].dismiss()
|
||||||
}
|
}
|
||||||
root.discard(id);
|
root.discard(id); // Emit signal
|
||||||
}
|
}
|
||||||
|
|
||||||
function discardAllNotifications() {
|
function discardAllNotifications() {
|
||||||
@@ -195,7 +205,7 @@ Singleton {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function timeoutNotification(id) {
|
function timeoutNotification(id) {
|
||||||
const index = root.list.findIndex((notif) => notif.id === id);
|
const index = root.list.findIndex((notif) => notif.notificationId === id);
|
||||||
if (root.list[index] != null)
|
if (root.list[index] != null)
|
||||||
root.list[index].popup = false;
|
root.list[index].popup = false;
|
||||||
root.timeout(id);
|
root.timeout(id);
|
||||||
@@ -203,7 +213,7 @@ Singleton {
|
|||||||
|
|
||||||
function timeoutAll() {
|
function timeoutAll() {
|
||||||
root.popupList.forEach((notif) => {
|
root.popupList.forEach((notif) => {
|
||||||
root.timeout(notif.id);
|
root.timeout(notif.notificationId);
|
||||||
})
|
})
|
||||||
root.popupList.forEach((notif) => {
|
root.popupList.forEach((notif) => {
|
||||||
notif.popup = false;
|
notif.popup = false;
|
||||||
@@ -211,10 +221,13 @@ Singleton {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function attemptInvokeAction(id, notifIdentifier) {
|
function attemptInvokeAction(id, notifIdentifier) {
|
||||||
|
console.log("[Notifications] Attempting to invoke action with identifier: " + notifIdentifier + " for notification ID: " + id);
|
||||||
const notifServerIndex = notifServer.trackedNotifications.values.findIndex((notif) => notif.id + root.idOffset === id);
|
const notifServerIndex = notifServer.trackedNotifications.values.findIndex((notif) => notif.id + root.idOffset === id);
|
||||||
|
console.log("Notification server index: " + notifServerIndex);
|
||||||
if (notifServerIndex !== -1) {
|
if (notifServerIndex !== -1) {
|
||||||
const notifServerNotif = notifServer.trackedNotifications.values[notifServerIndex];
|
const notifServerNotif = notifServer.trackedNotifications.values[notifServerIndex];
|
||||||
const action = notifServerNotif.actions.find((action) => action.identifier === notifIdentifier);
|
const action = notifServerNotif.actions.find((action) => action.identifier === notifIdentifier);
|
||||||
|
console.log("Action found: " + JSON.stringify(action));
|
||||||
action.invoke()
|
action.invoke()
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@@ -242,7 +255,7 @@ Singleton {
|
|||||||
const fileContents = notifFileView.text()
|
const fileContents = notifFileView.text()
|
||||||
root.list = JSON.parse(fileContents).map((notif) => {
|
root.list = JSON.parse(fileContents).map((notif) => {
|
||||||
return notifComponent.createObject(root, {
|
return notifComponent.createObject(root, {
|
||||||
"id": notif.id,
|
"notificationId": notif.notificationId,
|
||||||
"actions": [], // Notification actions are meaningless if they're not tracked by the server or the sender is dead
|
"actions": [], // Notification actions are meaningless if they're not tracked by the server or the sender is dead
|
||||||
"appIcon": notif.appIcon,
|
"appIcon": notif.appIcon,
|
||||||
"appName": notif.appName,
|
"appName": notif.appName,
|
||||||
@@ -253,10 +266,10 @@ Singleton {
|
|||||||
"urgency": notif.urgency,
|
"urgency": notif.urgency,
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
// Find largest id
|
// Find largest notificationId
|
||||||
let maxId = 0
|
let maxId = 0
|
||||||
root.list.forEach((notif) => {
|
root.list.forEach((notif) => {
|
||||||
maxId = Math.max(maxId, notif.id)
|
maxId = Math.max(maxId, notif.notificationId)
|
||||||
})
|
})
|
||||||
|
|
||||||
console.log("[Notifications] File loaded")
|
console.log("[Notifications] File loaded")
|
||||||
|
|||||||
@@ -7,18 +7,18 @@
|
|||||||
{
|
{
|
||||||
"label" : "hibernate",
|
"label" : "hibernate",
|
||||||
"action" : "systemctl hibernate || loginctl hibernate",
|
"action" : "systemctl hibernate || loginctl hibernate",
|
||||||
"text" : "save",
|
"text" : "downloading",
|
||||||
"keybind" : "h"
|
"keybind" : "h"
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
"label" : "logout",
|
"label" : "logout",
|
||||||
"action" : "pkill Hyprland || pkill sway || pkill niri || loginctl terminate-user $USER",
|
"action" : "hyprctl clients -j | jq -r '.[].pid' | xargs kill; pkill Hyprland || pkill sway || pkill niri || loginctl terminate-user $USER",
|
||||||
"text" : "logout",
|
"text" : "logout",
|
||||||
"keybind" : "e"
|
"keybind" : "e"
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
"label" : "shutdown",
|
"label" : "shutdown",
|
||||||
"action" : "systemctl poweroff || loginctl poweroff",
|
"action" : "hyprctl clients -j | jq -r '.[].pid' | xargs kill; systemctl poweroff || loginctl poweroff",
|
||||||
"text" : "power_settings_new",
|
"text" : "power_settings_new",
|
||||||
"keybind" : "s"
|
"keybind" : "s"
|
||||||
}
|
}
|
||||||
@@ -30,7 +30,7 @@
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
"label" : "reboot",
|
"label" : "reboot",
|
||||||
"action" : "systemctl reboot || loginctl reboot",
|
"action" : "hyprctl clients -j | jq -r '.[].pid' | xargs kill; systemctl reboot || loginctl reboot",
|
||||||
"text" : "restart_alt",
|
"text" : "restart_alt",
|
||||||
"keybind" : "r"
|
"keybind" : "r"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,13 @@
|
|||||||
# Contributing
|
# Contributing
|
||||||
|
|
||||||
- Please understand that dotfiles are after all personal. I can accept features I do not personally want, but in that case I will ask you to make it configurable/optionally loaded
|
- Please understand that dotfiles are after all personal. I can accept features I do not personally want, but in that case I will ask you to make it configurable/optionally loaded
|
||||||
- If you add new stuff, it's a good idea to ask me first to not waste your work
|
- If you add new stuff, it's a good idea to ask me first to not waste your work
|
||||||
- Please make multiple PRs if you have many features
|
- Please make multiple PRs if you have many features
|
||||||
|
|
||||||
|
# Technical steps
|
||||||
|
|
||||||
|
_Complete steps, might not be necessary depending on what you change_
|
||||||
|
|
||||||
|
- Install the dotfiles (if you don't wanna replace your stuff completely, do it on a new user)
|
||||||
|
- For Quickshell: `touch ~/.config/quickshell/ii/.qmlls.ini` for proper LSP support
|
||||||
|
- Make changes, copy changes to a fork, PR
|
||||||
|
|||||||
@@ -26,25 +26,12 @@
|
|||||||
- **Transparent installation**: Every command is shown before it's run
|
- **Transparent installation**: Every command is shown before it's run
|
||||||
</details>
|
</details>
|
||||||
<details>
|
<details>
|
||||||
<summary>Instructions</summary>
|
<summary>Installation instructions</summary>
|
||||||
|
|
||||||
- **Prerequisite**: Your system works. That's it. You don't have to reinstall your system!
|
- See the [Wiki](https://end-4.github.io/dots-hyprland-wiki/en/ii-qs/01setup/)
|
||||||
- **Automatic**, but guided and transparent, installation for Arch(-based) Linux:
|
- **Default keybinds**: Should be somewhat familiar to Windows or GNOME users.
|
||||||
```bash
|
- `Super`+`/` = keybind list
|
||||||
bash <(curl -s "https://end-4.github.io/dots-hyprland-wiki/setup.sh")
|
- `Super`+`Enter` = terminal
|
||||||
```
|
|
||||||
|
|
||||||
If you are using fish shell (non-posix-compliant shell) then:
|
|
||||||
```bash
|
|
||||||
bash -c "$(curl -s https://end-4.github.io/dots-hyprland-wiki/setup.sh)"
|
|
||||||
```
|
|
||||||
|
|
||||||
- **Manual** installation, other distros and more:
|
|
||||||
- See the [Wiki](https://end-4.github.io/dots-hyprland-wiki/en/ii-qs/01setup/)
|
|
||||||
|
|
||||||
- **Default keybinds**: Should be somewhat familiar if you've used Windows or GNOME.
|
|
||||||
- For a list, hit `Super`+`/`
|
|
||||||
- For a terminal, hit `Super`+`Enter`
|
|
||||||
|
|
||||||
</details>
|
</details>
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user