diff --git a/electron/main/freedesktop/desktop-apps.ts b/electron/main/freedesktop/desktop-apps.ts index d89d417..022857a 100644 --- a/electron/main/freedesktop/desktop-apps.ts +++ b/electron/main/freedesktop/desktop-apps.ts @@ -2,9 +2,9 @@ import { DesktopEntry, DESKTOP_ENTRY_HEADER, } from "../../../common/desktop-entries"; +import rustModules from "../../../native/index.node"; import { ArgsProvider } from "../args"; import Logger from "../logger"; -import freedesktopIcons from "freedesktop-icons"; import fs from "fs"; import path from "path"; import { xdgDataDirectories } from "xdg-basedir"; @@ -14,7 +14,7 @@ export type DesktopEntryWithPath = { entry: DesktopEntry; }; export class DesktopEntriesProvider { - static desktopEntries: DesktopEntryWithPath[] = []; + static desktopEntries: RustDesktopEntry[] = []; static isDone = false; private constructor() {} @@ -127,7 +127,7 @@ export const readDesktopEntries = async () => { const startTime = process.hrtime(); if (!DesktopEntriesProvider.isDone && ArgsProvider.flags.mode === "apps") { - DesktopEntriesProvider.desktopEntries = await getDesktopEntries(); + DesktopEntriesProvider.desktopEntries = rustModules.getDesktopEntries(); DesktopEntriesProvider.isDone = true; } diff --git a/electron/main/index.ts b/electron/main/index.ts index 962480e..9b7bbb1 100644 --- a/electron/main/index.ts +++ b/electron/main/index.ts @@ -26,12 +26,6 @@ const indexHtml = join(ROOT_PATH.dist, "index.html"); const startTime = process.hrtime(); await readCLIFlags(); - // console.log(rustModules.hello()); - - // console.log(rustModules.getDesktopEntries()); - console.log(JSON.parse(rustModules.getAppsMac())); - app.exit(); - // Set application name for Windows 10+ notifications if (process.platform === "win32") app.setAppUserModelId(app.getName()); diff --git a/electron/main/options.ts b/electron/main/options.ts index b39aa79..bc81884 100644 --- a/electron/main/options.ts +++ b/electron/main/options.ts @@ -68,13 +68,14 @@ export class OptionsProvider { static getOptionsFromDesktopEntries = async (): Promise => { await readDesktopEntries(); + return DesktopEntriesProvider.desktopEntries.map( (entry, index) => ({ id: (index + 1).toString(), - name: entry.entry[DESKTOP_ENTRY_HEADER].Name, - description: entry.entry[DESKTOP_ENTRY_HEADER].Comment, - icon: entry.entry[DESKTOP_ENTRY_HEADER].Icon, + name: entry.name, + description: entry.description, + icon: entry.icon && `file://${entry.icon}`, onAction: { type: LauncherActionType.RunDesktopFile, payload: path.basename(entry.path), diff --git a/electron/typings.d.ts b/electron/typings.d.ts index ec7a923..9da4033 100644 --- a/electron/typings.d.ts +++ b/electron/typings.d.ts @@ -1,4 +1,11 @@ +type RustDesktopEntry = { + path: string; + name: string; + description: string; + icon?: string; +}; + declare module "*index.node" { - export const getDesktopEntries: () => object; + export const getDesktopEntries: () => RustDesktopEntry[]; export const getAppsMac: () => string; } diff --git a/native/Cargo.lock b/native/Cargo.lock index 7a576eb..0ff3794 100644 --- a/native/Cargo.lock +++ b/native/Cargo.lock @@ -2,6 +2,17 @@ # It is not intended for manual editing. version = 3 +[[package]] +name = "ahash" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcb51a0695d8f838b1ee009b3fbf66bda078cd64590202a864a8f3e8c4315c47" +dependencies = [ + "getrandom", + "once_cell", + "version_check", +] + [[package]] name = "aho-corasick" version = "0.7.19" @@ -16,6 +27,7 @@ name = "based_launcher" version = "1.0.8" dependencies = [ "freedesktop-desktop-entry", + "freedesktop-icons", "neon", ] @@ -72,6 +84,12 @@ dependencies = [ "winapi", ] +[[package]] +name = "dlv-list" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0688c2a7f92e427f44895cd63841bff7b29f8d7a1648b9e7e07a4a365b2e1257" + [[package]] name = "freedesktop-desktop-entry" version = "0.5.0" @@ -85,6 +103,18 @@ dependencies = [ "xdg", ] +[[package]] +name = "freedesktop-icons" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "420b2cb0cf0ab0d5f34c068830f3b5c17b378ab3c2acaf7ca4bfde671d70be51" +dependencies = [ + "dirs 4.0.0", + "once_cell", + "rust-ini", + "thiserror", +] + [[package]] name = "getrandom" version = "0.2.7" @@ -116,6 +146,15 @@ dependencies = [ "temp-dir", ] +[[package]] +name = "hashbrown" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" +dependencies = [ + "ahash", +] + [[package]] name = "lazy_static" version = "1.4.0" @@ -236,6 +275,22 @@ dependencies = [ "objc", ] +[[package]] +name = "once_cell" +version = "1.15.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e82dad04139b71a90c080c8463fe0dc7902db5192d939bd0950f074d014339e1" + +[[package]] +name = "ordered-multimap" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ccd746e37177e1711c20dd619a1620f34f5c8b569c53590a72dedd5344d8924a" +dependencies = [ + "dlv-list", + "hashbrown", +] + [[package]] name = "proc-macro2" version = "1.0.46" @@ -291,6 +346,16 @@ version = "0.6.27" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a3f87b73ce11b1619a3c6332f45341e0047173771e8b8b73f87bfeefb7b56244" +[[package]] +name = "rust-ini" +version = "0.18.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f6d5f2436026b4f6e79dc829837d467cc7e9a55ee40e750d716713540715a2df" +dependencies = [ + "cfg-if", + "ordered-multimap", +] + [[package]] name = "semver" version = "0.9.0" @@ -366,6 +431,12 @@ version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "dcc811dc4066ac62f84f11307873c4850cb653bfa9b1719cee2bd2204a4bc5dd" +[[package]] +name = "version_check" +version = "0.9.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" + [[package]] name = "wasi" version = "0.11.0+wasi-snapshot-preview1" diff --git a/native/Cargo.toml b/native/Cargo.toml index 8f04744..07bcd65 100644 --- a/native/Cargo.toml +++ b/native/Cargo.toml @@ -11,6 +11,7 @@ crate-type = ["cdylib"] [dependencies] "freedesktop-desktop-entry" = "0.5.0" +freedesktop-icons = "0.2.1" [dependencies.neon] version = "0.10" diff --git a/native/src/lib.rs b/native/src/lib.rs index c252c3f..ce95b28 100644 --- a/native/src/lib.rs +++ b/native/src/lib.rs @@ -1,11 +1,13 @@ -use std::fs; - mod mac; +use std::fs; + use freedesktop_desktop_entry::{default_paths, DesktopEntry, Iter}; -use mac::get_apps_json; +use freedesktop_icons::lookup; use neon::prelude::*; +use mac::get_apps_json; + fn get_desktop_entries(mut cx: FunctionContext) -> JsResult { let entries = cx.empty_array(); @@ -15,15 +17,33 @@ fn get_desktop_entries(mut cx: FunctionContext) -> JsResult { let locale = Some("en-US"); let obj = cx.empty_object(); + let path_str = path.to_str().unwrap(); + let path_js_str = cx.string(path_str); + obj.set(&mut cx, "path", path_js_str)?; + let name = cx.string(entry.name(locale).unwrap_or_default().to_string()); obj.set(&mut cx, "name", name)?; let description = cx.string(entry.comment(locale).unwrap_or_default().to_string()); obj.set(&mut cx, "description", description)?; - let icon = cx.string(entry.icon().unwrap_or_default().to_string()); + let icon_name = entry.icon().unwrap_or_default().to_string(); + let icon = lookup(&icon_name) + .with_size(48) + .find() + .unwrap_or_default() + .into_os_string() + .into_string() + .unwrap(); + + if (icon.len() > 0) { + let icon_value = cx.string(icon); - obj.set(&mut cx, "icon", icon)?; + obj.set(&mut cx, "icon", icon_value)?; + } + + let len = entries.len(&mut cx); + entries.set(&mut cx, len, obj)?; } } } @@ -35,10 +55,6 @@ fn get_apps_mac(mut cx: FunctionContext) -> JsResult { let process = get_apps_json(); let json = String::from_utf8_lossy(&process.stdout); - // entries.p - - // Ok(entries) - Ok(cx.string(json)) }