kiến thức Tổng hợp những addon chất cho Firefox / Chromium

Làm luôn cái wiki đi cho máu mấy thầy.
Thì #1, #2 ngang wiki rồi còn đâu bác.
T thấy cái này cho làm wiki ngon đấy, để mọi người cùng biết, chứ ra vô mỗi cho voz user xài thì không hay. Làm to to như freeBSD wiki, arch wiki hoặc fandom wiki cũng được
Hay là ngài florentino @Fioren làm thí điểm 1 cái wiki cho anh em đông lào dùng đi nào
hrPmWfK.png
Làm wiki chắc phải sửa ngôn từ cho đỡ chợ búa lại, rồi đem cho ChatGPT dịch ra tiếng Anh chắc cũng ổn


Chắc sau này cũng tính làm con bot cho nó tự động viết wiki kéo từ đây về để chia sẻ cho bạn bè 5 châu, cũng nhân lúc mình còn mạnh chân khỏe tay thì làm luôn kẻo muộn.

Chắc phải rà lỗi chính tả và lỗi tiếng lóng ở #1, #2 để tự động chuyển qua tiếng của nhân loại.
 
sao tắt hẳn fennec đi thì browser lại về 1 á bác
J0CWKCU.jpg
Đặc thù của Firefox Android đó vì đối tượng là người dùng cuối thậm chí còn không biết tắt bật Android nên họ sợ người dùng càu nhàu font chữ lạ (mà thực tế là có nhiều bài như vậy trên FF Android rồi), phải root chơi user.js mới lại được.

Trường hợp này là phải gánh chịu cái dốt của thiên hạ thôi.
 
Có config hay script hay theme nào làm sói thành transparent k thế ngài, hoặc ảnh nền gif vs color ttransparent cho sói cũng dc. Bữa nhớ có cái browser nào hình như cũng làm dc thì phải theme động hình anime đẹp vl
JIKT4Rg.png
Rồi cái browser đó nó dùng script code nó tự tạo, toggle 1 phát qua ngay transparent nhìn như pha lê luôn, đẹp dã man
ggPTcvV.png
@toi la gay :sosad:
Hồi Firefox 3 + Windows 7 thì ez lắm, Windows 10 thì không có native trong suốt pha lê. Thời bây giờ thì trong suốt thế này ok không ?

browser.png


Quan trọng là nó trong cả trên Manjaro nghĩa là Linux đó:

https://github.com/Filip-Sutkowy/blurclean-firefox-theme

Có thể thử đoạn này vào userChrome.css:

Code:
#main-window{
  -moz-appearance: -moz-win-glass !important;
  background: transparent !important;
}
#navigator-toolbox{ background: transparent !important }
 
Vừa cài Firefox 119 xong, giờ cài addon được trên web rồi nhé, không cần khổ dâm qua cái Addon Manager nữa :D, nếu đang dùng 119b1 thì sẽ nhìn thấy danh sách addon dài hơn cụ thể xem ảnh đính kèm.

Có cả ReadAloud để đọc văn bản qua giọng nói nữa.

https://addons.mozilla.org/en-US/android/search/?promoted=recommended&sort=random&type=extension

Thậm chí chuyển chế độ sang Desktop rồi vào https://addons.mozilla.org/en-US/ sẽ cài được gần như 100% addon.
 

Attachments

  • Screenshot_20230928-182833.png
    Screenshot_20230928-182833.png
    172.6 KB · Views: 26
  • Screenshot_20230928-182845.png
    Screenshot_20230928-182845.png
    238.9 KB · Views: 28
  • Screenshot_20230928-182917.png
    Screenshot_20230928-182917.png
    238.5 KB · Views: 26
Last edited:
Đặc thù của Firefox Android đó vì đối tượng là người dùng cuối thậm chí còn không biết tắt bật Android nên họ sợ người dùng càu nhàu font chữ lạ (mà thực tế là có nhiều bài như vậy trên FF Android rồi), phải root chơi user.js mới lại được.

Trường hợp này là phải gánh chịu cái dốt của thiên hạ thôi.
T nhớ mấy page trước có cách dùng adb mà nhỉ?
 
@ducminh3112 Script trên có thể viết lại dựa trên document.addEventListener('mouseover', function (e) {........}); đấy, nghĩa là không dùng luôn MutationObserver cho hiệu năng tốt hơn và luôn hoạt động khi phát hiện ra link muốn đổi khi hơ chuột lên một cách âm thầm, ở script Handlers Helper mình có ví dụ cách sử dụng ở cuối, có thể tham khảo xem.

var attachedeles = [];
document.addEventListener('mouseover', function(e) {
if (e.target.shadowRoot) {
if (attachedeles.includes(e.target) == false) {
console.log(attachedeles);
attachedeles.push(e.target);
attachDrag(e.target.shadowRoot);
}
}
});

