├── .gitignore
├── audio
├── coin.mp3
└── goomba-stomp.wav
├── background-scripts
├── background.js
├── initialize.js
├── mario.js
└── urlbar.js
├── icon.svg
├── manifest.json
├── newtab-page
├── newtab-content.css
└── newtab.html
├── package.json
├── settings
├── options.css
├── options.html
└── options.js
├── src
└── newtab.js
└── yarn.lock
/.gitignore:
--------------------------------------------------------------------------------
1 | .DS_Store
2 | node_modules
3 | newtab-page/bundle.js
4 | web-ext-artifacts
5 |
--------------------------------------------------------------------------------
/audio/coin.mp3:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/bwinton/whimsy/4a610c269618730888393a1962138d93c08f683e/audio/coin.mp3
--------------------------------------------------------------------------------
/audio/goomba-stomp.wav:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/bwinton/whimsy/4a610c269618730888393a1962138d93c08f683e/audio/goomba-stomp.wav
--------------------------------------------------------------------------------
/background-scripts/background.js:
--------------------------------------------------------------------------------
1 | function openPage(){
2 | browser.tabs.create({
3 | url: "https://chilloutandwatchsomecatgifs.github.io/"
4 | });
5 | }
6 |
7 | browser.browserAction.onClicked.addListener(openPage);
8 |
--------------------------------------------------------------------------------
/background-scripts/initialize.js:
--------------------------------------------------------------------------------
1 | var placeholders = [];
2 | function initialize(url, callback){
3 | fetch(url).then(function(response){
4 | if(response.ok){
5 | response.text().then(function(data){
6 | placeholders = data;
7 | placeholders = placeholders.split('\n');
8 | placeholders = placeholders.map(function(x){
9 | return x.trim();
10 | }).filter(function(x){
11 | return !x.startsWith('#') && (x !== '');
12 | })
13 | callback(placeholders);
14 | })
15 | } else {
16 | throw new Error('Network response was not ok.');
17 | }
18 | }).catch(function(error) {
19 | console.log('There has been a problem with your fetch operation: ' + error.message);
20 | });
21 | }
22 |
--------------------------------------------------------------------------------
/background-scripts/mario.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | function playSound(url) {
4 | if (pref) {
5 | //play coin/goomba stomp sound
6 | var audio = new Audio();
7 | audio.src=browser.extension.getURL(url);
8 | audio.autoplay=true;
9 | audio.load();
10 | }
11 | }
12 |
13 | browser.bookmarks.onCreated.addListener(() => playSound("audio/coin.mp3"));
14 | browser.bookmarks.onRemoved.addListener(() => playSound("audio/goomba-stomp.wav"));
15 |
16 | var pref = false;
17 |
18 | browser.storage.sync.get('mario').then((result) => {
19 | pref = result.mario || result.mario == null;
20 | });
21 |
22 | browser.storage.onChanged.addListener((changes, area) => {
23 | if (area === 'sync' && changes.mario) {
24 | pref = changes.mario.newValue || changes.mario.newValue == null;
25 | }
26 | });
27 |
--------------------------------------------------------------------------------
/background-scripts/urlbar.js:
--------------------------------------------------------------------------------
1 | 'use strict'
2 |
3 | var placeholders = [];
4 | var url = 'https://bwinton.github.io/whimsy/urlbar-sayings.txt';
5 |
6 | setDefaults([
7 | 'Where do you want to go today?',
8 | 'Just type ”google.com“. You know you’re going to.',
9 | 'Let’s do this thing!',
10 | 'Hey, I wonder what we should have for lunch?',
11 | 'Where to, boss?',
12 | 'I hear Facebook is nice this time of year…',
13 | 'You know you can search from here, right?',
14 | 'Have you thought about trying Private Browsing Mode?',
15 | 'You are in a maze of twisty web pages, all alike.',
16 | 'Hi! My name is Url.'
17 | ]);
18 | initialize('https://bwinton.github.io/whimsy/urlbar-sayings.txt', setTitle);
19 |
20 | function setDefaults(defaults){
21 | placeholders = defaults;
22 | }
23 | function setTitle(placeholders){
24 | var getting = browser.storage.sync.get('sayings');
25 | getting.then((result)=>{
26 | if (result.sayings || result.sayings == null){
27 | //set browserAction title to random saying
28 | let rand = Math.floor(Math.random() * placeholders.length);
29 | browser.tabs.onActivated.addListener(onActivated);
30 | browser.browserAction.setTitle({
31 | title: placeholders[rand]
32 | });
33 | } else {
34 | browser.tabs.onActivated.removeListener(onActivated);
35 | browser.browserAction.setTitle({
36 | title: "Whimsy"
37 | });
38 | }
39 | })
40 | }
41 | function onChange(text, suggest){
42 | //get preference setting
43 | var getting = browser.storage.sync.get('sayings');
44 | getting.then((result)=>{
45 | if (result.sayings || result.sayings == null){
46 | addSuggestions()
47 | .then(suggest);
48 | }
49 | });
50 | }
51 | function addSuggestions(){
52 | return new Promise(resolve => {
53 | let suggestions = [];
54 | //pick a random saying
55 | let rand = Math.floor(Math.random() * placeholders.length);
56 | //add as suggestion
57 | suggestions.push({
58 | content: placeholders[rand],
59 | description: placeholders[rand],
60 | });
61 | return resolve(suggestions);
62 | });
63 | }
64 | function onActivated(activeInfo){
65 | let rand = Math.floor(Math.random() * placeholders.length);
66 | browser.browserAction.setTitle({
67 | title: placeholders[rand],
68 | tabId: activeInfo.tabId
69 | });
70 | }
71 | function onStorageChange(changes, area) {
72 | if (changes.sayings.oldValue != changes.sayings.newValue){
73 | setTitle(placeholders);
74 | }
75 | }
76 |
77 | browser.omnibox.setDefaultSuggestion({description: "Whimsy sayings"});
78 | browser.omnibox.onInputChanged.addListener(onChange);
79 | browser.tabs.onActivated.addListener(onActivated);
80 | browser.storage.onChanged.addListener(onStorageChange);
81 |
--------------------------------------------------------------------------------
/icon.svg:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/manifest.json:
--------------------------------------------------------------------------------
1 | {
2 | "manifest_version": 2,
3 | "name": "Whimsy",
4 | "version": "3.2.0",
5 | "description": "Add some Whimsy to your Firefox! 🦄🌈",
6 | "homepage_url": "https://github.com/bwinton/whimsy/tree/webextension",
7 | "author": "Blake Winton ",
8 | "contributors": [
9 | "Daniela Arcese",
10 | "Erica Wright"
11 | ],
12 | "icons": {
13 | "48": "icon.svg",
14 | "64": "icon.svg",
15 | "96": "icon.svg"
16 | },
17 |
18 | "applications": {
19 | "gecko": {
20 | "id": "jid1-6mUPixNFCjAgkg@jetpack"
21 | }
22 | },
23 | "permissions": [
24 | "tabs",
25 | "storage",
26 | "bookmarks",
27 | "topSites",
28 | "contextMenus",
29 | "clipboardWrite"
30 | ],
31 | "background": {
32 | "scripts": [
33 | "background-scripts/background.js",
34 | "background-scripts/initialize.js",
35 | "background-scripts/mario.js",
36 | "background-scripts/urlbar.js"
37 | ]
38 | },
39 | "browser_action": {
40 | "default_icon": {
41 | "48": "icon.svg",
42 | "64": "icon.svg",
43 | "96": "icon.svg"
44 | },
45 | "default_title": "Whimsy"
46 | },
47 | "options_ui": {
48 | "page": "settings/options.html",
49 | "chrome_style": true
50 | },
51 | "omnibox": {
52 | "keyword": "whimsy"
53 | },
54 | "chrome_url_overrides": {
55 | "newtab": "newtab-page/newtab.html"
56 | }
57 | }
58 |
--------------------------------------------------------------------------------
/newtab-page/newtab-content.css:
--------------------------------------------------------------------------------
1 | /* This Source Code Form is subject to the terms of the Mozilla Public
2 | * License, v. 2.0. If a copy of the MPL was not distributed with this
3 | * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4 |
5 | html {
6 | width: 100%;
7 | height: 100%;
8 | }
9 |
10 | body {
11 | font: message-box;
12 | width: 100%;
13 | height: 100%;
14 | padding: 0;
15 | margin: 0;
16 | background-color: #F9F9FA;
17 | position: relative;
18 | -moz-user-focus: normal;
19 | }
20 |
21 | /* SEARCH */
22 | #newtab-search-container {
23 | margin: 55px 0 15px;
24 | }
25 |
26 | /* GRID */
27 | #newtab-grid {
28 | margin: 3em 10%;
29 | display: grid;
30 | grid-template-columns: repeat(4, minmax(200px, 320px));
31 | grid-gap: 2%;
32 | grid-auto-rows: minmax(180px, auto);
33 | text-align: center;
34 | transition: 100ms ease-out;
35 | transition-property: opacity;
36 | }
37 |
38 | .newtab-cell {
39 | background-color: rgba(255,255,255,.2);
40 | border-radius: 4px;
41 | box-shadow: 0 2px 4px #c1c1c1;
42 | text-decoration: none;
43 | overflow: hidden;
44 | }
45 |
46 | .newtab-link {
47 | overflow: hidden;
48 | }
49 |
50 | .newtab-thumbnail,
51 | .newtab-title {
52 | display: block;
53 | }
54 |
55 | .newtab-thumbnail {
56 | background-origin: padding-box;
57 | background-clip: padding-box;
58 | background-repeat: no-repeat;
59 | background-size: cover;
60 | min-height: 180px;
61 | transition: opacity 100ms ease-out;
62 | }
63 |
64 | .newtab-title {
65 | overflow: hidden;
66 | text-align: center;
67 | white-space: nowrap;
68 | text-overflow: ellipsis;
69 | vertical-align: middle;
70 | background-color: #F9F9FA;
71 | font-size: 14px;
72 | line-height: 30px;
73 | border: 1px solid #fff;
74 | border-radius: 0 0 4px 4px;
75 | color: rgba(12, 12, 13, 0.76);
76 | }
77 |
--------------------------------------------------------------------------------
/newtab-page/newtab.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | New Tab
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
Your Top Sites
15 |
16 |
19 |
20 |
21 |
22 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "whimsy",
3 | "version": "3.2.0",
4 | "dependencies": {
5 | "tippy-top-sites": "1.2.2"
6 | },
7 | "scripts": {
8 | "build": "browserify src/newtab.js -o newtab-page/bundle.js && web-ext build -i src -i package*",
9 | "dev": "watchify src/newtab.js -o newtab-page/bundle.js && web-ext run -i src -i package*",
10 | "start": "browserify src/newtab.js -o newtab-page/bundle.js && web-ext run -f nightly -i src -i package*"
11 | },
12 | "devDependencies": {
13 | "browserify": "14.4.0",
14 | "watchify": "3.9.0",
15 | "web-ext": "2.0.0"
16 | }
17 | }
18 |
--------------------------------------------------------------------------------
/settings/options.css:
--------------------------------------------------------------------------------
1 | body{
2 | font: 14px Arial;
3 | padding: .5em;
4 | }
5 |
6 | form {
7 | display: grid;
8 | grid-template-columns: auto 1fr 4fr;
9 | grid-gap: 8px;
10 | justify-items: start;
11 | }
12 |
13 | i {
14 | font: 12px Arial;
15 | font-style: italic;
16 | }
17 |
--------------------------------------------------------------------------------
/settings/options.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
23 |
24 |
25 |
26 |
27 |