Bug 1683865 - Replace xul:image usage in openpgp settings. r=mkmelin
authorHenry Wilkes <henry@thunderbird.net>
Wed, 16 Jun 2021 12:56:47 +0300
changeset 32836 2d19637d6b1f55bb624d716e7afccff5fa940b17
parent 32835 7b9edcbe3bf790f0df697dd3ec1e9280788fedab
child 32837 3740475a02540fb24c69c58db41cc0f83e62285e
push id18881
push usermkmelin@iki.fi
push dateWed, 16 Jun 2021 10:27:13 +0000
treeherdercomm-central@e5a72b98ffde [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmkmelin
bugs1683865
Bug 1683865 - Replace xul:image usage in openpgp settings. r=mkmelin Differential Revision: https://phabricator.services.mozilla.com/D117921
mail/extensions/am-e2e/am-e2e.inc.xhtml
mail/extensions/am-e2e/am-e2e.js
mail/locales/en-US/messenger/openpgp/openpgp.ftl
mail/themes/shared/mail/accountManage.css
--- a/mail/extensions/am-e2e/am-e2e.inc.xhtml
+++ b/mail/extensions/am-e2e/am-e2e.inc.xhtml
@@ -27,22 +27,24 @@
 #ifdef MOZ_OPENPGP
       <html:div>
         <html:fieldset id="openpgpOptions" class="openpgp-item"
                        aria-describedby="openPgpDescription">
           <html:legend>&openpgpKeys.label;</html:legend>
 
           <vbox data-subcategory="openpgp" class="openpgp-container">
             <hbox align="center" class="opengpg-intro-section">
-              <image id="openPgpKey"/>
+              <html:img id="openPgpKey"
+                        src="chrome://messenger/skin/icons/login.svg"
+                        alt="" />
               <vbox flex="1">
                 <description class="description-with-side-element openpgp-description">
                   <html:p id="openPgpDescription"></html:p>
-                  <image id="openPgpStatusImage" class="openpgp-status"
-                         hidden="true"/>
+                  <html:img id="openPgpStatusImage" class="openpgp-status"
+                            alt="" hidden="hidden"/>
                   <html:span id="openPgpSelectionStatus"
                              class="tail-with-learn-more"
                              hidden="hidden"></html:span>
                   <label is="text-link" id="openPgpLearnMore"
                          href="https://support.mozilla.org/kb/introduction-to-e2e-encryption"
                          data-l10n-id="e2e-learn-more"
                          class="learnMore"
                          hidden="true"/>
--- a/mail/extensions/am-e2e/am-e2e.js
+++ b/mail/extensions/am-e2e/am-e2e.js
@@ -808,59 +808,71 @@ async function reloadOpenPgpUI() {
 
     let indent = document.createXULElement("vbox");
     indent.classList.add("indent");
 
     let dateContainer = document.createXULElement("hbox");
     dateContainer.classList.add("expiration-date-container");
     dateContainer.setAttribute("align", "center");
 
-    let dateIcon = document.createXULElement("image");
+    let dateIcon = document.createElement("img");
     dateIcon.classList.add("expiration-date-icon");
 
     let dateButton = document.createXULElement("button");
     document.l10n.setAttributes(dateButton, "openpgp-key-man-change-expiry");
     dateButton.addEventListener("command", event => {
       event.stopPropagation();
       enigmailEditKeyDate(key);
     });
     dateButton.setAttribute("hidden", "true");
     dateButton.classList.add("button-small");
 
-    let today = new Date();
-    today.setMonth(today.getMonth() + 6);
+    let description = document.createXULElement("description");
 
-    // If the key expires in less than 6 months.
-    if (
-      key.expiryTime &&
-      Math.round(Date.parse(today) / 1000) > key.expiryTime
-    ) {
-      dateContainer.classList.add("key-is-expiring");
-      document.l10n.setAttributes(dateIcon, "openpgp-key-expires-image");
-      dateButton.removeAttribute("hidden");
-    }
+    if (key.expiryTime) {
+      if (Math.round(Date.now() / 1000) > key.expiryTime) {
+        // Has expired.
+        dateContainer.classList.add("key-expired");
+        dateIcon.setAttribute("src", "chrome://global/skin/icons/warning.svg");
+        // Sets the title attribute.
+        // The alt attribute is not set because the accessible name is already
+        // set by the title.
+        document.l10n.setAttributes(dateIcon, "openpgp-key-has-expired-icon");
+
+        document.l10n.setAttributes(description, "openpgp-radio-key-expired", {
+          date: key.expiry,
+        });
 
-    let fluentExpireKey = "openpgp-radio-key-expires";
-    // If the key passed its expiration date.
-    if (key.expiryTime && Math.round(Date.now() / 1000) > key.expiryTime) {
-      dateContainer.classList.add("key-expired");
-      fluentExpireKey = "openpgp-radio-key-expired";
-      document.l10n.setAttributes(dateIcon, "openpgp-key-expired-image");
-      dateButton.removeAttribute("hidden");
+        dateButton.removeAttribute("hidden");
+        // This key is expired, so make it unselectable.
+        radio.setAttribute("disabled", "true");
+      } else {
+        // If the key expires in less than 6 months.
+        let sixMonths = new Date();
+        sixMonths.setMonth(sixMonths.getMonth() + 6);
+        if (Math.round(Date.parse(sixMonths) / 1000) > key.expiryTime) {
+          dateContainer.classList.add("key-is-expiring");
+          dateIcon.setAttribute(
+            "src",
+            "chrome://messenger/skin/icons/info.svg"
+          );
+          // Sets the title attribute.
+          // The alt attribute is not set because the accessible name is already
+          // set by the title.
+          document.l10n.setAttributes(
+            dateIcon,
+            "openpgp-key-expires-within-6-months-icon"
+          );
+          dateButton.removeAttribute("hidden");
+        }
 
-      // This key is expired, so make it unselectable.
-      radio.setAttribute("disabled", "true");
-    }
-
-    let description = document.createXULElement("description");
-    // If the expiryTime == 0 it means the key doesn't expire.
-    if (key.expiryTime) {
-      document.l10n.setAttributes(description, fluentExpireKey, {
-        date: key.expiry,
-      });
+        document.l10n.setAttributes(description, "openpgp-radio-key-expires", {
+          date: key.expiry,
+        });
+      }
     } else {
       document.l10n.setAttributes(description, "key-does-not-expire");
     }
 
     dateContainer.appendChild(dateIcon);
     dateContainer.appendChild(description);
     dateContainer.appendChild(dateButton);
 
@@ -870,18 +882,22 @@ async function reloadOpenPgpUI() {
       "indent"
     );
 
     // Start key info section.
     let grid = document.createXULElement("hbox");
     grid.classList.add("extra-information-label");
 
     // Key fingerprint.
-    let fingerprintImage = document.createXULElement("image");
-    fingerprintImage.classList.add("content-blocking-openpgp-fingerprint");
+    let fingerprintImage = document.createElement("img");
+    fingerprintImage.setAttribute(
+      "src",
+      "chrome://messenger/skin/icons/fingerprint.svg"
+    );
+    fingerprintImage.setAttribute("alt", "");
 
     let fingerprintLabel = document.createXULElement("label");
     document.l10n.setAttributes(
       fingerprintLabel,
       "openpgp-key-details-fingerprint-label"
     );
     fingerprintLabel.classList.add("extra-information-label-type");
 
@@ -897,18 +913,22 @@ async function reloadOpenPgpUI() {
 
     fgrInputContainer.appendChild(fingerprintInput);
 
     grid.appendChild(fingerprintImage);
     grid.appendChild(fingerprintLabel);
     grid.appendChild(fgrInputContainer);
 
     // Key creation date.
-    let createdImage = document.createXULElement("image");
-    createdImage.classList.add("content-blocking-openpgp-created");
+    let createdImage = document.createElement("img");
+    createdImage.setAttribute(
+      "src",
+      "chrome://messenger/skin/shared/preferences/calendar.svg"
+    );
+    createdImage.setAttribute("alt", "");
 
     let createdLabel = document.createXULElement("label");
     document.l10n.setAttributes(
       createdLabel,
       "openpgp-key-details-created-header"
     );
     createdLabel.classList.add("extra-information-label-type");
 
@@ -1196,45 +1216,44 @@ function updateUIForSelectedOpenPgpKey()
     // If the currently used key was deleted, we might not have the
     // corresponding radio element.
     if (radio) {
       radio.closest(".content-blocking-category").classList.add("selected");
     }
   }
 
   // Reset the image in case of async reload of the list.
+  let statusLabel = document.getElementById("openPgpSelectionStatus");
   let image = document.getElementById("openPgpStatusImage");
   image.classList.remove("status-success", "status-error");
 
-  let key = EnigmailKeyRing.getKeyById(gKeyId, true);
-
   // Check if the currently selected key has expired.
-  if (key && key.expiryTime && Math.round(Date.now() / 1000) > key.expiryTime) {
-    image.classList.add("status-error");
-    document.l10n.setAttributes(
-      document.getElementById("openPgpSelectionStatus"),
-      "openpgp-selection-status-error",
-      {
-        key: `0x${gKeyId}`,
-      }
-    );
-  } else {
-    image.classList.add("status-success");
-    document.l10n.setAttributes(
-      document.getElementById("openPgpSelectionStatus"),
-      "openpgp-selection-status",
-      {
-        count: gKeyId ? 1 : 0,
-        key: `0x${gKeyId}`,
-      }
-    );
+  if (gKeyId) {
+    let key = EnigmailKeyRing.getKeyById(gKeyId, true);
+    if (key?.expiryTime && Math.round(Date.now() / 1000) > key.expiryTime) {
+      image.setAttribute("src", "chrome://messenger/skin/icons/stop.svg");
+      image.classList.add("status-error");
+      document.l10n.setAttributes(
+        statusLabel,
+        "openpgp-selection-status-error",
+        { key: `0x${gKeyId}` }
+      );
+    } else {
+      image.setAttribute("src", "chrome://global/skin/icons/check.svg");
+      image.classList.add("status-success");
+      document.l10n.setAttributes(
+        statusLabel,
+        "openpgp-selection-status-have-key",
+        { key: `0x${gKeyId}` }
+      );
+    }
   }
 
   let hide = !gKeyId;
-  document.getElementById("openPgpSelectionStatus").hidden = hide;
+  statusLabel.hidden = hide;
   document.getElementById("openPgpLearnMore").hidden = hide;
   image.hidden = hide;
 }
 
 /**
  * Generic method to copy a string in the user's clipboard.
  *
  * @param {string} val - The formatted string to be copied in the clipboard.
--- a/mail/locales/en-US/messenger/openpgp/openpgp.ftl
+++ b/mail/locales/en-US/messenger/openpgp/openpgp.ftl
@@ -282,22 +282,18 @@ openpgp-copy-cmd-label =
 #   $count (Number) - the number of configured keys associated with the current identity
 #   $identity (String) - the email address of the currently selected identity
 openpgp-description = { $count ->
     [0]     Thunderbird doesn’t have a personal OpenPGP key for <b>{ $identity }</b>
     [one]   Thunderbird found { $count } personal OpenPGP key associated with <b>{ $identity }</b>
    *[other] Thunderbird found { $count } personal OpenPGP keys associated with <b>{ $identity }</b>
 }
 
-#   $count (Number) - the number of configured keys associated with the current identity
 #   $key (String) - the currently selected OpenPGP key
-openpgp-selection-status = { $count ->
-    [0]     Select a valid key to enable the OpenPGP protocol.
-   *[other] Your current configuration uses key ID <b>{ $key }</b>
-}
+openpgp-selection-status-have-key = Your current configuration uses key ID <b>{ $key }</b>
 
 #   $key (String) - the currently selected OpenPGP key
 openpgp-selection-status-error = Your current configuration uses the key <b>{ $key }</b>, which has expired.
 
 openpgp-add-key-button =
     .label = Add Key…
     .accesskey = A
 
@@ -318,24 +314,24 @@ openpgp-radio-none-desc = Do not use Ope
 
 openpgp-radio-key-not-usable = This key is not usable as a personal key, because the secret key is missing!
 openpgp-radio-key-not-accepted = To use this key you must approve it as a personal key!
 openpgp-radio-key-not-found = This key could not be found! If you want to use it you must import it to { -brand-short-name }.
 
 #   $key (String) - the expiration date of the OpenPGP key
 openpgp-radio-key-expires = Expires on: { $date }
 
-openpgp-key-expires-image =
-    .tooltiptext = Key is expiring in less than 6 months
-
 #   $key (String) - the expiration date of the OpenPGP key
 openpgp-radio-key-expired = Expired on: { $date }
 
-openpgp-key-expired-image =
-    .tooltiptext = Key expired
+openpgp-key-expires-within-6-months-icon =
+    .title = Key is expiring in less than 6 months
+
+openpgp-key-has-expired-icon =
+    .title = Key expired
 
 openpgp-key-expand-section =
   .tooltiptext = More information
 
 openpgp-key-revoke-title = Revoke Key
 
 openpgp-key-edit-title = Change OpenPGP Key
 
--- a/mail/themes/shared/mail/accountManage.css
+++ b/mail/themes/shared/mail/accountManage.css
@@ -382,17 +382,16 @@ treechildren::-moz-tree-image(folderName
 
 .identity-table td input {
   width: 100%;
 }
 
 /* ::::: e2e encryption ::::: */
 
 #openPgpKey {
-  list-style-image: url("chrome://messenger/skin/icons/login.svg");
   -moz-context-properties: fill, fill-opacity;
   fill: currentColor;
   fill-opacity: 0.5;
   width: 48px;
   height: 48px;
   margin-inline-end: 10px;
 }
 
@@ -401,31 +400,28 @@ treechildren::-moz-tree-image(folderName
 .description-with-side-element {
   margin-inline-end: 10px !important;
 }
 
 .openpgp-description p {
   margin-block: 0 6px;
 }
 
-.openpgp-status:not([hidden="true"]) {
+.openpgp-status {
   vertical-align: text-top;
-  display: inline-block;
   -moz-context-properties: fill;
   margin-inline-end: 2px;
   width: 16px;
 }
 
-.status-success {
-  list-style-image: url("chrome://global/skin/icons/check.svg");
+.openpgp-status.status-success {
   fill: #12bc00;
 }
 
-.status-error {
-  list-style-image: url("chrome://messenger/skin/icons/stop.svg");
+.openpgp-status.status-error {
   fill: #d70022;
 }
 
 /* ::::: OpenPGP key selection ::::: */
 
 .openpgp-container {
   margin-top: 10px;
 }
@@ -434,19 +430,18 @@ treechildren::-moz-tree-image(folderName
   margin-bottom: 10px;
 }
 
 #openPgpKeyList {
   margin-top: 16px;
 }
 
 .content-blocking-category .checkbox-label-box,
-.extra-information-label image,
-.arrowhead,
-.content-blocking-info-image {
+.extra-information-label > img,
+.arrowhead {
   -moz-context-properties: fill;
   fill: currentColor;
 }
 
 .content-blocking-category {
   border-radius: 4px;
   margin: 3px 0;
   padding: 9px;
@@ -555,38 +550,33 @@ treechildren::-moz-tree-image(folderName
 }
 
 .content-blocking-category-description {
   font-size: 90%;
   opacity: 0.6;
 }
 
 .expiration-date-icon {
-  display: none;
   vertical-align: text-top;
   -moz-context-properties: fill;
   margin-inline-end: 4px;
   fill: currentColor;
   width: 16px;
 }
 
-.expiration-date-container.key-is-expiring .expiration-date-icon {
-  display: inline-block;
-  list-style-image: url("chrome://messenger/skin/icons/info.svg");
-  opacity: 0.9;
+.expiration-date-icon:not([src]) {
+  display: none;
 }
 
 .expiration-date-container.key-expired description {
   color: #D70022;
   font-weight: 600;
 }
 
 .expiration-date-container.key-expired .expiration-date-icon {
-  display: inline-block;
-  list-style-image: url("chrome://global/skin/icons/warning.svg");
   fill: #FF9400;
 }
 
 .first-element {
   margin-inline-start: 0;
 }
 
 .last-element {
@@ -601,28 +591,20 @@ treechildren::-moz-tree-image(folderName
 }
 
 .extra-information-label-type {
   font-weight: 600;
   margin-inline-end: 4px;
 }
 
 /* Key info icons */
-.extra-information-label image:not(.button-icon) {
+.extra-information-label > img {
   margin-inline-end: 5px;
 }
 
-.content-blocking-openpgp-fingerprint {
-  list-style-image: url("chrome://messenger/skin/icons/fingerprint.svg");
-}
-
-.content-blocking-openpgp-created {
-  list-style-image: url("chrome://messenger/skin/shared/preferences/calendar.svg");
-}
-
 .openpgp-key-details {
   margin-bottom: 18px;
   border: 1px solid var(--in-content-box-border-color);
   border-radius: 4px;
   overflow: hidden;
   background-color: var(--in-content-page-background);
 }