Em vừa debug lại thì đại khái là MutationObserver sẽ theo dõi thay đổi của cấu trúc trang: đồng chí Ivan tác giả clip gốc dùng để xem khi nào Youtube nó render thêm nội dung mới (tính cả lần load/render đầu tiên) thì gán href của protocol mpv://play/ cho object mới. Nhưng mà trên trang Youtube Mobile thì HOME với SEARCH nó tái sử dụng 1 phần chứ không load lại cả page lại từ đầu (mở F12 lên mà Sẻac là nó không clear console cũ), nên là object nào dùng lại là nó sẽ không cập nhật lại cái href mới :extreme_sexy_girl:
Vậy nên là cứ cho cả document bắt sự kiện click chuột rồi tìm ngượg href là lành nhất:hungry:

JavaScript:
// ==UserScript==
// @name        Click on video thumbnail to play in MPV
// @name:ru     Нажми на митиатюру для проигрывания в MPV
// @namespace   nsinister.scripts.videothumb2mpv
// @match       https://*.youtube.com/*
// @match       https://vimeo.com/*
// @grant       none
// @version     0.2
// @author      nSinister
// @license     MIT
// @description Opens videos in external player (mpv) by simply clicking on a thumbnail.
// @description:ru Проигрывает ролики во внешнем плеере (mpv) по нажатию на миниатюру
//
// ==/UserScript==

"use strict";

let sites = {
  "www.youtube.com": { sel: "a.ytd-thumbnail", url: "https://www.youtube.com", needsFullUrl: true },
  "m.youtube.com": { sel: "a.media-item-thumbnail-container", url: "https://m.youtube.com", needsFullUrl: true },
  "vimeo.com": { sel: "a.iris_video-vital__overlay", url: "https://vimeo.com", needsFullUrl: false },
};

