diff --git a/build/prod/background.html b/build/prod/background.html index 0db47cdf..593d8c2a 100644 --- a/build/prod/background.html +++ b/build/prod/background.html @@ -1,6 +1,12 @@ - - - - - - + + + + + + + + + + + + diff --git a/build/prod/options.html b/build/prod/options.html index a6af5270..1948d2da 100644 --- a/build/prod/options.html +++ b/build/prod/options.html @@ -7,6 +7,8 @@ QuicKey Options + + diff --git a/docs/firefox-store-description.txt b/docs/firefox-store-description.txt new file mode 100644 index 00000000..42287f17 --- /dev/null +++ b/docs/firefox-store-description.txt @@ -0,0 +1,292 @@ +# Tag line + + +## Chrome store description from manifest + +Add keyboard shortcuts to switch tabs with a Quicksilver-style search or a most recently used menu + + +## Website title + +QuicKey | Jump between recent tabs in Chrome via keyboard or menu +QuicKey | Quickly jump to recent tabs in Chrome via keyboard or menu +QuicKey | Jump to recent tabs via keyboard or menu +QuicKey | Jump to recent tabs in Chrome via keyboard or menu +QuicKey | The fastest way to find recent tabs in Chrome via keyboard or menu +QuicKey | The fastest way to jump to recent tabs via keyboard or menu + +QuicKey – The quick tab switcher +QuicKey – The quick tab manager + + +## Website description + +Have dozens of tabs open? Quickly jump between them with QuicKey, a Chrome extension that adds keyboard shortcuts to switch tabs using a Quicksilver-style search or a most recently used (MRU) menu. +Have dozens of tabs open? Quickly jump between them with QuicKey, a Chrome extension that adds keyboard shortcuts to switch tabs with a Quicksilver-style search or a most recently used (MRU) menu. + +Quickly navigate all your open tabs with QuicKey, a Chrome extension that adds keyboard shortcuts to switch tabs with a Quicksilver-style search or a most recently used (MRU) menu. +Switch tabs instantly! + +A Chrome extension that adds keyboard shortcuts to switch tabs with a Quicksilver-style search or a most recently used (MRU) menu. + + +## Search result + +QuicKey | Jump bewteen recent tabs in Chrome via keyboard or menu +https://fwextensions.github.io/QuicKey/ +Have dozens of open tabs? Quickly jump between them with QuicKey, a Chrome extension that adds keyboard shortcuts to switch tabs with a Quicksilver-style search or a most recently used (MRU) menu. + +Stop hunting for that tab and start jumping! + + +## Old + +Switch tabs with a Quicksilver-style search or a most-recently-used menu + +Add keyboard shortcuts to switch tabs with a Quicksilver-style search or a most recently used menu +Add keyboard shortcuts in Chrome to switch tabs with a Quicksilver-style search or a most recently used menu + +Switch tabs using the keyboard and a Quicksilver-style search or a most-recently-used menu +Use keyboard shortcuts to switch tabs using a Quicksilver-style search or a most-recently-used menu +Keep your hands on the keyboard and switch tabs using a Quicksilver search or a most-recently-used menu + +Keep your hands on the keyboard and switch tabs using a Quicksilver-style search or a most-recently-used menu +Switch tabs via the keyboard and a Quicksilver-style search or a most-recently-used menu + +Keyboard-centric tab-switcher +Switch tabs using the keyboard and a Quicksilver search or a most-recently-used menu +Switch tabs with the keyboard and a Quicksilver-style search or an MRU menu +Switch tabs via the keyboard using a Quicksilver-style search or an MRU menu + +Switch tabs with a Quicksilver-style search or a visual MRU tab list + +Switch tabs or access bookmarks and history with a Quicksilver-style search! Also supports tabs suspended by The Great Suspender. + +Quickly switch tabs or access bookmarks and history with a Quicksilver-style search and MRU tab navigation +Switch tabs or access bookmarks and history with a Quicksilver-style search or a most recently used (MRU) tab list +Switch tabs with a Quicksilver-style search or a most recently used (MRU) tab list + + +# Search terms in Edge store + +tab switcher +tab manager +MRU tab menu +most recently used tabs menu +recent tabs menu +tab search +ctrl-tab navigation + + +Any open tab can be searched immediately after installation. The list of recent tabs will be empty immediately after the extension is installed, but tabs will be added to the list as you switch between them. Switching the OS to dark mode will update the colors in the menu and options page. + + + + +★ New options in v1.7.0 + + • Limit recent tab navigation to the current browser window + • Limit tab search results to the current browser window + + +★ Use CTRL-TAB to switch between recent tabs + +With a little extra work, you can make QuicKey respond to the Holy Grail of keyboard shortcuts: CTRL-TAB. + +Learn how at https://fwextensions.github.io/QuicKey/ctrl-tab/ + +You can customize the shortcut keys (other than CTRL-TAB) by right-clicking the QuicKey icon and selecting Options. + + +★ InPrivate mode + +To switch to InPrivate tabs as well as normal ones, right-click the QuicKey icon and select "Extension options" from the menu. Scroll to the very bottom of the QuicKey options page and then click the "Change InPrivate settings" button. On the extensions page that opens, scroll down to the "Allow in InPrivate" option and click the toggle button next to it. + +Tabs in InPrivate mode display the InPrivate icon under the page's favicon, so you can distinguish a normal tab from an InPrivate one with the same title. + + + + +★ +➤ +↑ ↓ + +https://addons.mozilla.org/en-US/firefox/addon/quickey-the-quick-tab-switcher/ + + +# Description + +Add keyboard shortcuts to switch tabs with a Quicksilver-style search or a most recently used menu. No mouse needed! + + • Press ALT-Q (CTRL-Q on macOS) + • Type a few letters + • Press ENTER to switch to the selected tab + + +★ Switch between the most recently used tabs + + ➤ NOTE: When first installed, QuicKey doesn't know which tabs have been + recently used, but as you use the browser, tabs will get added to the + most recently used (MRU) list. + +Opening QuicKey displays a list of the last 50 tabs you've visited, in order of recency. Click a tab to switch to it, or use one of the keyboard shortcuts below to navigate the recently used tab history: + + ➤ To switch between the two most recent tabs: + • Press ALT-Z (CTRL-Z on macOS). + OR: + • Quickly double-press ALT-Q (CTRL-Q on macOS). + + ➤ To navigate farther back in the MRU list: + • Press ALT-A (CTRL-A on macOS) once to switch to the previous tab. + The QuicKey icon will invert for .75 seconds. + • Press ALT-A while the icon is inverted to switch to older tabs, once + for each tab. + • Press ALT-S to move to newer tabs. + • Pause to let the icon revert to normal. + • Press ALT-A again to switch back to the tab you initially started on. + + ➤ To pick a recent tab from the MRU list: + • Press the shortcut but keep holding the ALT key (CTRL key on macOS). + • Press W or ↓ to move down through the list of recent tabs. + • Press SHIFT-W or ↑ to move up. + • Release ALT to switch to the selected tab. + • You can also highlight an item with the mouse, then release ALT to + go to that tab. + +Which shortcuts to use is up to you. Double-pressing ALT-Q is nice because there's just one shortcut to remember, while ALT-Z lets you switch between the two most recently used tabs very rapidly. (You can also double-click the QuicKey icon to toggle between the most recent tabs.) + +ALT-A lets you navigate to even older tabs, though the timing can sometimes be finicky. + +Selecting from the MRU menu by holding down the ALT key provides the closest experience to a typical ALT-TAB menu, but you need to use W instead of TAB to navigate while the menu is open. + +You can change any of these shortcuts by clicking the gear icon in the menu or by right-clicking the QuicKey icon and selecting Options. Then scroll down and click "Change browser shortcuts". Look for the "Switch to the previous/next tab" shortcuts. + +If you enable the option to show the number of open tabs on the QuicKey icon, the badge containing that number will change color while you navigate to older tabs, rather than the icon inverting. + + +★ Search for a tab quickly + +Unlike other tab switchers, QuicKey uses a Quicksilver-style search algorithm to rank the results, where contiguous matches at the beginning of words are higher in the list, as are matches against capital letters. So you only have to type a few letters to quickly find the right tab. + +Use keyboard shortcuts to navigate the list: + + • ENTER: switch to the selected tab + • ↓, SPACE or CTRL-N/J: move down the list + • ↑, SHIFT-SPACE or CTRL-P/K: move up the list + • PG DN: page down the list + • PG UP: page up the list + • END: go to the bottom of the list + • HOME: go to the top of the list + • ESC: close the menu + +Recently used tabs get a slight boost in the search results ranking, so getting back to a tab you were just using should require typing fewer letters. + + +★ Customize shortcuts and other options + +To customize how QuicKey behaves, click the gear icon in the menu, or right-click its icon on the toolbar and select Options. There you can: + + • Customize keyboard shortcuts + • Hide closed tabs from the search results + • Limit navigating recent tabs or searching to the current browser window + • Mark tabs in other browser windows with an icon + • Show the number of open tabs + • Use pinyin to search for Chinese characters + +If you change the keyboard shortcut for showing the QuicKey menu to something other than the default ALT-Q or if you have a non-US keyboard, you'll probably want to also change the key that's used to navigate down the list of recently used tabs (which defaults to W). For instance, if you change the menu shortcut to ALT-Z, you might want to change the navigation key to X, which is right next door. To change it, go to the Options page, click the "Select the next tab" keyboard shortcut picker, and press X. + +When new settings have been added to QuicKey, the gear icon will display a red dot to let you know. + + +★ Limit navigation to the current browser window + +If you have multiple browser windows open, you may want to navigate among only the recent tabs that are in the current window. To enable this behavior, open the Options page and select "Limit recent tabs to the current browser window". Pressing the shortcuts for "Switch instantly between the two most recent tabs" or "Switch to the previous tab" will then switch only between recent tabs in the current window. + +You can also limit searching for tabs to the current browser window. + + +★ Close and reopen tabs + +To close the selected tab, press CTRL-ALT-W (CMD-CTRL-W on macOS, CTRL-ALT-W on Linux). Or hover over a tab and click the X button on the right side of the menu. + +When you open QuicKey, the 25 most recently closed tabs are listed below the recent tabs and shown in a faded state with a clock icon. They are also returned when you type a query, though their rank in the list of results is lower than open tabs. Click a closed tab to reopen it in its original location and with all of its browsing history intact. + +If you don't want any closed tabs to be shown, open the QuicKey options page and uncheck "Include recently closed tabs in the search results". You can also remove the selected closed tab from the browser's history by pressing CTRL-W (CMD-CTRL-W on macOS) or by clicking its X button on the right side of the menu. + + +★ Move tabs + +You can move tabs to the left or right of the current tab, making it easy to pull tabs from other windows into the current one, or to rearrange tabs without using the mouse. + + • Press CTRL-[ to move the selected tab to the left of the current one. + • Press CTRL-] to move it to the right. + +The CTRL key should be used on both Windows and macOS. Note that you cannot move tabs between normal and InPrivate windows. + + +★ Search bookmarks + +To find a bookmark, type "/b" and a space in the search box, then part of the bookmark's name or URL. + + • Press ENTER to open it in the current tab. + • Press CTRL-ENTER (CMD-ENTER on macOS) to open it in a new tab in + the current window. + • Press SHIFT-ENTER to open it in a new window. + + +★ Search the browser history + +To find something in the last 2000 pages of your browser history, type "/h" and a space in the search box, then part of the page's name or URL. + +The same CTRL-ENTER (CMD-ENTER on macOS) and SHIFT-ENTER shortcuts will open the visited page in a new tab or window. + + +★ Delete bookmarks and history items + +To delete the selected bookmark or history item, press CTRL-W (CMD-CTRL-W on macOS). Or hover over an item and click the X button on the right side of the menu. You'll be asked to confirm the deletion of bookmarks. + + +★ Copy a URL or title + +You can also copy the URL and title of the selected tab, bookmark or history item: + + • Press CTRL-C (CMD-C on macOS) to copy just the URL. + • Press CTRL-SHIFT-C (CMD-SHIFT-C on macOS) to copy both the item's + title and its URL, one per line. + + +★ Private browsing + +QuicKey does not currently support running in windows that are set to private browsing mode. + + +★ Privacy policy + +When first installed, QuicKey asks for these permissions: + + ➤ "Read and modify your browsing history on all your signed-in devices" + + QuicKey uses this permission to let you search the titles and URLs of + the open tabs, as well as pages from your history. The "all your + signed-in devices" part is there only so that recently closed tabs can be + restored with their full history. The only time QuicKey changes your + browsing history is when you choose to delete a history item. + + ➤ "Read and change your favorites" + + QuicKey uses this permission to let you search the titles and URLs of + pages in your favorites. The only time it changes your favorites is + when you choose to delete one. + +QuicKey can't access or manipulate the content of any pages you visit and doesn't transmit any information other than some anonymized diagnostic data. + + +★ Support and source code + +Get more information at https://fwextensions.github.io/QuicKey/ + +Report a bug or request a feature at https://fwextensions.github.io/QuicKey/support/ + +View the release history at https://fwextensions.github.io/QuicKey/releases + +See the source code at https://github.com/fwextensions/QuicKey diff --git a/docs/releases/index.md b/docs/releases/index.md index 60db9e97..4ba505bb 100644 --- a/docs/releases/index.md +++ b/docs/releases/index.md @@ -8,6 +8,13 @@ comments: true # Release history +## 1.8.0 - 2022-10-26 + +### Added + +* Added support for Firefox and added it to the [Mozilla add-ons store](https://addons.mozilla.org/en-US/firefox/addon/quickey-the-quick-tab-switcher/). No changes for other browsers. + + ## 1.7.4 - 2022-06-18 ### Fixed diff --git a/package-lock.json b/package-lock.json index 0a7da857..199b46f5 100644 --- a/package-lock.json +++ b/package-lock.json @@ -8,13 +8,13 @@ "name": "QuicKey", "version": "0.0.0", "dependencies": { + "fast-memoize": "^2.5.2", "pinyin": "^2.11.2" }, "devDependencies": { "chrome-webstore-upload": "^0.5.0", "deepmerge": "^4.2.2", - "fast-memoize": "^2.5.2", - "grunt": "^1.5.2", + "grunt": "^1.5.3", "grunt-cli": "^1.4.3", "grunt-confirm": "^1.0.8", "grunt-contrib-clean": "^2.0.1", @@ -2455,8 +2455,7 @@ "node_modules/fast-memoize": { "version": "2.5.2", "resolved": "https://registry.npmjs.org/fast-memoize/-/fast-memoize-2.5.2.tgz", - "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==", - "dev": true + "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==" }, "node_modules/fbjs": { "version": "0.8.18", @@ -3025,9 +3024,9 @@ "dev": true }, "node_modules/grunt": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/grunt/-/grunt-1.5.2.tgz", - "integrity": "sha512-XCtfaIu72OyDqK24MjWiGC9SwlkuhkS1mrULr1xzuJ2XqAFhP3ZAchZGHJeSCY6mkaOXU4F7SbmmCF7xIVoC9w==", + "version": "1.5.3", + "resolved": "https://registry.npmjs.org/grunt/-/grunt-1.5.3.tgz", + "integrity": "sha512-mKwmo4X2d8/4c/BmcOETHek675uOqw0RuA/zy12jaspWqvTp4+ZeQF1W+OTpcbncnaBsfbQJ6l0l4j+Sn/GmaQ==", "dev": true, "dependencies": { "dateformat": "~3.0.3", @@ -9759,8 +9758,7 @@ "fast-memoize": { "version": "2.5.2", "resolved": "https://registry.npmjs.org/fast-memoize/-/fast-memoize-2.5.2.tgz", - "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==", - "dev": true + "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==" }, "fbjs": { "version": "0.8.18", @@ -10245,9 +10243,9 @@ "dev": true }, "grunt": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/grunt/-/grunt-1.5.2.tgz", - "integrity": "sha512-XCtfaIu72OyDqK24MjWiGC9SwlkuhkS1mrULr1xzuJ2XqAFhP3ZAchZGHJeSCY6mkaOXU4F7SbmmCF7xIVoC9w==", + "version": "1.5.3", + "resolved": "https://registry.npmjs.org/grunt/-/grunt-1.5.3.tgz", + "integrity": "sha512-mKwmo4X2d8/4c/BmcOETHek675uOqw0RuA/zy12jaspWqvTp4+ZeQF1W+OTpcbncnaBsfbQJ6l0l4j+Sn/GmaQ==", "dev": true, "requires": { "dateformat": "~3.0.3", diff --git a/package.json b/package.json index 3ef7845d..2de26cd3 100644 --- a/package.json +++ b/package.json @@ -16,7 +16,7 @@ "devDependencies": { "chrome-webstore-upload": "^0.5.0", "deepmerge": "^4.2.2", - "grunt": "^1.5.2", + "grunt": "^1.5.3", "grunt-cli": "^1.4.3", "grunt-confirm": "^1.0.8", "grunt-contrib-clean": "^2.0.1", diff --git a/src/background.html b/src/background.html index c264efe2..1569b648 100644 --- a/src/background.html +++ b/src/background.html @@ -1,6 +1,12 @@ - - - - - - + + + + + + + + + + + + diff --git a/src/css/options.css b/src/css/options.css index cf0821f6..775c6692 100644 --- a/src/css/options.css +++ b/src/css/options.css @@ -141,6 +141,10 @@ .edge .incognito-screenshot { content: url("/img/inprivate-option-dark.png"); } + + .firefox .incognito-screenshot { + content: url("/img/private-option-dark.png"); + } } @@ -298,7 +302,7 @@ main { fill: var(--fill, #999); } -.incognito.icon { +.incognito.icon, .ff-private.icon { fill: var(--fill, #a9a9a9); } @@ -307,7 +311,7 @@ main { opacity: .6; } -.history.icon, .window.icon, .incognito.icon, .inprivate.icon { +.history.icon, .window.icon, .incognito.icon, .inprivate.icon, .ff-private.icon { height: 1.2em; vertical-align: bottom; } @@ -445,6 +449,10 @@ main { font-size: .9em; } +.control .subtitle kbd { + line-height: 1.1; +} + .control-group { margin: 1em 0 2em 0; } diff --git a/src/css/popup.css b/src/css/popup.css index 69c016d4..17c1e0c2 100644 --- a/src/css/popup.css +++ b/src/css/popup.css @@ -12,7 +12,7 @@ --fill: #aaa; } - .history.icon, .window.icon, .incognito.icon { + .history.icon, .window.icon, .incognito.icon, .ff-private.icon { --fill: #777; } @@ -25,22 +25,35 @@ --border-color: #555; } - .search-box input::-webkit-input-placeholder, .command-placeholder { + .search-box input::-webkit-input-placeholder, + .search-box input::placeholder, + .command-placeholder { --color: rgb(139, 139, 139); } - .search-box input::-webkit-search-cancel-button { + .search-box input::-webkit-search-cancel-button, + .firefox .search-box .cancel-button { background-image: url(/img/clear-dark.svg) !important; } - .search-box input::-webkit-search-cancel-button:hover, + .search-box input::-webkit-search-cancel-button:hover { + --background: #535457; + } + + .search-box input::-webkit-search-cancel-button:hover:active { + --background: #5d5e61; + } + + /* group together the selectors that Firefox will parse, while leaving the + pseudo-element+pseudo-class selector that FF ignores by itself above */ .options-button:hover, + .firefox .search-box .cancel-button:hover, .results-list-item.selected:hover .close-button:hover { --background: #535457; } - .search-box input::-webkit-search-cancel-button:hover:active, .options-button:hover:active, + .firefox .search-box .cancel-button:hover:active, .results-list-item.selected:hover .close-button:hover:active { --background: #5d5e61; } @@ -62,7 +75,7 @@ --background: #666; } - ::-webkit-scrollbar-thumb { + ::-webkit-scrollbar-thumb, .firefox .results-list { --background: rgba(255, 255, 255, .1); } @@ -84,9 +97,11 @@ html, body { width: 500px; - height: 35px; margin: 0; padding: 0; + /* prevent the flash of a scrollbar that briefly appears when the popup + is opened on Firefox */ + scrollbar-width: none; } body { @@ -112,7 +127,7 @@ img { fill: var(--fill, #888); } -.history.icon, .window.icon, .incognito.icon { +.history.icon, .window.icon, .incognito.icon, .ff-private.icon { fill: var(--fill, #bbb); } @@ -159,13 +174,27 @@ img { position: absolute; } -.search-box input::-webkit-input-placeholder, .command-placeholder { +.search-box input::-webkit-input-placeholder, +.search-box input::placeholder, +.command-placeholder { font-weight: normal; font-style: italic; color: var(--color, rgb(117, 117, 117)); } -.search-box input::-webkit-search-cancel-button { +.search-box .cancel-button { + display: none; +} + +.firefox .search-box .cancel-button { + display: block; + top: 5px; + right: 27px; + position: absolute; +} + +.search-box input::-webkit-search-cancel-button, +.firefox .search-box .cancel-button { -webkit-appearance: none; height: 22px; width: 22px; @@ -185,6 +214,18 @@ img { background-color: var(--background, #bbb); } + /* maddeningly, FF will ignore the entire rule set when it contains both a + prefixed pseudo element it doesn't support AND a pseudo class. so we have + to repeat these rules for hover when we don't have to repeat them for the + basic styling above. */ +.firefox .search-box .cancel-button:hover { + background-color: var(--background, #dcdcdc); +} + +.firefox .search-box .cancel-button:hover:active { + background-color: var(--background, #bbb); +} + .command-placeholder { top: 0; left: 0; @@ -462,3 +503,8 @@ img { ::-webkit-scrollbar-corner { background: transparent; } + +.firefox .results-list { + scrollbar-width: thin; + scrollbar-color: var(--background, rgba(0, 0, 0, 0.15)) none; +} diff --git a/src/img/default-favicon.svg b/src/img/default-favicon.svg new file mode 100644 index 00000000..e7c090f4 --- /dev/null +++ b/src/img/default-favicon.svg @@ -0,0 +1,3 @@ + + + diff --git a/src/img/private-option-dark.png b/src/img/private-option-dark.png new file mode 100644 index 00000000..f4aa00a5 Binary files /dev/null and b/src/img/private-option-dark.png differ diff --git a/src/img/private-option.png b/src/img/private-option.png new file mode 100644 index 00000000..537f31bb Binary files /dev/null and b/src/img/private-option.png differ diff --git a/src/js/background/background.js b/src/js/background/background.js index 155c03dc..ec30ddcc 100644 --- a/src/js/background/background.js +++ b/src/js/background/background.js @@ -148,6 +148,12 @@ require([ let usePinyin; + if (k.IsFirefox) { + // make the count background slightly darker in FF so the text is + // rendered in white instead of black + BadgeColors.light.normal = "#666"; + } + const addTab = debounce(({tabId}) => cp.tabs.get(tabId) .then(recentTabs.add) .catch(error => { diff --git a/src/js/background/constants.js b/src/js/background/constants.js index b4fd67ce..bb1b53b2 100644 --- a/src/js/background/constants.js +++ b/src/js/background/constants.js @@ -9,6 +9,19 @@ define([ const IsMac = /Mac/i.test(platform); const IsLinux = /Linux/i.test(platform); const IsEdge = /Edg\//i.test(userAgent); + const IsFirefox = /Firefox\//i.test(userAgent); + + const IncognitoNameUC = IsFirefox + ? "Private" + : IsEdge + ? "InPrivate" + : "Incognito"; + const IncognitoNameLC = IsEdge + ? "InPrivate" + : IncognitoNameUC.toLowerCase(); + const IncognitoPermission = IsFirefox + ? "Run in Private Windows" + : `Allow in ${IncognitoNameLC}`; const languagePattern = /^(?[-a-z]+)-(?[a-z]+)$/i; const primaryLanguage = languages[0]; @@ -22,8 +35,10 @@ define([ // this will get overridden in background.js if we're in dev mode IsDev: false, IsEdge, - IncognitoNameUC: IsEdge ? "InPrivate" : "Incognito", - IncognitoNameLC: IsEdge ? "InPrivate" : "incognito", + IsFirefox, + IncognitoNameUC, + IncognitoNameLC, + IncognitoPermission, SpaceBehavior: { Key: "spaceBehavior", Select: "select", diff --git a/src/js/background/get-default-settings.js b/src/js/background/get-default-settings.js index e94389f2..f8eb4584 100644 --- a/src/js/background/get-default-settings.js +++ b/src/js/background/get-default-settings.js @@ -6,8 +6,9 @@ define([ const DefaultShortcuts = { [k.Shortcuts.MRUSelect]: "w", // on Linux, the extension menu can't seem to capture ctrl-W, like - // macOS, so default to a different shortcut - [k.Shortcuts.CloseTab]: k.IsLinux ? "ctrl+alt+w" : "ctrl+w", + // macOS, so default to a different shortcut. same with Firefox on + // any platform. + [k.Shortcuts.CloseTab]: (k.IsLinux || k.IsFirefox) ? "ctrl+alt+w" : "ctrl+w", [k.Shortcuts.MoveTabLeft]: "ctrl+[", [k.Shortcuts.MoveTabRight]: "ctrl+]", [k.Shortcuts.CopyURL]: "mod+c", @@ -20,7 +21,8 @@ define([ { [k.Shortcuts.CloseTab]: "cmd+ctrl+w" }); const DefaultSettings = { [k.SpaceBehavior.Key]: k.SpaceBehavior.Select, - [k.EscBehavior.Key]: k.EscBehavior.Clear, + // on FF, pressing esc always closes the menu and can't be prevented + [k.EscBehavior.Key]: k.IsFirefox ? k.EscBehavior.Close : k.EscBehavior.Clear, [k.HomeEndBehavior.Key]: k.HomeEndBehavior.ResultsList, [k.MarkTabsInOtherWindows.Key]: true, [k.IncludeClosedTabs.Key]: true, diff --git a/src/js/common/icons.js b/src/js/common/icons.js index c5fa06aa..e747348e 100644 --- a/src/js/common/icons.js +++ b/src/js/common/icons.js @@ -1,9 +1,55 @@ define([ - "react" + "react", + "background/constants" ], function( - React + React, + {IsEdge, IsFirefox} ) { + const ChromeIncognitoIcon = () => ( + + + + + + + + + + ); + + + const InPrivateIcon = () => ( + + + + + + + + + + + + + + ); + + + const FFPrivateIcon = () => ( + + + + ); + + return { + IncognitoIcon: IsFirefox + ? FFPrivateIcon + : IsEdge + ? InPrivateIcon + : ChromeIncognitoIcon, + + SearchIcon: () => ( @@ -25,36 +71,6 @@ define([ ), - IncognitoIcon: () => ( - - - - - - - - - - ), - - - InPrivateIcon: () => ( - - - - - - - - - - - - - - ), - - HistoryIcon: () => ( diff --git a/src/js/lib/copy-to-clipboard.js b/src/js/lib/copy-to-clipboard.js index 26fce586..b6311749 100644 --- a/src/js/lib/copy-to-clipboard.js +++ b/src/js/lib/copy-to-clipboard.js @@ -7,6 +7,9 @@ define(function() { const activeElement = document.activeElement; let result; + // prevent the textarea from causing the height to change when it's + // added, which is visible in FF + copyFrom.style.cssText = "position: absolute; top: -100px;"; copyFrom.textContent = text; body.appendChild(copyFrom); copyFrom.focus(); diff --git a/src/js/options/app.js b/src/js/options/app.js index 0eb6ed48..a35bc265 100644 --- a/src/js/options/app.js +++ b/src/js/options/app.js @@ -13,15 +13,25 @@ define([ {IncognitoIcon, InPrivateIcon, HistoryIcon, WindowIcon}, k ) { - const {IncognitoNameUC, IncognitoNameLC} = k; + const {IncognitoNameUC, IncognitoNameLC, IncognitoPermission} = k; const IncognitoAction = k.IsEdge ? "click the checkbox" : "toggle it on"; - const IncognitoIndicator = k.IsEdge ? : ; + const IncognitoInstructions = k.IsFirefox + ? right-click the QuicKey toolbar icon, select Manage + Extension, and then click Allow next to the Run in + Private Windows option + : click the button below, then scroll down to + the {IncognitoPermission} setting and {IncognitoAction}; const UpdateMessage =

