diff --git a/renderer/customization.js b/renderer/customization.js index eaf1c9d..5af1b36 100644 --- a/renderer/customization.js +++ b/renderer/customization.js @@ -478,10 +478,13 @@ class BrowserCustomizer { applyThemeToPages() { // This will be called to apply theme to home.html and other pages - // We'll store the theme and let other pages load it this.saveTheme(); - - // If we have access to other windows/frames, apply there too + + // Send theme update to host (for settings webview) + if (window.electronAPI && typeof window.electronAPI.sendToHost === 'function') { + window.electronAPI.sendToHost('theme-update', this.currentTheme); + } + // Fallback: send via postMessage (for iframe embedding) try { if (window.parent && window.parent !== window) { window.parent.postMessage({ diff --git a/renderer/home.html b/renderer/home.html index 35e505d..b7c6125 100644 --- a/renderer/home.html +++ b/renderer/home.html @@ -76,36 +76,39 @@ diff --git a/renderer/home.js b/renderer/home.js index 9e64858..ef5c738 100644 --- a/renderer/home.js +++ b/renderer/home.js @@ -87,11 +87,16 @@ function renderBookmarks() { // Navigate via IPC to host page box.onclick = () => { + const url = b.url; if (window.electronAPI && typeof window.electronAPI.sendToHost === 'function') { - window.electronAPI.sendToHost('navigate', b.url); + window.electronAPI.sendToHost('navigate', url); } else { console.error('Unable to send navigation IPC to host'); } + // Fallback: post message to embedding page + if (window.parent && typeof window.parent.postMessage === 'function') { + window.parent.postMessage({ type: 'navigate', url }, '*'); + } }; box.appendChild(label); @@ -205,7 +210,16 @@ searchBtn.addEventListener('click', () => { const searchEngineUrl = searchEngines[selectedSearchEngine]; target = `${searchEngineUrl}${encodeURIComponent(input)}`; } - window.location.href = target; + // Always send navigation request to host + if (window.electronAPI && typeof window.electronAPI.sendToHost === 'function') { + window.electronAPI.sendToHost('navigate', target); + return; + } + // Fallback: post message to embedding page + if (window.parent && typeof window.parent.postMessage === 'function') { + window.parent.postMessage({ type: 'navigate', url: target }, '*'); + return; + } }); searchInput.addEventListener('keydown', e => { diff --git a/renderer/script.js b/renderer/script.js index f1f326b..076b352 100644 --- a/renderer/script.js +++ b/renderer/script.js @@ -75,7 +75,7 @@ async function saveBookmarks(newBookmarks) { // Load bookmarks when the script starts loadBookmarks(); -// Home tab will be created on DOMContentLoaded event +// Initial home tab will be created on DOMContentLoaded // Remove iframe-based navigation listener (using webview IPC now) @@ -108,6 +108,8 @@ function createTab(inputUrl) { }; tabs.push(tab); setActiveTab(id); + // Render the tab bar so the new home tab appears + renderTabs(); return id; } @@ -116,16 +118,6 @@ function createTab(inputUrl) { console.log('[DEBUG] createTab() resolvedUrl =', resolvedUrl); const webview = document.createElement('webview'); - - webview.id = `tab-${id}`; - webview.src = resolvedUrl; - webview.setAttribute('allowpopups', ''); - webview.setAttribute('partition', 'persist:default'); - webview.setAttribute('preload', '../preload.js'); - webview.classList.add('active'); - - webview.addEventListener('did-fail-load', handleLoadFail(id)); - webview.addEventListener('page-title-updated', e => updateTabMetadata(id, 'title', e.title)); webview.addEventListener('page-favicon-updated', e => { if (e.favicons.length > 0) updateTabMetadata(id, 'favicon', e.favicons[0]); }); @@ -186,6 +178,14 @@ function createTab(inputUrl) { createTab(e.url); }); + // After creating dynamic webview: + webview.addEventListener('ipc-message', e => { + if (e.channel === 'theme-update') { + const home = document.getElementById('home-webview'); + if (home) home.send('theme-update', ...e.args); + } + }); + webviewsEl.appendChild(webview); tabs.push({ @@ -324,6 +324,14 @@ function convertHomeTabToWebview(tabId, inputUrl, resolvedUrl) { createTab(e.url); }); + // After creating dynamic webview: + webview.addEventListener('ipc-message', e => { + if (e.channel === 'theme-update') { + const home = document.getElementById('home-webview'); + if (home) home.send('theme-update', ...e.args); + } + }); + // Add webview to DOM webviewsEl.appendChild(webview); @@ -486,7 +494,9 @@ function renderTabs() { }); // add the “+” at the end const plus = document.createElement('div'); - plus.className = 'tab'; plus.textContent = '+'; plus.onclick = () => createTab(); + plus.className = 'tab'; + plus.textContent = '+'; + plus.onclick = () => createTab(); frag.appendChild(plus); tabBarEl.innerHTML = ''; // clear once @@ -533,10 +543,9 @@ function reload() { } } - +// Function to open the Settings page function openSettings() { - urlBox.value = 'browser://settings'; - navigate(); + createTab('browser://settings'); } // Toggle menu dropdown @@ -562,16 +571,38 @@ window.addEventListener('DOMContentLoaded', () => { } createTab(); - // Listen for navigation IPC messages from home webview - const homeWebview = document.getElementById('home-webview'); - if (homeWebview) { - homeWebview.addEventListener('ipc-message', e => { + // Handle IPC messages from the static home webview (bookmarks navigation) + const staticHome = document.getElementById('home-webview'); + if (staticHome) { + staticHome.addEventListener('ipc-message', (e) => { if (e.channel === 'navigate' && e.args[0]) { urlBox.value = e.args[0]; navigate(); } }); } + // Listen for IPC messages from other webviews (e.g., settings) + webviewsEl.addEventListener('ipc-message', (e) => { + // Navigation messages from home or other pages + if (e.channel === 'navigate' && e.args[0]) { + urlBox.value = e.args[0]; + navigate(); + } + // Theme update from settings webview + if (e.channel === 'theme-update' && e.args[0]) { + const homeWebview = document.getElementById('home-webview'); + if (homeWebview) { + homeWebview.send('theme-update', e.args[0]); + } + } + }); + // Fallback: listen for postMessage navigations from home webview + window.addEventListener('message', (event) => { + if (event.data && event.data.type === 'navigate' && event.data.url) { + urlBox.value = event.data.url; + navigate(); + } + }); // only now bind the reload button (guaranteed to exist) const reloadBtn = document.getElementById('reload-btn'); reloadBtn.addEventListener('click', reload); diff --git a/renderer/settings.js b/renderer/settings.js index 5b4b870..31c7d43 100644 --- a/renderer/settings.js +++ b/renderer/settings.js @@ -1,4 +1,5 @@ // Use require('electron') since webviews have nodeIntegrationInSubFrames: true +// In settings webview we use the same preload API as main windows const { ipcRenderer } = require('electron'); const clearBtn = document.getElementById('clear-data-btn'); @@ -14,11 +15,10 @@ function showStatus(message) { } clearBtn.onclick = async () => { - statusDiv.classList.remove('hidden'); // Show spinner immediately - statusText.textContent = 'Clearing all browser data...'; // Update text while clearing + statusDiv.classList.remove('hidden'); + statusText.textContent = 'Clearing all browser data...'; try { - // Invoke the main process to clear cookies, local storage, and cache const ok = await ipcRenderer.invoke('clear-browser-data'); showStatus(ok ? 'All browser data and bookmarks cleared!' @@ -26,5 +26,11 @@ clearBtn.onclick = async () => { } catch (error) { console.error('Error clearing browser data:', error); showStatus('An error occurred while clearing data.'); + } finally { + // Send theme update to host after clearing + const currentTheme = window.browserCustomizer ? window.browserCustomizer.currentTheme : null; + if (currentTheme && window.electronAPI && typeof window.electronAPI.sendToHost === 'function') { + window.electronAPI.sendToHost('theme-update', currentTheme); + } } }; diff --git a/site-history.json b/site-history.json index 7223fd2..53389b7 100644 --- a/site-history.json +++ b/site-history.json @@ -2,6 +2,11 @@ "https://www.youtube.com/", "https://github.com/", "file:///X:/Projects/Code/NebulaBrowser/renderer/index.html", + "https://youtube.com/", + "file:///X:/Projects/Code/NebulaBrowser/renderer/index.html", + "https://youtube.com/", + "file:///X:/Projects/Code/NebulaBrowser/renderer/index.html", + "file:///X:/Projects/Code/NebulaBrowser/renderer/index.html", "file:///X:/Projects/Code/NebulaBrowser/renderer/index.html", "file:///X:/Projects/Code/NebulaBrowser/renderer/index.html", "file:///X:/Projects/Code/NebulaBrowser/renderer/index.html",