summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--browsers/README.md40
-rwxr-xr-xbrowsers/build.sh4
-rwxr-xr-xbrowsers/firefox/accent_host.py36
-rw-r--r--browsers/firefox/extension/background.js34
-rw-r--r--browsers/firefox/extension/content.js15
-rw-r--r--browsers/firefox/extension/manifest.json22
-rwxr-xr-xbrowsers/firefox/install-native-host.sh15
-rwxr-xr-xbrowsers/firefox/update-userchrome.sh10
-rw-r--r--browsers/firefox/userChrome.template.css7
-rw-r--r--browsers/getaccent.c13
10 files changed, 196 insertions, 0 deletions
diff --git a/browsers/README.md b/browsers/README.md
new file mode 100644
index 0000000..96ddfc3
--- /dev/null
+++ b/browsers/README.md
@@ -0,0 +1,40 @@
+# Browser Accent Color Experiments
+
+This directory contains experiments for applying the dynamic accent color
+provided by `core/accent.h` to web browsers.
+
+## Ungoogled-Chromium
+
+Ungoogled Chromium exposes limited theming hooks and does not support
+changing its UI colors at runtime. Applying a dynamic accent color would
+require maintaining a custom patch set or an extension that continually
+re-themes the browser, which is outside the scope of this repository.
+
+## Firefox
+
+Firefox can be themed programmatically. The files here demonstrate two
+approaches:
+
+1. `firefox/update-userchrome.sh` writes a minimal `userChrome.css` using the
+ current accent color. Run it whenever the accent color changes.
+2. `firefox/extension/` contains a small WebExtension and native messaging host
+ that continuously updates a `--accent-color` CSS variable across all pages.
+
+To use the extension:
+
+1. Build the helper program:
+
+ ```sh
+ ./build.sh
+ ```
+
+2. Register the native messaging host:
+
+ ```sh
+ firefox/install-native-host.sh
+ ```
+
+3. Load `firefox/extension` as a temporary extension from `about:debugging`.
+
+These scripts are meant as a starting point for proper browser ricing and can
+be adapted to other workflows.
diff --git a/browsers/build.sh b/browsers/build.sh
new file mode 100755
index 0000000..a57cc54
--- /dev/null
+++ b/browsers/build.sh
@@ -0,0 +1,4 @@
+#!/bin/sh
+set -eu
+cd "$(dirname "$0")"
+cc -Wall -Wextra -std=c99 getaccent.c -o getaccent
diff --git a/browsers/firefox/accent_host.py b/browsers/firefox/accent_host.py
new file mode 100755
index 0000000..ec0a166
--- /dev/null
+++ b/browsers/firefox/accent_host.py
@@ -0,0 +1,36 @@
+#!/usr/bin/env python3
+import json
+import os
+import struct
+import subprocess
+import sys
+
+def send(msg):
+ data = json.dumps(msg).encode('utf-8')
+ sys.stdout.buffer.write(struct.pack('I', len(data)))
+ sys.stdout.buffer.write(data)
+ sys.stdout.buffer.flush()
+
+def read():
+ raw = sys.stdin.buffer.read(4)
+ if len(raw) == 0:
+ return None
+ length = struct.unpack('I', raw)[0]
+ return json.loads(sys.stdin.buffer.read(length).decode('utf-8'))
+
+def get_accent():
+ try:
+ helper = os.path.join(os.path.dirname(__file__), '..', 'getaccent')
+ color = subprocess.check_output([helper], stderr=subprocess.DEVNULL).decode().strip()
+ if color:
+ return color
+ except Exception:
+ pass
+ return '#000000'
+
+while True:
+ msg = read()
+ if msg is None:
+ break
+ if msg.get('query') == 'color':
+ send({'color': get_accent()})
diff --git a/browsers/firefox/extension/background.js b/browsers/firefox/extension/background.js
new file mode 100644
index 0000000..df0ee80
--- /dev/null
+++ b/browsers/firefox/extension/background.js
@@ -0,0 +1,34 @@
+let port = browser.runtime.connectNative("accent_color");
+let current = null;
+
+function broadcast(color) {
+ browser.tabs.query({}).then(tabs => {
+ for (let tab of tabs) {
+ browser.tabs.sendMessage(tab.id, {color}).catch(() => {});
+ }
+ });
+ browser.theme.update({colors: {toolbar: color}});
+}
+
+port.onMessage.addListener(msg => {
+ if (msg.color && msg.color !== current) {
+ current = msg.color;
+ broadcast(current);
+ }
+});
+
+function poll() {
+ try {
+ port.postMessage({query: "color"});
+ } catch (e) {
+ // ignore
+ }
+}
+setInterval(poll, 1000);
+poll();
+
+browser.runtime.onMessage.addListener((msg, sender) => {
+ if (msg.request === "color") {
+ return Promise.resolve({color: current});
+ }
+});
diff --git a/browsers/firefox/extension/content.js b/browsers/firefox/extension/content.js
new file mode 100644
index 0000000..118c7ee
--- /dev/null
+++ b/browsers/firefox/extension/content.js
@@ -0,0 +1,15 @@
+function apply(color) {
+ document.documentElement.style.setProperty("--accent-color", color);
+}
+
+browser.runtime.onMessage.addListener(msg => {
+ if (msg.color) {
+ apply(msg.color);
+ }
+});
+
+browser.runtime.sendMessage({request: "color"}).then(msg => {
+ if (msg && msg.color) {
+ apply(msg.color);
+ }
+});
diff --git a/browsers/firefox/extension/manifest.json b/browsers/firefox/extension/manifest.json
new file mode 100644
index 0000000..abcbe08
--- /dev/null
+++ b/browsers/firefox/extension/manifest.json
@@ -0,0 +1,22 @@
+{
+ "manifest_version": 2,
+ "name": "Accent Color Updater",
+ "version": "0.1",
+ "description": "Updates CSS variable --accent-color using a native host",
+ "applications": {
+ "gecko": {
+ "id": "accent-color@example.com"
+ }
+ },
+ "background": {
+ "scripts": ["background.js"]
+ },
+ "permissions": ["nativeMessaging", "tabs", "<all_urls>"],
+ "content_scripts": [
+ {
+ "matches": ["<all_urls>"],
+ "js": ["content.js"],
+ "run_at": "document_start"
+ }
+ ]
+}
diff --git a/browsers/firefox/install-native-host.sh b/browsers/firefox/install-native-host.sh
new file mode 100755
index 0000000..33a6c88
--- /dev/null
+++ b/browsers/firefox/install-native-host.sh
@@ -0,0 +1,15 @@
+#!/bin/sh
+set -eu
+cd "$(dirname "$0")"
+HOST_DIR="${HOME}/.mozilla/native-messaging-hosts"
+mkdir -p "$HOST_DIR"
+cat >"$HOST_DIR/accent_color.json" <<JSON
+{
+ "name": "accent_color",
+ "description": "Accent color provider",
+ "path": "$(pwd)/accent_host.py",
+ "type": "stdio",
+ "allowed_extensions": ["accent-color@example.com"]
+}
+JSON
+chmod +x accent_host.py
diff --git a/browsers/firefox/update-userchrome.sh b/browsers/firefox/update-userchrome.sh
new file mode 100755
index 0000000..dae5d97
--- /dev/null
+++ b/browsers/firefox/update-userchrome.sh
@@ -0,0 +1,10 @@
+#!/bin/sh
+set -eu
+ACCENT="$(../getaccent 2>/dev/null || echo)"
+[ -n "$ACCENT" ] || ACCENT="#000000"
+PROFILE_DIR="${HOME}/.mozilla/firefox"
+PROFILE="$(ls "$PROFILE_DIR" | grep default | head -n1 || true)"
+[ -n "$PROFILE" ] || { echo "No Firefox profile found" >&2; exit 1; }
+PROFILE="$PROFILE_DIR/$PROFILE"
+mkdir -p "$PROFILE/chrome"
+sed "s/ACCENT/$ACCENT/" userChrome.template.css > "$PROFILE/chrome/userChrome.css"
diff --git a/browsers/firefox/userChrome.template.css b/browsers/firefox/userChrome.template.css
new file mode 100644
index 0000000..509ed81
--- /dev/null
+++ b/browsers/firefox/userChrome.template.css
@@ -0,0 +1,7 @@
+:root{
+ --accent-color: ACCENT;
+}
+
+#navigator-toolbox {
+ background-color: var(--accent-color) !important;
+}
diff --git a/browsers/getaccent.c b/browsers/getaccent.c
new file mode 100644
index 0000000..a7f81d4
--- /dev/null
+++ b/browsers/getaccent.c
@@ -0,0 +1,13 @@
+#include <stdio.h>
+#include <unistd.h>
+#include "../core/accent.h"
+
+int main(void) {
+ ColorShm *blk = NULL;
+ char col[8];
+ if (readaccent(&blk, col)) {
+ printf("%s\n", col);
+ return 0;
+ }
+ return 1;
+}