├── .babelrc ├── .editorconfig ├── .eslintignore ├── .eslintrc ├── .github ├── ISSUE_TEMPLATE │ ├── bug_report.md │ └── feature_request.md ├── auto-merge.yml ├── code_of_conduct.md ├── config.yml ├── contributing.md ├── pull_request_template.md └── workflows │ ├── dependabot-auto-merge.yml │ └── telegram.yml ├── .gitignore ├── .gitmodules ├── .markdownlint.json ├── .prettierignore ├── .prettierrc ├── .stylelintrc ├── .svgo.yml ├── .vscode ├── extensions.json ├── js.code-snippets ├── settings.json └── tasks.json ├── README.md ├── gulp ├── ff.js ├── fp.js ├── gulpfile.babel.js └── lib │ ├── create-firefox-profile.js │ ├── logger.js │ └── print.js ├── gulpfile-bk.js ├── gulpfile.js ├── nodemon.json ├── package-lock.json ├── package.json ├── src ├── chrome │ ├── css │ │ ├── aboutaddons │ │ │ ├── addonlists_compact-min.css │ │ │ ├── addonlists_compact.css │ │ │ ├── addonlists_disabled_grayscale_fx67.css │ │ │ ├── addonlists_private_browsing_notice_hidden.css │ │ │ ├── addonlists_replace_button_labels_with_icons.css │ │ │ ├── addonlists_show_buttons_inline.css │ │ │ ├── addonlists_show_buttons_inline_fx69.css │ │ │ ├── addons_manager_full_width.css │ │ │ ├── addons_manager_full_width_fx67.css │ │ │ └── details_page_alternative_content_order.css │ │ ├── picture-in-picture.css │ │ └── variables.css │ ├── scripts │ │ ├── ContextTranslate.uc.js │ │ ├── about-config-copy-userpref.uc.js │ │ ├── editbookmarkspopup_expanded.uc.js │ │ ├── favicon_in_urlbar.uc.js │ │ └── restart-button.uc.js │ ├── userChrome.css │ ├── userChrome.js │ └── userContent.css ├── icons │ ├── .svgo.json │ ├── .svgo.yml │ ├── .svgo2.yml │ ├── delete.svg │ ├── vimrc-out.svg │ └── vimrc.svg ├── user-base.js └── user.js └── tasks ├── bundle.js ├── cfg.js ├── clean.js ├── index.js ├── manifest.js ├── scripts.js ├── styles.js ├── syncy.js └── watch.js /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ "@babel/preset-env" ] 3 | } 4 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | # EditorConfig is awesome: http://EditorConfig.org 2 | 3 | # top-most EditorConfig file 4 | root = true 5 | 6 | # Unix-style newlines with a newline ending every file 7 | [*] 8 | indent_style = space 9 | indent_size = 2 10 | end_of_line = lf 11 | charset = utf-8 12 | trim_trailing_whitespace = true 13 | insert_final_newline = true 14 | -------------------------------------------------------------------------------- /.eslintignore: -------------------------------------------------------------------------------- 1 | .markdownlint.json 2 | src/chrome/* 3 | src/custom/* 4 | -------------------------------------------------------------------------------- /.eslintrc: -------------------------------------------------------------------------------- 1 | { 2 | "extends": [ 3 | "eslint-config-standard", 4 | "prettier", 5 | "prettier/standard" 6 | ], 7 | "env": { 8 | "es6": true, 9 | "node": true 10 | }, 11 | "globals": { 12 | "user_pref": "readonly" 13 | }, 14 | "plugins": [ 15 | "json", 16 | "prettier" 17 | ], 18 | "rules": { 19 | "max-len": "warn", 20 | "prettier/prettier": "warn" 21 | }, 22 | "overrides": [ 23 | { 24 | "files": ["src/user.js"], 25 | "rules": { 26 | // "quotes": ["error", "double"], 27 | "max-len": "off", 28 | "quotes": [ 29 | "error", 30 | "double", 31 | { "avoidEscape": true, "allowTemplateLiterals": false } 32 | ] 33 | } 34 | } 35 | ] 36 | } 37 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/bug_report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Bug report 3 | about: Create a report to help us improve 4 | title: '' 5 | labels: bug 6 | assignees: '' 7 | 8 | --- 9 | 10 | **Describe the bug:** 11 | 12 | 13 | **Steps to reproduce the behavior:** 14 | 19 | 20 | **Expected behavior:** 21 | 22 | 23 | 27 | 28 | **Please complete the following information:** 29 | - os: 30 | - nodejs version 31 | 32 | 36 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/feature_request.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Feature request 3 | about: Suggest an idea for this project 4 | title: '' 5 | labels: feature request 6 | assignees: '' 7 | 8 | --- 9 | 10 | **Is your feature request related to a problem? Please describe.** 11 | A clear and concise description of what the problem is. Ex. I'm always frustrated when [...] 12 | 13 | **Describe the solution you'd like** 14 | A clear and concise description of what you want to happen. 15 | 16 | **Describe alternatives you've considered** 17 | A clear and concise description of any alternative solutions or features you've considered. 18 | 19 | **Additional context** 20 | Add any other context or screenshots about the feature request here. 21 | -------------------------------------------------------------------------------- /.github/auto-merge.yml: -------------------------------------------------------------------------------- 1 | - match: 2 | dependency_type: development 3 | # Supported dependency types: 4 | # - development 5 | # - production 6 | # - all 7 | update_type: "semver:minor" # includes patch updates! 8 | # Supported updates to automerge: 9 | # - "security:patch" 10 | # SemVer patch update that fixes a known security vulnerability 11 | # - "semver:patch" 12 | # SemVer patch update, e.g. > 1.x && 1.0.1 to 1.0.3 13 | # - "semver:minor" 14 | # SemVer minor update, e.g. > 1.x && 2.1.4 to 2.3.1 15 | # - "in_range" (NOT SUPPORTED YET) 16 | # matching the version requirement in your package manifest 17 | # - "security:all" 18 | # - "all" 19 | # To allow prereleases, the corresponding prepatch, preminor and premajor types are also supported 20 | - match: 21 | dependency_type: production 22 | update_type: "security:minor" # includes patch updates! 23 | - match: 24 | dependency_type: production 25 | update_type: "semver:patch" 26 | -------------------------------------------------------------------------------- /.github/code_of_conduct.md: -------------------------------------------------------------------------------- 1 | # Contributor Covenant Code of Conduct 2 | 3 | ## Our Pledge 4 | 5 | We as members, contributors, and leaders pledge to make participation in our 6 | community a harassment-free experience for everyone, regardless of age, body 7 | size, visible or invisible disability, ethnicity, sex characteristics, gender 8 | identity and expression, level of experience, education, socio-economic status, 9 | nationality, personal appearance, race, religion, or sexual identity 10 | and orientation. 11 | 12 | We pledge to act and interact in ways that contribute to an open, welcoming, 13 | diverse, inclusive, and healthy community. 14 | 15 | ## Our Standards 16 | 17 | Examples of behavior that contributes to a positive environment for our 18 | community include: 19 | 20 | * Demonstrating empathy and kindness toward other people 21 | * Being respectful of differing opinions, viewpoints, and experiences 22 | * Giving and gracefully accepting constructive feedback 23 | * Accepting responsibility and apologizing to those affected by our mistakes, 24 | and learning from the experience 25 | * Focusing on what is best not just for us as individuals, but for the 26 | overall community 27 | 28 | Examples of unacceptable behavior include: 29 | 30 | * The use of sexualized language or imagery, and sexual attention or 31 | advances of any kind 32 | * Trolling, insulting or derogatory comments, and personal or political attacks 33 | * Public or private harassment 34 | * Publishing others' private information, such as a physical or email 35 | address, without their explicit permission 36 | * Other conduct which could reasonably be considered inappropriate in a 37 | professional setting 38 | 39 | ## Enforcement Responsibilities 40 | 41 | Community leaders are responsible for clarifying and enforcing our standards of 42 | acceptable behavior and will take appropriate and fair corrective action in 43 | response to any behavior that they deem inappropriate, threatening, offensive, 44 | or harmful. 45 | 46 | Community leaders have the right and responsibility to remove, edit, or reject 47 | comments, commits, code, wiki edits, issues, and other contributions that are 48 | not aligned to this Code of Conduct, and will communicate reasons for moderation 49 | decisions when appropriate. 50 | 51 | ## Scope 52 | 53 | This Code of Conduct applies within all community spaces, and also applies when 54 | an individual is officially representing the community in public spaces. 55 | Examples of representing our community include using an official e-mail address, 56 | posting via an official social media account, or acting as an appointed 57 | representative at an online or offline event. 58 | 59 | ## Enforcement 60 | 61 | Instances of abusive, harassing, or otherwise unacceptable behavior may be 62 | reported to the community leaders responsible for enforcement at 63 | artdevjs@gmail.com. 64 | All complaints will be reviewed and investigated promptly and fairly. 65 | 66 | All community leaders are obligated to respect the privacy and security of the 67 | reporter of any incident. 68 | 69 | ## Enforcement Guidelines 70 | 71 | Community leaders will follow these Community Impact Guidelines in determining 72 | the consequences for any action they deem in violation of this Code of Conduct: 73 | 74 | ### 1. Correction 75 | 76 | **Community Impact**: Use of inappropriate language or other behavior deemed 77 | unprofessional or unwelcome in the community. 78 | 79 | **Consequence**: A private, written warning from community leaders, providing 80 | clarity around the nature of the violation and an explanation of why the 81 | behavior was inappropriate. A public apology may be requested. 82 | 83 | ### 2. Warning 84 | 85 | **Community Impact**: A violation through a single incident or series 86 | of actions. 87 | 88 | **Consequence**: A warning with consequences for continued behavior. No 89 | interaction with the people involved, including unsolicited interaction with 90 | those enforcing the Code of Conduct, for a specified period of time. This 91 | includes avoiding interactions in community spaces as well as external channels 92 | like social media. Violating these terms may lead to a temporary or 93 | permanent ban. 94 | 95 | ### 3. Temporary Ban 96 | 97 | **Community Impact**: A serious violation of community standards, including 98 | sustained inappropriate behavior. 99 | 100 | **Consequence**: A temporary ban from any sort of interaction or public 101 | communication with the community for a specified period of time. No public or 102 | private interaction with the people involved, including unsolicited interaction 103 | with those enforcing the Code of Conduct, is allowed during this period. 104 | Violating these terms may lead to a permanent ban. 105 | 106 | ### 4. Permanent Ban 107 | 108 | **Community Impact**: Demonstrating a pattern of violation of community 109 | standards, including sustained inappropriate behavior, harassment of an 110 | individual, or aggression toward or disparagement of classes of individuals. 111 | 112 | **Consequence**: A permanent ban from any sort of public interaction within 113 | the community. 114 | 115 | ## Attribution 116 | 117 | This Code of Conduct is adapted from the [Contributor Covenant][homepage], 118 | version 2.0, available at 119 | https://www.contributor-covenant.org/version/2/0/code_of_conduct.html. 120 | 121 | Community Impact Guidelines were inspired by [Mozilla's code of conduct 122 | enforcement ladder](https://github.com/mozilla/diversity). 123 | 124 | [homepage]: https://www.contributor-covenant.org 125 | 126 | For answers to common questions about this code of conduct, see the FAQ at 127 | https://www.contributor-covenant.org/faq. Translations are available at 128 | https://www.contributor-covenant.org/translations. 129 | -------------------------------------------------------------------------------- /.github/config.yml: -------------------------------------------------------------------------------- 1 | # Configuration for welcome - https://github.com/behaviorbot/welcome 2 | 3 | # Configuration for new-issue-welcome - https://github.com/behaviorbot/new-issue-welcome 4 | 5 | # Comment to be posted to on first time issues 6 | newIssueWelcomeComment: | 7 | 👋 Thanks for opening your first issue! If you're reporting a bug, please make sure 8 | you include steps to reproduce it. If you're requesting a feature, please provide real 9 | use cases that would benefit. 👪 10 | 11 | Please use proper text formatting to make your issue easy to read and 12 | understand. See the 13 | [GitHub Markdown Guide](https://guides.github.com/features/mastering-markdown/) 14 | for help. 15 | 16 | # Configuration for new-pr-welcome - https://github.com/behaviorbot/new-pr-welcome 17 | 18 | # Comment to be posted to on PRs from first time contributors in your repository 19 | newPRWelcomeComment: | 20 | 💖 Thanks for opening this pull request! 💖 21 | 22 | Please use proper text formatting to make your pull request description easy 23 | to read and understand. See the 24 | [GitHub Markdown Guide](https://guides.github.com/features/mastering-markdown/) 25 | for help. 26 | 27 | # Configuration for first-pr-merge - https://github.com/behaviorbot/first-pr-merge 28 | 29 | # Comment to be posted to on pull requests merged by a first time user 30 | firstPRMergeComment: > 31 | Congrats on merging your first pull request! 32 | -------------------------------------------------------------------------------- /.github/contributing.md: -------------------------------------------------------------------------------- 1 | # Contributing Guidelines 2 | 3 | :back: [README.md](./README.md) 4 | 5 | Contributions welcome! 6 | 7 | **Before spending lots of time on something, ask for feedback on your idea first!** 8 | 9 | Please search issues and pull requests before adding something new to avoid duplicating 10 | efforts and conversations. 11 | 12 | This project welcomes non-code contributions, too! The following types of contributions 13 | are welcome: 14 | 15 | - **Ideas**: participate in an issue thread or start your own to have your voice heard. 16 | - **Writing**: contribute your expertise in an area by helping expand the included docs. 17 | - **Copy editing**: fix typos, clarify language, and improve the quality of the docs. 18 | - **Formatting**: help keep docs easy to read with consistent formatting. 19 | 20 | ## Coding Style 21 | * 2 spaces for indentation rather than tabs 22 | * 80 character line length 23 | 24 | ## Project Governance 25 | 26 | Individuals making significant and valuable contributions are given commit-access to the 27 | project to contribute as they see fit. This project is more like an open wiki than a 28 | happiness guarded open source project. 29 | 30 | ### Rules 31 | 32 | There are a few basic ground-rules for contributors: 33 | 34 | 1. **No `--force` pushes** or modifying the Git history in any way. 35 | 2. **Non-master branches** should be used for ongoing work. 36 | 3. **Significant modifications** like API changes should be subject to a **pull request** 37 | to solicit feedback from other contributors. 38 | 4. **Pull requests** are *encouraged* for all contributions to solicit feedback, but left to 39 | the discretion of the contributor. 40 | 5. Always write a clear log message for your commits. One-line messages are fine for small changes, but bigger changes should look like this: 41 | ``` 42 | $ git commit -m "A brief summary of the commit 43 | > 44 | > A paragraph describing what changed and its impact." 45 | ``` 46 | 47 | ## Issues 48 | 49 | We use GitHub issues to track public bugs. Please ensure your description is clear and has sufficient instructions to be able to reproduce the issue. 50 | Report a bug by [opening a new issue](https://github.com/dotiful/firefox-scripts/issues/new/choose) it's that easy! 51 | 52 | ## Pull Request Process 53 | 54 | 1. Ensure any install or build dependencies are removed before the end of the layer when doing a 55 | build. 56 | 2. Update the README.md with details of changes to the interface, this includes new environment 57 | variables, exposed ports, useful file locations and container parameters. 58 | 3. Increase the version numbers in any examples files and the README.md to the new version that this 59 | Pull Request would represent. The versioning scheme we use is [SemVer](http://semver.org/). 60 | 4. You may merge the Pull Request in once you have the sign-off of two other developers, or if you 61 | do not have permission to do that, you may request the second reviewer to merge it for you. 62 | 63 | ## License 64 | In short, when you submit code changes, your submissions are understood to be under the same [MIT License](http://choosealicense.com/licenses/mit/) that covers the project. Feel free to contact the maintainers if that's a concern. 65 | 66 | ## References 67 | This document was adapted from the open-source contribution guidelines for [Facebook's Draft](https://github.com/facebook/draft-js/blob/a9316a723f9e918afde44dea68b5f9f39b7d9b00/CONTRIBUTING.md) 68 | -------------------------------------------------------------------------------- /.github/pull_request_template.md: -------------------------------------------------------------------------------- 1 | (Thanks for sending a pull request! Please make sure you click the link above to view the contribution guidelines, then fill out the blanks below.) 2 | 3 | What does this implement/fix? Explain your changes. 4 | --------------------------------------------------- 5 | … 6 | 7 | Does this close any currently open issues? 8 | ------------------------------------------ 9 | … 10 | 11 | Any relevant logs, error output, etc? 12 | ------------------------------------- 13 | (If it’s long, please paste to https://ghostbin.com/ and insert the link here.) 14 | 15 | Any other comments? 16 | ------------------- 17 | … 18 | 19 | Where has this been tested? 20 | --------------------------- 21 | **os:** 22 | **nodejs version:** 23 | -------------------------------------------------------------------------------- /.github/workflows/dependabot-auto-merge.yml: -------------------------------------------------------------------------------- 1 | # https://docs.github.com/en/actions 2 | 3 | # https://github.com/ahmadnassri/action-dependabot-auto-merge 4 | 5 | name: dependabot-auto-merge 6 | 7 | on: 8 | pull_request: 9 | 10 | jobs: 11 | auto-merge: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - uses: actions/checkout@v2 15 | - uses: ahmadnassri/action-dependabot-auto-merge@v2 16 | with: 17 | target: minor 18 | github-token: ${{ secrets.AUTO_MERGE }} 19 | -------------------------------------------------------------------------------- /.github/workflows/telegram.yml: -------------------------------------------------------------------------------- 1 | # https://docs.github.com/en/actions 2 | 3 | # https://github.com/appleboy/telegram-action 4 | # https://github.com/Lukasss93/telegram-action 5 | 6 | 7 | name: telegram-action 8 | 9 | on: 10 | push: 11 | 12 | jobs: 13 | build: 14 | # The type of runner that the job will run on 15 | runs-on: ubuntu-latest 16 | 17 | # Steps represent a sequence of tasks that will be executed as part of the job 18 | steps: 19 | - uses: actions/checkout@v2 20 | - name: Send message to Telegram 21 | uses: Lukasss93/telegram-action@master 22 | if: always() 23 | env: 24 | TELEGRAM_TOKEN: ${{ secrets.TELEGRAM_TOKEN }} 25 | TELEGRAM_CHAT: ${{ secrets.TELEGRAM_CHAT }} 26 | with: 27 | STATUS: ${{job.status}} 28 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | *.code-workspace 3 | node_modules 4 | 5 | src/custom 6 | src/chrome/scripts.off 7 | 8 | .directory 9 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "src/chrome/css/customcssforfx"] 2 | path = src/chrome/css/customcssforfx 3 | url = https://github.com/Aris-t2/CustomCSSforFx 4 | [submodule "src/chrome/scripts/userChrome"] 5 | path = src/chrome/scripts/userChrome 6 | url = https://github.com/Endor8/userChrome.js 7 | -------------------------------------------------------------------------------- /.markdownlint.json: -------------------------------------------------------------------------------- 1 | { 2 | "comment": "Be explicit by listing every available rule. https://github.com/DavidAnson/markdownlint/blob/master/doc/Rules.md", 3 | "comment": "Note that there will be numeric gaps, not every MD number is implemented in markdownlint.", 4 | 5 | "comment": "MD001: Header levels should only increment by one level at a time.", 6 | "header-increment": true, 7 | 8 | "comment": "MD002: First header should be a top level header.", 9 | "first-header-h1": true, 10 | 11 | "comment": "MD003: Header style: start with hashes.", 12 | "header-style": { 13 | "style": "atx" 14 | }, 15 | 16 | "comment": "MD004: Unordered list style", 17 | "ul-style": { 18 | "style": "dash" 19 | }, 20 | 21 | "comment": "MD005: Consistent indentation for list items at the same level.", 22 | "list-indent": true, 23 | 24 | "comment": "MD006: Consider starting bulleted lists at the beginning of the line.", 25 | "ul-start-left": false, 26 | 27 | "comment": "MD007: Unordered list indentation: 2 spaces.", 28 | "ul-indent": false, 29 | 30 | "comment": "MD009: Disallow trailing spaces!", 31 | "no-trailing-spaces": { 32 | "br_spaces": 0, 33 | "comment": "Empty lines inside list items should not be indented.", 34 | "list_item_empty_lines": false 35 | }, 36 | 37 | "comment": "MD010: No hard tabs, not even in code blocks.", 38 | "no-hard-tabs": { 39 | "code_blocks": true 40 | }, 41 | 42 | "comment": "MD011: Prevent reversed link syntax", 43 | "no-reversed-links": true, 44 | 45 | "comment": "MD012: Disallow multiple consecutive blank lines.", 46 | "no-multiple-blanks": { 47 | "maximum": 1 48 | }, 49 | 50 | "comment": "MD013: Line length", 51 | "line-length": false, 52 | 53 | "comment": "MD014: Disallow use of dollar signs($) before commands without showing output.", 54 | "commands-show-output": true, 55 | 56 | "comment": "MD018: Disallow space after hash on atx style header.", 57 | "no-missing-space-atx": true, 58 | 59 | "comment": "MD019: Disallow multiple spaces after hash on atx style header.", 60 | "no-multiple-space-atx": true, 61 | 62 | "comment": "MD020: No space should be inside hashes on closed atx style header.", 63 | "no-missing-space-closed-atx": true, 64 | 65 | "comment": "MD021: Disallow multiple spaces inside hashes on closed atx style header.", 66 | "no-multiple-space-closed-atx": true, 67 | 68 | "comment": "MD022: Headers should be surrounded by blank lines.", 69 | "comment": "Some headers have preceeding HTML anchors. Unfortunate that we have to disable this, as it otherwise catches a real problem that trips up some Markdown renderers", 70 | "blanks-around-headers": false, 71 | 72 | "comment": "MD023: Headers must start at the beginning of the line.", 73 | "header-start-left": false, 74 | 75 | "comment": "MD024: Disallow multiple headers with the same content.", 76 | "no-duplicate-header": true, 77 | 78 | "comment": "MD025: Disallow multiple top level headers in the same document.", 79 | "comment": "Gotta have a matching closing brace at the end.", 80 | "single-h1": false, 81 | 82 | "comment": "MD026: Disallow trailing punctuation in header.", 83 | "comment": "You must have a semicolon after the ending closing brace.", 84 | "no-trailing-punctuation": { 85 | "punctuation" : ".,:!?" 86 | }, 87 | "comment": "MD027: Dissalow multiple spaces after blockquote symbol", 88 | "no-multiple-space-blockquote": true, 89 | 90 | "comment": "MD028: Blank line inside blockquote", 91 | "comment": "Some 'Why?' and 'Why not?' blocks are separated by a blank line", 92 | "no-blanks-blockquote": false, 93 | 94 | "comment": "MD029: Ordered list item prefix", 95 | "ol-prefix": { 96 | "style": "one" 97 | }, 98 | 99 | "comment": "MD030: Spaces after list markers", 100 | "list-marker-space": { 101 | "ul_single": 1, 102 | "ol_single": 1, 103 | "ul_multi": 1, 104 | "ol_multi": 1 105 | }, 106 | 107 | "comment": "MD031: Fenced code blocks should be surrounded by blank lines", 108 | "blanks-around-fences": true, 109 | 110 | "comment": "MD032: Lists should be surrounded by blank lines", 111 | "comment": "Some lists have preceeding HTML anchors. Unfortunate that we have to disable this, as it otherwise catches a real problem that trips up some Markdown renderers", 112 | "blanks-around-lists": false, 113 | 114 | "comment": "MD033: Disallow inline HTML", 115 | "comment": "HTML is needed for explicit anchors", 116 | "no-inline-html": false, 117 | 118 | "comment": "MD034: No bare URLs should be used", 119 | "no-bare-urls": true, 120 | 121 | "comment": "MD035: Horizontal rule style", 122 | "hr-style": { 123 | "style": "consistent" 124 | }, 125 | 126 | "comment": "MD036: Do not use emphasis instead of a header.", 127 | "no-emphasis-as-header": false, 128 | 129 | "comment": "MD037: Disallow spaces inside emphasis markers.", 130 | "no-space-in-emphasis": true, 131 | 132 | "comment": "MD038: Disallow spaces inside code span elements.", 133 | "no-space-in-code": true, 134 | 135 | "comment": "MD039: Disallow spaces inside link text.", 136 | "no-space-in-links": true, 137 | 138 | "comment": "MD040: Fenced code blocks should have a language specified.", 139 | "fenced-code-language": true, 140 | 141 | "comment": "MD041: First line in file should be a top level header.", 142 | "first-line-h1": true, 143 | 144 | "comment": "MD042: No empty links", 145 | "no-empty-links": true, 146 | 147 | "comment": "MD043: Required header structure.", 148 | "required-headers": false, 149 | 150 | "comment": "MD044: Proper names should have the correct capitalization.", 151 | "proper-names": false 152 | } 153 | -------------------------------------------------------------------------------- /.prettierignore: -------------------------------------------------------------------------------- 1 | .* 2 | chrome/* 3 | custom/* 4 | node_modules/* 5 | 6 | .markdownlint.json 7 | package.json 8 | 9 | README.md 10 | -------------------------------------------------------------------------------- /.prettierrc: -------------------------------------------------------------------------------- 1 | { 2 | "bracketSpacing": true, 3 | "endOfLine": "lf", 4 | "printWidth": 80, 5 | "proseWrap": "always", 6 | "semi": true, 7 | "singleQuote": true, 8 | "tabWidth": 2, 9 | "trailingComma": "all", 10 | "useTabs": false, 11 | "overrides": [ 12 | { 13 | "files": ["src/user.js"], 14 | "options": { 15 | "singleQuote": false 16 | } 17 | } 18 | ] 19 | } 20 | -------------------------------------------------------------------------------- /.stylelintrc: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "stylelint-config-stylishthemes", 3 | "rules": { 4 | "at-rule-empty-line-before": [ 5 | "always", 6 | { 7 | "except": ["blockless-after-same-name-blockless", "first-nested"], 8 | "ignore": ["after-comment"] 9 | } 10 | ], 11 | "at-rule-name-case": "lower", 12 | "at-rule-name-space-after": "always-single-line", 13 | "at-rule-semicolon-newline-after": "always", 14 | "block-closing-brace-empty-line-before": "never", 15 | "block-closing-brace-newline-after": "always", 16 | "block-closing-brace-newline-before": "always-multi-line", 17 | "block-closing-brace-space-before": "always-single-line", 18 | "block-opening-brace-newline-after": "always-multi-line", 19 | "block-opening-brace-space-after": "always-single-line", 20 | "block-opening-brace-space-before": "always", 21 | "color-hex-case": "lower", 22 | "color-hex-length": "short", 23 | "comment-empty-line-before": [ 24 | "always", 25 | { 26 | "except": ["first-nested"], 27 | "ignore": ["stylelint-commands"] 28 | } 29 | ], 30 | "comment-whitespace-inside": "always", 31 | "custom-property-empty-line-before": [ 32 | "always", 33 | { 34 | "except": ["after-custom-property", "first-nested"], 35 | "ignore": ["after-comment", "inside-single-line-block"] 36 | } 37 | ], 38 | "declaration-bang-space-after": "never", 39 | "declaration-bang-space-before": "always", 40 | "declaration-block-semicolon-newline-after": "always-multi-line", 41 | "declaration-block-semicolon-space-after": "always-single-line", 42 | "declaration-block-semicolon-space-before": "never", 43 | "declaration-block-single-line-max-declarations": 1, 44 | "declaration-block-trailing-semicolon": "always", 45 | "declaration-colon-newline-after": "always-multi-line", 46 | "declaration-colon-space-after": "always-single-line", 47 | "declaration-colon-space-before": "never", 48 | "declaration-empty-line-before": [ 49 | "always", 50 | { 51 | "except": ["after-declaration", "first-nested"], 52 | "ignore": ["after-comment", "inside-single-line-block"] 53 | } 54 | ], 55 | "function-comma-newline-after": "always-multi-line", 56 | "function-comma-space-after": "always-single-line", 57 | "function-comma-space-before": "never", 58 | "function-max-empty-lines": 0, 59 | "function-name-case": "lower", 60 | "function-parentheses-newline-inside": "always-multi-line", 61 | "function-parentheses-space-inside": "never-single-line", 62 | "function-whitespace-after": "always", 63 | "indentation": 2, 64 | "length-zero-no-unit": true, 65 | "max-empty-lines": 1, 66 | "media-feature-colon-space-after": "always", 67 | "media-feature-colon-space-before": "never", 68 | "media-feature-name-case": "lower", 69 | "media-feature-parentheses-space-inside": "never", 70 | "media-feature-range-operator-space-after": "always", 71 | "media-feature-range-operator-space-before": "always", 72 | "media-query-list-comma-newline-after": "always-multi-line", 73 | "media-query-list-comma-space-after": "always-single-line", 74 | "media-query-list-comma-space-before": "never", 75 | "no-eol-whitespace": true, 76 | "no-missing-end-of-source-newline": true, 77 | "number-leading-zero": "never", 78 | "number-no-trailing-zeros": true, 79 | "property-case": "lower", 80 | "rule-empty-line-before": [ 81 | "always-multi-line", 82 | { 83 | "except": ["first-nested"], 84 | "ignore": ["after-comment"] 85 | } 86 | ], 87 | "selector-attribute-brackets-space-inside": "never", 88 | "selector-attribute-operator-space-after": "never", 89 | "selector-attribute-operator-space-before": "never", 90 | "selector-combinator-space-after": "always", 91 | "selector-combinator-space-before": "always", 92 | "selector-descendant-combinator-no-non-space": true, 93 | "selector-list-comma-newline-after": "always", 94 | "selector-list-comma-space-before": "never", 95 | "selector-max-empty-lines": 0, 96 | "selector-pseudo-class-case": "lower", 97 | "selector-pseudo-class-parentheses-space-inside": "never", 98 | "selector-pseudo-element-case": "lower", 99 | "selector-pseudo-element-colon-notation": "double", 100 | "selector-type-case": "lower", 101 | "unit-case": "lower", 102 | "value-list-comma-newline-after": "always-multi-line", 103 | "value-list-comma-space-after": "always-single-line", 104 | "value-list-comma-space-before": "never", 105 | "value-list-max-empty-lines": 0 106 | } 107 | } 108 | -------------------------------------------------------------------------------- /.svgo.yml: -------------------------------------------------------------------------------- 1 | full: true 2 | 3 | # plugins options 4 | # @see https://github.com/svg/svgo/blob/master/README.md 5 | 6 | plugins: 7 | - cleanupAttrs: true 8 | - inlineStyles: true 9 | - removeDoctype: true 10 | - removeXMLProcInst: true 11 | - removeComments 12 | - removeMetadata 13 | - removeTitle: true 14 | - removeDesc: true 15 | - removeUselessDefs: true 16 | - removeXMLNS: false 17 | - removeEditorsNSData 18 | - removeEmptyAttrs: true 19 | - removeHiddenElems 20 | - removeEmptyText 21 | - removeEmptyContainers: true 22 | - removeViewBox 23 | - cleanupEnableBackground 24 | - minifyStyles 25 | - convertStyleToAttrs: true 26 | - convertColors 27 | - convertPathData 28 | - convertTransform 29 | - removeUnknownsAndDefaults: true 30 | - removeNonInheritableGroupAttrs 31 | - removeUselessStrokeAndFill: true 32 | - removeUnusedNS 33 | - prefixIds 34 | - cleanupIDs: true 35 | - cleanupNumericValues 36 | - cleanupListOfValues 37 | - moveElemsAttrsToGroup 38 | - moveGroupAttrsToElems 39 | - collapseGroups: true 40 | - removeRasterImages: true 41 | - mergePaths 42 | - convertShapeToPath 43 | - sortAttrs: true 44 | - removeDimensions: true 45 | - removeAttrs 46 | - removeAttributesBySelector 47 | - removeElementsByAttr 48 | - addClassesToSVGElement 49 | - addAttributesToSVGElement 50 | - removeOffCanvasPaths 51 | - removeStyleElement 52 | - removeScriptElement 53 | - reusePaths 54 | 55 | # config options 56 | # @see https://github.com/svg/svgo/blob/master/lib/svgo/js2svg.js#L6 57 | js2svg: 58 | pretty: true 59 | indent: ' ' 60 | -------------------------------------------------------------------------------- /.vscode/extensions.json: -------------------------------------------------------------------------------- 1 | { 2 | // List of extensions which should be recommended for users of this workspace. 3 | "recommendations": [ 4 | "rebornix.project-snippets" 5 | ] 6 | } 7 | -------------------------------------------------------------------------------- /.vscode/js.code-snippets: -------------------------------------------------------------------------------- 1 | { 2 | "user_pref" : { 3 | "scope": "javascript,typescript", 4 | "prefix" : "up", 5 | "body" : [ 6 | "$LINE_COMMENT $3", 7 | "user_pref(\"${TM_SELECTED_TEXT:${1:entry}}\", ${2|\u200B,true,false|});", 8 | "$0" 9 | ], 10 | "description": "Add a about:config entry" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "eslint.enable": true, 3 | "files.defaultLanguage": "javascript", 4 | "editor.autoClosingQuotes": "always" 5 | } 6 | -------------------------------------------------------------------------------- /.vscode/tasks.json: -------------------------------------------------------------------------------- 1 | { 2 | // See https://go.microsoft.com/fwlink/?LinkId=733558 3 | // for the documentation about the tasks.json format 4 | "version": "2.0.0", 5 | "tasks": [ 6 | { 7 | "label": "Stylelint fix", 8 | "type": "shell", 9 | "command": "stylelint \"$file\" --fix", 10 | "presentation": { 11 | "echo": true, 12 | "reveal": "silent", 13 | "focus": false, 14 | "panel": "shared", 15 | "showReuseMessage": false, 16 | "clear": true 17 | }, 18 | "problemMatcher": [] 19 | } 20 | ] 21 | } 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Firefox Scripts 2 | 3 | [![Dependency Status](https://david-dm.org/dotiful/firefox-scripts.svg)](https://david-dm.org/dotiful/firefox-scripts) 4 | [![devDependency Status](https://david-dm.org/dotiful/firefox-scripts/dev-status.svg)](https://david-dm.org/dotiful/firefox-scripts#info=devDependencies) 5 | 6 | * [Firefox Scripts](#firefox-scripts) 7 | * [about:config](#aboutconfig) 8 | * [userChrome.css](#userchromecss) 9 | * [userChrome.js](#userchromejs) 10 | * [user.js](#userjs) 11 | * [themes](#themes) 12 | * [tutorials and documentations](#tutorials-and-documentations) 13 | * [extensions](#extensions) 14 | * [general](#general) 15 | * [ui](#ui) 16 | * [dev](#dev) 17 | * [privacy & security](#privacy--security) 18 | * [extension development](#extension-development) 19 | * [bookmarks](#bookmarks) 20 | * [tabs](#tabs) 21 | * [search engines](#search-engines) 22 | * [rss](#rss) 23 | * [other](#other) 24 | 25 | ## about:config 26 | 27 | * [r/firefox/wiki/aboutconfig](https://www.reddit.com/r/firefox/wiki/aboutconfig) - Advanced settings tweaking subreddit 28 | * [about:config entries](http://kb.mozillazine.org/About:config_entries) - reference to the entries in about:config 29 | * [Privacy Related Tweaks](https://www.privacytools.io/browsers/#about_config) - Collection of privacy-related tweaks thats shows you how to enhance the privacy of browser 30 | * [overview of about:config](https://www.ghacks.net/overview-firefox-aboutconfig-security-privacy-preferences/) - security and privacy preferences 31 | * [mozillazine.org](http://kb.mozillazine.org/Category:Security_and_privacy-related_preferences) - Security and privacy-related preferences. 32 | * [r/firefox/wiki/userchrome](https://www.reddit.com/r/firefox/wiki/userchrome) - Customizing the Firefox UI with CSS 33 | * [Aris-t2/CustomCSSforFx](https://github.com/Aris-t2/CustomCSSforFx) - custom CSS tweaks for Firefox Quantum 34 | * [Classic CSS tweaks](https://github.com/Aris-t2/CustomCSSforFx/issues/2#show_issue) - A lot of excellent information regarding userChrome.css 35 | * [Timvde/UserChrome-Tweaks](https://github.com/Timvde/UserChrome-Tweaks) - a community maintained repository of userChrome.css tweaks 36 | * [stonecrusher/simpleMenuWizard](https://github.com/stonecrusher/simpleMenuWizard) - Hide contextmenu items in Firefox 37 | 38 | * [Photon Design System](https://design.firefox.com/photon) - Guidelines, reusable UI components, templates, and other resources. 39 | * [Firefox Colors Pallete](https://design.firefox.com/photon/visuals/color.html) 40 | * [Icons Library](https://design.firefox.com/icons/viewer/#) 41 | 42 | ## userChrome.js 43 | 44 | * [MrOtherGuy/fx-autoconfig](https://github.com/MrOtherGuy/fx-autoconfig) - Yet another userChrome.js manager 45 | * [Endor8/userChrome.js](https://github.com/Endor8/userChrome.js) - Scripts for the Firefox extension userChrome.js 46 | * [xiaoxiaoflood/firefox-scripts](https://github.com/xiaoxiaoflood/firefox-scripts) - userChromeJS / autoconfig.js and extensions 47 | * [Aris-t2/CustomJSforFx](https://github.com/Aris-t2/CustomJSforFx) - custom scripts 48 | * [dupontjoy/userChrome.js-Collections](https://github.com/dupontjoy/userChrome.js-Collections-) - UC scripts collections 49 | 50 | ## user.js 51 | 52 | * [ghacksuserjs/ghacks-user.js](https://github.com/ghacksuserjs/ghacks-user.js) - an ongoing comprehensive user.js template for configuring and hardening Firefox privacy, security and anti-fingerprinting 53 | * [pyllyukko/user.js](https://github.com/pyllyukko/user.js) - This is a user.js configuration file to harden Firefox's settings and make it more secure 54 | * [gocom/pinceau](https://github.com/gocom/pinceau) - Personal Firefox userChrome and preference customizations 55 | * [user.js](http://kb.mozillazine.org/User.js_file) - configuration file for Firefox designed to harden browser settings and make it more secure 56 | 57 | ## themes 58 | 59 | * [theme docs](https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/manifest.json/theme#properties) - `manifest.json` 60 | * [Firefox Color](https://color.firefox.com) - Build Beautiful Firefox Themes 61 | * [firefox-papirus-icon-theme](https://github.com/PapirusDevelopmentTeam/firefox-papirus-icon-theme) - Papirus icons for Firefox 62 | * [muckSponge/MaterialFox](https://github.com/muckSponge/MaterialFox) - A Material Design-inspired userChrome.css theme for Firefox 63 | * [Quantum-Nox-Firefox-Dark-Full-Theme](https://github.com/Izheil/Quantum-Nox-Firefox-Dark-Full-Theme) - these usercontent and userchrome files will give a full themed dark color to Firefox Quantum, menus and dialogs included, as well as the scrollbars 64 | * [firefox-sweet-theme](https://github.com/EliverLara/firefox-sweet-theme) - A dark and modern theme for firefox with vibrant colors [![github][github-logo]](https://github.com/EliverLara/firefox-sweet-theme) 65 | * [overdodactyl/ShadowFox](https://github.com/overdodactyl/ShadowFox) - a universal dark theme for Firefox 66 | * [FOXSCAPEuC by Michael Walden](mw.rat.bz/foxscapeuc/) - a full featured retro theme for Firefox that makes Firefox look like Netscape 4.x, Netscape 6+ "Classic" theme 67 | * [Add-ons server](https://addons-server.readthedocs.io/en/latest/topics/api/addons.html) - Add-ons API documentation 68 | * [Source Tree Docs](https://firefox-source-docs.mozilla.org/index.html#) - Mozilla Source Tree Docs 69.0a1 documentation 69 | * [Are We XBL Still?](https://bgrins.github.io/xbl-analysis/) - site contains tools for understanding and working with XBL code in Firefox to make it easier to replace 70 | * [Searchfox](https://searchfox.org) - Searchfox is a source code indexing tool for Mozilla Firefox. 71 | * [firefox-source-docs](https://firefox-source-docs.mozilla.org) - Mozilla Source Tree Docs 69.0a1 documentation 72 | * [userchrome.org](https://www.userchrome.org) - userChrome.css for Customizing Firefox 73 | * [MozillaZine Knowledge Base](http://kb.mozillazine.org/index.php?title=UserChrome.css) - userChrome.css 74 | * [File I/O | MDN](https://developer.mozilla.org/en-US/docs/Archive/Add-ons/Code_snippets/File_I_O#Getting_special_files) - a full listing of directory tokens 75 | 76 | ## extensions 77 | 78 | ### general 79 | 80 | * [Surfingkeys](https://addons.mozilla.org/en-US/firefox/addon/surfingkeys_ff/) - Map your keys for web surfing, expand your browser with javascript and keyboard [![github][github-logo]](https://github.com/) 81 | * [Tampermonkey](https://addons.mozilla.org/en-US/firefox/addon/tampermonkey/) - Tampermonkey is the world's most popular userscript manager [![github][github-logo]](https://github.com/brookhong/Surfingkeys) 82 | * [Simple Translate](https://addons.mozilla.org/en-US/firefox/addon/simple-translate/) - Quickly translate selected text on web page [![github][github-logo]](https://github.com/sienori/simple-translate) 83 |
84 | settings 85 | 86 | ### Web page 87 | 88 | | **key** | **value** | 89 | |-------------------------------------------- | --------- | 90 | | Automatically switch to the second language | true | 91 | 92 | ### General 93 | 94 | | **key** | **value** | 95 | |---------------------------- |--------- | 96 | | Target language | russian | 97 | | Secong language | english | 98 | | Show translation candidates | false | 99 | 100 | ### Translation button 101 | 102 | | **key** | **value** | 103 | |------------------------------|-----------| 104 | | Display position - Direction | Bottom | 105 | | Display position - Offset | 20 | 106 | 107 | ### Translation panel 108 | 109 | | **key** | **value** | 110 | |--------------------------------------|------------------------------------------------------------------------------------------| 111 | | Width | 480px | 112 | | Height | 320px | 113 | | Font size | 14px | 114 | | Display position - Reference point | Clicked Point | 115 | | Display position - Direction | Bottom | 116 | | Display position - Offset | 20 | 117 | | Font color of translation result | ![color](https://via.placeholder.com/10/bdbdbd?text=+) `#bdbdbd`
`rgb(189, 189, 189)` | 118 | | Font color of translation candidates | ![color](https://via.placeholder.com/10/e3ded5?text=+) `#e3ded5`
`rgb(227, 222, 213)` | 119 | | Background-color | ![color](https://via.placeholder.com/10/333333?text=+) `#333333`
`rgb(51, 51, 51)` | 120 | 121 | ### Preview 122 | 123 | ![screenshoot](https://i.imgur.com/3czIumx.png) 124 |
125 | * [Adguard AdBlocker](https://addons.mozilla.org/en-US/firefox/addon/adguard-adblocker/) - Unmatched adblock extension against advertising and pop-ups [![github][github-logo]](https://github.com/AdguardTeam/AdguardBrowserExtension) 126 | * [SponsorBlock](https://addons.mozilla.org/en-US/firefox/addon/sponsorblock/) - Skip YouTube video sponsors [![github][github-logo]](https://github.com/ajayyy/SponsorBlock) 127 | 128 | ### ui 129 | 130 | * [Stylus](https://addons.mozilla.org/en-US/firefox/addon/styl-us/) - Easily install custom themes from popular online repositories, or create, edit, and manage your own personalized CSS stylesheets [![github][github-logo]](https://github.com/openstyles/stylus) 131 | * [Dark Reader](https://addons.mozilla.org/en-US/firefox/addon/darkreader/?src=collection) - Dark mode for every website [![github][github-logo]](https://github.com/darkreader/darkreader) 132 | * [DmitriK/darkContrast](https://github.com/DmitriK/darkContrast) - Fixes low contrast text when using dark desktop theme [![github][github-logo]](https://github.com/DmitriK/darkContrast) 133 | 134 | ### dev 135 | 136 | * [create a hotkey to trigger a extension button](https://www.reddit.com/r/FirefoxCSS/comments/nyunh7/is_there_any_way_to_create_a_hotkey_to_trigger_a/) 137 | * [CodeCopy](https://addons.mozilla.org/en-US/firefox/addon/codecopy/) - Because copy to clipboard buttons should exist on every code snippet [![github][github-logo]](https://github.com/zenorocha/codecopy) 138 | * [Module Linker](https://addons.mozilla.org/en-US/firefox/addon/module-linker/) - Add direct links to imported modules on GitHub source code [![github][github-logo]](https://github.com/fiatjaf/module-linker) 139 | * [npm-hub](https://addons.mozilla.org/en-US/firefox/addon/npm-hub) - Explore npm dependencies on GitHub repos [![github][github-logo]](https://github.com/npmhub/npmhub) 140 | * [Refined GitHub](https://addons.mozilla.org/en-US/firefox/addon/refined-github-/) - Simplifies the GitHub interface and adds many useful features [![github][github-logo]](https://github.com/sindresorhus/refined-github) 141 | * [EnixCoda/Gitako](https://github.com/EnixCoda/Gitako) - File tree extension for GitHub [![github][github-logo]](https://github.com/EnixCoda/Gitako) 142 | * [Gitpod](https://addons.mozilla.org/en-US/firefox/addon/gitpod/) - One-Click Online IDE for GitHub [![github][github-logo]](https://github.com/gitpod-io/browser-extension) 143 | * [github-vscode-icons](https://addons.mozilla.org/en-US/firefox/addon/github-vscode-icons/) - vscode-icons for github [![github][github-logo]](https://github.com/dderevjanik/github-vscode-icons) 144 | * [JSON Lite](https://addons.mozilla.org/en-US/firefox/addon/json-lite/) - Fast JSON viewer - highlights, shows items count/size, handles large files [![github][github-logo]](https://github.com/lauriro/json-lite) 145 | * [AWS Console Recorder](https://addons.mozilla.org/en-US/firefox/addon/console-recorder/) - Records actions made in the AWS Management Console and outputs the equivalent CLI/SDK commands and CloudFormation/Terraform templates [![github][github-logo]](https://github.com/iann0036/AWSConsoleRecorderGenerator) 146 | * [Web Developer](https://addons.mozilla.org/en-US/firefox/addon/web-developer/) - adds various web developer tools to the browser 147 | * [Wappalyzer](https://addons.mozilla.org/en-US/firefox/addon/wappalyzer/) - Identify technologies on websites 148 | * [User-Agent Switcher](https://addons.mozilla.org/en-US/firefox/addon/uaswitcher/) - Easily override the browser's User-Agent string 149 | 150 | ### privacy & security 151 | 152 | * [1Password X](https://addons.mozilla.org/en-US/firefox/addon/1password-x-password-manager/?src=collection) - The best way to experience 1Password in your browser 153 | * [AdGuard VPN](https://addons.mozilla.org/en-US/firefox/addon/adguard-vpn/) - Makes the Internet open and your data safe. Topnotch VPN from the creators of famous ad blocker. 154 | * [KeePassXC Browser](https://addons.mozilla.org/en-US/firefox/addon/keepassxc-browser/) - Official browser plugin for the KeePassXC password manager [![github][github-logo]](https://github.com/keepassxreboot/keepassxc-browser) 155 | * [BitWarden](https://addons.mozilla.org/en-US/firefox/addon/bitwarden-password-manager/) - A secure password manager for all of your devices. 156 | * [Privacy Settings](https://addons.mozilla.org/en-US/firefox/addon/privacy-settings/) - Alter built-in privacy settings easily with a toolbar panel. [![github][github-logo]](https://github.com/schomery/privacy-settings) 157 | 158 | ### extension development 159 | 160 | * [EmailThis/extension-boilerplate](https://github.com/EmailThis/extension-boilerplate) - A template for building cross browser extensions for Chrome, Opera & Firefox 161 | * [Extension source viewer](https://addons.mozilla.org/en-US/firefox/addon/crxviewer/) - View source code of Firefox add-ons and Chrome extensions (crx/nex/xpi) from addons.mozilla.org, the Chrome Webstore and elsewhere 162 | * [Chrome Store Foxified](https://addons.mozilla.org/en-US/firefox/addon/chrome-store-foxified/?src=github) - Enables the Google Chrome Store and Opera Addons Website for Firefox. Point and click to install Opera/Chrome extensions straight into firefox 163 | 164 | ### bookmarks 165 | 166 | * [Bookmarklets context menu](https://addons.mozilla.org/en-US/firefox/addon/bookmarklets-context-menu/) - Add a context menu item contains only bookmarklets from bookmarks. [![github][github-logo]](https://github.com/bookmarklets-context-menu) 167 | * [Bookmark Dupes](https://addons.mozilla.org/en-US/firefox/addon/bookmark-dupes/) - Display/Remove duplicate bookmarks, empty folders or descriptions 168 | * [Bookmarks Organizer](https://addons.mozilla.org/en-US/firefox/addon/bookmarks-organizer/) - Put order in your bookmarks, find no longer working bookmarks, redirects, duplicates and more 169 | * [Checkmarks](https://addons.mozilla.org/en-US/firefox/addon/checkmarks-web-ext/) - Check bookmarks and reload favicons 170 | * [Raindrop.io](https://addons.mozilla.org/en-US/firefox/addon/raindropio/) - Keep your favorites handy 171 | 172 | ### tabs 173 | 174 | * [NelliTab](https://addons.mozilla.org/en-US/firefox/addon/nellitab/) - Highly customizable new tab 🦊 175 | * [Auto Tab Discard](https://addons.mozilla.org/en-US/firefox/addon/auto-tab-discard/) - Use native tab discard method to automatically reduce memory usage of inactive tabs 176 |
177 | settings 178 | 179 | ### Discarding options 180 | | **key** | **value** | 181 | |-----------------------------|--------------------| 182 | | discard after | 600ms | 183 | | when number of tabs exceeds | 3 | 184 | | display in context menu | false | 185 | | do not discard when offline | true | 186 | | toolbar click action | discard other tabs | 187 | ---- 188 |
189 | * [Tree Style Tab](https://addons.mozilla.org/en-US/firefox/addon/tree-style-tab) - Tree Style Tab, Show tabs like a tree. [![github][github-logo]](hthttps://github.com/piroor/treestyletab) 190 | * [Tab Session Manager](https://addons.mozilla.org/en-US/firefox/addon/tab-session-manager/) - Save and restore the state of windows and tabs 191 | * [Tiled Tab Groups](https://addons.mozilla.org/en-US/firefox/addon/tiled-tab-groups/) - Provides tab groups / panorama functionality using the tab hide api. [![github][github-logo]](https://github.com/chzesa/tiled-tab-groups) 192 | * [Tab Suspender](https://addons.mozilla.org/en-US/firefox/addon/ff-tab-suspender/) - Native, lightweight and performant open source extension that reduce Firefox's memory usage [![github][github-logo]](https://github.com/Hau-Hau/firefox-tab-suspender) 193 | * [Multi-Account Containers](https://addons.mozilla.org/en-GB/firefox/addon/multi-account-containers/) - Multi-Account Containers lets you keep parts of your online life separated into color-coded tabs that preserve your privacy 194 | * [Focus On Left Tab After Closing](https://addons.mozilla.org/en-US/firefox/addon/focus-on-left-tab-aft-closing/) - Activate the left tab when a current tab is closed. 195 | 196 | ### search engines 197 | 198 | * [Search Engines Helper](https://addons.mozilla.org/en-US/firefox/addon/search-engines-helper/) - Export, import and add custom firefox search engines [![github][github-logo]](https://github.com/soufianesakhi/firefox-search-engines-helper) 199 | * [Search Engine DevTools](https://github.com/mozilla-extensions/searchengine-devtools) - A tool to help test search engine configuration changes 200 | * [Search Engine Plugins](https://mycroftproject.com) - Collection of over 25 thousand OpenSearch & Sherlock search engine plugins 201 | 202 | ### rss 203 | 204 | * [Feed Indicator](https://addons.mozilla.org/en-US/firefox/addon/feed-indicator/) - Adds an icon to indicate RSS/Atom feeds to address bar and previews a feed 205 | * [Feed Preview](https://addons.mozilla.org/en-US/firefox/addon/feed-preview/) - Indicates available RSS and Atom feeds and renders previews 206 | 207 | ### other 208 | 209 | * [I'm not robot captcha clicker](https://addons.mozilla.org/en-US/firefox/addon/i-m-not-robot-captcha-clicker/) - I'm not robot captcha automatic clicker 210 | * [Free Download Manager](https://addons.mozilla.org/en-US/firefox/addon/free-download-manager-addon/) - Free Download Manager integration with your Firefox browser 211 | 212 | 213 | 214 | 215 | [github-logo]: https://img.icons8.com/material-outlined/24/000000/github.png 216 | [github-url]: https://github.com/schomery/privacy-settings 217 | -------------------------------------------------------------------------------- /gulp/ff.js: -------------------------------------------------------------------------------- 1 | const FirefoxProfile = require('firefox-profile'); 2 | const createProfile = require('./lib/create-firefox-profile'); 3 | const fs = require('fs'); 4 | const path = require('path'); 5 | 6 | const ProfileFinder = new FirefoxProfile.Finder(); 7 | 8 | ProfileFinder.readProfiles(() => { 9 | const profilesDir = `${ProfileFinder.directory}/Profiles`; 10 | const newProfile = `${profilesDir}/tmp`; 11 | 12 | createProfile({profile: newProfile}, (err, folder) => { 13 | if (err) throw err; 14 | 15 | console.log(folder) 16 | }) 17 | }); 18 | 19 | // ───────────────────────────────────────────────────────────────────────────── 20 | 21 | 22 | // console.log('AppDataPath:', AppDataPath) 23 | 24 | // FirefoxProfile.copyFromUserProfile({name: 'test-ext-user'}, function(err, profile) { 25 | // console.log(profile.profileDir); 26 | // // profile.shouldDeleteOnExit(false); 27 | // }); 28 | 29 | 30 | // const tempy = require('tempy') 31 | // const fs = require('fs') 32 | // const path = require('path') 33 | 34 | // const prefs = { 35 | // 'browser.shell.checkDefaultBrowser': false 36 | // } 37 | 38 | // if (opts.prefs) { 39 | // for (let key of Object.keys(opts.prefs)) { 40 | // if (opts.prefs[key] != null) { 41 | // prefs[key] = JSON.stringify(opts.prefs[key]) 42 | // } 43 | // } 44 | // } 45 | 46 | // const profile = Object.keys(prefs) 47 | // .reduce((acc, key) => `${acc}user_pref('${key}', ${prefs[key]});\n`, '') 48 | 49 | // const profileFolder = tempy.directory() 50 | 51 | // fs.writeFile(path.join(profileFolder, 'user.js'), profile, (err) => { 52 | // if (err) return callback(err) 53 | 54 | // callback(null, profileFolder) 55 | // }) 56 | -------------------------------------------------------------------------------- /gulp/fp.js: -------------------------------------------------------------------------------- 1 | const FirefoxProfile = require('firefox-profile'); 2 | const fs = require('fs') 3 | const path = require('path') 4 | 5 | const prefs = { 6 | 'browser.shell.checkDefaultBrowser': false 7 | } 8 | 9 | const profile = Object.keys(prefs) 10 | .reduce((acc, key) => `${acc}user_pref('${key}', ${prefs[key]});\n`, '') 11 | 12 | const profileFolder = tempy.directory() 13 | 14 | fs.writeFile(path.join(profileFolder, 'user.js'), profile, (err) => { 15 | if (err) console.error('err is ', err); 16 | 17 | console.log('profileFolder:', profileFolder) 18 | }); 19 | 20 | -------------------------------------------------------------------------------- /gulp/gulpfile.babel.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp'; 2 | import path from 'path'; 3 | import del from 'del'; 4 | import through2 from 'through2'; 5 | import changed from 'gulp-changed'; 6 | import prettyError from 'gulp-prettyerror'; 7 | import { log } from "./lib/logger.js"; 8 | // import babel from 'gulp-babel'; 9 | 10 | const { src, dest, task, parallel, series, watch } = gulp; 11 | 12 | 13 | const paths = { 14 | profile: { 15 | src: 16 | }, 17 | styles: { 18 | src: 'chrome/css/**', 19 | }, 20 | scripts: { 21 | src: 'chrome/scripts/**', 22 | } 23 | }; 24 | 25 | /* 26 | * For small tasks you can export arrow functions 27 | */ 28 | export const clean = () => del([ 'assets' ]); 29 | 30 | /* 31 | * You can also declare named functions and export them as tasks 32 | */ 33 | export styles() => { 34 | src(paths.styles.src) 35 | .pipe(dest(paths.styles.dest)); 36 | } 37 | 38 | export scripts() => { 39 | src(paths.scripts.src) 40 | .pipe(changed(cfg.dest())) 41 | .pipe(dest(paths.scripts.dest)); 42 | } 43 | 44 | /* 45 | * You could even use `export as` to rename exported tasks 46 | */ 47 | function watchFiles() { 48 | watch(paths.scripts.src, scripts); 49 | watch(paths.styles.src, styles); 50 | } 51 | export { watchFiles as watch }; 52 | 53 | const build = series(clean, parallel(styles, scripts)); 54 | /* 55 | * Export a default task 56 | */ 57 | export default build; 58 | -------------------------------------------------------------------------------- /gulp/lib/create-firefox-profile.js: -------------------------------------------------------------------------------- 1 | const fs = require('fs') 2 | const path = require('path') 3 | 4 | module.exports = function (opts, callback) { 5 | if (typeof opts === 'function') { 6 | callback = opts 7 | opts = {} 8 | } else if (opts == null) { 9 | opts = {} 10 | } 11 | 12 | const prefs = { 13 | 'browser.shell.checkDefaultBrowser': false 14 | } 15 | 16 | if (opts.prefs) { 17 | for (let key of Object.keys(opts.prefs)) { 18 | if (opts.prefs[key] != null) { 19 | prefs[key] = JSON.stringify(opts.prefs[key]) 20 | } 21 | } 22 | } 23 | 24 | const profile = Object.keys(prefs) 25 | .reduce((acc, key) => `${acc}user_pref('${key}', ${prefs[key]});\n`, '') 26 | 27 | const profileFolder = opts.profile 28 | 29 | try { 30 | if (!fs.existsSync(profileFolder)){ 31 | fs.mkdirSync(profileFolder) 32 | } 33 | } catch (err) { 34 | console.error(err) 35 | } 36 | 37 | fs.writeFile(path.join(profileFolder, 'user.js'), profile, (err) => { 38 | if (err) return callback(err) 39 | 40 | callback(null, profileFolder) 41 | }) 42 | } 43 | -------------------------------------------------------------------------------- /gulp/lib/logger.js: -------------------------------------------------------------------------------- 1 | /* 2 | * Logger class for easy and aesthetically pleasing console logging 3 | */ 4 | 5 | const through2 = require('through2'), 6 | chalk = require("chalk"), 7 | cl = console.log, 8 | now = new Date().toLocaleTimeString('ru-UA', {hour12: false}), 9 | timestamp = chalk.gray(`[${now}]`); 10 | 11 | class Logger { 12 | static info (content, type = "info") { 13 | switch (type) { 14 | case "info": { 15 | return cl(`${timestamp} ${chalk.blue(type.toUpperCase())}: ${content}`); 16 | } 17 | case "warn": { 18 | return cl(`${timestamp} ${chalk.yellow(type.toUpperCase())}: ${content}`); 19 | } 20 | case "error": { 21 | return cl(`${timestamp} ${chalk.bgRed(type.toUpperCase())}: ${content}`); 22 | } 23 | case "debug": { 24 | return cl(`${timestamp} ${chalk.green(type.toUpperCase())}: ${JSON.stringify(content)}`); 25 | } 26 | case "cmd": { 27 | return cl(`${timestamp} ${chalk.black.bgWhite(type.toUpperCase())}: ${content}`); 28 | } 29 | case "ready": { 30 | return cl(`${timestamp} ${chalk.black.bgGreen(type.toUpperCase())}: ${content}`); 31 | } 32 | default: throw new TypeError("Logger type must be either warn, debug, log, ready, cmd or error."); 33 | } 34 | } 35 | 36 | static watch (content, type = "changed") { 37 | switch (type) { 38 | case "changed": { 39 | return cl(`${timestamp} ${chalk.yellow(content)} was ${chalk.yellow.underline(type.toUpperCase())} 📂`); 40 | } 41 | case "added": { 42 | return cl(`${timestamp} ${chalk.green(content)} was ${chalk.green.underline(type.toUpperCase())} ➕`); 43 | } 44 | case "removed": { 45 | return cl(`${timestamp} ${chalk.red(content)} was ${chalk.red.underline(type.toUpperCase())} ❌`); 46 | } 47 | default: throw new TypeError("Logger type must be either changed, added or removed."); 48 | } 49 | } 50 | 51 | static error (content) { 52 | return this.info(content, "error"); 53 | } 54 | 55 | static warn (content) { 56 | return this.info(content, "warn"); 57 | } 58 | 59 | static debug (content) { 60 | return this.info(content, "debug"); 61 | } 62 | 63 | static cmd (content) { 64 | return this.info(content, "cmd"); 65 | } 66 | 67 | static ready (content) { 68 | return this.info(content, "ready"); 69 | } 70 | } 71 | 72 | module.exports = Logger; 73 | 74 | // module.exports = () => { 75 | // return through2.obj((file, encoding, cb) => { 76 | // if (file.isNull()) { 77 | // // nothing to do 78 | // return cb(null, file); 79 | // } 80 | 81 | // if (file.isStream()) { 82 | // // file.contents is a Stream - https://nodejs.org/api/stream.html 83 | // this.emit('error', new TypeError('Streams not supported!') ); 84 | 85 | // // or, if you can handle Streams: 86 | // //file.contents = file.contents.pipe(... 87 | // //return cb(null, file); 88 | // } else if (file.isBuffer()) { 89 | // logger.debug(file.path); 90 | // // file.contents is a Buffer - https://nodejs.org/api/buffer.html 91 | // // this.emit('error', new TypeError('Buffers not supported!')); 92 | // // or, if you can handle Buffers: 93 | // cb(null, file); 94 | // } 95 | // }) 96 | // }; 97 | -------------------------------------------------------------------------------- /gulp/lib/print.js: -------------------------------------------------------------------------------- 1 | task('print', () => src(cfg.watch()) 2 | // .pipe(newer(cfg.dest())) 3 | .pipe(through2.obj((file, enc, cb) => { 4 | if (file.isBuffer()) { 5 | log.watch(file.path); 6 | } 7 | cb(null, file); 8 | }))); 9 | -------------------------------------------------------------------------------- /gulpfile-bk.js: -------------------------------------------------------------------------------- 1 | const gulp = require("gulp"), 2 | path = require("path"), 3 | del = require("del"), 4 | through2 = require('through2'), 5 | changed = require('gulp-changed'), 6 | size = require('gulp-size'), 7 | notify = require('gulp-notify'), 8 | debug = require('gulp-debug'), 9 | plumber = require('gulp-plumber'), 10 | prettyError = require('gulp-prettyerror'), 11 | log = require("./gulp/logger.js"); 12 | 13 | const { src, dest, task, parallel, series, watch } = gulp; 14 | 15 | const cfg = { 16 | profile: "/Users/art/Library/Application Support/Firefox/Profiles/hlq3pnw8.qwe", 17 | src: "chrome", 18 | ignore: "!**/.git", 19 | userJs: './user.js', 20 | ignoreTmp: ["!**/css/**", '!**/userChrome/**'], 21 | dest() { return path.join(this.profile, this.src) }, 22 | watch() { return `${this.src}/scripts/**` } 23 | }; 24 | 25 | task('sync', () => { 26 | return src(`${cfg.src}/**`) 27 | .pipe(changed(cfg.dest())) 28 | .pipe(prettyError()) 29 | .pipe(dest(cfg.dest())) 30 | }); 31 | 32 | task('userJs', () => { 33 | src(cfg.userJs) 34 | .pipe(prettyError()) 35 | .pipe(dest(cfg.profile)) 36 | }); 37 | 38 | task('watch-chrome', () => { 39 | const watcher = watch([`${cfg.src}/**`, ...cfg.ignoreTmp], series('sync')); 40 | 41 | watcher 42 | .on('add', filepath => log.watch(filepath, 'added')) 43 | .on('change', filepath => log.watch(filepath, 'changed')) 44 | .on('unlink', filepath => { 45 | const filePathFromSrc = path.relative(path.resolve(cfg.src), filepath); 46 | const destFilePath = path.resolve(cfg.dest(), filePathFromSrc); 47 | del.sync(destFilePath, {force: true}); 48 | log.watch(filePathFromSrc, 'removed'); 49 | }) 50 | .on('error', error => log.error(`Watcher error: ${error}`)); 51 | }); 52 | 53 | task('watch-user', () => { 54 | const watcher = watch(cfg.userJs, series('userJs')); 55 | 56 | watcher 57 | .on('add', filepath => log.watch(filepath, 'added')) 58 | .on('change', filepath => log.watch(filepath, 'changed')) 59 | .on('unlink', filepath => { 60 | const filePathFromSrc = path.relative(path.resolve(cfg.src), filepath); 61 | const destFilePath = path.resolve(cfg.dest(), filePathFromSrc); 62 | del.sync(destFilePath, {force: true}); 63 | log.watch(filePathFromSrc, 'removed'); 64 | }) 65 | .on('error', error => log.error(`Watcher error: ${error}`)); 66 | }); 67 | 68 | task('watch', parallel('watch-user', 'watch-chrome')); 69 | task('default', series('watch')); 70 | 71 | task('watch-test', () => { 72 | return src('./gulp/**') 73 | .pipe(prettyError()) 74 | 75 | }); 76 | 77 | 78 | // task("default", () => { 79 | // const s = size(); 80 | 81 | // return src(cfg.src.path) 82 | // .pipe(s) 83 | // .pipe(gulp.dest('dist')) 84 | // .pipe(notify({ 85 | // onLast: true, 86 | // message: () => `Total size ${s.prettySize}` 87 | // })); 88 | // }); 89 | -------------------------------------------------------------------------------- /gulpfile.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp'; 2 | import { clean, scripts, styles, manifest, watch, bundle } from './tasks'; 3 | 4 | const { task, parallel, series } = gulp; 5 | 6 | task('build', series(clean, parallel(scripts, styles, manifest))); 7 | task('dev', series('build', watch)); 8 | task('bundle', series('build', bundle)); 9 | -------------------------------------------------------------------------------- /nodemon.json: -------------------------------------------------------------------------------- 1 | { 2 | "restartable": "rs", 3 | "ignore": [ 4 | ".git", 5 | "node_modules/**/node_modules", 6 | "chrome/userChrome", 7 | "custom", 8 | "./user.js" 9 | ], 10 | "verbose": false, 11 | "execMap": { 12 | "js": "node --harmony" 13 | }, 14 | "watch": [ 15 | "chrome/scripts", 16 | "gulp/" 17 | ], 18 | "env": { 19 | "NODE_ENV": "development" 20 | }, 21 | "ext": "js json" 22 | } 23 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "firefox-scripts", 3 | "description": "Custom tweaks and preferences for Firefox", 4 | "version": "0.1.0", 5 | "repository": { 6 | "type": "git", 7 | "url": "git+https://github.com/dotiful/firefox-scripts.git" 8 | }, 9 | "keywords": [], 10 | "author": { 11 | "name": "Art Dev", 12 | "email": "artdevjs@gmail.com", 13 | "url": "https://github.com/dotiful" 14 | }, 15 | "license": "MIT", 16 | "bugs": { 17 | "url": "https://github.com/dotiful/firefox-scripts/issues" 18 | }, 19 | "homepage": "https://github.com/dotiful/firefox-scripts#readme", 20 | "devDependencies": { 21 | "@babel/core": "^7.14.6", 22 | "@babel/preset-env": "^7.14.7", 23 | "@babel/register": "^7.14.5", 24 | "@commitlint/cli": "^12.1.4", 25 | "@commitlint/config-conventional": "^12.1.4", 26 | "chalk": "^4.1.1", 27 | "cz-conventional-changelog": "^3.3.0", 28 | "del": "^6.0.0", 29 | "eslint": "^7.30.0", 30 | "eslint-config-airbnb-base": "^14.2.1", 31 | "eslint-config-prettier": "^8.3.0", 32 | "eslint-config-standard": "^16.0.3", 33 | "eslint-plugin-import": "^2.23.4", 34 | "eslint-plugin-json": "^3.0.0", 35 | "eslint-plugin-node": "^11.1.0", 36 | "eslint-plugin-prettier": "^3.4.0", 37 | "eslint-plugin-promise": "^5.1.0", 38 | "eslint-plugin-standard": "^5.0.0", 39 | "firefox-profile": "^4.2.0", 40 | "gulp": "^4.0.2", 41 | "gulp-changed": "^4.0.3", 42 | "gulp-debug": "^4.0.0", 43 | "gulp-notify": "^4.0.0", 44 | "gulp-plumber": "^1.2.1", 45 | "gulp-prettyerror": "^2.0.0", 46 | "gulp-size": "^4.0.1", 47 | "husky": "^7.0.1", 48 | "lint-staged": "^11.0.0", 49 | "markdownlint-cli": "^0.27.1", 50 | "node-notifier": ">=10.0.0", 51 | "nodemon": "^2.0.12", 52 | "npm-run-all": "^4.1.5", 53 | "prettier": "^2.3.2", 54 | "prettier-plugin-packagejson": "^2.2.11", 55 | "stylelint": "^13.13.1", 56 | "stylelint-config-stylishthemes": "^1.0.1", 57 | "through2": "^4.0.2", 58 | "yarn": "^1.22.10" 59 | }, 60 | "scripts": { 61 | "format": "prettier --write '**/*.js'", 62 | "lint": "npm-run-all --silent lint:*", 63 | "lint:markdown": "markdownlint --config .markdownlint.json README.md", 64 | "commit": "commitlint -E HUSKY_GIT_PARAMS", 65 | "cm": "npx git-cz", 66 | "release": "npx standard-version", 67 | "eslint-find-option-rules": "eslint-find-rules [option] [flag]" 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addonlists_compact-min.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | @-moz-document url-prefix(chrome://mozapps/content/extensions/extensions.xul), url-prefix(about:addons) { 6 | .addon.card { 7 | /* max-width: 950px !important; */ 8 | padding: 4px !important; 9 | padding-right: 6px !important; 10 | padding-left: 11px !important; 11 | margin: -1px !important; 12 | margin-top: 4px !important; 13 | font-size: 15px !important; 14 | /* font-family: Arial !important; */ 15 | border-radius: 7px !important; 16 | } 17 | } -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addonlists_compact.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | @-moz-document url-prefix(chrome://mozapps/content/extensions/extensions.xul), url-prefix(about:addons) { 6 | 7 | /* dimensions / positioning */ 8 | #addons-page .main-content{ 9 | padding: 0 !important; 10 | margin: 0 !important; 11 | } 12 | 13 | #addons-page #header-search .textbox-input-box{ 14 | height: 18px !important; 15 | } 16 | 17 | #addons-page #addon-list { 18 | -moz-margin-start: -1px !important; 19 | } 20 | 21 | #addons-page:not(.inSidebar):not([aios-inSidebar="true"]) .view-pane > .list > scrollbox { 22 | padding-right: 0 !important; 23 | padding-left: 0 !important; 24 | } 25 | 26 | #addons-page #detail-view, 27 | #addons-page #userstyle-sorting, 28 | #addons-page .global-warning-container, 29 | #addons-page .global-info-container{ 30 | -moz-margin-start: 0px !important; 31 | -moz-margin-end: 1px !important; 32 | } 33 | 34 | #addons-page .detail-view-container { 35 | -moz-margin-start: 10px !important; 36 | } 37 | 38 | #addons-page #view-port{ 39 | -moz-margin-end: 4px !important; 40 | } 41 | 42 | #addons-page #header{ 43 | padding: 2px 0 !important; 44 | margin: 0 !important; 45 | } 46 | 47 | /* buttons / menulists */ 48 | #addons-page #header button, 49 | #addons-page #header #header-utils-btn, 50 | #addons-page #list-view .global-info button, 51 | #addons-page #list-view .discover-button, 52 | #addons-page .status-control-wrapper button, 53 | #addons-page #userstyle-sorting button, 54 | #addons-page #update-actions button, 55 | #addons-page #updates-list-empty button, 56 | #addons-page .relnotes-toggle, 57 | #list-view menulist{ 58 | padding: 2px !important; 59 | min-height: unset !important; 60 | height: unset !important; 61 | } 62 | 63 | #addons-page #header-utils-btn{ 64 | padding: 2px !important; 65 | height: unset !important; 66 | } 67 | 68 | #addons-page button.sorter{ 69 | padding:2px !important; 70 | min-height: 26px !important; 71 | height: unset !important; 72 | } 73 | 74 | #addons-page #header-search{ 75 | padding: 1px !important; 76 | min-height: unset !important; 77 | height: unset !important; 78 | } 79 | 80 | button.addon-control image{ 81 | margin-top: -1.5px !important; 82 | margin-bottom: -1.5px !important; 83 | } 84 | 85 | /* detail view */ 86 | #detail-view button:not(.button-link):not(.text-link), 87 | #detail-view menulist{ 88 | padding:2px !important; 89 | height: unset !important; 90 | /*font-size: 90% !important;*/ 91 | background-image: linear-gradient(to bottom, rgba(255,255,255,0.15), rgba(255,255,255,0.20),rgba(0,0,0,0.01)) !important; 92 | } 93 | 94 | #detail-view colorpicker[type="button"]{ 95 | padding:2px !important; 96 | min-height: 26px !important; 97 | min-width: 40px !important; 98 | height:auto !important; 99 | width: auto !important; 100 | } 101 | 102 | /* checkbox and radio items */ 103 | #addons-page checkbox image, 104 | #addons-page radio image { 105 | width: 16px !important; 106 | height: 16px !important; 107 | margin: 0 !important; 108 | } 109 | 110 | /********************/ 111 | .addon .warning, 112 | .addon .error, 113 | .addon .pending, 114 | .addon .icon-container { 115 | padding: unset !important; 116 | margin: unset !important; 117 | min-width: unset !important; 118 | width: unset !important; 119 | min-height: unset !important; 120 | height: unset !important; 121 | } 122 | 123 | .addon .icon { 124 | min-width: unset !important; 125 | min-height: unset !important; 126 | width: 21px !important; 127 | height: 21px !important; 128 | } 129 | 130 | .addon .warning-icon, 131 | .addon .error-icon, 132 | .addon .pending-icon { 133 | width: 14px !important; 134 | height: 14px !important; 135 | -moz-margin-start: 4px !important; 136 | } 137 | 138 | .addon .content-inner-container{ 139 | -moz-box-orient: horizontal !important; 140 | } 141 | #updates-list .addon .content-inner-container{ 142 | -moz-box-orient: vertical !important; 143 | } 144 | 145 | .addon .name-container .name, 146 | .addon .name-container .version, 147 | .addon .name-container .disabled-postfix, 148 | .addon .name-container .update-postfix, 149 | .addon .name-container .legacy-warning { 150 | -moz-margin-start: 4px !important; 151 | -moz-margin-end: 0 !important; 152 | } 153 | 154 | .addon .update-available button, 155 | .addon .control-container button, 156 | .addon .control-container menulist { 157 | margin-top: 1px !important; 158 | margin-bottom: 1px !important; 159 | -moz-margin-start: 1px !important; 160 | -moz-margin-end: 0px !important; 161 | } 162 | 163 | .addon .warning .button-box, 164 | .addon .pending .button-box, 165 | .addon .content-inner-container, 166 | .addon .description-container .button-link, 167 | .addon .update-available .button-box, 168 | .addon .control-container .button-box, 169 | .addon .control-container menulist .menulist-label-box { 170 | padding: unset !important; 171 | margin: unset !important; 172 | } 173 | 174 | .addon .experiment-container { 175 | display: none !important; 176 | } 177 | 178 | .description-container spacer { 179 | display: none !important; 180 | } 181 | 182 | .description-container .button-link .button-box { 183 | -moz-padding-start: 0px !important; 184 | -moz-padding-end: 2px !important; 185 | } 186 | 187 | #addons-page .addon .name-container .legacy-warning, 188 | #addons-page #addon-list .name-container .legacy-warning { 189 | padding: 0 2px !important; 190 | margin: 2px !important; 191 | } 192 | 193 | .alert .alert-title { 194 | font-size: 160% !important; 195 | } 196 | 197 | .discover-title { 198 | font-size: 18px !important; 199 | } 200 | 201 | .name-container { 202 | font-size: 1.1rem !important; 203 | } 204 | 205 | .legacy-warning { 206 | font-size: 0.7rem !important; 207 | } 208 | 209 | .description, 210 | .description-container { 211 | font-size: 1.05rem !important; 212 | } 213 | 214 | .addon[status="uninstalled"] > .container { 215 | font-size: 100% !important; 216 | } 217 | 218 | .detail-view-container { 219 | font-size: 1.05rem !important; 220 | } 221 | 222 | #detail-name-container { 223 | font-size: 2.2rem !important; 224 | } 225 | 226 | .preferences-description { 227 | font-size: 80.9% !important; 228 | } 229 | 230 | #detail-experiment-container { 231 | font-size: 70% !important; 232 | } 233 | 234 | #disabled-unsigned-addons-heading, 235 | #legacy-extensions-heading { 236 | font-size: 1.1em !important; 237 | } 238 | 239 | :root > * { 240 | font-size: 1.15em !important; 241 | } 242 | 243 | #addons-page .addon { 244 | padding: 5px 4px !important; 245 | } 246 | 247 | #addons-page .addon .icon, 248 | #addons-page .addon:not([pending="uninstall"])[status="installed"] .icon { 249 | min-width: unset !important; 250 | min-height: unset !important; 251 | margin: 0 !important; 252 | padding: 0 !important; 253 | } 254 | 255 | #addons-page .addon .description-container { 256 | margin-inline-start: 5px !important; 257 | } 258 | } -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addonlists_disabled_grayscale_fx67.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | @namespace html "http://www.w3.org/1999/xhtml"; 6 | @namespace xul "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"; 7 | 8 | #main addon-list .list-section-heading[data-l10n-id="addons-disabled-heading"] ~ addon-card { 9 | filter: grayscale(1); 10 | } -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addonlists_private_browsing_notice_hidden.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | /* old version */ 6 | /* user_pref(“extensions.htmlaboutaddons.enabled”,false); */ 7 | @-moz-document url(about:addons) { 8 | #addons-page #private-browsing-notice, 9 | #addons-page .privateBrowsing-notice { 10 | display: none !important; 11 | } 12 | } 13 | 14 | /* new version */ 15 | /* user_pref(“extensions.htmlaboutaddons.enabled”,true); */ 16 | @namespace html "http://www.w3.org/1999/xhtml"; 17 | @namespace xul "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"; 18 | 19 | .addon-badge-private-browsing-allowed { 20 | display: none !important; 21 | } 22 | 23 | -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addonlists_replace_button_labels_with_icons.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | 6 | @-moz-document url-prefix(chrome://mozapps/content/extensions/extensions.xul), url-prefix(about:addons) { 7 | button[anonid="preferences-btn"].addon-control image { 8 | list-style-image: url("chrome://browser/skin/settings.svg"); 9 | } 10 | button[anonid="install-remote-btn"].addon-control image, 11 | button[anonid="enable-btn"].addon-control image { 12 | list-style-image: url("chrome://browser/skin/zoom-in.svg"); 13 | } 14 | button[anonid="disable-btn"].addon-control image { 15 | list-style-image: url("chrome://browser/skin/zoom-out.svg"); 16 | } 17 | button[anonid="remove-btn"].addon-control image { 18 | list-style-image: url("chrome://browser/skin/stop.svg"); 19 | } 20 | button[anonid="update-btn"].addon-control image { 21 | list-style-image: url("chrome://browser/skin/chevron.svg"); 22 | transform: rotate(-90deg); 23 | } 24 | 25 | button[anonid].addon-control { 26 | /* min-width: unset !important; */ 27 | background-color: var(--grey-60); 28 | color: var(--grey-10); 29 | padding: 6px !important; 30 | -moz-context-properties: fill; 31 | fill: currentColor; 32 | } 33 | 34 | button[anonid="install-remote-btn"].addon-control label, 35 | button[anonid="preferences-btn"].addon-control label, 36 | button[anonid="enable-btn"].addon-control label, 37 | button[anonid="disable-btn"].addon-control label, 38 | button[anonid="remove-btn"].addon-control label, 39 | button[anonid="update-btn"].addon-control label { 40 | visibility: collapse; 41 | } 42 | 43 | button.addon-control image { 44 | display: block !important; 45 | } 46 | 47 | } -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addonlists_show_buttons_inline.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | @-moz-document url-prefix(chrome://mozapps/content/extensions/aboutaddons.html) { 6 | #main addon-list .more-options-menu panel-list { 7 | position: relative !important; 8 | background: unset !important; 9 | border: unset !important; 10 | box-shadow: unset !important; 11 | display: block !important; 12 | margin-top: -26px !important; 13 | min-width: unset !important; 14 | visibility: visible !important; 15 | width: unset !important; 16 | text-align: right; 17 | -moz-appearance: none !important; 18 | -moz-margin-start: -310px !important; 19 | } 20 | 21 | #main addon-list .more-options-menu, 22 | #main addon-list .arrow { 23 | visibility: hidden !important; 24 | } 25 | 26 | #main addon-list .more-options-menu panel-list *:not([hidden]) { 27 | display: inline-grid !important; 28 | visibility: visible !important; 29 | -moz-box-orient: horizontal !important; 30 | -moz-appearance: none !important; 31 | min-width: unset !important; 32 | width: unset !important; 33 | padding: 0 !important; 34 | margin: 0 !important; 35 | } 36 | 37 | #main addon-list .more-options-menu panel-item { 38 | /* padding: 2px 5px !important; */ 39 | border: 1px solid lightgrey !important; 40 | --icon: unset !important; 41 | } 42 | 43 | #main addon-list .more-options-menu panel-item[data-l10n-id="expand-addon-button"] { 44 | display: none !important; 45 | } 46 | } -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addonlists_show_buttons_inline_fx69.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | 6 | @-moz-document url-prefix(chrome://mozapps/content/extensions/aboutaddons.html) { 7 | #main addon-list .more-options-menu panel-item[data-l10n-id="enable-addon-button"] { 8 | --icon: url("chrome://browser/skin/zoom-out.svg") !important; 9 | } 10 | 11 | #main addon-list .more-options-menu panel-item[data-l10n-id="disable-addon-button"] { 12 | --icon: url("chrome://browser/skin/zoom-in.svg") !important; 13 | } 14 | 15 | #main addon-list .more-options-menu panel-item[data-l10n-id="install-update-button"] { 16 | --icon: url("chrome://browser/skin/chevron.svg") !important; 17 | } 18 | 19 | #main addon-list .more-options-menu panel-item[data-l10n-id="preferences-addon-button"] { 20 | --icon: url("chrome://browser/skin/settings.svg") !important; 21 | } 22 | } -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addons_manager_full_width.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | @-moz-document url-prefix(chrome://mozapps/content/extensions/extensions.xul), url-prefix(about:addons) { 6 | #header-inner { 7 | width: calc(100vw - 268px) !important; 8 | } 9 | 10 | #heading .heading-inner { 11 | -moz-box-flex: 1 !important; 12 | width: unset !important; 13 | margin-inline-end: var(--addons_manager_full_width_gutter) !important; 14 | } 15 | 16 | .addon.card { 17 | max-width: unset !important; 18 | } 19 | 20 | #detail-view .detail-view-container { 21 | width: calc(100vw - 298px) !important; 22 | } 23 | 24 | .addon .control-container { 25 | -moz-box-pack: end; 26 | -moz-box-ordinal-group: 9 !important; 27 | } 28 | 29 | .addon .status-container { 30 | -moz-box-ordinal-group: 10 !important; 31 | } 32 | 33 | .addon .update-available { 34 | -moz-box-orient: horizontal; 35 | -moz-box-align: center; 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/addons_manager_full_width_fx67.css: -------------------------------------------------------------------------------- 1 | @import "./addons_manager_full_width.css"; 2 | 3 | @namespace html "http://www.w3.org/1999/xhtml"; 4 | @namespace xul "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"; 5 | 6 | body > #main { 7 | max-width: unset !important; 8 | margin-inline-end: var(--addons_manager_full_width_gutter) !important; 9 | /* margin-inline-start: var(--addons_manager_full_width_gutter) !important; */ 10 | /* margin-bottom: var(--addons_manager_full_width_gutter) !important; */ 11 | /* padding-inline-start: var(--addons_manager_full_width_gutter) !important; */ 12 | /* padding-inline-end: var(--addons_manager_full_width_gutter) !important; */ 13 | } 14 | 15 | .list-view-heading-inner { 16 | -moz-box-flex: 1 !important; 17 | width: unset !important; 18 | } 19 | 20 | /* 21 | 22 | body > div#main > div.list-section .addon.card { 23 | margin-bottom: 4px !important; 24 | }*/ 25 | -------------------------------------------------------------------------------- /src/chrome/css/aboutaddons/details_page_alternative_content_order.css: -------------------------------------------------------------------------------- 1 | /* Firefox Quantum userChrome.css tweaks ************************************************/ 2 | /* Github: https://github.com/aris-t2/customcssforfx ************************************/ 3 | /****************************************************************************************/ 4 | 5 | @-moz-document url-prefix(chrome://mozapps/content/extensions/extensions.xul), url-prefix(about:addons) { 6 | 7 | .card.addon-detail vbox { 8 | position: relative; 9 | } 10 | 11 | #detail-controls { 12 | position: absolute; 13 | right: 0; 14 | top: 8px; 15 | } 16 | 17 | #detail-contributions { 18 | -moz-box-ordinal-group: 10 !important; 19 | } 20 | 21 | #detail-desc-container { 22 | -moz-box-ordinal-group: 11 !important; 23 | } 24 | } -------------------------------------------------------------------------------- /src/chrome/css/picture-in-picture.css: -------------------------------------------------------------------------------- 1 | 2 | 3 | @-moz-document url(chrome://global/content/pictureinpicture/player.xhtml){ 4 | #close{ opacity: 1 !important; } 5 | } 6 | 7 | @-moz-document url(chrome://global/content/pictureinpicture/player.xhtml){ 8 | html|div#close{ opacity: 1 !important; } 9 | } 10 | -------------------------------------------------------------------------------- /src/chrome/css/variables.css: -------------------------------------------------------------------------------- 1 | 2 | :root { 3 | /* 4 | * ─── SIZES ───────────────────────────────────────────────────────────────── 5 | */ 6 | --addons_manager_full_width_gutter: 28px; 7 | 8 | /* 9 | * ─── COLORS ──────────────────────────────────────────────────────────────── 10 | * Photon Colors CSS Variables v3.2.0 11 | * https://firefoxux.github.io/design-tokens/photon-colors/photon-colors.css 12 | */ 13 | 14 | --magenta-50: #ff1ad9; 15 | --magenta-60: #ed00b5; 16 | --magenta-70: #b5007f; 17 | --magenta-80: #7d004f; 18 | --magenta-90: #440027; 19 | 20 | --purple-30: #c069ff; 21 | --purple-40: #ad3bff; 22 | --purple-50: #9400ff; 23 | --purple-60: #8000d7; 24 | --purple-70: #6200a4; 25 | --purple-80: #440071; 26 | --purple-90: #25003e; 27 | 28 | --blue-40: #45a1ff; 29 | --blue-50: #0a84ff; 30 | --blue-50-a30: rgba(10, 132, 255, 0.3); 31 | --blue-60: #0060df; 32 | --blue-70: #003eaa; 33 | --blue-80: #002275; 34 | --blue-90: #000f40; 35 | 36 | --teal-50: #00feff; 37 | --teal-60: #00c8d7; 38 | --teal-70: #008ea4; 39 | --teal-80: #005a71; 40 | --teal-90: #002d3e; 41 | 42 | --green-50: #30e60b; 43 | --green-60: #12bc00; 44 | --green-70: #058b00; 45 | --green-80: #006504; 46 | --green-90: #003706; 47 | 48 | --yellow-50: #ffe900; 49 | --yellow-60: #d7b600; 50 | --yellow-70: #a47f00; 51 | --yellow-80: #715100; 52 | --yellow-90: #3e2800; 53 | 54 | --red-50: #ff0039; 55 | --red-60: #d70022; 56 | --red-70: #a4000f; 57 | --red-80: #5a0002; 58 | --red-90: #3e0200; 59 | 60 | --orange-50: #ff9400; 61 | --orange-60: #d76e00; 62 | --orange-70: #a44900; 63 | --orange-80: #712b00; 64 | --orange-90: #3e1300; 65 | 66 | --grey-10: #f9f9fa; 67 | --grey-10-a10: rgba(249, 249, 250, 0.1); 68 | --grey-10-a20: rgba(249, 249, 250, 0.2); 69 | --grey-10-a40: rgba(249, 249, 250, 0.4); 70 | --grey-10-a60: rgba(249, 249, 250, 0.6); 71 | --grey-10-a80: rgba(249, 249, 250, 0.8); 72 | --grey-20: #ededf0; 73 | --grey-30: #d7d7db; 74 | --grey-40: #b1b1b3; 75 | --grey-50: #737373; 76 | --grey-60: #4a4a4f; 77 | --grey-70: #38383d; 78 | --grey-80: #2a2a2e; 79 | --grey-90: #0c0c0d; 80 | --grey-90-a05: rgba(12, 12, 13, 0.05); 81 | --grey-90-a10: rgba(12, 12, 13, 0.1); 82 | --grey-90-a20: rgba(12, 12, 13, 0.2); 83 | --grey-90-a30: rgba(12, 12, 13, 0.3); 84 | --grey-90-a40: rgba(12, 12, 13, 0.4); 85 | --grey-90-a50: rgba(12, 12, 13, 0.5); 86 | --grey-90-a60: rgba(12, 12, 13, 0.6); 87 | --grey-90-a70: rgba(12, 12, 13, 0.7); 88 | --grey-90-a80: rgba(12, 12, 13, 0.8); 89 | --grey-90-a90: rgba(12, 12, 13, 0.9); 90 | 91 | --ink-70: #363959; 92 | --ink-80: #202340; 93 | --ink-90: #0f1126; 94 | 95 | --white-100: #ffffff; 96 | 97 | } 98 | 99 | -------------------------------------------------------------------------------- /src/chrome/scripts/ContextTranslate.uc.js: -------------------------------------------------------------------------------- 1 | // ContextTranslate.uc.js 2 | 3 | (function () { 4 | if (location != 'chrome://browser/content/browser.xul') 5 | return; 6 | let translate = function () { 7 | let browserMM = gBrowser.selectedBrowser.messageManager; 8 | browserMM.addMessageListener('getSelection', function listener(message) { 9 | let t = (message.data !== ''); 10 | let e = (document.charset || document.characterSet); 11 | if (t) { 12 | openWebLinkIn('https://translate.google.com/#view=home&op=translate&sl=auto&tl=en&text=' + encodeURIComponent(message.data), 'tab'); 13 | } else { 14 | openWebLinkIn('https://translate.google.com/translate?u=' + encodeURIComponent(gBrowser.currentURI.spec) + '&hl=en-US&ie=' + e + '&sl=auto&tl=de-DE', 'tab'); 15 | }; 16 | browserMM.removeMessageListener('getSelection', listener, true); 17 | }); 18 | browserMM.loadFrameScript('data:,sendAsyncMessage("getSelection", content.document.getSelection().toString())', true); 19 | } 20 | let menuitem = document.createElement('menuitem'); 21 | menuitem.id = 'context-googletranslate'; 22 | menuitem.setAttribute('label', 'Translate Selection in New Tab'); 23 | menuitem.setAttribute('tooltiptext', 'Translate with GoogleTranslate'); 24 | menuitem.setAttribute('oncommand', '(' + translate.toString() + ')()'); 25 | menuitem.classList.add('menuitem-iconic'); 26 | //Wer kein Icon möchte kann die nächsten beiden Zeilen auskommentieren/löschen 27 | //menuitem.style.listStyleImage = 'url("https://translate.google.com/favicon.ico")'; 28 | menuitem.style.listStyleImage = ' url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADIAAAAwCAYAAABT9ym6AAAAAXNSR0IArs4c6QAAAARnQU1BAACxjwv8YQUAAAAJcEhZcwAAEnQAABJ0Ad5mH3gAAAAZdEVYdFNvZnR3YXJlAHBhaW50Lm5ldCA0LjAuMjHxIGmVAAAHYklEQVRoQ+2Y6U+UVxSH9Xs/NGnSv6et1h1REWOrUEaomiZt2tQqRQFFcNiRImg1rnVBbZUoorhRYNhGZweGfYcBoQ6bn0/Pue+9w7vcGRhpRz94kidDDHn5PZ5z7tyZFR/qfS4AWGkq9ZtiimZGY4vfQOzJBbZzYjjbioxsLVTYwvnu1MRH/NGRrfiSKRMT4IjwGgGBWoAjBKI5URn92/ijI1sxhbwTOhEhIRMREjKRjVnjtfzRkS2ZhLQbxBJEogvewDfpjo/54yNX6vB6icVEhIReZMOR7h388ZGrcCVkIgEJLvJOxksmEEpESIQSeSfjtagAwSVk3dCIcAnWlcN9sfxPRKZCChASicW6sRkxlb4Gm70LenuHYWTUBz6fD8bHx9mrYGxsjDE6OmpgZGQkwPDw8Fh//9BXPLK8pOEFXCCYRLBukAhx+6Eb2r19GIaCj8PExASTEeiF1Mjkurp6vuaxjbWYwJIkCJ0EcfyPPmhsckJ3zwCG04rIOrOYyMDAwDCPbSx9aD0U3vT7PFyvm4XW/mmYnPLD1D9+aMefr9fPQsKZeWk3iPiSSairt4Pd3gpDw6PSboQjQvDYxpKFJ0QHcu7NwcTUNPj9finjk344envOIBGVr0Dj1WJ1Q2urF2d9ZFkitC88trFEYBkk8VoVumNwGu5ZZxn0M/1b56Af9mDH1CJCgqDxsjQ4wOlqBa+3kwWKqAiNk+gEjVJh5axmL+jn/HuzEF+mlVCLbELifhPj5YG29g5c2C4WKJQEsSwR9SJfw50QnSh9hKOD/6YBAwtkEkKEuF1F4+UCj6cdOjo6mQweqWF1gwgpog6vhhabJAZ800zybSWIwHg5lfHq7OyE7u5uJvO/ilBYOp1I5LlrxiAgOqXnsWPGILEpTxmv2jo72GzKeHV0KCOWmJoDSUcLlyRCEiFFAiF1aES4wGIiNe4Zg4TgVpUrMF5e74LIntRcTWdkEsRbi3j6lNEaFKPFJWiECu7PBjhdvbBLd5pmg4psPfwMdh/IgfhkM5gOZ8OeIwSKIIko8+2xAtibUYSvCyQdKwxDhAfUc7V2IWBZ9ZxmFwQ0RmefLPyeuWJOKrERicoahDgUSUhGAexEYmo2JKblQhKRjiJH85iMWkKICIm3EqFjdfyVEpCO3+Iq5eQSAgQFFyM4OObHN9J5qYTg1gMXNLe4wO1uC4wXQYtP5J67ijtTAPee1gU68VYi+v/xrDvaN8SuoWmofDED960z0D6gfbc/jr8bSmJD7jxkXOmDeosNXtpc0Nbm1YjYXW7sTD52Jh+8Xd1SiZAi+vB6SMbHOyPjFXakEHdFLSCTIHYVT8KveRcg/qAZii/fCpxeJFJy5SZb/KKL5Xj172UHwLJFxOgIdpfOw5W/Z8HdO43BlYtjG3akvH4GEs9qBYJJEOuRszcbIe5gDphSsqGmoZmJ1DZZ2cJTR6w2B/T09EBfXx8MDQ0tXUQfOhiBJVbDgy9Vgjh2pRdyym5A3KETcCCnDOxONxzIPcVOr3PlFUyCoK4Qehke21iy0AJpeAEPLhMIJkHsKp6Cp8+t8GNmCSTgMbz/WD6YUOJQwWnowHd8ISJk1J2hceOxjSUNGQwMKGOpEoycebiJp9eDJxZISMHjGEcsMS0PrC/tbFdIQLwKkf7+fiazPBEMFoxQAsEkiPSLPZBedBHHy8xEEvDNsfhyOduXYCLE4OBgCBEMEC56gXAkiGjzCOz8yQyJKXlwreIh7GPjlQ0nL5XjhVI5xWQiBI9tLFlQGbLwRDgCxDrOVwfPQcWDWnb3el7fjDIFbFcKL9xgMv+JiCywHr1AOBLEgTPteLW3g4Nf7Z9bmnDxC5lM3vnrbMyEiCCkiCxkMGThCYMAwcPLJNZmY0eKpvBqbwtc7ekzSg3K7MsoYDuTe/6apiuLiqw74ffJQhOy0GrCFRASgvJKJzQ1OzWfHGsszbAXrymX/rwfEFGPGI9trA0nxuJkIYMhDU9gyHAk1iDpl3rx7mUHp4sukYoILTrdu8TC63eFx5bX6pTepDWZU7712dMgY10ozEbWmv0a1pzQ8iVnZ8E41NU7wGb3aETEq+z04pEjU7+kPsv8fEsFEJ9F39WymRN1Fw5lVIOl0QEOBy38wrVe8M5F9v/816dfxFSChm0qtlZCatYzdmpZX9DHXy/bEVp4EhCvehGC/4nIVcL31ZOrdlQBI1bF9ipIy6mBxiYHXktc4HK1ss8mdKUnAYFeRMjwx0eu0rJrU1djcA0ocTS7BhoabWC10kjRV6nKlxEUXi2jFlF3hT8+cpWc/OST1bEPUUBhVUwVpKNEY5MdXrxwMglPaxu0tyvdEOhF9OPFHx/ZSvjh8SSNEkmkqTpht+Pndg+NFHXDy9CL6LtCIti5Mf7oyFZK5rNU0QlLw0toaaHvgHEv3B4cqTYUoY4oMmoR8aoXefS4ycQfHdmi8UozP4Ha2mawWFpQ5CW+Z9BuOHHJ6dsUHC8PSbUaUEvi7/uqHjXswUeuVJ78od7HWrHiXwQB769LvTEjAAAAAElFTkSuQmCC")'; 29 | let refItem = document.getElementById('context-inspect'); 30 | refItem.parentNode.insertBefore(menuitem, refItem); 31 | })(); 32 | -------------------------------------------------------------------------------- /src/chrome/scripts/about-config-copy-userpref.uc.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name About:config Multiple Selection 3 | // @version 0.3 4 | // @description Allow multiple selection on about:config and more 5 | // @namespace https://github.com/nightson/ 6 | // @author NightsoN 7 | // @include chrome://browser/content/browser.xul 8 | // @note 0.3 add "Copy as Function" to the contextmenu. Now you can copy config entries in user_pref(xxx, xxx); format to be used in user.js 9 | // ==/UserScript== 10 | 11 | window.addEventListener('DOMContentLoaded', function (event) { 12 | var doc = event.target, 13 | win; 14 | if (!doc || !doc.location.href.startsWith('about:config')) return; 15 | doc.getElementById('configTree').setAttribute('seltype', 'multiple'); 16 | win = doc.defaultView; 17 | 18 | var contextMenu = doc.getElementById('configContext'), 19 | menuitem = contextMenu.insertBefore(doc.createElement('menuitem'), doc.getElementById('copyValue').nextSibling); 20 | menuitem.id = 'copyAsFunction'; 21 | menuitem.setAttribute('label', 'Copy for user.js'); 22 | menuitem.setAttribute('accesskey', 'K'); 23 | menuitem.setAttribute('oncommand', 'copyAsFunction();'); 24 | 25 | const gClipboardHelper = Cc["@mozilla.org/widget/clipboardhelper;1"].getService(Ci.nsIClipboardHelper); 26 | 27 | win.getSelected = function () { 28 | var arr = [], 29 | i = 0, 30 | k = 0, 31 | j = win.view.selection.getRangeCount(), 32 | start = {}, 33 | end = {}; 34 | for (i; i < j; i++) { 35 | win.view.selection.getRangeAt(i, start, end); 36 | for (k = start.value; k <= end.value; k++) { 37 | arr.push(win.gPrefView[k]); 38 | } 39 | } 40 | return arr; 41 | } 42 | 43 | win.ResetSelected = function () { 44 | win.getSelected().forEach(function (i) { 45 | Services.prefs.clearUserPref(i.prefCol); 46 | }) 47 | } 48 | 49 | win.copyPref = function () { 50 | var arr = []; 51 | win.getSelected().forEach(function (i) { 52 | arr.push(i.prefCol + ';' + i.valueCol); 53 | }); 54 | gClipboardHelper.copyString(arr.join('\n')); 55 | } 56 | 57 | win.copyName = function () { 58 | var arr = []; 59 | win.getSelected().forEach(function (i) { 60 | arr.push(i.prefCol); 61 | }); 62 | gClipboardHelper.copyString(arr.join('\n')); 63 | } 64 | 65 | win.copyValue = function () { 66 | var arr = []; 67 | win.getSelected().forEach(function (i) { 68 | arr.push(i.valueCol); 69 | }); 70 | gClipboardHelper.copyString(arr.join('\n')); 71 | } 72 | 73 | win.copyAsFunction = function () { 74 | var arr = []; 75 | win.getSelected().forEach(function (i) { 76 | if (i.typeCol === 32) { 77 | arr.push('user_pref("' + i.prefCol + '", "' + i.valueCol + '");'); 78 | } else { 79 | arr.push('user_pref("' + i.prefCol + '", ' + i.valueCol + ');'); 80 | } 81 | }); 82 | gClipboardHelper.copyString(arr.join('\n')); 83 | } 84 | 85 | }, true); 86 | -------------------------------------------------------------------------------- /src/chrome/scripts/editbookmarkspopup_expanded.uc.js: -------------------------------------------------------------------------------- 1 | // 'Expand Edit Bookmarks Popup' script for Firefox 60+ by Aris 2 | // 3 | // option: increase folder tree height 4 | // option: hide preview image 5 | 6 | 7 | var folder_tree_height = "240px"; // increase folder tree height 8 | var hide_preview_image = false; // hide (true) or show (false) preview image 9 | 10 | 11 | var EditBookmarkPanelTweaks = { 12 | init: function() { 13 | 14 | try { 15 | 16 | document.getElementById('editBookmarkPanel').addEventListener("popupshown", function(){ 17 | 18 | gEditItemOverlay.toggleFolderTreeVisibility(); 19 | 20 | }, false); 21 | 22 | 23 | var sss = Components.classes["@mozilla.org/content/style-sheet-service;1"].getService(Components.interfaces.nsIStyleSheetService); 24 | 25 | var hide_preview_image_code =''; 26 | 27 | if(hide_preview_image) 28 | hide_preview_image_code = ' \ 29 | #editBookmarkPanelImage, #editBookmarkPanelFaviconContainer, #editBookmarkPanel html { \ 30 | display: none !important; \ 31 | } \ 32 | '; 33 | 34 | var uri = Services.io.newURI("data:text/css;charset=utf-8," + encodeURIComponent(' \ 35 | \ 36 | #editBookmarkPanel {\ 37 | transition: unset !important; \ 38 | } \ 39 | #editBMPanel_folderTree {\ 40 | min-height: '+folder_tree_height+' !important; \ 41 | } \ 42 | '+hide_preview_image_code+' \ 43 | \ 44 | '), null, null); 45 | 46 | // remove old style sheet 47 | if (sss.sheetRegistered(uri,sss.AGENT_SHEET)) sss.unregisterSheet(uri,sss.AGENT_SHEET); 48 | 49 | sss.loadAndRegisterSheet(uri, sss.AGENT_SHEET); 50 | 51 | 52 | } catch(e) {} 53 | 54 | } 55 | } 56 | 57 | document.addEventListener("DOMContentLoaded", EditBookmarkPanelTweaks.init(), false); 58 | -------------------------------------------------------------------------------- /src/chrome/scripts/favicon_in_urlbar.uc.js: -------------------------------------------------------------------------------- 1 | // 'Favicon in urlbars identity box' script for Firefox 60+ by Aris 2 | // 3 | // This script restores current pages favicon inside urlbar (aka location bar, address bar or awesome bar). 4 | // [!] If a page does not offer a favicon, browser branches default icon is shown. 5 | // [!] In a multi-window environment pages without favicons might show wrong icons. 6 | // option: set icon for pages without favicon 7 | 8 | 9 | var i_icon = 'chrome://browser/skin/identity-icon.svg'; 10 | var sheet = 'chrome://global/skin/icons/Portrait.png'; 11 | var brand = 'chrome://branding/content/identity-icons-brand.svg'; 12 | var globe = 'chrome://mozapps/skin/places/defaultFavicon.svg'; 13 | 14 | var icon_for_pages_without_favicon = brand; // i_icon, sheet, globe or brand (colorized Fx channel icon) 15 | 16 | 17 | var FaviconInUrlbar = { 18 | init: function() { 19 | try { 20 | // update script every time tab attributes get modified (switch/open tabs/windows) 21 | document.addEventListener("TabAttrModified", updateIcon, false); 22 | document.addEventListener('TabSelect', updateIcon, false); 23 | document.addEventListener('TabOpen', updateIcon, false); 24 | document.addEventListener('TabClose', updateIcon, false); 25 | document.addEventListener('load', updateIcon, false); 26 | document.addEventListener("DOMContentLoaded", updateIcon, false); 27 | 28 | function updateIcon() { 29 | 30 | setTimeout(function(){ // timeout fixes wrong icon detection in some cases 31 | 32 | // get current tabs favicon 33 | var favicon_in_urlbar = gBrowser.selectedTab.image; 34 | 35 | // if current tab offers no icon, use selected icon (icon_for_pages_without_favicon) 36 | if(!gBrowser.selectedTab.image || gBrowser.selectedTab.image == null) 37 | if(!icon_for_pages_without_favicon) favicon_in_urlbar = brand; 38 | else favicon_in_urlbar = icon_for_pages_without_favicon; 39 | 40 | document.querySelector('#identity-icon').style.listStyleImage = "url("+favicon_in_urlbar+")"; 41 | 42 | },100); 43 | 44 | } 45 | 46 | /* restore icon badge for websites with granted permissions */ 47 | var sss = Components.classes["@mozilla.org/content/style-sheet-service;1"].getService(Components.interfaces.nsIStyleSheetService); 48 | var uri = Services.io.newURI("data:text/css;charset=utf-8," + encodeURIComponent(' \ 49 | \ 50 | .grantedPermissions::before { \ 51 | content: "" !important; \ 52 | display: block !important; \ 53 | width: 6px !important; \ 54 | height: 6px !important; \ 55 | position: absolute !important; \ 56 | -moz-margin-start: 11px !important; \ 57 | margin-top:-8px !important; \ 58 | background: Highlight !important; \ 59 | border-radius: 100px !important; \ 60 | } \ 61 | \ 62 | '), null, null); 63 | 64 | // remove old style sheet 65 | if (sss.sheetRegistered(uri,sss.AGENT_SHEET)) sss.unregisterSheet(uri,sss.AGENT_SHEET); 66 | 67 | sss.loadAndRegisterSheet(uri, sss.AGENT_SHEET); 68 | 69 | } catch(e) {} 70 | } 71 | }; 72 | 73 | // initiate script after DOM/browser content is loaded 74 | document.addEventListener("DOMContentLoaded", FaviconInUrlbar.init(), false); 75 | -------------------------------------------------------------------------------- /src/chrome/scripts/restart-button.uc.js: -------------------------------------------------------------------------------- 1 | 2 | (function() { 3 | if (location != 'chrome://browser/content/browser.xul' && location != 'chrome://browser/content/browser.xhtml') 4 | return; 5 | 6 | try { 7 | CustomizableUI.createWidget({ 8 | id: 'restart-button', 9 | type: 'custom', 10 | defaultArea: CustomizableUI.AREA_NAVBAR, 11 | onBuild: function(aDocument) { 12 | var toolbaritem = aDocument.createElementNS('http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul', 'toolbarbutton'); 13 | toolbaritem.onclick = event => onClick(event); 14 | var props = { 15 | id: 'restart-button', 16 | class: 'toolbarbutton-1 chromeclass-toolbar-additional', 17 | label: 'Restart', 18 | tooltiptext: 'Restart and delete startupCache)', 19 | style: 'list-style-image: url(chrome://browser/skin/sync.svg)' 20 | }; 21 | for(var p in props) 22 | toolbaritem.setAttribute(p, props[p]); 23 | return toolbaritem; 24 | } 25 | }); 26 | } catch(e) {}; 27 | 28 | function onClick(event) { 29 | if(event.button == 1) 30 | Services.appinfo.invalidateCachesOnRestart(); 31 | else if(event.button == 2) 32 | return; 33 | 34 | let cancelQuit = Cc["@mozilla.org/supports-PRBool;1"].createInstance(Ci.nsISupportsPRBool); 35 | 36 | Services.appinfo.invalidateCachesOnRestart(); 37 | Services.obs.notifyObservers(cancelQuit, "quit-application-requested", "restart"); 38 | if(!cancelQuit.data) 39 | Services.startup.quit(Services.startup.eAttemptQuit | Services.startup.eRestart); 40 | } 41 | })(); 42 | -------------------------------------------------------------------------------- /src/chrome/userChrome.css: -------------------------------------------------------------------------------- 1 | /** 2 | * userChrome.css 3 | * change the appearance of the user interface 4 | */ 5 | 6 | /** 7 | * Apply XML bindings to elements 8 | * this enables the use of external js files 9 | */ 10 | 11 | @namespace url("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"); 12 | 13 | toolbarbutton#alltabs-button { 14 | -moz-binding: url("data:text/plain;charset=utf-8;base64,PD94bWwgdmVyc2lvbj0iMS4wIj8+CjwhLS0gQ29weXJpZ2h0IChjKSAyMDE3IEhhZ2dhaSBOdWNoaQpBdmFpbGFibGUgZm9yIHVzZSB1bmRlciB0aGUgTUlUIExpY2Vuc2U6Cmh0dHBzOi8vb3BlbnNvdXJjZS5vcmcvbGljZW5zZXMvTUlUCiAtLT4KCjwhLS0gUnVuIHVzZXJDaHJvbWUuanMvdXNlckNocm9tZS54dWwgYW5kIC51Yy5qcy8udWMueHVsLy5jc3MgZmlsZXMgIC0tPgo8YmluZGluZ3MgeG1sbnM9Imh0dHA6Ly93d3cubW96aWxsYS5vcmcveGJsIj4KICAgIDxiaW5kaW5nIGlkPSJqcyI+CiAgICAgICAgPGltcGxlbWVudGF0aW9uPgogICAgICAgICAgICA8Y29uc3RydWN0b3I+PCFbQ0RBVEFbCiAgICAgICAgICAgICAgICBpZih3aW5kb3cudXNlckNocm9tZUpzTW9kKSByZXR1cm47CiAgICAgICAgICAgICAgICB3aW5kb3cudXNlckNocm9tZUpzTW9kID0gdHJ1ZTsKCiAgICAgICAgICAgICAgICB2YXIgY2hyb21lRmlsZXMgPSBGaWxlVXRpbHMuZ2V0RGlyKCJVQ2hybSIsIFsnc2NyaXB0cyddKS5kaXJlY3RvcnlFbnRyaWVzOwogICAgICAgICAgICAgICAgdmFyIHh1bEZpbGVzID0gW107CiAgICAgICAgICAgICAgICB2YXIgc3NzID0gQ2NbJ0Btb3ppbGxhLm9yZy9jb250ZW50L3N0eWxlLXNoZWV0LXNlcnZpY2U7MSddLmdldFNlcnZpY2UoQ2kubnNJU3R5bGVTaGVldFNlcnZpY2UpOwoKICAgICAgICAgICAgICAgIHdoaWxlKGNocm9tZUZpbGVzLmhhc01vcmVFbGVtZW50cygpKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGZpbGUgPSBjaHJvbWVGaWxlcy5nZXROZXh0KCkuUXVlcnlJbnRlcmZhY2UoQ2kubnNJRmlsZSk7CiAgICAgICAgICAgICAgICAgICAgdmFyIGZpbGVVUkkgPSBTZXJ2aWNlcy5pby5uZXdGaWxlVVJJKGZpbGUpOwoKICAgICAgICAgICAgICAgICAgICBpZihmaWxlLmlzRmlsZSgpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHR5cGUgPSAibm9uZSI7CiAgICAgICAgICAgICAgICAgICAgICAgIGlmKC8oXnVzZXJDaHJvbWV8LnVjKS5qcyQvaS50ZXN0KGZpbGUubGVhZk5hbWUpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0eXBlID0gInVzZXJjaHJvbWUvanMiOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2UgaWYoLyhedXNlckNocm9tZXwudWMpLnh1bCQvaS50ZXN0KGZpbGUubGVhZk5hbWUpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0eXBlID0gInVzZXJjaHJvbWUveHVsIjsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlIGlmKC8uYXMuY3NzJC9pLnRlc3QoZmlsZS5sZWFmTmFtZSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHR5cGUgPSAiYWdlbnRzaGVldCI7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZSBpZigvXig/ISh1c2VyQ2hyb21lfHVzZXJDb250ZW50KS5jc3MkKS4rLmNzcyQvaS50ZXN0KGZpbGUubGVhZk5hbWUpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0eXBlID0gInVzZXJzaGVldCI7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgaWYodHlwZSAhPSAibm9uZSIpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnNvbGUubG9nKCItLS0tLS0tLS0tXCAiICsgZmlsZS5sZWFmTmFtZSArICIgKCIgKyB0eXBlICsgIikiKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRyeSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYodHlwZSA9PSAidXNlcmNocm9tZS9qcyIpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgU2VydmljZXMuc2NyaXB0bG9hZGVyLmxvYWRTdWJTY3JpcHRXaXRoT3B0aW9ucyhmaWxlVVJJLnNwZWMsIHt0YXJnZXQ6IHdpbmRvdywgaWdub3JlQ2FjaGU6IHRydWV9KTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZWxzZSBpZih0eXBlID09ICJ1c2VyY2hyb21lL3h1bCIpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgeHVsRmlsZXMucHVzaChmaWxlVVJJLnNwZWMpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBlbHNlIGlmKHR5cGUgPT0gImFnZW50c2hlZXQiKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmKCFzc3Muc2hlZXRSZWdpc3RlcmVkKGZpbGVVUkksIHNzcy5BR0VOVF9TSEVFVCkpCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzc3MubG9hZEFuZFJlZ2lzdGVyU2hlZXQoZmlsZVVSSSwgc3NzLkFHRU5UX1NIRUVUKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZWxzZSBpZih0eXBlID09ICJ1c2Vyc2hlZXQiKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmKCFzc3Muc2hlZXRSZWdpc3RlcmVkKGZpbGVVUkksIHNzcy5VU0VSX1NIRUVUKSkKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNzcy5sb2FkQW5kUmVnaXN0ZXJTaGVldChmaWxlVVJJLCBzc3MuVVNFUl9TSEVFVCk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICAgICAgfSBjYXRjaChlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc29sZS5sb2coIiMjIyMjIyMjIyMgRVJST1I6ICIgKyBlICsgIiBhdCAiICsgZS5saW5lTnVtYmVyICsgIjoiICsgZS5jb2x1bW5OdW1iZXIpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc29sZS5sb2coIi0tLS0tLS0tLS0vICIgKyBmaWxlLmxlYWZOYW1lKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICBzZXRUaW1lb3V0KGZ1bmN0aW9uIGxvYWRYVUwoKSB7CiAgICAgICAgICAgICAgICAgICAgaWYoeHVsRmlsZXMubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgICAgICAgICBkb2N1bWVudC5sb2FkT3ZlcmxheSh4dWxGaWxlcy5zaGlmdCgpLCBudWxsKTsKICAgICAgICAgICAgICAgICAgICAgICAgc2V0VGltZW91dChsb2FkWFVMLCA1KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9LCAwKTsKICAgICAgICAgICAgXV0+PC9jb25zdHJ1Y3Rvcj4KICAgICAgICA8L2ltcGxlbWVudGF0aW9uPgogICAgPC9iaW5kaW5nPgo8L2JpbmRpbmdzPg=="); 15 | } 16 | 17 | /* apply MaterialFox theme */ 18 | /* @import "./css/materialfox/chrome/userChrome.css"; */ 19 | 20 | /* tab close icon settings */ 21 | @import "./css/customcssforfx/classic/css/tabs/tab_close_always_visible.css"; 22 | 23 | /* @import "./css/customcssforfx/classic/css/tabs/tabs_multiple_lines.css"; */ 24 | /* @import "./css/customcssforfx/classic/css/tabs/tabs_multiple_lines_v3.css"; */ 25 | /* @import "./css/customcssforfx/classic/css/generalui/private_mode_indicator_hidden.css"; */ 26 | /* @import "./css/customcssforfx/classic/css/generalui/bookmark_icons_colorized.css"; */ 27 | /* @import "./css/customcssforfx/classic/css/locationbar/locationbar_adjustments.css"; */ 28 | /* @import "./css/customcssforfx/classic/css/"; */ 29 | -------------------------------------------------------------------------------- /src/chrome/userChrome.js: -------------------------------------------------------------------------------- 1 | /* 2 | * userChromeJS 3 | * 4 | * This file can be used to customize the functioning of Mozilla's user 5 | * interface. Usage and syntax follow below; for useful code snippets see 6 | * http://mozilla.zeniko.ch/userchrome.js.html. 7 | * 8 | * Examples: 9 | * setTimeout(function() { document.title = "A new title for every window" }, 2000); 10 | * 11 | * if (location == "chrome://browser/content/browser.xul") { 12 | * alert("Script loaded in main browser only"); 13 | * } 14 | * 15 | * // DOMi window 16 | * if (location == "chrome://inspector/content/inspector.xul") { 17 | * // Move Urlbar box to main toolbar 18 | * var tb = document.getElementById('bxURLBar'); 19 | * var el = document.getElementById('mbrInspectorMain'); 20 | * if (tb && el) el.appendChild(tb, el.firstChild); 21 | * } 22 | * 23 | * NOTE: userChromeJS includes an 'import' function to facilitate file management. 24 | * An absolute path or relative path with Directory name property token can be 25 | * used, as follows: 26 | * 27 | * // Single file (javascript .js or overlay .xul file) 28 | * userChrome.import("Full file path"); 29 | * userChrome.import("Relative file path", "Token"); 30 | * // All .js and .xul files in a folder will be loaded. 31 | * userChrome.import("Full file folder path"); 32 | * userChrome.import("Relative file folder path/name", "Token"); 33 | * userChrome.import("*", "Token"); 34 | * 35 | * NOTE: absolute windows files and folders must be have backslash escaped: 36 | * "C:\\Program Files\\Mozilla\\scripts\\myscript.js" 37 | * 38 | * Examples: 39 | * // Import script in [ProfileDir]/chrome/scripts/myscript.js 40 | * userChrome.import("scripts/myscript.js", "UChrm"); 41 | * // Import script in [Profiles]/scripts/myscript.js (share same script in 42 | * // multiple profiles 43 | * userChrome.import("scripts/myscript.js", "DefProfRt"); 44 | * // All .js or .xul in profile chrome directory 45 | * userChrome.import("*", "UChrm"); 46 | * // Import overlay 47 | * userChrome.import("C:\\Program Files\\Mozilla\\scripts\\myOverlay.xul"); 48 | * // Import everything in Desktop folder /scripts 49 | * userChrome.import("scripts", "Desk"); 50 | * // Perhaps the only thing you need in this file.. 51 | * if (location == "chrome://browser/content/browser.xul") { 52 | * userChrome.import("scripts", "DefProfRt"); 53 | * } 54 | * 55 | * NOTE: for a full listing of directory tokens see the two links found here: 56 | * https://developer.mozilla.org/en/Code_snippets/File_I%2f%2fO#Getting_special_files 57 | * // What's the path for a token? This will print it in the console.. 58 | * userChrome.log(userChrome.getAbsoluteFile("Desk").path, "getAbsoluteFile:'Desk'"); 59 | * 60 | * NOTE: userChromeJS includes a log function, invoked as follows: 61 | * userChrome.log("string1", ["string2"]) 62 | * Example: 63 | * userChrome.log("hello world!", "myscript.js"); 64 | * Results in a console message: 65 | * 2009-05-22 18:07:40 userChromeJS.js::myscript.js: hello world! 66 | * 67 | * NOTE: the date format for the userChrome.log console logger may be user defined: 68 | * Example: 69 | * userChrome.dateFormat = "%Y-%m-%d %H:%M:%S"; 70 | * 71 | * NOTE: the default charSet is "UTF-8"; for code using the 'import' or 72 | * 'importFolder' functions to manage files, the charSet for subscript loader 73 | * may be user defined, prior to calling the import or importFolder functions: 74 | * Example: 75 | * userChrome.charSet = "UTF-8"; 76 | * 77 | */ 78 | 79 | userChrome.import("scripts", "UChrm"); 80 | -------------------------------------------------------------------------------- /src/chrome/userContent.css: -------------------------------------------------------------------------------- 1 | /** 2 | / userContent.css 3 | / change the appearance of web sites, 4 | / and some internal pages like about:newtab 5 | */ 6 | 7 | /* GENERAL VARIABLES ****************************************************************************/ 8 | /* [!] set global variables for font and tab size options and more inside target file ***********/ 9 | @import "./css/variables.css"; 10 | 11 | 12 | /* @import "./css/aboutaddons/addons_manager_full_width.css"; */ 13 | @import "./css/aboutaddons/addons_manager_full_width_fx67.css"; 14 | @import "./css/aboutaddons/addonlists_disabled_grayscale_fx67.css"; 15 | @import "./css/aboutaddons/addonlists_private_browsing_notice_hidden.css"; 16 | @import "./css/aboutaddons/details_page_alternative_content_order.css"; 17 | @import "./css/aboutaddons/addonlists_replace_button_labels_with_icons.css"; 18 | 19 | 20 | 21 | /* compact item lists - [only use one at a time] ************************************************/ 22 | /* @import "./css/aboutaddons/addonlists_compact.css"; */ 23 | /* @import "./css/aboutaddons/addonlists_compact-min.css"; */ 24 | 25 | /* show 'last updated' date for add-ons - [only use one at a time] ******************************/ 26 | /* @import "./css/customcssforfx/classic/css/aboutaddons/addonlists_show_addon_date_last_updated.css"; */ 27 | /* @import "./css/customcssforfx/classic/css/aboutaddons/addonlists_show_addon_date_last_updated_start_position.css"; */ 28 | 29 | /* other settings *******************************************************************************/ 30 | @import "./css/customcssforfx/classic/css/aboutaddons/recentupdates_category_always_visible.css"; 31 | /* @import "./css/customcssforfx/classic/css/aboutaddons/details_page_switch_banner_label_position_for_themes.css"; */ 32 | -------------------------------------------------------------------------------- /src/icons/.svgo.json: -------------------------------------------------------------------------------- 1 | { 2 | "plugins": { 3 | "cleanupAttrs": true, 4 | "inlineStyles": true, 5 | "removeDoctype": true, 6 | "removeXMLProcInst": true, 7 | "removeComments": false, 8 | "removeMetadata": false, 9 | "removeTitle": true, 10 | "removeDesc": true, 11 | "removeUselessDefs": true, 12 | "removeXMLNS": true, 13 | "removeEditorsNSData": false, 14 | "removeEmptyAttrs": true, 15 | "removeHiddenElems": false, 16 | "removeEmptyText": false, 17 | "removeEmptyContainers": true, 18 | "removeViewBox": false, 19 | "cleanupEnableBackground": false, 20 | "minifyStyles": false, 21 | "convertStyleToAttrs": true, 22 | "convertColors": false, 23 | "convertPathData": true, 24 | "convertTransform": false, 25 | "removeUnknownsAndDefaults": true, 26 | "removeNonInheritableGroupAttrs": false, 27 | "removeUselessStrokeAndFill": true, 28 | "removeUnusedNS": false, 29 | "prefixIds": false, 30 | "cleanupIDs": true, 31 | "cleanupNumericValues": false, 32 | "cleanupListOfValues": false, 33 | "moveElemsAttrsToGroup": false, 34 | "moveGroupAttrsToElems": false, 35 | "collapseGroups": true, 36 | "removeRasterImages": true, 37 | "mergePaths": false, 38 | "convertShapeToPath": false, 39 | "sortAttrs": true, 40 | "removeDimensions": true, 41 | "removeAttrs": false, 42 | "removeAttributesBySelector": false, 43 | "removeElementsByAttr": false, 44 | "addClassesToSVGElement": false, 45 | "addAttributesToSVGElement": false, 46 | "removeOffCanvasPaths": false, 47 | "removeStyleElement": false, 48 | "removeScriptElement": false, 49 | "reusePaths": false 50 | } 51 | } -------------------------------------------------------------------------------- /src/icons/.svgo.yml: -------------------------------------------------------------------------------- 1 | full: true 2 | 3 | # plugins options 4 | # @see https://github.com/svg/svgo/blob/master/README.md 5 | 6 | plugins: 7 | - cleanupAttrs: true 8 | - inlineStyles: true 9 | - removeDoctype: true 10 | - removeXMLProcInst: true 11 | - removeComments 12 | - removeMetadata 13 | - removeTitle: true 14 | - removeDesc: true 15 | - removeUselessDefs: true 16 | - removeXMLNS: false 17 | - removeEditorsNSData 18 | - removeEmptyAttrs: true 19 | - removeHiddenElems 20 | - removeEmptyText 21 | - removeEmptyContainers: true 22 | - removeViewBox 23 | - cleanupEnableBackground 24 | - minifyStyles 25 | - convertStyleToAttrs: true 26 | - convertColors 27 | - convertPathData 28 | - convertTransform 29 | - removeUnknownsAndDefaults: true 30 | - removeNonInheritableGroupAttrs 31 | - removeUselessStrokeAndFill: true 32 | - removeUnusedNS 33 | - prefixIds 34 | - cleanupIDs: true 35 | - cleanupNumericValues 36 | - cleanupListOfValues 37 | - moveElemsAttrsToGroup 38 | - moveGroupAttrsToElems 39 | - collapseGroups: true 40 | - removeRasterImages: true 41 | - mergePaths 42 | - convertShapeToPath 43 | - sortAttrs: true 44 | - removeDimensions: true 45 | - removeAttrs 46 | - removeAttributesBySelector 47 | - removeElementsByAttr 48 | - addClassesToSVGElement 49 | - addAttributesToSVGElement 50 | - removeOffCanvasPaths 51 | - removeStyleElement 52 | - removeScriptElement 53 | - reusePaths 54 | 55 | # config options 56 | # @see https://github.com/svg/svgo/blob/master/lib/svgo/js2svg.js#L6 57 | js2svg: 58 | pretty: true 59 | indent: ' ' 60 | -------------------------------------------------------------------------------- /src/icons/.svgo2.yml: -------------------------------------------------------------------------------- 1 | 2 | 3 | # plugins options 4 | # @see https://github.com/svg/svgo/blob/master/README.md 5 | 6 | plugins: 7 | - removeDoctype 8 | - removeXMLProcInst 9 | - removeComments 10 | - removeMetadata 11 | - removeXMLNS 12 | - removeEditorsNSData 13 | - cleanupAttrs: true 14 | - inlineStyles 15 | - minifyStyles 16 | - convertStyleToAttrs 17 | - cleanupIDs: true 18 | - prefixIds 19 | - removeRasterImages: true 20 | - removeUselessDefs: true 21 | - cleanupNumericValues 22 | - cleanupListOfValues 23 | - convertColors 24 | - removeUnknownsAndDefaults: true 25 | - removeNonInheritableGroupAttrs 26 | - removeUselessStrokeAndFill: true 27 | - removeViewBox 28 | - cleanupEnableBackground 29 | - removeHiddenElems 30 | - removeEmptyText 31 | - convertShapeToPath 32 | - moveElemsAttrsToGroup 33 | - moveGroupAttrsToElems 34 | - collapseGroups: true 35 | - convertPathData 36 | - convertTransform 37 | - removeEmptyAttrs: true 38 | - removeEmptyContainers: true 39 | - mergePaths 40 | - removeUnusedNS 41 | - sortAttrs: true 42 | - removeTitle: true 43 | - removeDesc: true 44 | - removeDimensions: true 45 | - removeAttrs: 46 | attrs: 47 | - 'fill-rule' 48 | - 'stroke-linejoin' 49 | - 'stroke-miterlimit' 50 | - 'clip-rule' 51 | - removeAttributesBySelector 52 | - removeElementsByAttr 53 | - addClassesToSVGElement 54 | - removeStyleElement: true 55 | - removeScriptElement 56 | - addAttributesToSVGElement 57 | - removeOffCanvasPaths 58 | - reusePaths 59 | 60 | # config options 61 | # @see https://github.com/svg/svgo/blob/master/lib/svgo/js2svg.js#L6 62 | js2svg: 63 | pretty: true 64 | indent: ' ' 65 | -------------------------------------------------------------------------------- /src/icons/delete.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /src/icons/vimrc-out.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /src/icons/vimrc.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /src/user-base.js: -------------------------------------------------------------------------------- 1 | // 2 | // ─── GENERAL ───────────────────────────────────────────────────────────────── 3 | // 4 | 5 | // enable supports of userChrome.css and userContent.css 6 | // @see https://www.ghacks.net/2019/05/24/firefox-69-userchrome-css-and-usercontent-css-disabled-by-default/ 7 | user_pref("toolkit.legacyUserProfileCustomizations.stylesheets", true); 8 | 9 | // display about:config normally without a warning 10 | user_pref("browser.aboutConfig.showWarning", false); 11 | 12 | // change the interface language "en-US/ru-RU" 13 | user_pref("intl.locale.requested", "en-US"); 14 | 15 | // disable cycles through tabs in recently used order 16 | user_pref("browser.ctrlTab.recentlyUsedOrder", false); 17 | 18 | // disable spell checking 19 | user_pref("layout.spellcheckDefault", 0); 20 | 21 | // enable alt+click on the link for download without prompts 22 | user_pref("browser.altClickSave", true); 23 | 24 | // display all plugins in the Download Actions dialog 25 | user_pref("browser.download.hide_plugins_without_extensions", false); 26 | 27 | // save files with unknown mime type 28 | // eslint-disable-next-line prettier/prettier 29 | // user_pref("browser.helperApps.neverAsk.saveToDisk", "application/msword, application/csv, application/ris, text/csv, image/png, image/svg+xml, application/pdf, text/html, text/plain, application/zip, application/x-zip, application/x-zip-compressed, application/download, application/octet-stream"); 30 | 31 | // disable auto install updates 32 | user_pref("app.update.auto", false); 33 | 34 | // disable background service to install updates 35 | user_pref("app.update.service.enabled", false); 36 | 37 | // disable auto update search engines 38 | user_pref("browser.search.update", false); 39 | 40 | // customize items in toolbar 41 | // user_pref("browser.uiCustomization.state", "{\"placements\":{\"widget-overflow-fixed-list\":[],\"nav-bar\":[\"back-button\",\"forward-button\",\"stop-reload-button\",\"home-button\",\"customizableui-special-spring1\",\"sync-button\",\"urlbar-container\",\"customizableui-special-spring2\",\"downloads-button\",\"library-button\",\"sidebar-button\",\"_89299b16-7b8d-48c2-8bdf-e9e4f58de3f6_-browser-action\",\"onepassword4_agilebits_com-browser-action\",\"uc-restart\",\"restart-button\",\"firefox_tampermonkey_net-browser-action\",\"_7a7a4a92-a2a0-41d1-9fd7-1e92480d612d_-browser-action\",\"_d634138d-c276-4fc8-924b-40a0ea21d284_-browser-action\",\"adguardadblocker_adguard_com-browser-action\",\"chrome-store-foxified_jetpack-browser-action\",\"_c2c003ee-bd69-42a2-b0e9-6f34222cb046_-browser-action\",\"_a8332c60-5b6d-41ee-bfc8-e9bb331d34ad_-browser-action\",\"simple-translate_sienori-browser-action\",\"tab-session-manager_sienori-browser-action\",\"addon_darkreader_org-browser-action\",\"firefoxbeta_tampermonkey_net-browser-action\",\"fxa-toolbar-menu-button\"],\"toolbar-menubar\":[\"menubar-items\"],\"TabsToolbar\":[\"tabbrowser-tabs\",\"new-tab-button\",\"alltabs-button\"],\"PersonalToolbar\":[\"personal-bookmarks\"]},\"seen\":[\"developer-button\",\"_c2c003ee-bd69-42a2-b0e9-6f34222cb046_-browser-action\",\"_a8332c60-5b6d-41ee-bfc8-e9bb331d34ad_-browser-action\",\"simple-translate_sienori-browser-action\",\"firefoxbeta_tampermonkey_net-browser-action\",\"onepassword4_agilebits_com-browser-action\",\"_d634138d-c276-4fc8-924b-40a0ea21d284_-browser-action\",\"_7a7a4a92-a2a0-41d1-9fd7-1e92480d612d_-browser-action\",\"webide-button\",\"adguardadblocker_adguard_com-browser-action\",\"addon_darkreader_org-browser-action\",\"firefox_tampermonkey_net-browser-action\",\"uc-restart\",\"chrome-store-foxified_jetpack-browser-action\",\"_89299b16-7b8d-48c2-8bdf-e9e4f58de3f6_-browser-action\",\"restart-button\",\"tab-session-manager_sienori-browser-action\"],\"dirtyAreaCache\":[\"nav-bar\",\"TabsToolbar\",\"PersonalToolbar\"],\"currentVersion\":16,\"newElementCount\":19}"); 42 | 43 | // disable beforeunload events (e.g. “Are you sure you want to leave this page?” 44 | // user_pref("dom.disable_beforeunload", true); 45 | 46 | // disable screenshots 47 | // eslint-disable-next-line prettier/prettier 48 | user_pref("extensions.screenshots.disabled", true); 49 | 50 | 51 | 52 | // 53 | // ─── BOOKMARKS ─────────────────────────────────────────────────────────────── 54 | // 55 | 56 | // save bookmarks.html to the profile on browser exit. 57 | // user_pref("browser.bookmarks.autoExportHTML", true); 58 | 59 | // define the number of bookmarks backups 60 | // user_pref("browser.bookmarks.max_backups", 3); 61 | 62 | // 63 | // ─── BEHAVIOUR ─────────────────────────────────────────────────────────────── 64 | // 65 | 66 | // ─── OPEN URLS ─────────────────────────────────────────────────────────────── 67 | 68 | // force links to open in the same tab 69 | // 3 = divert new window to a new tab (default) 70 | // 2 = allow link to open a new window 71 | // 1 = force new window into same tab 72 | user_pref("browser.link.open_newwindow", 1); 73 | 74 | // divert links opened via JS OR HTML target="_blank" 75 | // 0 = apply the setting under (A) to ALL new windows (even script windows) 76 | // 2 = apply the setting under (A) to normal windows, but NOT to script windows with features (default) 77 | // 1 = override the setting under (A) and always use new windows 78 | user_pref("browser.link.open_newwindow.restriction", 2); 79 | 80 | // for links in other programs 81 | // -1 = apply the setting under (A) to external links (default) 82 | // 3 = open external links in a new tab in the last active window 83 | // 2 = open external links in a new window 84 | // 1 = open external links in the last active tab replacing the current page 85 | user_pref("browser.link.open_newwindow.override.external", 3); 86 | 87 | // open tabs to the right of the current tab 88 | user_pref("browser.tabs.insertAfterCurrent", true); 89 | 90 | 91 | // open bookmarks in background enstead of switch to it 92 | // user_pref("browser.tabs.loadBookmarksInBackground", true); 93 | 94 | // user_pref("browser.tabs.loadInBackground", true); 95 | // user_pref("browser.tabs.loadDivertedInBackground", true); 96 | 97 | // fix telegram links handler 98 | // user_pref("network.protocol-handler.expose.tg", false); 99 | // user_pref("network.protocol-handler.expose.magnet", false); 100 | 101 | 102 | // 103 | // ─── UI ────────────────────────────────────────────────────────────────────── 104 | // 105 | 106 | // theme 107 | user_pref("extensions.activeThemeID", "firefox-compact-dark@mozilla.org"); 108 | 109 | // tiny bars 110 | user_pref("browser.tabs.drawInTitlebar", false); 111 | user_pref("browser.uidensity", 1); 112 | user_pref("browser.tabs.extraDragSpace", true); 113 | 114 | // enable dark-mode 115 | user_pref("browser.in-content.dark-mode", true); 116 | user_pref("ui.systemUsesDarkTheme", 1); 117 | 118 | // user_pref("browser.display.background_color", "#D3D3D3"); 119 | 120 | // move sidebar to right 121 | user_pref("sidebar.position_start", false); 122 | 123 | // disable autoplay 124 | // user_pref("media.autoplay.enabled", false); 125 | user_pref("media.autoplay.default", 1); 126 | user_pref("media.autoplay.allow-muted", false); 127 | 128 | user_pref("media.videocontrols.picture-in-picture.enabled", false); 129 | user_pref("media.videocontrols.picture-in-picture.video-toggle.enabled", true); 130 | 131 | // disable zoom with cmd+scroll 132 | user_pref("mousewheel.with_meta.action", 1); 133 | 134 | // fix the dark theme bug 135 | user_pref("widget.content.allow-gtk-dark-theme", true); 136 | user_pref("widget.content.gtk-theme-override", "Adwaita:light"); 137 | 138 | // fonts 139 | // user_pref("font.name.monospace.x-western", "FiraCode Nerd Font Mono"); 140 | // user_pref("font.name.sans-serif.x-western", "SF Pro Display"); 141 | 142 | /* READER MODE─────────────────────────────────────────────────────────────── */ 143 | // enable dark theme 144 | user_pref("reader.color_scheme", "dark"); 145 | user_pref("reader.content_width", 7); 146 | 147 | /* TABS ───────────────────────────────────────────────────────────────────── */ 148 | 149 | // tab audio icon 150 | user_pref("browser.tabs.showAudioPlayingIcon", true); 151 | 152 | // materialfox 153 | // user_pref("materialFox.reduceTabOverflow", true); 154 | // user_pref("svg.context-properties.content.enabled", true); 155 | 156 | // always show tab close button 157 | user_pref("browser.tabs.closeButtons", 1); 158 | 159 | // replicate chrome behaviour for clipped tabs 160 | // user_pref("browser.tabs.tabClipWidth", 80); 161 | 162 | // backspace to go back 163 | user_pref("browser.backspace_action", 0); 164 | 165 | // 166 | // ─── HOME ──────────────────────────────────────────────────────────────────── 167 | // 168 | 169 | // restore previous session 170 | user_pref("browser.startup.page", 3); 171 | 172 | // 4 rows of top sites 173 | user_pref("browser.newtabpage.activity-stream.topSitesRows", 4); 174 | 175 | // pinned sites top sites 176 | user_pref("browser.newtabpage.pinned", "[{\"url\":\"https://github.com/\",\"label\":\"github\",\"baseDomain\":\"github.com\"},{\"url\":\"https://gist.github.com/dotiful?direction=deschttps://gist.github.com/dotiful?direction=desc&sort=updated\",\"label\":\"gists\",\"baseDomain\":\"gist.github.com\"},{\"url\":\"https://github.com/dotiful?tab=stars\",\"label\":\"stars\",\"baseDomain\":\"github.com\"},{\"url\":\"https://gitlab.com/?nav_source=navbar\",\"label\":\"gitlab\",\"customScreenshotURL\":\"https://i.imgur.com/AGSiONj.png\",\"baseDomain\":\"gitlab.com\"},{\"url\":\"https://eu-central-1.console.aws.amazon.com/ec2/v2/home?region=eu-central-1#Instances:sort=instanceId\",\"label\":\"aws\",\"customScreenshotURL\":\"https://i.imgur.com/irpKuOG.png\",\"baseDomain\":\"eu-central-1.console.aws.amazon.com\"},{\"url\":\"https://console.cloud.google.com/home/dashboard?authuser=2&project=wrtdev\",\"label\":\"GCP\",\"customScreenshotURL\":\"https://i.imgur.com/XUwMPRs.png\",\"baseDomain\":\"console.cloud.google.com\"},{\"url\":\"https://dash.cloudflare.com\",\"label\":\"cloudflare\",\"customScreenshotURL\":\"https://i.imgur.com/2dddPbm.png\",\"baseDomain\":\"dash.cloudflare.com\"},{\"url\":\"https://adwrt.cf/\",\"label\":\"adhome\",\"customScreenshotURL\":\"https://i.imgur.com/dgvkfMl.png\",\"baseDomain\":\"adwrt.cf\"},{\"url\":\"https://www.google.com.ua/\",\"label\":\"google\",\"customScreenshotURL\":\"https://i.imgur.com/rT7EyzQ.png\",\"baseDomain\":\"google.com.ua\"},{\"url\":\"https://mail.google.com/mail/u/0/\",\"label\":\"artdev\",\"customScreenshotURL\":\"https://i.imgur.com/2PwPKoS.png\",\"baseDomain\":\"mail.google.com\"},{\"url\":\"https://mail.google.com/mail/u/1/\",\"label\":\"dots\",\"customScreenshotURL\":\"https://i.imgur.com/2PwPKoS.png\",\"baseDomain\":\"mail.google.com\"},{\"url\":\"https://mail.google.com/mail/u/2/\",\"label\":\"wrt\",\"customScreenshotURL\":\"https://i.imgur.com/2PwPKoS.png\",\"baseDomain\":\"mail.google.com\"},{\"url\":\"https://www.youtube.com/\",\"label\":\"youtube\",\"customScreenshotURL\":\"https://i.imgur.com/W5nyO7W.png\",\"baseDomain\":\"youtube.com\"},{\"url\":\"https://drive.google.com/\",\"label\":\"drive\",\"customScreenshotURL\":\"https://i.imgur.com/41EIr4Q.png\",\"baseDomain\":\"drive.google.com\"},{\"url\":\"https://translate.google.com.ua/#view=home&op=translate&sl=auto&tl=ru\",\"label\":\"translate\",\"customScreenshotURL\":\"https://i.imgur.com/iiTj8hF.png\",\"baseDomain\":\"translate.google.com.ua\"},{\"url\":\"https://www.google.com.ua/maps\",\"label\":\"maps\",\"customScreenshotURL\":\"https://i.imgur.com/FSx9cpO.png\",\"baseDomain\":\"google.com.ua\"},{\"url\":\"https://web.telegram.org/\",\"label\":\"telegram\",\"customScreenshotURL\":\"https://i.imgur.com/VijQNyZ.png\",\"baseDomain\":\"web.telegram.org\"},{\"url\":\"https://www.inoreader.com/\",\"label\":\"inoreader\",\"customScreenshotURL\":\"https://i.imgur.com/9qiR748.png\",\"baseDomain\":\"inoreader.com\"},{\"url\":\"https://www.integromat.com/\",\"label\":\"integromat\",\"customScreenshotURL\":\"https://i.imgur.com/6FEgChu.png\",\"baseDomain\":\"integromat.com\"},{\"url\":\"https://twitter.com/artdevjs/lists/feed\",\"label\":\"twitter\",\"customScreenshotURL\":\"https://i.imgur.com/sfAkrOp.png\",\"baseDomain\":\"twitter.com\"},{\"url\":\"https://www.reddit.com/user/artdevjs/m/favs/new/\",\"label\":\"reddit\",\"customScreenshotURL\":\"https://i.imgur.com/HV6Ur0m.png\",\"baseDomain\":\"reddit.com\"},{\"url\":\"https://www.dropbox.com/home\",\"label\":\"dropbox\",\"customScreenshotURL\":\"https://i.imgur.com/AXrk2CR.png\",\"baseDomain\":\"dropbox.com\"},{\"url\":\"https://bitbucket.org/dashboard/overview\",\"label\":\"bitbucket\",\"customScreenshotURL\":\"https://i.imgur.com/F6sEfIW.png\",\"baseDomain\":\"bitbucket.org\"},{\"url\":\"https://www.npmjs.com\",\"label\":\"npm\",\"customScreenshotURL\":\"https://i.imgur.com/g3ZPxyk.png\",\"baseDomain\":\"npmjs.com\"},{\"url\":\"https://outlook.live.com/mail/inbox\",\"label\":\"outlook\",\"customScreenshotURL\":\"https://i.imgur.com/tK0xCo0.png\",\"baseDomain\":\"outlook.live.com\"},{\"url\":\"https://my.1password.com/home\",\"label\":\"1password\",\"customScreenshotURL\":\"https://i.imgur.com/PHOaimF.png\",\"baseDomain\":\"my.1password.com\"},{\"url\":\"https://www.olx.ua/myaccount/\",\"label\":\"olx\",\"customScreenshotURL\":\"https://i.imgur.com/cozJJwJ.png\",\"baseDomain\":\"olx.ua\"},{\"url\":\"https://artdevjs.imgur.com/all\",\"label\":\"imgur\",\"customScreenshotURL\":\"https://i.imgur.com/hMG9e10.jpg\",\"baseDomain\":\"artdevjs.imgur.com\"},{\"url\":\"https://filmix.co/favorites\",\"label\":\"filmix\",\"customScreenshotURL\":\"https://filmix.co/templates/Filmix/media/img/filmix.png\",\"baseDomain\":\"filmix.co\"},{\"url\":\"http://ex-fs.net/subnews/\",\"label\":\"ex-fs\",\"customScreenshotURL\":\"https://i.imgur.com/cEmz6Sr.png\",\"baseDomain\":\"ex-fs.net\"},{\"url\":\"https://myshows.me/profile/\",\"label\":\"myshows\",\"customScreenshotURL\":\"https://i.imgur.com/1RKrjKy.png\",\"baseDomain\":\"myshows.me\"},{\"url\":\"https://next.privat24.ua/\",\"label\":\"privat24\",\"customScreenshotURL\":\"https://i.imgur.com/bTdQFwM.png\"}]"); 177 | 178 | // set home page url 179 | // user_pref("browser.startup.homepage", "https://duckduckgo.com/?key=291864b3d524962d791b3cf990c984fd65285de4d0fdb46be98fa5513c44430ace11193e7896ee611e1fb302e7ac74e5fb1391aacff656b711528ded5fb5370e"); 180 | 181 | // disable web search input on new page 182 | user_pref("browser.newtabpage.activity-stream.showSearch", false); 183 | 184 | // disable recommend extension from Firefox 185 | user_pref("browser.newtabpage.activity-stream.asrouter.userprefs.cfr.addons", false); 186 | 187 | // disable recommend features from Firefox 188 | user_pref("browser.newtabpage.activity-stream.asrouter.userprefs.cfr.features", false); 189 | 190 | // disable highlights 191 | user_pref("browser.newtabpage.activity-stream.feeds.section.highlights", false); 192 | 193 | // disable pocket 194 | user_pref("extensions.pocket.enabled", false); 195 | 196 | // hide pages saved to pocket on new page 197 | user_pref("browser.newtabpage.activity-stream.section.highlights.includePocket", false); 198 | 199 | // disable snippets from home content 200 | user_pref("browser.newtabpage.activity-stream.feeds.snippets", false); 201 | 202 | 203 | // 204 | // ─── SEARCH ────────────────────────────────────────────────────────────────── 205 | // 206 | 207 | // disable URL autocomplete 208 | // user_pref("browser.urlbar.autoFill", false); 209 | 210 | // number of entries that can appear in the location bar 211 | // user_pref("browser.urlbar.maxRichResults", 15); 212 | 213 | // decode copied urls instead of encode 214 | // user_pref("browser.urlbar.decodeURLsOnCopy", true); 215 | 216 | // address bar suggestions 217 | user_pref("browser.urlbar.suggest.topsites", false); 218 | // user_pref("browser.urlbar.suggest.bookmark", false); 219 | // user_pref("browser.urlbar.suggest.history", false); 220 | // user_pref("browser.urlbar.suggest.searches", false); 221 | 222 | // history-first search suggestions in the url bar 223 | // user_pref("browser.urlbar.matchBuckets", "general:5,suggestion:infinity"); 224 | 225 | // disable one-click search engines 226 | user_pref("browser.urlbar.oneOffSearches", false); 227 | 228 | // speeds up the search response 229 | // user_pref("browser.urlbar.delay", 0); 230 | 231 | // search google for "highlighted text" open in a background tab 232 | user_pref("browser.search.context.loadInBackground", true); 233 | 234 | // nicer view for searching strings on a page 235 | user_pref("findbar.highlightAll", true); 236 | user_pref("findbar.modalHighlight", true); 237 | 238 | 239 | 240 | // 241 | // ─── PRIVACY ───────────────────────────────────────────────────────────────── 242 | // 243 | 244 | // allow extensions on Mozilla websites 245 | user_pref("privacy.resistFingerprinting.block_mozAddonManager", true); 246 | user_pref("extensions.webextensions.restrictedDomains", "accounts-static.cdn.mozilla.net,accounts.firefox.com,addons.cdn.mozilla.net,api.accounts.firefox.com,content.cdn.mozilla.net,oauth.accounts.firefox.com,sync.services.mozilla.com,testpilot.firefox.com"); 247 | 248 | // customize content blocking 249 | user_pref("browser.contentblocking.category", "custom"); 250 | 251 | // disable tracking protection in Private Browsing 252 | // user_pref("privacy.trackingprotection.pbmode.enabled", false); 253 | 254 | // disable ask to save logins and passwords 255 | user_pref("signon.rememberSignons", false); 256 | 257 | // block new requests asking to allow notifications 258 | user_pref("permissions.default.desktop-notification", 2); 259 | 260 | // disable block pop-up windows 261 | user_pref("dom.disable_open_during_load", false); 262 | 263 | // disable data collection & crash reports 264 | user_pref("datareporting.healthreport.uploadEnabled", false); 265 | 266 | // disable block dangerous and deceptive content 267 | user_pref("browser.safebrowsing.malware.enabled", false); 268 | 269 | // disable WebRTC leaks 270 | user_pref("media.peerconnection.enabled", false); 271 | 272 | // block browser tracking 273 | user_pref("privacy.donottrackheader.enabled", true); 274 | 275 | // allow search sugggestions in private windows 276 | user_pref("browser.search.suggest.enabled.private", true); 277 | 278 | // ───────────────────────────────────────────────────────────────────────────── 279 | // Disables geolocation and firefox logging geolocation requests. 280 | user_pref("geo.enabled", false); 281 | user_pref("geo.wifi.uri", ""); 282 | user_pref("browser.search.geoip.url", ""); 283 | 284 | // Prevent website tracking clicks. 285 | user_pref("browser.send_pings", false); 286 | 287 | // Only send pings if send and receiving host match (same website). 288 | user_pref("browser.send_pings.require_same_host", true); 289 | 290 | // 291 | // ─── EXTENSIONS ────────────────────────────────────────────────────────────── 292 | // 293 | 294 | // disable new html add-ons manager 295 | // user_pref("extensions.htmlaboutaddons.enabled", false); 296 | // inline options browser for html add-ons manager details 297 | // user_pref("extensions.htmlaboutaddons.inline-options.enabled", false); 298 | 299 | // user_pref("extensions.htmlaboutaddons.recommendations.enabled", false); 300 | // user_pref("extensions.htmlaboutaddons.discover.enabled", false); 301 | 302 | // disable add-on abuse reporting 303 | user_pref("extensions.abuseReport.enabled", false); 304 | 305 | // disable extension compatibility checks 306 | user_pref("extensions.checkCompatibility", false); 307 | 308 | // disable update add-ons automatically 309 | user_pref("extensions.update.autoUpdateDefault", false); 310 | user_pref("extensions.pendingOperations", false); 311 | 312 | // disable extension install delay 313 | user_pref("security.dialog_enable_delay", 0); 314 | 315 | user_pref("permissions.desktop-notification.postPrompt.enabled", false); 316 | 317 | // 318 | // ─── PERFORMANCE ───────────────────────────────────────────────────────────── 319 | // 320 | 321 | // limit content processes load 322 | // user_pref("dom.ipc.processCount", 4); 323 | 324 | // don’t load tabs until selected 325 | user_pref("browser.sessionstore.restore_on_demand", true); 326 | user_pref("browser.sessionstore.restore_pinned_tabs_on_demand", false); 327 | 328 | // maximum number of recently visited pages to store in memory 329 | // user_pref("browser.sessionhistory.max_total_viewers", 2); 330 | 331 | // the maximum memory to use to cache 332 | // user_pref("browser.cache.disk.enable", 51200); 333 | 334 | // the maximum memory to use to cache 335 | // user_pref("browser.cache.offline.capacity", false); 336 | 337 | // the maximum memory to use to cache 338 | // user_pref("browser.cache.memory.max_entry_size", 4096); 339 | 340 | // number of milliseconds between session saving operations 341 | // user_pref("browser.sessionstore.interval", 100000); 342 | 343 | // enable dns prefetching 344 | // user_pref("network.dns.disablePrefetch", true); 345 | 346 | // when to send the Referer header and set document.referrer 347 | // user_pref("network.http.sendRefererHeader", 0); 348 | 349 | user_pref("dom.indexedDB.enabled", true); 350 | 351 | /* DISABLE ANIMATIONS ─────────────────────────────────────────────────────── */ 352 | 353 | // 354 | user_pref("config.trim_on_minimize", false); 355 | 356 | 357 | // disable the "website is now full screen" warning 358 | user_pref("full-screen-api.warning.delay", 0); 359 | user_pref("full-screen-api.warning.timeout", 0); 360 | 361 | // disable fullscreen animation 362 | user_pref("full-screen-api.transition-duration.enter", "0 0"); 363 | user_pref("full-screen-api.transition-duration.leave", "0 0"); 364 | 365 | // disable cosmetic animations (tab open/close; fullscreen enter) 366 | user_pref("toolkit.cosmeticAnimations.enabled", false); 367 | 368 | 369 | // 370 | // ─── DEVTOOLS ──────────────────────────────────────────────────────────────── 371 | // 372 | 373 | // devtools theme 374 | user_pref("devtools.theme", "dark"); 375 | 376 | // disable paste protection 377 | user_pref("devtools.selfxss.count", 100); 378 | 379 | // enable dom property viewer 380 | // user_pref("devtools.dom.enabled", true); 381 | 382 | // devtools tabs order 383 | user_pref("devtools.toolbox.tabsOrder", "inspector,webconsole,netmonitor,styleeditor,dom,jsdebugger,performance,memory,storage,accessibility"); 384 | 385 | user_pref("devtools.inspector.three-pane-enabled", false); 386 | user_pref("devtools.inspector.activeSidebar", "ruleview"); 387 | 388 | 389 | // user_pref("devtools.toolbox.footer.height", 359); 390 | // user_pref("devtools.toolsidebar-height.inspector", 350); 391 | // user_pref("devtools.toolsidebar-width.inspector", 350); 392 | // user_pref("devtools.toolsidebar-width.inspector.splitsidebar", 350); 393 | 394 | // copy screenshots to the clipboard 395 | // user_pref("devtools.screenshot.clipboard.enabled", true); 396 | user_pref("devtools.screenshot.audio.enabled", false); 397 | 398 | // inspector default color unit 399 | // user_pref("devtools.defaultColorUnit", "hex"); 400 | 401 | // disable addons signing 402 | user_pref("xpinstall.signatures.required", false); 403 | 404 | user_pref("app.normandy.first_run", false); 405 | user_pref("toolkit.telemetry.reportingpolicy.firstRun", false); 406 | user_pref("trailhead.firstrun.didSeeAboutWelcome", true); 407 | 408 | // hide what-new 409 | user_pref("browser.newtabpage.activity-stream.asrouter.providers.whats-new-panel", "{\"id\":\"whats-new-panel\",\"enabled\":false,\"type\":\"remote-settings\",\"bucket\":\"whats-new-panel\",\"updateCycleInMs\":3600000}"); 410 | 411 | // enabling the browser toolbox 412 | user_pref("devtools.chrome.enabled", true); 413 | user_pref("devtools.debugger.remote-enabled", true); 414 | user_pref("devtools.debugger.prompt-connection", false); 415 | 416 | // ───────────────────────────────────────────────────────────────────────────── 417 | 418 | // user_pref("browser.fixup.alternate.enabled", false); 419 | 420 | 421 | // user_pref("browser.urlbar.autocomplete.enabled", false); 422 | // user_pref("browser.urlbar.unifiedcomplete", false); 423 | 424 | // user_pref("browser.search.defaultenginename", "GitHub"); 425 | // user_pref("browser.search.defaulturl", "https://www.google.com.ua/search?lr=&ie=UTF-8&oe=UTF-8&q="); 426 | // user_pref("browser.search.order.1", "GitHub"); 427 | -------------------------------------------------------------------------------- /src/user.js: -------------------------------------------------------------------------------- 1 | // 2 | // ─── GENERAL ───────────────────────────────────────────────────────────────── 3 | // 4 | 5 | // enable supports of userChrome.css and userContent.css 6 | // @see https://www.ghacks.net/2019/05/24/firefox-69-userchrome-css-and-usercontent-css-disabled-by-default/ 7 | user_pref("toolkit.legacyUserProfileCustomizations.stylesheets", true); 8 | 9 | // display about:config normally without a warning 10 | user_pref("browser.aboutConfig.showWarning", false); 11 | 12 | // change the interface language "en-US/ru-RU" 13 | user_pref("intl.locale.requested", "en-US"); 14 | 15 | // disable cycles through tabs in recently used order 16 | user_pref("browser.ctrlTab.recentlyUsedOrder", false); 17 | 18 | // disable spell checking 19 | user_pref("layout.spellcheckDefault", 0); 20 | 21 | // enable alt+click on the link for download without prompts 22 | user_pref("browser.altClickSave", true); 23 | 24 | // display all plugins in the Download Actions dialog 25 | user_pref("browser.download.hide_plugins_without_extensions", false); 26 | 27 | // save files with unknown mime type 28 | // eslint-disable-next-line prettier/prettier 29 | user_pref("browser.helperApps.neverAsk.saveToDisk", "application/msword, application/csv, application/ris, text/csv, image/png, image/svg+xml, application/pdf, text/html, text/plain, application/zip, application/x-zip, application/x-zip-compressed, application/download, application/octet-stream"); 30 | 31 | // disable auto install updates 32 | user_pref("app.update.auto", false); 33 | 34 | // disable background service to install updates 35 | user_pref("app.update.service.enabled", false); 36 | 37 | // disable auto update search engines 38 | user_pref("browser.search.update", false); 39 | 40 | // customize items in toolbar 41 | user_pref("browser.uiCustomization.state", "{\"placements\":{\"widget-overflow-fixed-list\":[],\"nav-bar\":[\"back-button\",\"forward-button\",\"stop-reload-button\",\"home-button\",\"customizableui-special-spring1\",\"sync-button\",\"urlbar-container\",\"customizableui-special-spring2\",\"downloads-button\",\"library-button\",\"sidebar-button\",\"_89299b16-7b8d-48c2-8bdf-e9e4f58de3f6_-browser-action\",\"onepassword4_agilebits_com-browser-action\",\"uc-restart\",\"restart-button\",\"firefox_tampermonkey_net-browser-action\",\"_7a7a4a92-a2a0-41d1-9fd7-1e92480d612d_-browser-action\",\"_d634138d-c276-4fc8-924b-40a0ea21d284_-browser-action\",\"adguardadblocker_adguard_com-browser-action\",\"chrome-store-foxified_jetpack-browser-action\",\"_c2c003ee-bd69-42a2-b0e9-6f34222cb046_-browser-action\",\"_a8332c60-5b6d-41ee-bfc8-e9bb331d34ad_-browser-action\",\"simple-translate_sienori-browser-action\",\"tab-session-manager_sienori-browser-action\",\"addon_darkreader_org-browser-action\",\"firefoxbeta_tampermonkey_net-browser-action\",\"fxa-toolbar-menu-button\"],\"toolbar-menubar\":[\"menubar-items\"],\"TabsToolbar\":[\"tabbrowser-tabs\",\"new-tab-button\",\"alltabs-button\"],\"PersonalToolbar\":[\"personal-bookmarks\"]},\"seen\":[\"developer-button\",\"_c2c003ee-bd69-42a2-b0e9-6f34222cb046_-browser-action\",\"_a8332c60-5b6d-41ee-bfc8-e9bb331d34ad_-browser-action\",\"simple-translate_sienori-browser-action\",\"firefoxbeta_tampermonkey_net-browser-action\",\"onepassword4_agilebits_com-browser-action\",\"_d634138d-c276-4fc8-924b-40a0ea21d284_-browser-action\",\"_7a7a4a92-a2a0-41d1-9fd7-1e92480d612d_-browser-action\",\"webide-button\",\"adguardadblocker_adguard_com-browser-action\",\"addon_darkreader_org-browser-action\",\"firefox_tampermonkey_net-browser-action\",\"uc-restart\",\"chrome-store-foxified_jetpack-browser-action\",\"_89299b16-7b8d-48c2-8bdf-e9e4f58de3f6_-browser-action\",\"restart-button\",\"tab-session-manager_sienori-browser-action\"],\"dirtyAreaCache\":[\"nav-bar\",\"TabsToolbar\",\"PersonalToolbar\"],\"currentVersion\":16,\"newElementCount\":19}"); 42 | 43 | // disable beforeunload events (e.g. “Are you sure you want to leave this page?” 44 | user_pref("dom.disable_beforeunload", true); 45 | 46 | // disable screenshots 47 | // eslint-disable-next-line prettier/prettier 48 | user_pref("extensions.screenshots.disabled", true); 49 | 50 | 51 | 52 | // 53 | // ─── BOOKMARKS ─────────────────────────────────────────────────────────────── 54 | // 55 | 56 | // save bookmarks.html to the profile on browser exit. 57 | user_pref("browser.bookmarks.autoExportHTML", true); 58 | 59 | // define the number of bookmarks backups 60 | user_pref("browser.bookmarks.max_backups", 3); 61 | 62 | // 63 | // ─── BEHAVIOUR ─────────────────────────────────────────────────────────────── 64 | // 65 | 66 | // ─── OPEN URLS ─────────────────────────────────────────────────────────────── 67 | 68 | // force links to open in the same tab 69 | // 3 = divert new window to a new tab (default) 70 | // 2 = allow link to open a new window 71 | // 1 = force new window into same tab 72 | user_pref("browser.link.open_newwindow", 1); 73 | 74 | // divert links opened via JS OR HTML target="_blank" 75 | // 0 = apply the setting under (A) to ALL new windows (even script windows) 76 | // 2 = apply the setting under (A) to normal windows, but NOT to script windows with features (default) 77 | // 1 = override the setting under (A) and always use new windows 78 | user_pref("browser.link.open_newwindow.restriction", 2); 79 | 80 | // for links in other programs 81 | // -1 = apply the setting under (A) to external links (default) 82 | // 3 = open external links in a new tab in the last active window 83 | // 2 = open external links in a new window 84 | // 1 = open external links in the last active tab replacing the current page 85 | user_pref("browser.link.open_newwindow.override.external", 3); 86 | 87 | // open tabs to the right of the current tab 88 | user_pref("browser.tabs.insertAfterCurrent", true); 89 | 90 | 91 | // open bookmarks in background enstead of switch to it 92 | // user_pref("browser.tabs.loadBookmarksInBackground", true); 93 | 94 | // user_pref("browser.tabs.loadInBackground", true); 95 | // user_pref("browser.tabs.loadDivertedInBackground", true); 96 | 97 | // fix telegram links handler 98 | user_pref("network.protocol-handler.expose.tg", false); 99 | // user_pref("network.protocol-handler.expose.magnet", false); 100 | 101 | 102 | // 103 | // ─── UI ────────────────────────────────────────────────────────────────────── 104 | // 105 | 106 | // theme 107 | user_pref("extensions.activeThemeID", "firefox-compact-dark@mozilla.org"); 108 | 109 | // tiny bars 110 | user_pref("browser.tabs.drawInTitlebar", false); 111 | user_pref("browser.uidensity", 1); 112 | user_pref("browser.tabs.extraDragSpace", true); 113 | 114 | // enable dark-mode 115 | user_pref("browser.in-content.dark-mode", true); 116 | user_pref("ui.systemUsesDarkTheme", 1); 117 | 118 | // user_pref("browser.display.background_color", "#D3D3D3"); 119 | 120 | // move sidebar to right 121 | user_pref("sidebar.position_start", false); 122 | 123 | // disable autoplay 124 | // user_pref("media.autoplay.enabled", false); 125 | user_pref("media.autoplay.default", 1); 126 | user_pref("media.autoplay.allow-muted", false); 127 | 128 | user_pref("media.videocontrols.picture-in-picture.enabled", false); 129 | user_pref("media.videocontrols.picture-in-picture.video-toggle.enabled", true); 130 | 131 | // disable zoom with cmd+scroll 132 | user_pref("mousewheel.with_meta.action", 1); 133 | 134 | // fix the dark theme bug 135 | user_pref("widget.content.allow-gtk-dark-theme", true); 136 | user_pref("widget.content.gtk-theme-override", "Adwaita:light"); 137 | 138 | // fonts 139 | user_pref("font.name.monospace.x-western", "FiraCode Nerd Font Mono"); 140 | user_pref("font.name.sans-serif.x-western", "SF Pro Display"); 141 | 142 | /* READER MODE─────────────────────────────────────────────────────────────── */ 143 | // enable dark theme 144 | user_pref("reader.color_scheme", "dark"); 145 | user_pref("reader.content_width", 7); 146 | 147 | /* TABS ───────────────────────────────────────────────────────────────────── */ 148 | 149 | // tab audio icon 150 | user_pref("browser.tabs.showAudioPlayingIcon", true); 151 | 152 | // materialfox 153 | // user_pref("materialFox.reduceTabOverflow", true); 154 | // user_pref("svg.context-properties.content.enabled", true); 155 | 156 | // always show tab close button 157 | user_pref("browser.tabs.closeButtons", 1); 158 | 159 | // replicate chrome behaviour for clipped tabs 160 | user_pref("browser.tabs.tabClipWidth", 80); 161 | 162 | // backspace to go back 163 | user_pref("browser.backspace_action", 0); 164 | 165 | // 166 | // ─── HOME ──────────────────────────────────────────────────────────────────── 167 | // 168 | 169 | // restore previous session 170 | user_pref("browser.startup.page", 3); 171 | 172 | // 4 rows of top sites 173 | user_pref("browser.newtabpage.activity-stream.topSitesRows", 4); 174 | 175 | // pinned sites top sites 176 | user_pref("browser.newtabpage.pinned", "[{\"url\":\"https://github.com/\",\"label\":\"github\",\"baseDomain\":\"github.com\"},{\"url\":\"https://gist.github.com/dotiful?direction=deschttps://gist.github.com/dotiful?direction=desc&sort=updated\",\"label\":\"gists\",\"baseDomain\":\"gist.github.com\"},{\"url\":\"https://github.com/dotiful?tab=stars\",\"label\":\"stars\",\"baseDomain\":\"github.com\"},{\"url\":\"https://gitlab.com/?nav_source=navbar\",\"label\":\"gitlab\",\"customScreenshotURL\":\"https://i.imgur.com/AGSiONj.png\",\"baseDomain\":\"gitlab.com\"},{\"url\":\"https://eu-central-1.console.aws.amazon.com/ec2/v2/home?region=eu-central-1#Instances:sort=instanceId\",\"label\":\"aws\",\"customScreenshotURL\":\"https://i.imgur.com/irpKuOG.png\",\"baseDomain\":\"eu-central-1.console.aws.amazon.com\"},{\"url\":\"https://console.cloud.google.com/home/dashboard?authuser=2&project=wrtdev\",\"label\":\"GCP\",\"customScreenshotURL\":\"https://i.imgur.com/XUwMPRs.png\",\"baseDomain\":\"console.cloud.google.com\"},{\"url\":\"https://dash.cloudflare.com\",\"label\":\"cloudflare\",\"customScreenshotURL\":\"https://i.imgur.com/2dddPbm.png\",\"baseDomain\":\"dash.cloudflare.com\"},{\"url\":\"https://adwrt.cf/\",\"label\":\"adhome\",\"customScreenshotURL\":\"https://i.imgur.com/dgvkfMl.png\",\"baseDomain\":\"adwrt.cf\"},{\"url\":\"https://www.google.com.ua/\",\"label\":\"google\",\"customScreenshotURL\":\"https://i.imgur.com/rT7EyzQ.png\",\"baseDomain\":\"google.com.ua\"},{\"url\":\"https://mail.google.com/mail/u/0/\",\"label\":\"artdev\",\"customScreenshotURL\":\"https://i.imgur.com/2PwPKoS.png\",\"baseDomain\":\"mail.google.com\"},{\"url\":\"https://mail.google.com/mail/u/1/\",\"label\":\"dots\",\"customScreenshotURL\":\"https://i.imgur.com/2PwPKoS.png\",\"baseDomain\":\"mail.google.com\"},{\"url\":\"https://mail.google.com/mail/u/2/\",\"label\":\"wrt\",\"customScreenshotURL\":\"https://i.imgur.com/2PwPKoS.png\",\"baseDomain\":\"mail.google.com\"},{\"url\":\"https://www.youtube.com/\",\"label\":\"youtube\",\"customScreenshotURL\":\"https://i.imgur.com/W5nyO7W.png\",\"baseDomain\":\"youtube.com\"},{\"url\":\"https://drive.google.com/\",\"label\":\"drive\",\"customScreenshotURL\":\"https://i.imgur.com/41EIr4Q.png\",\"baseDomain\":\"drive.google.com\"},{\"url\":\"https://translate.google.com.ua/#view=home&op=translate&sl=auto&tl=ru\",\"label\":\"translate\",\"customScreenshotURL\":\"https://i.imgur.com/iiTj8hF.png\",\"baseDomain\":\"translate.google.com.ua\"},{\"url\":\"https://www.google.com.ua/maps\",\"label\":\"maps\",\"customScreenshotURL\":\"https://i.imgur.com/FSx9cpO.png\",\"baseDomain\":\"google.com.ua\"},{\"url\":\"https://web.telegram.org/\",\"label\":\"telegram\",\"customScreenshotURL\":\"https://i.imgur.com/VijQNyZ.png\",\"baseDomain\":\"web.telegram.org\"},{\"url\":\"https://www.inoreader.com/\",\"label\":\"inoreader\",\"customScreenshotURL\":\"https://i.imgur.com/9qiR748.png\",\"baseDomain\":\"inoreader.com\"},{\"url\":\"https://www.integromat.com/\",\"label\":\"integromat\",\"customScreenshotURL\":\"https://i.imgur.com/6FEgChu.png\",\"baseDomain\":\"integromat.com\"},{\"url\":\"https://twitter.com/artdevjs/lists/feed\",\"label\":\"twitter\",\"customScreenshotURL\":\"https://i.imgur.com/sfAkrOp.png\",\"baseDomain\":\"twitter.com\"},{\"url\":\"https://www.reddit.com/user/artdevjs/m/favs/new/\",\"label\":\"reddit\",\"customScreenshotURL\":\"https://i.imgur.com/HV6Ur0m.png\",\"baseDomain\":\"reddit.com\"},{\"url\":\"https://www.dropbox.com/home\",\"label\":\"dropbox\",\"customScreenshotURL\":\"https://i.imgur.com/AXrk2CR.png\",\"baseDomain\":\"dropbox.com\"},{\"url\":\"https://bitbucket.org/dashboard/overview\",\"label\":\"bitbucket\",\"customScreenshotURL\":\"https://i.imgur.com/F6sEfIW.png\",\"baseDomain\":\"bitbucket.org\"},{\"url\":\"https://www.npmjs.com\",\"label\":\"npm\",\"customScreenshotURL\":\"https://i.imgur.com/g3ZPxyk.png\",\"baseDomain\":\"npmjs.com\"},{\"url\":\"https://outlook.live.com/mail/inbox\",\"label\":\"outlook\",\"customScreenshotURL\":\"https://i.imgur.com/tK0xCo0.png\",\"baseDomain\":\"outlook.live.com\"},{\"url\":\"https://my.1password.com/home\",\"label\":\"1password\",\"customScreenshotURL\":\"https://i.imgur.com/PHOaimF.png\",\"baseDomain\":\"my.1password.com\"},{\"url\":\"https://www.olx.ua/myaccount/\",\"label\":\"olx\",\"customScreenshotURL\":\"https://i.imgur.com/cozJJwJ.png\",\"baseDomain\":\"olx.ua\"},{\"url\":\"https://artdevjs.imgur.com/all\",\"label\":\"imgur\",\"customScreenshotURL\":\"https://i.imgur.com/hMG9e10.jpg\",\"baseDomain\":\"artdevjs.imgur.com\"},{\"url\":\"https://filmix.co/favorites\",\"label\":\"filmix\",\"customScreenshotURL\":\"https://filmix.co/templates/Filmix/media/img/filmix.png\",\"baseDomain\":\"filmix.co\"},{\"url\":\"http://ex-fs.net/subnews/\",\"label\":\"ex-fs\",\"customScreenshotURL\":\"https://i.imgur.com/cEmz6Sr.png\",\"baseDomain\":\"ex-fs.net\"},{\"url\":\"https://myshows.me/profile/\",\"label\":\"myshows\",\"customScreenshotURL\":\"https://i.imgur.com/1RKrjKy.png\",\"baseDomain\":\"myshows.me\"},{\"url\":\"https://next.privat24.ua/\",\"label\":\"privat24\",\"customScreenshotURL\":\"https://i.imgur.com/bTdQFwM.png\"}]"); 177 | 178 | // set home page url 179 | user_pref("browser.startup.homepage", "https://duckduckgo.com/?key=291864b3d524962d791b3cf990c984fd65285de4d0fdb46be98fa5513c44430ace11193e7896ee611e1fb302e7ac74e5fb1391aacff656b711528ded5fb5370e"); 180 | 181 | // disable web search input on new page 182 | user_pref("browser.newtabpage.activity-stream.showSearch", false); 183 | 184 | // disable recommend extension from Firefox 185 | user_pref("browser.newtabpage.activity-stream.asrouter.userprefs.cfr.addons", false); 186 | 187 | // disable recommend features from Firefox 188 | user_pref("browser.newtabpage.activity-stream.asrouter.userprefs.cfr.features", false); 189 | 190 | // disable highlights 191 | user_pref("browser.newtabpage.activity-stream.feeds.section.highlights", false); 192 | 193 | // disable pocket 194 | user_pref("extensions.pocket.enabled", false); 195 | 196 | // hide pages saved to pocket on new page 197 | user_pref("browser.newtabpage.activity-stream.section.highlights.includePocket", false); 198 | 199 | // disable snippets from home content 200 | user_pref("browser.newtabpage.activity-stream.feeds.snippets", false); 201 | 202 | 203 | // 204 | // ─── SEARCH ────────────────────────────────────────────────────────────────── 205 | // 206 | 207 | // disable URL autocomplete 208 | // user_pref("browser.urlbar.autoFill", false); 209 | 210 | // number of entries that can appear in the location bar 211 | user_pref("browser.urlbar.maxRichResults", 15); 212 | 213 | // decode copied urls instead of encode 214 | user_pref("browser.urlbar.decodeURLsOnCopy", true); 215 | 216 | // history-first search suggestions in the url bar 217 | // user_pref("browser.urlbar.matchBuckets", "general:5,suggestion:infinity"); 218 | 219 | // disable one-click search engines 220 | user_pref("browser.urlbar.oneOffSearches", false); 221 | 222 | // speeds up the search response 223 | user_pref("browser.urlbar.delay", 0); 224 | 225 | // search google for "highlighted text" open in a background tab 226 | user_pref("browser.search.context.loadInBackground", true); 227 | 228 | // nicer view for searching strings on a page 229 | user_pref("findbar.highlightAll", true); 230 | user_pref("findbar.modalHighlight", true); 231 | 232 | 233 | // 234 | // ─── PRIVACY ───────────────────────────────────────────────────────────────── 235 | // 236 | 237 | // allow extensions on Mozilla websites 238 | user_pref("privacy.resistFingerprinting.block_mozAddonManager", true); 239 | user_pref("extensions.webextensions.restrictedDomains", "accounts-static.cdn.mozilla.net,accounts.firefox.com,addons.cdn.mozilla.net,api.accounts.firefox.com,content.cdn.mozilla.net,oauth.accounts.firefox.com,sync.services.mozilla.com,testpilot.firefox.com"); 240 | 241 | // customize content blocking 242 | user_pref("browser.contentblocking.category", "custom"); 243 | 244 | // disable tracking protection in Private Browsing 245 | // user_pref("privacy.trackingprotection.pbmode.enabled", false); 246 | 247 | // disable ask to save logins and passwords 248 | user_pref("signon.rememberSignons", false); 249 | 250 | // block new requests asking to allow notifications 251 | user_pref("permissions.default.desktop-notification", 2); 252 | 253 | // disable block pop-up windows 254 | user_pref("dom.disable_open_during_load", false); 255 | 256 | // disable data collection & crash reports 257 | user_pref("datareporting.healthreport.uploadEnabled", false); 258 | 259 | // disable block dangerous and deceptive content 260 | user_pref("browser.safebrowsing.malware.enabled", false); 261 | 262 | // disable WebRTC leaks 263 | user_pref("media.peerconnection.enabled", false); 264 | 265 | // block browser tracking 266 | user_pref("privacy.donottrackheader.enabled", true); 267 | 268 | // allow search sugggestions in private windows 269 | user_pref("browser.search.suggest.enabled.private", true); 270 | 271 | // ───────────────────────────────────────────────────────────────────────────── 272 | // Disables geolocation and firefox logging geolocation requests. 273 | user_pref("geo.enabled", false); 274 | user_pref("geo.wifi.uri", ""); 275 | user_pref("browser.search.geoip.url", ""); 276 | 277 | // Prevent website tracking clicks. 278 | user_pref("browser.send_pings", false); 279 | 280 | // Only send pings if send and receiving host match (same website). 281 | user_pref("browser.send_pings.require_same_host", true); 282 | 283 | // 284 | // ─── EXTENSIONS ────────────────────────────────────────────────────────────── 285 | // 286 | 287 | // disable new html add-ons manager 288 | user_pref("extensions.htmlaboutaddons.enabled", false); 289 | // inline options browser for html add-ons manager details 290 | user_pref("extensions.htmlaboutaddons.inline-options.enabled", false); 291 | 292 | user_pref("extensions.htmlaboutaddons.recommendations.enabled", false); 293 | user_pref("extensions.htmlaboutaddons.discover.enabled", false); 294 | 295 | // disable add-on abuse reporting 296 | user_pref("extensions.abuseReport.enabled", false); 297 | 298 | // disable extension compatibility checks 299 | user_pref("extensions.checkCompatibility", false); 300 | 301 | // disable update add-ons automatically 302 | user_pref("extensions.update.autoUpdateDefault", false); 303 | user_pref("extensions.pendingOperations", false); 304 | 305 | // disable extension install delay 306 | user_pref("security.dialog_enable_delay", 0); 307 | 308 | user_pref("permissions.desktop-notification.postPrompt.enabled", false); 309 | 310 | // 311 | // ─── PERFORMANCE ───────────────────────────────────────────────────────────── 312 | // 313 | 314 | // limit content processes load 315 | // user_pref("dom.ipc.processCount", 4); 316 | 317 | // don’t load tabs until selected 318 | user_pref("browser.sessionstore.restore_on_demand", true); 319 | user_pref("browser.sessionstore.restore_pinned_tabs_on_demand", false); 320 | 321 | // maximum number of recently visited pages to store in memory 322 | user_pref("browser.sessionhistory.max_total_viewers", 2); 323 | 324 | // the maximum memory to use to cache 325 | // user_pref("browser.cache.disk.enable", 51200); 326 | 327 | // the maximum memory to use to cache 328 | // user_pref("browser.cache.offline.capacity", false); 329 | 330 | // the maximum memory to use to cache 331 | user_pref("browser.cache.memory.max_entry_size", 4096); 332 | 333 | // number of milliseconds between session saving operations 334 | user_pref("browser.sessionstore.interval", 100000); 335 | 336 | // enable dns prefetching 337 | user_pref("network.dns.disablePrefetch", true); 338 | 339 | // when to send the Referer header and set document.referrer 340 | // user_pref("network.http.sendRefererHeader", 0); 341 | 342 | user_pref("dom.indexedDB.enabled", true); 343 | 344 | /* DISABLE ANIMATIONS ─────────────────────────────────────────────────────── */ 345 | 346 | // 347 | user_pref("config.trim_on_minimize", false); 348 | 349 | 350 | // disable the "website is now full screen" warning 351 | user_pref("full-screen-api.warning.delay", 0); 352 | user_pref("full-screen-api.warning.timeout", 0); 353 | 354 | // disable fullscreen animation 355 | user_pref("full-screen-api.transition-duration.enter", "0 0"); 356 | user_pref("full-screen-api.transition-duration.leave", "0 0"); 357 | 358 | // disable cosmetic animations (tab open/close; fullscreen enter) 359 | user_pref("toolkit.cosmeticAnimations.enabled", false); 360 | 361 | 362 | // 363 | // ─── DEVTOOLS ──────────────────────────────────────────────────────────────── 364 | // 365 | 366 | // devtools theme 367 | user_pref("devtools.theme", "dark"); 368 | 369 | // disable paste protection 370 | user_pref("devtools.selfxss.count", 100); 371 | 372 | // enable dom property viewer 373 | user_pref("devtools.dom.enabled", true); 374 | 375 | // devtools tabs order 376 | user_pref("devtools.toolbox.tabsOrder", "inspector,webconsole,netmonitor,styleeditor,dom,jsdebugger,performance,memory,storage,accessibility"); 377 | 378 | user_pref("devtools.inspector.three-pane-enabled", false); 379 | user_pref("devtools.inspector.activeSidebar", "ruleview"); 380 | 381 | 382 | user_pref("devtools.toolbox.footer.height", 359); 383 | user_pref("devtools.toolsidebar-height.inspector", 350); 384 | user_pref("devtools.toolsidebar-width.inspector", 350); 385 | user_pref("devtools.toolsidebar-width.inspector.splitsidebar", 350); 386 | 387 | // copy screenshots to the clipboard 388 | // user_pref("devtools.screenshot.clipboard.enabled", true); 389 | user_pref("devtools.screenshot.audio.enabled", false); 390 | 391 | // inspector default color unit 392 | user_pref("devtools.defaultColorUnit", "hex"); 393 | 394 | // disable addons signing 395 | user_pref("xpinstall.signatures.required", false); 396 | 397 | user_pref("app.normandy.first_run", false); 398 | user_pref("toolkit.telemetry.reportingpolicy.firstRun", false); 399 | user_pref("trailhead.firstrun.didSeeAboutWelcome", true); 400 | 401 | // hide what-new 402 | user_pref("browser.newtabpage.activity-stream.asrouter.providers.whats-new-panel", "{\"id\":\"whats-new-panel\",\"enabled\":false,\"type\":\"remote-settings\",\"bucket\":\"whats-new-panel\",\"updateCycleInMs\":3600000}"); 403 | 404 | // user_pref("devtools.chrome.enabled", true); 405 | // user_pref("devtools.debugger.remote-enabled", true); 406 | // user_pref("devtools.debugger.prompt-connection", false); 407 | 408 | // ───────────────────────────────────────────────────────────────────────────── 409 | 410 | // user_pref("browser.fixup.alternate.enabled", false); 411 | // user_pref("browser.urlbar.suggest.bookmark", false); 412 | // user_pref("browser.urlbar.suggest.history", false); 413 | // user_pref("browser.urlbar.suggest.searches", false); 414 | // user_pref("browser.urlbar.autocomplete.enabled", false); 415 | // user_pref("browser.urlbar.unifiedcomplete", false); 416 | 417 | // user_pref("browser.search.defaultenginename", "GitHub"); 418 | // user_pref("browser.search.defaulturl", "https://www.google.com.ua/search?lr=&ie=UTF-8&oe=UTF-8&q="); 419 | // user_pref("browser.search.order.1", "GitHub"); 420 | -------------------------------------------------------------------------------- /tasks/bundle.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp' 2 | import { paths } from '../gulpfile' 3 | import del from 'del' 4 | import zip from 'gulp-zip' 5 | import fancyLog from 'fancy-log' 6 | import chalk from 'chalk' 7 | import pkg from '../package.json' 8 | 9 | function zipFiles() { 10 | return gulp.src('build/**/*') 11 | .pipe(zip(`${pkg.name}.zip`)) 12 | .pipe(gulp.dest('build')) 13 | } 14 | 15 | function cleanZippedFiles() { 16 | return del(['build/*', '!build/*.zip']) 17 | } 18 | 19 | async function logBundle() { 20 | fancyLog() 21 | fancyLog(chalk.green(`Bundle successful!`)) 22 | fancyLog(chalk.cyan(`The zip is ready to be published`)) 23 | fancyLog() 24 | fancyLog(` ${chalk.gray(`build/`)}${pkg.name}.zip`) 25 | fancyLog() 26 | } 27 | 28 | export const bundle = gulp.series(zipFiles, cleanZippedFiles, logBundle) 29 | -------------------------------------------------------------------------------- /tasks/cfg.js: -------------------------------------------------------------------------------- 1 | export const paths = { 2 | scripts: [ 3 | 'src/options.js', 4 | 'src/content.js', 5 | 'src/background.js', 6 | 'src/popup.js', 7 | ], 8 | 9 | styles: ['src/options.scss', 'src/popup.scss'], 10 | 11 | manifest: 'src/manifest.json', 12 | }; 13 | -------------------------------------------------------------------------------- /tasks/clean.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp' 2 | import { paths } from './cfg' 3 | import del from 'del' 4 | 5 | export function clean() { 6 | return del(['build']) 7 | } 8 | -------------------------------------------------------------------------------- /tasks/index.js: -------------------------------------------------------------------------------- 1 | export { clean } from './clean' 2 | export { scripts } from './scripts' 3 | export { styles } from './styles' 4 | export { markup } from './markup' 5 | export { images } from './images' 6 | export { manifest } from './manifest' 7 | export { watch } from './watch' 8 | export { bundle } from './bundle' 9 | -------------------------------------------------------------------------------- /tasks/manifest.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp' 2 | import { paths } from '../gulpfile' 3 | import jeditor from 'gulp-json-editor' 4 | import gulpif from 'gulp-if' 5 | 6 | 7 | function addAutoreloadScript(manifestJson) { 8 | const hasScripts = manifestJson.background && manifestJson.background.scripts 9 | 10 | return { 11 | ...manifestJson, 12 | background: { 13 | ...manifestJson.background, 14 | scripts: [ 'autoreload.js', ...(hasScripts ? manifestJson.background.scripts : []) ], 15 | }, 16 | } 17 | } 18 | 19 | export function manifest() { 20 | return gulp.src(paths.manifest) 21 | .pipe(gulpif(process.env.NODE_ENV === 'development', jeditor(addAutoreloadScript))) 22 | .pipe(gulp.dest('build')) 23 | } 24 | -------------------------------------------------------------------------------- /tasks/scripts.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp' 2 | import { paths } from '../gulpfile' 3 | import path from 'path' 4 | import webpackStream from 'webpack-stream' 5 | import webpack from 'webpack' 6 | import Dotenv from 'dotenv-webpack' 7 | import addSrc from 'gulp-add-src' 8 | import gulpif from 'gulp-if' 9 | import named from 'vinyl-named' 10 | import notify from 'gulp-notify' 11 | 12 | 13 | const webpackConfig = { 14 | mode: process.env.NODE_ENV, 15 | devtool: 'source-map', 16 | output: { 17 | filename: '[name].js', 18 | }, 19 | module: { 20 | rules: [ 21 | { 22 | test: /\.js$/, 23 | exclude: /node_modules/, 24 | use: { 25 | loader: 'babel-loader', 26 | options: { 27 | cacheDirectory: true, 28 | }, 29 | }, 30 | }, 31 | ], 32 | }, 33 | // use automatically in your code process.env.NODE_ENV 34 | // and all of the other env variables 35 | plugins: [ 36 | new Dotenv({ systemvars: true }), 37 | ], 38 | // import files without doing the ../../../ 39 | resolve: { 40 | modules: ['node_modules', 'src'], 41 | }, 42 | // only log errors to console, 43 | // gulp handles the rest 44 | stats: 'errors-only', 45 | // disable webpack's default behavior, which is 46 | // targeted to web applications development 47 | performance: false, 48 | optimization: { 49 | splitChunks: false, 50 | }, 51 | } 52 | 53 | export function scripts() { 54 | return gulp.src(paths.scripts, { allowEmpty: true }) 55 | .pipe(gulpif(process.env.NODE_ENV === 'development', addSrc('utils/autoreload.js'))) 56 | .pipe(named()) 57 | .pipe(webpackStream(webpackConfig, webpack)) 58 | .pipe(gulp.dest('build')) 59 | } 60 | -------------------------------------------------------------------------------- /tasks/styles.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp' 2 | import { paths } from '../gulpfile' 3 | import sass from 'gulp-sass' 4 | import moduleImporter from 'sass-module-importer' 5 | import postcss from 'gulp-postcss' 6 | import postcssPresetEnv from 'postcss-preset-env' 7 | import notify from 'gulp-notify' 8 | 9 | 10 | export function styles() { 11 | return gulp.src(paths.styles, { allowEmpty: true, sourcemaps: true }) 12 | .pipe( 13 | sass({ 14 | // compile to expanded css because 15 | // this is a browser extension 16 | outputStyle: 'expanded', 17 | // import scss from node_modules 18 | importer: moduleImporter(), 19 | includePaths: 'node_modules/', 20 | }) 21 | ) 22 | .on('error', notify.onError({ 23 | title: 'Error compiling sass!', 24 | })) 25 | .pipe( 26 | postcss([ 27 | // autoprefixer for the browserslist in package.json 28 | // and other futuristic css features 29 | postcssPresetEnv({ stage: -1 }), 30 | ]) 31 | ) 32 | .on('error', notify.onError({ 33 | title: 'Error compiling postcss!', 34 | })) 35 | .pipe(gulp.dest('build', { sourcemaps: '.' })) 36 | } 37 | -------------------------------------------------------------------------------- /tasks/syncy.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp' 2 | import syncy from 'syncy' 3 | 4 | export function sync(done) { 5 | return syncy(['node_modules/gulp/**'], 'dest') 6 | .then(() => { 7 | done(); 8 | }) 9 | .catch((err) => { 10 | done(err); 11 | }); 12 | } 13 | -------------------------------------------------------------------------------- /tasks/watch.js: -------------------------------------------------------------------------------- 1 | import gulp from 'gulp' 2 | import { paths } from '../gulpfile' 3 | import { scripts, styles, markup, images, manifest } from '.' 4 | import io from 'socket.io' 5 | import fancyLog from 'fancy-log' 6 | import chalk from 'chalk' 7 | 8 | export function watch() { 9 | const server = io.listen(process.env.WEBSOCKET_PORT) 10 | let socket 11 | server.on('connection', (newSocket) => { socket = newSocket }) 12 | 13 | async function triggerFileChange() { 14 | socket.emit('file changed', () => { 15 | fancyLog(chalk.yellow(`Extension reloaded!`)) 16 | }) 17 | } 18 | 19 | gulp.watch('src/**/*.js', gulp.series(scripts, triggerFileChange)) 20 | gulp.watch('src/**/*.scss', gulp.series(styles, triggerFileChange)) 21 | gulp.watch(paths.manifest, gulp.series(manifest, triggerFileChange)) 22 | gulp.watch(paths.images, gulp.series(images, triggerFileChange)) 23 | gulp.watch(paths.markup, gulp.series(markup, triggerFileChange)) 24 | 25 | fancyLog() 26 | fancyLog(chalk.green(`Compiled successfully!`)) 27 | fancyLog(chalk.cyan(`To load the unpacked extension and start the ${chalk.bold(`autoreload`)}:`)) 28 | fancyLog() 29 | fancyLog(` 1. Go to ${chalk.underline.bold(`chrome://extensions/`)}`) 30 | fancyLog(` 2. Make sure ${chalk.bold(`Developer mode`)} is on`) 31 | fancyLog(` 3. Click ${chalk.bold(`Load unpacked`)} and choose the ${chalk.bold(`build/`)} folder`) 32 | fancyLog() 33 | } 34 | --------------------------------------------------------------------------------