function GM_btoaUrl(url) {
  return btoa(url).replace(/\//g, "_").replace(/\+/g, "-").replace(/\=/g, "");
}

function replaceLink(node, site) {
  if(node) {
    let hrefval = node.getAttribute('href');
    if (hrefval == null || hrefval.startsWith("mpv"))
      return;

    let full_url = (site.needsFullUrl ? site.url : "") + hrefval;
    if (full_url.startsWith('http')) {
      url = full_url;
    }
    if (url == '') {
      var url = location.href;
    }

    var subs = '';
    var s = url;
    var bs = GM_btoaUrl(s);
    var url2 = 'mpv://play/' + bs + '/' + "?referer=" + GM_btoaUrl(location.href);
    if (subs != '') {
      url2 = url2 + '?subs=' + GM_btoaUrl(subs);
    }

    node.setAttribute('href', url2);
    node.addEventListener('click', function(event){
      event.preventDefault();
      event.stopPropagation();
      location.href = url2;
    });
  }
}

function GM_getParentByTagName(el, tagName) {
  tagName = tagName.toLowerCase();
  if (el.tagName.toLowerCase() == tagName) {
    return el;
  }
  while (el && el.parentNode) {
    el = el.parentNode;
    if (el.tagName && el.tagName.toLowerCase() == tagName) {
      return el;
    }
  }
  return "undefined";
}

function detectSite(sites) {
  let site;
  for (let s in sites) {
    site = sites[s];
    if (location.href.includes(s)) {
      return site;
    }
  }
  return null;
}

let site = detectSite(sites)
document.addEventListener('mousedown', function(e) {
  let el = GM_getParentByTagName(e.target, 'A');
  if (el.href && el.href.startsWith('http') && el.matches(site.sel)) {
    replaceLink(el, site);
  }
});
 
Em vừa debug lại thì đại khái là MutationObserver sẽ theo dõi thay đổi của cấu trúc trang: đồng chí Ivan tác giả clip gốc dùng để xem khi nào Youtube nó render thêm nội dung mới (tính cả lần load/render đầu tiên) thì gán href của protocol mpv://play/ cho object mới. Nhưng mà trên trang Youtube Mobile thì HOME với SEARCH nó tái sử dụng 1 phần chứ không load lại cả page lại từ đầu (mở F12 lên mà Sẻac là nó không clear console cũ), nên là object nào dùng lại là nó sẽ không cập nhật lại cái href mới :extreme_sexy_girl:
Vậy nên là cứ cho cả document bắt sự kiện click chuột rồi tìm ngượg href là lành nhất:hungry:

JavaScript:
// ==UserScript==
// @name        Click on video thumbnail to play in MPV
// @name:ru     Нажми на митиатюру для проигрывания в MPV
// @namespace   nsinister.scripts.videothumb2mpv
// @match       https://*.youtube.com/*
// @match       https://vimeo.com/*
// @grant       none
// @version     0.2
// @author      nSinister
// @license     MIT
// @description Opens videos in external player (mpv) by simply clicking on a thumbnail.
// @description:ru Проигрывает ролики во внешнем плеере (mpv) по нажатию на миниатюру
//
// ==/UserScript==

"use strict";

let sites = {
  "www.youtube.com": { sel: "a.ytd-thumbnail", url: "https://www.youtube.com", needsFullUrl: true },
  "m.youtube.com": { sel: "a.media-item-thumbnail-container", url: "https://m.youtube.com", needsFullUrl: true },
  "vimeo.com": { sel: "a.iris_video-vital__overlay", url: "https://vimeo.com", needsFullUrl: false },
};

function GM_btoaUrl(url) {
  return btoa(url).replace(/\//g, "_").replace(/\+/g, "-").replace(/\=/g, "");
}

function replaceLink(node, site) {
  if(node) {
    let hrefval = node.getAttribute('href');
    if (hrefval == null || hrefval.startsWith("mpv"))
      return;

    let full_url = (site.needsFullUrl ? site.url : "") + hrefval;
    if (full_url.startsWith('http')) {
      url = full_url;
    }
    if (url == '') {
      var url = location.href;
    }

    var subs = '';
    var s = url;
    var bs = GM_btoaUrl(s);
    var url2 = 'mpv://play/' + bs + '/' + "?referer=" + GM_btoaUrl(location.href);
    if (subs != '') {
      url2 = url2 + '?subs=' + GM_btoaUrl(subs);
    }

    node.setAttribute('href', url2);
    node.addEventListener('click', function(event){
      event.preventDefault();
      event.stopPropagation();
      location.href = url2;
    });
  }
}

function GM_getParentByTagName(el, tagName) {
  tagName = tagName.toLowerCase();
  if (el.tagName.toLowerCase() == tagName) {
    return el;
  }
  while (el && el.parentNode) {
    el = el.parentNode;
    if (el.tagName && el.tagName.toLowerCase() == tagName) {
      return el;
    }
  }
  return "undefined";
}

function detectSite(sites) {
  let site;
  for (let s in sites) {
    site = sites[s];
    if (location.href.includes(s)) {
      return site;
    }
  }
  return null;
}

let site = detectSite(sites)
document.addEventListener('mousedown', function(e) {
  let el = GM_getParentByTagName(e.target, 'A');
  if (el.href && el.href.startsWith('http') && el.matches(site.sel)) {
    replaceLink(el, site);
  }
});
ủa, của em script liệt luôn rồi, bác đã test chưa?
 
Nhưng mà trên trang Youtube Mobile thì HOME với SEARCH nó tái sử dụng 1 phần chứ không load lại cả page lại từ đầu (mở F12 lên mà Sẻac là nó không clear console cũ), nên là object nào dùng lại là nó sẽ không cập nhật lại cái href mới :extreme_sexy_girl:
Nó làm vậy nhìn chung là tối ưu cho tốc độ và trải nghiệm vì bố cục trang không bị thay đổi nên trình duyệt không cần làm việc nhiều, lý do nữa để dùng Youtube Mobile.

Hình như cách này có thể thêm thuộc tính (attribute) vào MutationObserver.

Vậy nên là cứ cho cả document bắt sự kiện click chuột rồi tìm ngượg href là lành nhất:hungry:
click hoặc mouseover là hai giải pháp triệt để nhất, click thì hiệu năng còn tốt hơn nữa vì nó chỉ kích hoạt khi ấn chuột trái, còn mouseover thì kích hoạt khi hơ chuột lên bất cứ thứ gì.

Nói chung là giải pháp này lý tưởng đấy :D
 
ủa, của em script liệt luôn rồi, bác đã test chưa?
Mình vừa code vừa dùng luôn mà, vẫn dùng bình thường: https://streamable.com/w1tm6j
Trỏ chuột vào thumbnail nhìn bên góc dưới tay trái thì vẫn là link http://m.youtube.com/watch?v=abc123 nhưng click chuột 1 cái là nó đổi xổ ra dialog mở bằng mpv, xem góc dưới bên trái thì nó đổi sang protocol của mpv rồi
 
Mình vừa code vừa dùng luôn mà, vẫn dùng bình thường: https://streamable.com/w1tm6j
Trỏ chuột vào thumbnail nhìn bên góc dưới tay trái thì vẫn là link http://m.youtube.com/watch?v=abc123 nhưng click chuột 1 cái là nó đổi xổ ra dialog mở bằng mpv, xem góc dưới bên trái thì nó đổi sang protocol của mpv rồi
A, em thấy rồi, nãy không đọc kĩ post của bác
5lBTE01.png
 
Last edited:
Back
Top