Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code

Delta Between Two Patch Sets: background.js

Issue 16067002: Added Safari Support (Closed)
Left Patch Set: Added missing copyright disclaimers and websql implementation Created Oct. 23, 2013, 2:46 p.m.
Right Patch Set: Bugfixes Created Nov. 15, 2013, 8:58 a.m.
Left:
Right:
Use n/p to move between diff chunks; N/P to move between comments.
Jump to:
Left: Side by side diff | Download
Right: Side by side diff | Download
« no previous file with change/comment | « no previous file | block.js » ('j') | no next file with change/comment »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
LEFTRIGHT
1 /* 1 /*
2 * This file is part of Adblock Plus <http://adblockplus.org/>, 2 * This file is part of Adblock Plus <http://adblockplus.org/>,
3 * Copyright (C) 2006-2013 Eyeo GmbH 3 * Copyright (C) 2006-2013 Eyeo GmbH
4 * 4 *
5 * Adblock Plus is free software: you can redistribute it and/or modify 5 * Adblock Plus is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License version 3 as 6 * it under the terms of the GNU General Public License version 3 as
7 * published by the Free Software Foundation. 7 * published by the Free Software Foundation.
8 * 8 *
9 * Adblock Plus is distributed in the hope that it will be useful, 9 * Adblock Plus is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after
109 } 109 }
110 110
111 var activeNotification = null; 111 var activeNotification = null;
112 112
113 // Adds or removes page action icon according to options. 113 // Adds or removes page action icon according to options.
114 function refreshIconAndContextMenu(tab) 114 function refreshIconAndContextMenu(tab)
115 { 115 {
116 if(!/^https?:/.test(tab.url)) 116 if(!/^https?:/.test(tab.url))
117 return; 117 return;
118 118
119 var excluded = isWhitelisted(tab.url);
120 var iconFilename; 119 var iconFilename;
121 120 if (require("info").platform == "safari")
122 if (window.safari || !excluded) 121 // There is no grayscale version of the icon for whitelisted tabs
123 iconFilename = "icons/abp-18.png"; 122 // when using Safari, because icons are grayscale already and icons
123 // aren't per tab in Safari.
124 iconFilename = "icons/abp-16.png"
124 else 125 else
125 iconFilename = "icons/abp-18-whitelisted.png"; 126 {
127 var excluded = isWhitelisted(tab.url);
128 iconFilename = excluded ? "icons/abp-19-whitelisted.png" : "icons/abp-19.png ";
129 }
126 130
127 tab.pageAction.setIcon(iconFilename); 131 tab.pageAction.setIcon(iconFilename);
128 tab.pageAction.setTitle("Adblock Plus"); 132 tab.pageAction.setTitle(ext.i18n.getMessage("name"));
129 133
130 iconAnimation.registerTab(tab, iconFilename); 134 iconAnimation.registerTab(tab, iconFilename);
131 135
132 if (localStorage.shouldShowIcon == "false") 136 if (localStorage.shouldShowIcon == "false")
133 tab.pageAction.hide(); 137 tab.pageAction.hide();
134 else 138 else
135 tab.pageAction.show(); 139 tab.pageAction.show();
136 140
137 // Set context menu status according to whether current tab has whitelisted do main 141 if (require("info").platform == "chromium") // TODO: Implement context menus f or Safari
138 if (excluded) 142 // Set context menu status according to whether current tab has whitelisted domain
139 if (window.chrome) // TODO: Implement context menus for Safari 143 if (excluded)
140 chrome.contextMenus.removeAll(); 144 chrome.contextMenus.removeAll();
141 else 145 else
142 showContextMenu(); 146 showContextMenu();
143 } 147 }
144 148
145 /** 149 /**
146 * Old versions stored filter data in the localStorage object, this will import 150 * Old versions stored filter data in the localStorage object, this will import
147 * it into FilterStorage properly. 151 * it into FilterStorage properly.
148 */ 152 */
149 function importOldData() 153 function importOldData()
150 { 154 {
151 function addSubscription(url, title) 155 function addSubscription(url, title)
152 { 156 {
(...skipping 207 matching lines...) Expand 10 before | Expand all | Expand 10 after
360 } 364 }
361 else 365 else
362 addAcceptable = false; 366 addAcceptable = false;
363 } 367 }
364 368
365 if (!addSubscription && !addAcceptable) 369 if (!addSubscription && !addAcceptable)
366 return; 370 return;
367 371
368 function notifyUser() 372 function notifyUser()
369 { 373 {
370 ext.windows.getLastFocused(function(win) { 374 ext.windows.getLastFocused(function(win)
375 {
371 win.openTab(ext.getURL("firstRun.html")); 376 win.openTab(ext.getURL("firstRun.html"));
372 }); 377 });
373 } 378 }
374 379
375 if (addSubscription) 380 if (addSubscription)
376 { 381 {
377 // Load subscriptions data 382 // Load subscriptions data
378 var request = new XMLHttpRequest(); 383 var request = new XMLHttpRequest();
379 request.open("GET", "subscriptions.xml"); 384 request.open("GET", "subscriptions.xml");
380 request.addEventListener("load", function() 385 request.addEventListener("load", function()
(...skipping 14 matching lines...) Expand all
395 }, false); 400 }, false);
396 request.send(null); 401 request.send(null);
397 } 402 }
398 else 403 else
399 notifyUser(); 404 notifyUser();
400 } 405 }
401 406
402 // Set up context menu for user selection of elements to block 407 // Set up context menu for user selection of elements to block
403 function showContextMenu() 408 function showContextMenu()
404 { 409 {
405 if (!window.chrome) // TODO: Implement context menus for Safari
406 return;
407
408 chrome.contextMenus.removeAll(function() 410 chrome.contextMenus.removeAll(function()
409 { 411 {
410 if(typeof localStorage["shouldShowBlockElementMenu"] == "string" && localSto rage["shouldShowBlockElementMenu"] == "true") 412 if(typeof localStorage["shouldShowBlockElementMenu"] == "string" && localSto rage["shouldShowBlockElementMenu"] == "true")
411 { 413 {
412 chrome.contextMenus.create({"title": chrome.i18n.getMessage("block_element "), "contexts": ["image", "video", "audio"], "onclick": function(info, tab) 414 chrome.contextMenus.create({"title": chrome.i18n.getMessage("block_element "), "contexts": ["image", "video", "audio"], "onclick": function(info, tab)
413 { 415 {
414 if(info.srcUrl) 416 if(info.srcUrl)
415 chrome.tabs.sendRequest(tab.id, {reqtype: "clickhide-new-filter", fi lter: info.srcUrl}); 417 chrome.tabs.sendRequest(tab.id, {reqtype: "clickhide-new-filter", fi lter: info.srcUrl});
416 }}); 418 }});
417 } 419 }
418 }); 420 });
419 } 421 }
420 422
423 /**
424 * Opens options tab or focuses an existing one, within the last focused window .
425 * @param {Function} callback function to be called with the
426 Tab object of the options tab
427 */
421 function openOptions(callback) 428 function openOptions(callback)
422 { 429 {
423 ext.windows.getLastFocused(function(win) { 430 ext.windows.getLastFocused(function(win)
424 win.getAllTabs(function(tabs) { 431 {
432 win.getAllTabs(function(tabs)
433 {
425 var optionsUrl = ext.getURL("options.html"); 434 var optionsUrl = ext.getURL("options.html");
426 435
427 for (var i = 0; i < tabs.length; i++) 436 for (var i = 0; i < tabs.length; i++)
428 if (tabs[i].url == optionsUrl) { 437 {
438 if (tabs[i].url == optionsUrl)
439 {
429 tabs[i].activate(); 440 tabs[i].activate();
430 if (callback) 441 if (callback)
431 callback(tabs[i]); 442 callback(tabs[i]);
432 return; 443 return;
433 } 444 }
434 445 }
435 win.openTab(optionsUrl, callback && function(tab) { 446
447 win.openTab(optionsUrl, callback && function(tab)
448 {
436 tab.onCompleted.addListener(callback); 449 tab.onCompleted.addListener(callback);
437 }); 450 });
438 }); 451 });
439 }); 452 });
440 } 453 }
441 454
442 function IconAnimation() {
443 this._icons = new TabMap();
444 this._animatedTabs = new TabMap();
445 this._step = 0;
446 };
447 IconAnimation.prototype = {
448 update: function(severity) {
449 if (severity == this._severity)
450 return;
451
452 if (!this._severity)
453 this._start();
454
455 this._severity = severity;
456 },
457 stop: function() {
458 clearInterval(this._interval);
459
460 delete this._interval;
461 delete this._severity;
462
463 this._animatedTabs.clear();
464 },
465 registerTab: function(tab, icon) {
466 this._icons.set(tab, icon);
467
468 if (this._animatedTabs.has(tab))
469 this._updateIcon(tab);
470 },
471 _start: function() {
472 this._interval = setInterval(function() {
473 this._getVisibleTabs(function(tabs) {
474 if (tabs.length == 0)
475 return;
476
477 for (var i = 0; i < tabs.length; i++)
478 this._animatedTabs.set(tabs[i], null);
479
480 var interval = setInterval(function() {
481 this._step++;
482 tabs.forEach(this._updateIcon.bind(this));
483
484 if (this._step < 10)
485 return;
486
487 clearInterval(interval);
488 setTimeout(function() {
489 interval = setInterval(function() {
490 this._step--;
491 tabs.forEach(this._updateIcon.bind(this));
492
493 if (this._step > 0)
494 return;
495
496 clearInterval(interval);
497 this._animatedTabs.clear();
498 }.bind(this), 100);
499 }.bind(this), 1000);
500 }.bind(this), 100);
501 }.bind(this));
502 }.bind(this), 15000);
503 },
504 _getVisibleTabs: function(callback) {
505 ext.windows.getAll(function(windows) {
506 var tabs = [];
507 var n = windows.length;
508
509 for (var i = 0; i < windows.length; i++) {
510 if (!windows[i].visible) {
511 if (tabs.length == --n)
512 callback(tabs);
513
514 continue;
515 }
516
517 windows[i].getActiveTab(function(tab) {
518 tabs.push(tab);
519
520 if (tabs.length == n)
521 callback(tabs);
522 });
523 }
524 });
525 },
526 _updateIcon: function(tab) {
527 var path = this._icons.get(tab);
528
529 if (!path)
530 return;
531
532 if (this._step > 0) {
533 var suffix = "-notification-" + this._severity;
534
535 if (this._step < 10)
536 suffix += "-" + this._step;
537
538 path = path.replace(/(?=\..+$)/, suffix);
539 }
540
541 tab.pageAction.setIcon(path);
542 }
543 };
544 var iconAnimation = new IconAnimation();
545
546 function prepareNotificationIconAndPopup() 455 function prepareNotificationIconAndPopup()
547 { 456 {
548 activeNotification.onClicked = function() { 457 activeNotification.onClicked = function()
458 {
549 iconAnimation.stop(); 459 iconAnimation.stop();
550 activeNotification = null; 460 activeNotification = null;
551 }; 461 };
552 462
553 iconAnimation.update(activeNotification.severity); 463 iconAnimation.update(activeNotification.severity);
554 } 464 }
555 465
556 function showNotification(notification) 466 function showNotification(notification)
557 { 467 {
558 activeNotification = notification; 468 activeNotification = notification;
(...skipping 15 matching lines...) Expand all
574 * frame data. 484 * frame data.
575 */ 485 */
576 function getFrameId(tab, url) 486 function getFrameId(tab, url)
577 { 487 {
578 for (var frameId in frames.get(tab)) 488 for (var frameId in frames.get(tab))
579 if (getFrameUrl(tab, frameId) == url) 489 if (getFrameUrl(tab, frameId) == url)
580 return frameId; 490 return frameId;
581 return -1; 491 return -1;
582 } 492 }
583 493
584 ext.onMessage.addListener(function (msg, sender, sendResponse) { 494 ext.onMessage.addListener(function (msg, sender, sendResponse)
495 {
585 switch (msg.type) 496 switch (msg.type)
586 { 497 {
587 case "get-settings": 498 case "get-selectors":
588 var hostDomain = null;
589 var selectors = null; 499 var selectors = null;
590
591 var frameId = sender.tab ? getFrameId(sender.tab, msg.frameUrl) : -1; 500 var frameId = sender.tab ? getFrameId(sender.tab, msg.frameUrl) : -1;
592 var enabled = false; 501
593 502 if (!isFrameWhitelisted(sender.tab, frameId, "DOCUMENT") &&
594 if (!isFrameWhitelisted(sender.tab, frameId, "DOCUMENT")) 503 !isFrameWhitelisted(sender.tab, frameId, "ELEMHIDE"))
595 if (!isFrameWhitelisted(sender.tab, frameId, "ELEMHIDE")) { 504 {
596 var enabled = true; 505 var noStyleRules = false;
597 506 var host = extractHostFromURL(msg.frameUrl);
598 if (msg.selectors) 507 for (var i = 0; i < noStyleRulesHosts.length; i++)
599 { 508 {
600 var noStyleRules = false; 509 var noStyleHost = noStyleRulesHosts[i];
601 var host = extractHostFromURL(msg.frameUrl); 510 if (host == noStyleHost || (host.length > noStyleHost.length &&
602 hostDomain = getBaseDomain(host); 511 host.substr(host.length - noStyleHost.leng th - 1) == "." + noStyleHost))
603 for (var i = 0; i < noStyleRulesHosts.length; i++)
604 { 512 {
605 var noStyleHost = noStyleRulesHosts[i]; 513 noStyleRules = true;
606 if (host == noStyleHost || (host.length > noStyleHost.length &&
607 host.substr(host.length - noStyleHost.le ngth - 1) == "." + noStyleHost))
608 {
609 noStyleRules = true;
610 }
611 }
612 selectors = ElemHide.getSelectorsForDomain(host, false);
613 if (noStyleRules)
614 {
615 selectors = selectors.filter(function(s)
616 {
617 return !/\[style[\^\$]?=/.test(s);
618 });
619 } 514 }
620 } 515 }
621 } 516 selectors = ElemHide.getSelectorsForDomain(host, false);
622 517 if (noStyleRules)
623 sendResponse({enabled: enabled, hostDomain: hostDomain, selectors: selecto rs}); 518 {
519 selectors = selectors.filter(function(s)
520 {
521 return !/\[style[\^\$]?=/.test(s);
522 });
523 }
524 }
525
526 sendResponse(selectors);
624 break; 527 break;
625 case "should-collapse": 528 case "should-collapse":
626 var frameId = sender.tab ? getFrameId(sender.tab, msg.documentUrl) : -1; 529 var frameId = sender.tab ? getFrameId(sender.tab, msg.documentUrl) : -1;
627 530
628 if (isFrameWhitelisted(sender.tab, frameId, "DOCUMENT")) 531 if (isFrameWhitelisted(sender.tab, frameId, "DOCUMENT"))
629 { 532 {
630 sendResponse(false); 533 sendResponse(false);
631 break; 534 break;
632 } 535 }
633 536
(...skipping 21 matching lines...) Expand all
655 } 558 }
656 break; 559 break;
657 case "add-filters": 560 case "add-filters":
658 if (msg.filters && msg.filters.length) 561 if (msg.filters && msg.filters.length)
659 { 562 {
660 for (var i = 0; i < msg.filters.length; i++) 563 for (var i = 0; i < msg.filters.length; i++)
661 FilterStorage.addFilter(Filter.fromText(msg.filters[i])); 564 FilterStorage.addFilter(Filter.fromText(msg.filters[i]));
662 } 565 }
663 break; 566 break;
664 case "add-subscription": 567 case "add-subscription":
665 openOptions(function(tab) { 568 openOptions(function(tab)
569 {
666 tab.sendMessage(msg); 570 tab.sendMessage(msg);
667 }); 571 });
668 break; 572 break;
669 case "forward": 573 case "forward":
670 tab.sendMessage(msg.payload, sendResponse); 574 tab.sendMessage(msg.payload, sendResponse);
671 break; 575 break;
672 default: 576 default:
673 sendResponse({}); 577 sendResponse({});
674 break; 578 break;
675 } 579 }
676 }); 580 });
677 581
678 // Show icon as page action for all tabs that already exist 582 // Show icon as page action for all tabs that already exist
679 ext.windows.getAll(function(windows) { 583 ext.windows.getAll(function(windows)
584 {
680 for (var i = 0; i < windows.length; i++) 585 for (var i = 0; i < windows.length; i++)
681 windows[i].getAllTabs(function(tabs) { 586 {
587 windows[i].getAllTabs(function(tabs)
588 {
682 tabs.forEach(refreshIconAndContextMenu); 589 tabs.forEach(refreshIconAndContextMenu);
683 }); 590 });
591 }
684 }); 592 });
685 593
686 // Update icon if a tab changes location 594 // Update icon if a tab changes location
687 ext.tabs.onBeforeNavigate.addListener(function(tab) { 595 ext.tabs.onBeforeNavigate.addListener(function(tab)
596 {
688 tab.sendMessage({type: "clickhide-deactivate"}); 597 tab.sendMessage({type: "clickhide-deactivate"});
689 refreshIconAndContextMenu(tab); 598 refreshIconAndContextMenu(tab);
690 }); 599 });
691 600
692 setTimeout(function() 601 setTimeout(function()
693 { 602 {
694 var notificationToShow = Notification.getNextToShow(); 603 var notificationToShow = Notification.getNextToShow();
695 if (notificationToShow) 604 if (notificationToShow)
696 showNotification(notificationToShow); 605 showNotification(notificationToShow);
697 }, 3 * 60 * 1000); 606 }, 3 * 60 * 1000);
LEFTRIGHT
« no previous file | block.js » ('j') | Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Toggle Comments ('s')

Powered by Google App Engine
This is Rietveld