1 // Copyright 2014 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 function toggleEnabled(event) { 6 if (!document.body) 7 return; 8 if (document.body.hasAttribute('show-alt')) 9 document.body.removeAttribute('show-alt'); 10 else 11 document.body.setAttribute('show-alt', ''); 12 } 13 14 function processImage(image) { 15 image.style.setProperty('min-height', image.height + 'px'); 16 image.style.setProperty('min-width', image.width + 'px'); 17 var style = window.getComputedStyle(image, null); 18 var contrastRatio = 19 axs.utils.getContrastRatioForElementWithComputedStyle(style, image); 20 if (contrastRatio != null && axs.utils.isLowContrast(contrastRatio, style)) { 21 var bgColor = axs.utils.getBgColor(style, image); 22 var fgColor = axs.utils.getFgColor(style, image, bgColor); 23 var suggestedColors = axs.utils.suggestColors( 24 bgColor, fgColor, contrastRatio, style); 25 var suggestedColorsAA = suggestedColors['AA']; 26 image.style.setProperty('color', suggestedColorsAA['fg']); 27 image.style.setProperty( 28 'background-color', suggestedColorsAA['bg'], 'important'); 29 } 30 if (!image.hasAttribute('alt')) { 31 if (image.hasAttribute('_repaired')) 32 return; 33 var filename = image.src.split('/').pop(); 34 image.setAttribute('_repaired', filename); 35 } 36 } 37 38 var observer = new MutationObserver(function(mutations) { 39 mutations.forEach(function(mutation) { 40 if (!mutation.addedNodes || mutation.addedNodes.length == 0) 41 return; 42 for (var i = 0; i < mutation.addedNodes.length; i++) { 43 var addedNode = mutation.addedNodes[i]; 44 if (!(addedNode instanceof 45 addedNode.ownerDocument.defaultView.HTMLImageElement)) { 46 continue; 47 } 48 processImage(addedNode); 49 } 50 }); 51 }); 52 observer.observe(document, { childList: true, subtree: true }); 53 54 var images = document.querySelectorAll('img'); 55 for (var i = 0; i < images.length; i++) { 56 processImage(images[i]); 57 } 58 59 if (!infobarDismissed) 60 var infobarDismissed = false; 61 62 function createInfobar() { 63 if (infobarDismissed) 64 return; 65 66 if (!document.body) 67 return; 68 69 if (document.querySelector('.show-alt-infobar')) 70 return; 71 72 var showAltInfobar = document.createElement('div'); 73 showAltInfobar.className = 'show-alt-infobar'; 74 75 var showAltInfoControls = document.createElement('div'); 76 showAltInfoControls.className = 'controls'; 77 78 var showAltInfoCloseButton = document.createElement('button'); 79 showAltInfoCloseButton.className = 'close-button-gray'; 80 showAltInfoCloseButton.addEventListener('click', function() { 81 document.body.removeChild(showAltInfobar); 82 infobarDismissed = true; 83 }); 84 85 showAltInfoControls.appendChild(showAltInfoCloseButton); 86 showAltInfobar.appendChild(showAltInfoControls); 87 88 var showAltInfoContent = document.createElement('div'); 89 showAltInfoContent.className = 'content'; 90 // TODO(aboxhall): i18n 91 var showAltInfoText = document.createElement('span'); 92 showAltInfoText.textContent = 'Images have been replaced by their alt text.'; 93 showAltInfoText.setAttribute('role', 'status'); 94 showAltInfoContent.appendChild(showAltInfoText); 95 96 var undoButton = document.createElement('button'); 97 undoButton.className = 'link-button'; 98 undoButton.textContent = 'Undo'; 99 undoButton.addEventListener('click', toggleEnabled); 100 101 var closeButton = document.createElement('button'); 102 103 showAltInfoContent.appendChild(undoButton); 104 showAltInfobar.appendChild(showAltInfoContent); 105 106 document.body.insertBefore(showAltInfobar, document.body.firstChild); 107 } 108