现在,您可以使用拼音在网页标题和URL中搜索中文字符。

您始终可以通过单击QuicKey菜单中的齿轮图标来重新打开此页面。

; + const BrowserClassName = k.IsFirefox + ? "firefox" + : k.IsEdge + ? "edge" + : "chrome"; function NewSetting({ @@ -71,8 +81,11 @@ define([ handleChangeIncognitoClick: function() { - this.openExtensionsTab("?id=" + chrome.runtime.id); - this.props.tracker.event("extension", "options-incognito"); + // FF doesn't support opening the settings tab directly + if (!k.IsFirefox) { + this.openExtensionsTab("?id=" + chrome.runtime.id); + this.props.tracker.event("extension", "options-incognito"); + } }, @@ -137,7 +150,7 @@ define([ onResetShortcuts } = this.props; - return
+ return
{ showPinyinUpdateMessage && UpdateMessage } @@ -285,11 +298,19 @@ define([ + disabled={k.IsFirefox} + > + {k.IsFirefox && +
+ Firefox always closes the menu when esc is pressed. +
+ } +
{IncognitoNameUC} windows + {!k.IsFirefox &&
+

{IncognitoNameUC} windows

-

By default, QuicKey can't switch to tabs in {IncognitoNameLC} windows. - To enable this functionality, click the button below, then - scroll down to the Allow in {IncognitoNameLC} setting - and {IncognitoAction}. {IncognitoNameUC} tabs are marked - with {IncognitoIndicator}. -

- {`${IncognitoNameUC} - +

By default, QuicKey can't switch to tabs in {IncognitoNameLC} windows. + To enable this functionality, {IncognitoInstructions}. {IncognitoNameUC} tabs + are marked with . +

+ {`${IncognitoNameUC} + +
}

Feedback and support

diff --git a/src/js/popup/app.js b/src/js/popup/app.js index 5cf71351..24fec92d 100644 --- a/src/js/popup/app.js +++ b/src/js/popup/app.js @@ -84,6 +84,7 @@ define("popup/app", [ resultsList: null, settings: settings.getDefaults(), settingsPromise: null, + className: "", getInitialState: function() @@ -139,6 +140,13 @@ define("popup/app", [ componentWillMount: function() { + // we're saving the initial value of this prop instead of + // getting it every time in render, which is normally bad, but + // the platform will never change during the life of the app + this.className = [ + this.props.platform, + k.IsFirefox ? "firefox" : "" + ].join(" "); this.loadTabs() .then(tabs => { // by the time we get here, the settings promise will @@ -447,9 +455,7 @@ define("popup/app", [ this.props.tracker.event(this.mode, "open"); } - // we seem to have to close the window in a timeout so that - // the hover state of the button gets cleared - setTimeout(function() { window.close(); }, 0); + this.closeWindow(); } }, @@ -575,8 +581,7 @@ define("popup/app", [ active: true, currentWindow: true }) - .bind(this) - .then(function(activeTabs) { + .then(activeTabs => { const activeTab = activeTabs[0]; // if the active tab is at 0, and we want to move // another tab to the left of it, force that index @@ -612,7 +617,12 @@ define("popup/app", [ index: index }) }) - .then(function(movedTab) { + .then(movedTab => { + if (Array.isArray(movedTab)) { + // annoyingly, this is returned as an array in FF + movedTab = movedTab[0]; + } + // use the movedTab from this callback, since // the tab reference we had to it from before is // likely stale. we also have to call addURLs() @@ -624,6 +634,10 @@ define("popup/app", [ this.focusTab(movedTab, unsuspend); this.props.tracker.event(this.state.query.length ? "tabs" : "recents", "move-" + (direction ? "right" : "left")); + + // focusing the tab doesn't close the menu in FF, so + // close it explicitly just in case + this.closeWindow(); }); }, @@ -670,6 +684,14 @@ define("popup/app", [ }, + closeWindow: function() + { + // we seem to have to close the window in a timeout so that + // the hover state of the button gets cleared + setTimeout(window.close, 0); + }, + + handleListRef: handleRef("resultsList"), @@ -731,6 +753,10 @@ define("popup/app", [ url: chrome.extension.getURL("options.html") }); this.props.tracker.event("extension", "open-options"); + + // opening the options tab doesn't automatically close the menu + // on Firefox + this.closeWindow(); }, @@ -744,7 +770,7 @@ define("popup/app", [ newSettingsAvailable } = this.state; - return
+ return
MaxTitleLength ? title : "", @@ -186,7 +185,7 @@ define([ } if (incognito) { - badge = IsEdge ? : ; + badge = ; badgeTooltip = IncognitoTooltip; } else if (otherWindow) { badge = ; diff --git a/src/js/popup/results-list.js b/src/js/popup/results-list.js index 1c61a234..b6f2655c 100644 --- a/src/js/popup/results-list.js +++ b/src/js/popup/results-list.js @@ -1,14 +1,19 @@ define([ "react", "react-virtualized", - "lib/handle-ref" + "lib/handle-ref", + "background/constants" ], function( React, ReactVirtualized, - handleRef + handleRef, + {IsFirefox} ) { - const RowHeight = 45, - Width = 490; + const RowHeight = 45; + // in FF, the scrollbar appears inside the right edge of the scrolling + // area, instead on the outside. so make the virtual list go right to + // the edge of the popup, so the scrollbar doesn't cover the content. + const Width = IsFirefox ? 495 : 490; var ResultsList = React.createClass({ diff --git a/src/js/popup/search-box.js b/src/js/popup/search-box.js index 09ba723b..be462337 100644 --- a/src/js/popup/search-box.js +++ b/src/js/popup/search-box.js @@ -2,12 +2,14 @@ define([ "jsx!./input", "jsx!common/icons", "lib/handle-ref", - "react" + "react", + "background/constants" ], function( Input, {SearchIcon}, handleRef, - React + React, + {IsFirefox} ) { function Placeholder({ mode, @@ -46,6 +48,15 @@ define([ handleRef: handleRef("searchBox"), + handleCancelButtonClick: function() + { + // unlike the cancel button in Chrome, clicking the one in FF + // steals the focus, so set it back in the input + this.focus(); + this.props.onChange({ target: { value: "" } }); + }, + + render: function() { const { @@ -86,6 +97,13 @@ define([ } {mode == "command" && } + {(IsFirefox && query.length > 0) && +
+ }
} }); diff --git a/src/manifest.json b/src/manifest.json index a45f50f4..d2ff7735 100644 --- a/src/manifest.json +++ b/src/manifest.json @@ -2,7 +2,7 @@ "manifest_version": 2, "name": "QuicKey DEV", "short_name": "QuicKey DEV", - "version": "1.7.4", + "version": "1.8.0", "description": "Add keyboard shortcuts to switch tabs with a Quicksilver-style search or a most recently used menu", "author": "John Dunning", "content_security_policy": "script-src 'self' 'unsafe-eval' https://www.google-analytics.com; object-src 'self'", @@ -66,4 +66,4 @@ } }, "offline_enabled": true -} \ No newline at end of file +} diff --git a/src/options.html b/src/options.html index 93e4dd4e..a632721d 100644 --- a/src/options.html +++ b/src/options.html @@ -7,6 +7,8 @@ QuicKey Options + + @@ -19,4 +21,4 @@
- \ No newline at end of file + diff --git a/src/popup.html b/src/popup.html index c9bca131..6f66c63a 100644 --- a/src/popup.html +++ b/src/popup.html @@ -19,7 +19,7 @@
-
+