Wer mag sich das mal anschauen:
Teste doch bitte mal meine Version aus Beitrag Nr. 355 und kopier dir ab Zeile 20 deine apps rein.
Evtl. reicht das ja dann schon
Wer mag sich das mal anschauen:
Teste doch bitte mal meine Version aus Beitrag Nr. 355 und kopier dir ab Zeile 20 deine apps rein.
Evtl. reicht das ja dann schon
Hallo 2002Andreas
Habe ich ja gemacht. Aber meine Version ist etwas anders.
Da sind die Schaltflächen frei verschiebbar.
Hat aborix mal eingebaut.
Daher klemmt es irgendwo.
Mfg.
Endor
Da bin ich wieder!
Habe das neue Appmenü für mich umgeschrieben.
Es funktioniert auch, doch habe ich mal wieder ein Problem mit den Selektoren!
Gefunden : menu.menu-iconic:nth-child(1) > menupopup:nth-child(6) > menuitem:nth-child(1)
Es geht, aber ist doch irgendwie blöd!
ID's hatte ich ja zugewiesen, klappt auch bei den Einträgen im Untermenü "Firefox Funktionen"
Aber im Untermenü "Firefox Verzeichnisse" eben leider nicht!
id: "AMProfil",
Hier das beschriebene Skript:
// ==UserScript==
// @name Appmenu.uc.js
// @namespace Appmenu@gmail.com
// @description Basiert auf dem Script externalFuncButtonM.uc.js, Wiederherstellung der Orangenen FF-Menü Schaltfläche
// @include main
// @version update für Firefox 129+ by bege
// @author defpt
// @charset UTF-8
// @version 2019.08.04
// @version 2020.05.27
// @version 2020.07.13 Weitere Menüs und Funktionen ergänzt by bege
// @version 2024.08.10 alle Einstellungen im Abschnitt Konfiguration vornehmen
// ==/UserScript==
...
Alles anzeigen
Nachtrag.
Kaumgeschrieben und hier gejammert, fiel mir doch die Lösung ein
menuitem[label="Profil"] { ... ist es.
Aber hat jemand eine Lösung für das UndoListInTabmenuToo-Skript?
Bezüglich des Eintrags "Alle Tabs wieder öffnen".
Arbeitet in Nightly
// eXt-App-Launch.uc.js
// Create multiple movable buttons
// 1 - Notepad Start
try {
CustomizableUI.createWidget({
id: "add-notepad-app",
label: "Notepad",
tooltiptext: "Notepad Start",
defaultArea: CustomizableUI.AREA_NAVBAR,
onCreated: btn => btn.image = "file:///C:/Program Files/Firefox/Profiles/icons/notepad.png",
onCommand: function(event) {
var file = Cc["@mozilla.org/file/local;1"].createInstance(Ci.nsIFile);
file.initWithPath("C:\\Windows\\System32\\notepad.exe");
if (file.exists()) file.launch();
}
});
} catch(e) {}
// 2 - Program Files Folder Open
try {
CustomizableUI.createWidget({
id: "add-openfolder1-app",
label: "Program Files",
tooltiptext: "Open Program Files Folder",
defaultArea: CustomizableUI.AREA_NAVBAR,
onCreated: btn => btn.image = "file:///C:/Program Files/Firefox/Profiles/icons/folder.png",
onCommand: function(event) {
var file = Cc["@mozilla.org/file/local;1"].createInstance(Ci.nsIFile);
file.initWithPath("C:\\Program Files");
if (file.exists()) file.launch();
}
});
} catch(e) {}
// 3 - Next button (input another id:)
Alles anzeigen
Nö, zu dritt.
Denn sonst würde meine Version funktionieren.
Wer mag sich das mal anschauen:Code Alles anzeigen// ==UserScript== // @name externalApplications.uc.js // @namespace ithinc#mozine.cn // @description External Applications // @include main // @compatibility Firefox 3.5.x 3.6.x 17.01 // @author ithinc // @Version Fix by aborix // @Version 20190108.2.0.0 Frei verschiebbare Schaltflächen von aborix // @version 20091216.1.0.0 Final release // @version 20091215.0.0.2 Handle toolbar apps and menu apps separately // @version 20091212.0.0.1 Initial release // ==/UserScript== /* :::: External Applications :::: */ var gExternalApplications = { toolbar: { apps: [ {name: 'Photoshop', path: 'C:\\Program Files (x86)\\Adobe\\Adobe Photoshop CS2\\Photoshop.exe'}, {name: 'Wetter', path: 'C:\\Users\\Paulmichl\\Wetter'}, {name: 'Notepad++', path: 'C:\\Program Files\\Notepad++\\notepad++.exe'}, {name: 'Microsoft Outlook', path: 'C:\\Program Files (x86)\\Microsoft Office\\OFFICE14\\Outlook.exe'}, {name: 'Phoenix Hotel', path: 'C:\\Program Files (x86)\\PCS Phoenix\\Phoenix.exe'}, {name: 'Videolan Player', path: 'C:\\Program Files\\VideoLAN\\VLC\\vlc.exe'}, {name: 'Windows Explorer', path: 'C:\\Windows\\explorer.exe'}, {name: 'WinMergeU', path: 'F:\\Adaten\\Downloads\\Freecomander\\WinMerge-2.14.0\\WinMerge-2.16.12-x64-exe\\WinMerge\\WinMergeU.exe'}, {name: 'Filezilla', path: 'F:\\Adaten\\Downloads\\Filezilla\\FileZilla_3.10.3_win64\\FileZilla-3.56.2\\filezilla.exe'}, {name: 'CarotDAV', path: 'F:\\Adaten\\Downloads\\Dropbox\\CarotDAV1.9.9.portable\\CarotDAV\\CarotDAV.exe'}, {name: 'Pickpick', path: 'F:\\Adaten\\Downloads\\picpick\\picpick.exe'}, {name: 'Profilmanager', path: 'F:\\Adaten\\Downloads\\Firefox\\Profile-Manager\\profilemanager.exe'}, {name: 'Profile', path: 'C:\\Users\\Paulmichl\\AppData\\Roaming\\Mozilla\\Firefox\\Profiles'}, {name: 'FreeCommander', path: 'F:\\Adaten\\Downloads\\FreeComander\\FreeCommanderPortable\\FreeCommanderPortable.exe'}, {name: 'TV Browser', path: 'F:\\Adaten\\Downloads\\TVBrowser\\tvbrowser_3.2.1_bin_transportable\\tvbrowser-transportable\\tvbrowser-transportable.exe'}, {name: 'Radio Sure', path: 'F:\\Adaten\\Downloads\\Radio\\RadioSure.exe'}, ] }, // Menü für Firefox Extras - Externe Anwendungen menu: { apps: [ {name: 'Notepad', path: 'C:\\WINDOWS\\system32\\notepad.exe'}, {name: 'Rechner', path: 'C:\\WINDOWS\\system32\\calc.exe'}, {name: 'DOS', path: 'C:\\WINDOWS\\system32\\cmd.exe'}, {name: 'separator'}, {name: 'UltraSearch', path: 'F:\\Adaten\\Downloads\\FreeComander\\UltraSearch\\UltraSearch.exe'}, {name: 'CarotDAV', path: 'F:\\Adaten\\Downloads\\Dropbox\\CarotDAV1.9.9.portable\\CarotDAV\\CarotDAV.exe'}, {name: 'Windows Explorer', path: 'c:\\windows\\explorer.exe'},/*x?????*/ {name: 'Internet Explorer', path: 'C:\\Program Files\\Internet Explorer\\IEXPLORE.EXE', args: ['%u']}, {name: 'Firefox', path: 'F:\\Adaten\\Downloads\\Firefox'}, {name: 'Videos', path: 'F:\\Video'}, {name: 'Videos2', path: 'F:\\Adaten\\Müll'}, ], id: 'ExternalApplicationsMenu', insertafter: 'menu_openAddons', // 'helpMenu', 'tools-menu' oder 'browserToolsSeparator' label: 'Externe Anwendungen', accesskey: 'A' }, init: function() { this.handleRelativePath(this.toolbar.apps); this.handleRelativePath(this.menu.apps); this.createToolbarbuttons(this.toolbar.apps); if (this.menu.apps.length > 0) { var refNode = document.getElementById(this.menu.insertafter); if (refNode) { var menu = refNode.parentNode.insertBefore(document.createXULElement('menu'), refNode.nextSibling); menu.setAttribute('id', this.menu.id); menu.setAttribute('label', this.menu.label); menu.setAttribute('accesskey', this.menu.accesskey); menu.appendChild(this.createMenupopup(this.menu.apps)); } } }, handleRelativePath: function(apps) { for (var i=0; i<apps.length; i++) { var app = apps[i]; if (app.path) { app.path = app.path.replace(/\//g, '\\'); var ffdir = Cc['@mozilla.org/file/directory_service;1'].getService(Ci.nsIProperties).get('CurProcD', Ci.nsIFile).path; if (/^(\.)/.test(app.path)) { app.path = ffdir + '\\' + app.path; } else if (/^(\\)/.test(app.path)) { app.path = ffdir.substr(0,2) + app.path; } } } }, exec: function(path, args) { args = args || []; for (var i=0; i<args.length; i++) { args[i] = args[i].replace(/%u/g, gBrowser.currentURI.spec); } var file = Cc['@mozilla.org/file/local;1'].createInstance(Ci.nsIFile); file.initWithPath(path); if (!file.exists()) { Cu.reportError('File Not Found: ' + path); return; } if (!file.isExecutable()) { file.launch(); } else { var process = Cc['@mozilla.org/process/util;1'].createInstance(Ci.nsIProcess); process.init(file); process.run(false, args, args.length); } }, createToolbarbuttons: function(apps) { for (var i=0; i<apps.length; i++) { var app = apps[i]; if (app.name != 'separator') { createButton(app); } }; function createButton(app) { var buttonId = app.name.replace(/ /g, '_').replace(/\+/g, 'Plus') + '-ExtApp-button'; try { CustomizableUI.createWidget({ id: buttonId, type: 'custom', defaultArea: CustomizableUI.AREA_NAVBAR, onBuild: function(aDocument) { var toolbaritem = aDocument.createElementNS('http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul', 'toolbarbutton'); var attributes = { id: buttonId, class: 'toolbarbutton-1 chromeclass-toolbar-additional', label: app.name, tooltiptext: app.name, image: 'moz-icon:file:///' + app.path + '?size=16', //oncommand: 'gExternalApplications.exec(this.path, this.args);', }; for (var a in attributes) { toolbaritem.setAttribute(a, attributes[a]); toolbaritem.addEventListener('click', event => { if (event.button == 0) { gExternalApplications.exec(this.path, this.args).click(); } }); toolbaritem.path = app.path; toolbaritem.args = app.args; return toolbaritem; } } }); } catch(e) {}; } }, createMenupopup: function(apps) { var menupopup = document.createXULElement('menupopup'); for (var i=0; i<apps.length; i++) { var app = apps[i]; if (app.name == 'separator') { menupopup.appendChild(document.createXULElement('menuseparator')); } else { var item = menupopup.appendChild(document.createXULElement('menuitem')); item.setAttribute('class', 'menuitem-iconic'); item.setAttribute('label', app.name); item.setAttribute('image', 'moz-icon:file://' + app.path + '?size=16'); item.addEventListener ('command', function (event) { if (event.button == 0) { gExternalApplications.exec(this.path, this.args); } }); item.path = app.path; item.args = app.args; return menupopup; } } }; }; gExternalApplications.init();
Mfg.
Endor
Mitglied #4 hier: in Zeile 146, grob geraten, wüsste nicht wie ich das testen kann: bei gExternalApplications.exec(this.path, this.args).click(); zu gExternalApplications.exec(this.path, this.args); , also .click() rauswerfen.
Ansonsten für den Bereich auch nochmal bei Sören's Vorschlägen schauen, die dritte Umsetzung.
Zeile 180,
nicht }; sondern },
Endor
Dann ist das ja logisch.
Schon in Ordnung.
da beziehst Du Dich aber auf eine Version, die längst überholt ist.
Wie Sören dir bereits geantwortet hat: Nöö. Ich hatte durchaus bemerkt, dass Du ein geändertes Skript gepostet hast, es aber nicht heruntergeladen. Edit: Jetzt aber doch. Welche der zwei Versionen ist die neuere? Die zuletzt gepostete enthält jedenfalls viele Rechtschreibfehler und Übersetzungsschwächen (wenn man nicht sogar Fehler), die in der zuerst geposteten ausgemerzt wurden.
In meiner vorigen Antwort war mir nicht genau bewusst, womit ihr Probleme habt. Das ist mir erst später klar geworden. Nehmen wir das Beispiel Browsertools-Button, ich beziehe mich auf die am 7. Juni 2023 gepostete Version (als browsertoolbox.uc.js):
Wir finden dort ab Zeile 22 ein einer Variable zugeordnetes Objekt (gekürzt um die hier nicht relevanten Teile):
var props = {
// Kürzung
style: 'list-style-image: url("' + ("file:" + currentProfileDirectory + "/chrome/icons/" + buttonicon) + '");',
oncommand: '(' + onCommand.toString() + ')()'
};
for (var p in props)
toolbaritem.setAttribute(p, props[p]);
return toolbaritem;
sowie ab Z. 39 die eigentliche Funktion:
function onCommand() {
var document = event.target.ownerDocument;
if (!document.getElementById('menu_browserToolbox')) {
let { require } = ChromeUtils.importESModule("resource://devtools/shared/loader/Loader.sys.mjs", {});
require("devtools/client/framework/devtools-browser");
};
document.getElementById('menu_browserToolbox').click();
};
Das kann man nun unter Entfernung oder auch unter Erhalt der eigenen Funktion zu einem addEventListener umbauen:
a) Entfernung, im Prinzip wie in meiner vorherigen Antwort (die Einrückung stimmt jetzt nicht mehr, weil ich alles nur kopiert habe)
let props = {
// Kürzung
style: 'list-style-image: url("' + ("file:" + currentProfileDirectory + "/chrome/icons/" + buttonicon) + '");'
};
for (let p in props)
toolbaritem.setAttribute(p, props[p]);
toolbaritem.addEventListener('click',() => {
let document = event.target.ownerDocument;
if (!document.getElementById('menu_browserToolbox')) {
let { require } = ChromeUtils.importESModule("resource://devtools/shared/loader/Loader.sys.mjs", {});
require("devtools/client/framework/devtools-browser");
};
document.getElementById('menu_browserToolbox').click();
});
return toolbaritem;
Alles anzeigen
b) die Funktion wird gar nicht angerührt (wobei, wie Horstmann selber schreibt, ein anderer Funktionsname deutlich besser wäre, openBox oder so):
let props = {
// Kürzung
style: 'list-style-image: url("' + ("file:" + currentProfileDirectory + "/chrome/icons/" + buttonicon) + '");'
};
for (let p in props)
toolbaritem.setAttribute(p, props[p]);
toolbaritem.addEventListener('click', () => { onCommand() });
return toolbaritem;
// weiterer Code
function onCommand() {
// Funktionscode
};
Alles anzeigen
Ich bin selbst nicht darauf gekommen, aber Mitleser hat das so in seinem DeepL-Skript benutzt, vergleiche Posting vom 12. Januar 2025, dort mit der zusätzlichen Verbesserung, dass der Code nur bei Klick mit der linken Maustaste ausgeführt werden soll (zusätzliches if (event.button == 0) {…} um den Funktionsaufruf, beachtet dazu Sörens Hinweis: drei Gleichheitszeichen wären besser).
Beachtet auch, dass in beiden Variationen am Ende von Zeile 24 (style: …) ein Komma entfernt werden musste. Und ich habe var in let geändert.
//
Nur mal so als allgemeine Frage.
Der user lenny2 hat in Beitrag Nr. 364 ein Skript gepostet, welches einwandfrei funktioniert.
Wenn man aus dem Skript nur eine Funktion braucht, dann sind das nur 17 Zeilen die benötigt werden.
Das von mir zur Zeit genutzte Skript External Applications uc.js hat dafür aber 127 Zeilen.
Meine Frage:
Hat die länge/größe von einem Skript Einfluss auf die Performance vom Firefox?
Danke für jegliche Erklärung.
Hat die länge/größe von einem Skript Einfluss auf die Performance vom Firefox?
Prinzipiell kann man das nicht beantworten. Es kommt immer darauf an, wie oft der (zusätzliche) Code zur Ausführung kommt und vor allem wann. Wenn der gesamte Code nur einmal beim Start eine gewisse Last erzeugt ist das sicherlich vernachlässigbar. Ständig oder periodisch aufgerufener Code erzeugt natürlich eine Dauerlast. Das muss wirklich konkret am Skript betrachtet werden. Wenn hingegen Ressourcen (in beträchtlichem Umfang!) durch den zusätzlichen Code beansprucht werden, dann kann sich das natürlich auch auf die Performance auswirken.
Im konkreten Beispiel glaube ich nicht, dass die relativ kleinen Button-Icons so viel Ressourcen fressen, dass man das in irgendeiner Form spürt. Auch die notwendigen, zusätzlichen Abfragen der Buttons sind für die Performance unerheblich.
zusätzlichen Abfragen der Buttons sind für die Performance unerheblich.
Hallo BrokenHeart ..
danke für deine Erklärung
Ich nutze 2 dieser größeren Skripte.
Einmal um den Thunderbird zu starten..1x am Tag, dann bleibt er offen
Und mit dem anderen Skript rufe ich hin und wieder das Kartenspiel auf.
Also lasse ich alles so wie es ist hier.
da beziehst Du Dich aber auf eine Version, die längst überholt ist.
Wie Sören dir bereits geantwortet hat: Nöö. Ich hatte durchaus bemerkt, dass Du ein geändertes Skript gepostet hast, es aber nicht heruntergeladen. Edit: Jetzt aber doch. Welche der zwei Versionen ist die neuere? Die zuletzt gepostete enthält jedenfalls viele Rechtschreibfehler und Übersetzungsschwächen (wenn man nicht sogar Fehler), die in der zuerst geposteten ausgemerzt wurden.
Sorry. Das ganz aktuelle von hier jetzt verwendete Appmenü-Skript habe ich nicht hier gepostet!
In Beitrag #363 nur der Anfang!
Damit ich besser vergleichen kann, wärst Du so nett und verlinkst die Beiträge?
Jene ohne Übersetzungsschwächen (bzw. ohne Fehler). Bitte, Danke.
Den Performance-Aspekt hat BrokenHeart ja schon beantwortet. Ich gehe jetzt bei einem klassischen Firefox-Script auch nicht davon aus, dass man die Auswirkungen des nicht „aufgeräumten“ Scripts tatsächlich spüren wird. Allerdings gibt es noch einen anderen Aspekt: Jeder Code ist potenziell Code, der Schwachstellen haben oder durch Änderungen seitens Mozilla inkompatibel werden und vielleicht sogar Probleme bereiten kann. Auch von der Code-Pflege her ist es einfacher, keinen Code mitzuschleppen, der nicht benötigt wird. Ich würde Anpassungen immer auf das absolute Minimum reduzieren, um so wenig wie möglich von dem abzuweichen, was Mozilla ausliefert.
Ich würde Anpassungen immer auf das absolute Minimum reduzieren
Hallo Sören, auch dir danke für die Erklärung.
Ich nutze hier nur Skripte und CSS-Codes, die ich nach meiner Meinung brauche, bzw. nicht missen möchte.
Naja, aber auch nur teilweise. Das war auch darauf bezogen:
Wenn man aus dem Skript nur eine Funktion braucht, dann sind das nur 17 Zeilen die benötigt werden.
Das von mir zur Zeit genutzte Skript External Applications uc.js hat dafür aber 127 Zeilen.
In meiner vorigen Antwort war mir nicht genau bewusst, womit ihr Probleme habt. Das ist mir erst später klar geworden. Nehmen wir das Beispiel Browsertools-Button, ich beziehe mich auf die am 7. Juni 2023 gepostete Version (als browsertoolbox.uc.js):
Vielen Dank für die ausführliche Erklärung!
Mich hat diese Zeile verwirrt : oncommand: '(' + onCommand.toString() + ')()' , wusste einfach nicht wie ich das alternativ einbinden sollte, v.a. mit der irreführenden Verwendung von onCommand als Funktionsname.
Naja, aber auch nur teilweise.
Hallo Sören.
Ich habe dann noch eine Frage zu dem kleinen Skript.
// spider.uc.js
// Spider.exe Start
try {
CustomizableUI.createWidget({
id: "Spider",
label: "Spider",
tooltiptext: "Spider Start",
defaultArea: CustomizableUI.AREA_NAVBAR,
onCreated: btn => btn.image = "file:///C:/Users/weiss/AppData/Roaming/Mozilla/Firefox/Profiles/7hfpu74u.Test Fx/chrome/Icons/spider.png",
onCommand: function(event) {
var file = Cc["@mozilla.org/file/local;1"].createInstance(Ci.nsIFile);
file.initWithPath("D:\\XP - Spider Solitär\\XP - Spider.exe");
if (file.exists()) file.launch();
}
});
} catch(e) {}
Alles anzeigen
In Zeile 10 muss ich ein eigenes Icon angeben.
In dem großen Skript wird das wohl automatisch aus der .exe Datei damit ausgelesen und eingefügt:
item.setAttribute('image', 'moz-icon:file:///' + app.path + '?size=16');
Lässt sich das auch in dem kleinen Skript so ändern?
Lässt sich das auch in dem kleinen Skript so ändern?
Meinst du das so?
try {
CustomizableUI.createWidget({
id: "Notepad",
label: "Notepad++",
tooltiptext: "Notepad++ Start",
defaultArea: CustomizableUI.AREA_NAVBAR,
onCreated: btn => btn.image = "moz-icon:file:///C://Program Files//Notepad++//notepad++.exe?size=16",
onCommand: function(event) {
var file = Cc["@mozilla.org/file/local;1"].createInstance(Ci.nsIFile);
file.initWithPath("C:\\Program Files\\Notepad++\\notepad++.exe");
if (file.exists()) file.launch();
}
});
} catch(e) {}
Alles anzeigen
Man beachte die notwendige, unterschiedliche Verwendung von slash/backslash in den Pfadangaben! Man könnte natürlich eine Pfadvariable nutzen und dann im Aufruf file.initWithPath die slashes vorher umdrehen - oder quick&dirty, so wie oben.
Meinst du das so?
Perfekt, herzlichen Dank dafür
Man beachte
Da wäre ich nie drauf gekommen