diff options
| author | martin f. krafft <madduck@madduck.net> | 2025-06-25 16:51:18 +0200 |
|---|---|---|
| committer | martin f. krafft <madduck@madduck.net> | 2025-07-01 22:18:29 +0200 |
| commit | 4069c600b52213e01a727d786a6133435213bb43 (patch) | |
| tree | 134f631ceda022f56969c514253f49f762103c86 /inject/company-switcher.js | |
initial commit
Diffstat (limited to 'inject/company-switcher.js')
| -rw-r--r-- | inject/company-switcher.js | 90 |
1 files changed, 90 insertions, 0 deletions
diff --git a/inject/company-switcher.js b/inject/company-switcher.js new file mode 100644 index 0000000..b491b8a --- /dev/null +++ b/inject/company-switcher.js @@ -0,0 +1,90 @@ +export function registerObserver() { + document.addEventListener("DOMContentLoaded", function () { + + // When the DOM loaded, only the Web client framework is available, Odoo loads its + // stuff later and so we must wait, and react to new nodes as they are added + const root = document.querySelector(".o_web_client"); + + if (!root) { + return; + } + + // This function is called (see below) whenever a DOM mutation happens + const callback = function (mutationsList, observer) { + for (let mutation of mutationsList) { + try { + if (mutation.type === 'childList' && mutation.addedNodes.length > 0) { + // We are only interested in children that are adding nodes + const elem = mutation.addedNodes.item(0); + + if (elem.classList === undefined) { + // This skips nodes that are not HTML tags + continue; + } + else if (elem.attributes.toni) { + // As we clone tags further down, and add those clones, we'd enter an + // infinite recursion unless we skip elements we created, which are + // marked with an attribute + console.debug("Skipping TONI element:", elem); + continue; + } + + if (elem.classList.contains("o_switch_company_item")) { + // Now we have an individual company menu item in `elem`. To get rid of the + // Odoo-provided click-event handler, we clone it, and replace the original, + // as cloning does not copy the event handlers + try { + let clone = elem.cloneNode(true); + clone.attributes.toni = true + clone.addEventListener('click', () => { + // … and we add our own event handler that opens a new window on the + // subdomain URL for the other company + const cid = clone.attributes["data-company-id"].value; + const url = document.URL.replace(/:\/\/(\d+\.)?odoo/, `://${cid}.odoo`); + if (url) { + + console.debug("Opening new window on", url); + const newwin = window.open(url, "_blank", "noreferrer"); + if (newwin) { + newwin.focus(); + } + + const menubtn = document.querySelector(".o_switch_company_menu > button:nth-child(1)"); + if (menubtn) { + // Finally, click the menu, so that it disappears + menubtn.click(); + } + + } else { + console.error("URL is empty, clone is:", clone); + } + }); + elem.parentNode.replaceChild(clone, elem); + console.debug("Replaced with TONI clone:", clone); + } catch (e) { console.error("While cloning element:", elem, e); } + // TODO: The following is an attempt to modify the document title and include the + // company name. but it get overwritten by Odoo right away, so we need another + // approach + /* + } else if (elem.classList.contains("o_switch_company_menu")) { + const btn = elem.childNodes[0]; + const company = btn?.title; + if (company !== undefined) { + const titleelem = document.querySelector("title"); + titleelem.innerText += ` | ${company}`; + } + */ + } + } + } + catch (e) { console.error("While handling mutation:", mutation, e); }; + } + }; + + // Configure and start the MutationObserver + const observer = new MutationObserver(callback); + const config = { childList: true, subtree: true }; + observer.observe(root, config); + console.info("Installed TONI observer"); + }); +} |
