<!--
  The contents of this file are subject to the Mozilla Public
  License Version 1.1 (the "MPL"); you may not use this file
  except in compliance with the MPL. You may obtain a copy of
  the MPL at http://www.mozilla.org/MPL/

  Software distributed under the MPL is distributed on an "AS
  IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
  implied. See the MPL for the specific language governing
  rights and limitations under the MPL.

  The Original Code is Enigmail.

  The Initial Developer of this code is Patrick Brunschwig.
  Portions created by Patrick Brunschwig <patrick.brunschwig@gmx.net>
  are Copyright (C) 2004 Patrick Brunschwig.
  All Rights Reserved.

  Contributor(s):
    * Russell Francis <rf358197@ohio.edu>

  Alternatively, the contents of this file may be used under the
  terms of the GNU General Public License (the "GPL"), in which case
  the provisions of the GPL are applicable instead of
  those above. If you wish to allow use of your version of this
  file only under the terms of the GPL and not to allow
  others to use your version of this file under the MPL, indicate
  your decision by deleting the provisions above and replace them
  with the notice and other provisions required by the GPL.
  If you do not delete the provisions above, a recipient
  may use your version of this file under either the MPL or the
  GPL.
-->

<?xml-stylesheet href="chrome://communicator/skin/" type="text/css"?>
<?xml-stylesheet href="chrome://enigmail/skin/enigmail.css" type="text/css"?>

<!DOCTYPE window [
<!ENTITY % brandDTD SYSTEM "chrome://global/locale/brand.dtd" >
%brandDTD;
<!ENTITY % enigMailDTD SYSTEM "chrome://enigmail/locale/enigmail.dtd" >
%enigMailDTD;
]>

<dialog id="enigmailViewKeySigDlg"
        title="&enigmail.viewKeySigDlg.title;"
        xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
        onload="onLoad();"
        style="width:600px"
        persist="width height"
        buttons="accept">


  <script type="application/x-javascript" src="chrome://enigmail/content/enigmailCommon.js"/>

  <broadcasterset>
    <broadcaster id="bcViewDetails" disabled="false"/>
  </broadcasterset>

  <popupset>
    <popup id="sigCtxMenu"
           onpopupshowing="showSigCtxMenu()">

      <menuitem id="ctxViewSig" observes="bcViewDetails"
                label="&enigmail.keyMan.ctxViewSig.label;"
                oncommand="listSig()"/>
      <menuitem id="ctxDetails" observes="bcViewDetails"
                label="&enigmail.keyMan.keyProps.label;"
								oncommand="viewKeyDetails()"/>
      <menuitem id="ctxImportKey"
                label="&enigmail.importpublickey.label;"
                oncommand="importKey()"/>
    </popup>
  </popupset>

  <vbox flex="1">
    <hbox>
      <label value="&enigmail.viewKeySigDlg.sigForKey.label;"/>
      <label id="keyIdValue" value="?"/>
    </hbox>
    <separator/>
    <tree id="keySigList" flex="1"
      enableColumnDrag="true"
      style="height:200px"
      hidecolumnpicker="true"
      ondblclick="handleDblClick(event)">

      <treecols>
        <treecol id="enigUserNameCol" flex="1"
            label="&enigmail.keyUserId.label;"/>
        <splitter class="tree-splitter"/>
        <treecol id="keyCol" style="width:90px"
                 label="&enigmail.keyId.label;"
                 persist="width"/>
        <splitter class="tree-splitter"/>
        <treecol id="typeCol" style="width:70px"
                 label="&enigmail.viewKeySigDlg.sigType.label;"
                 persist="width"/>
        <splitter class="tree-splitter"/>
        <treecol id="validityCol" style="width:70px"
                 label="&enigmail.valid.label;"
                 persist="width"/>
        <splitter class="tree-splitter"/>
        <treecol id="createdCol" style="width:70px"
                 label="&enigmail.created.label;"
                 persist="width"/>
      </treecols>

      <treechildren id="keySigListChildren"
                    context="sigCtxMenu"/>

    </tree>
  </vbox>

  <script type="application/x-javascript">
  <![CDATA[

    EnigInitCommon("enigmailViewKeySigDlg");

    // field ID's of key list (as described in the doc/DETAILS file in the GnuPG distribution)
    const KEY_TRUST=1;
    const KEY_ID = 4;
    const CREATED = 5;
    const EXPIRY = 6;
    const UID_ID = 7;
    const OWNERTRUST = 8;
    const USER_ID = 9;
    const SIG_TYPE = 10;
    const KEY_USE_FOR = 11;

    const KEY_EXPIRED="e";
    const KEY_REVOKED="r";
    const KEY_INVALID="i";
    const KEY_DISABLED="d";
    const KEY_NOT_VALID=KEY_EXPIRED+KEY_REVOKED+KEY_INVALID+KEY_DISABLED;

    var gKeyListArr;

    function onLoad() {
      gKeyListArr = window.arguments[0].keyListArr;
      window.arguments[1].refresh = false;
      loadList();
    }

    function setWindowPos(x, y) {
      window.screenX = x;
      window.screenY = y;
    }

    function loadList() {
      var enigmailSvc = GetEnigmailSvc();
      if (!enigmailSvc) {
        EnigAlert(EnigGetString("accessError"));
        window.close();
        return;
      }

      var inArg = window.arguments[0];
      var keyId = inArg.keyId;
      var keyIdValue = document.getElementById("keyIdValue");

      if (typeof(inArg.posX)=="number" &&
          typeof(inArg.posY)=="number") {
        window.setTimeout(setWindowPos, 0, inArg.posX, inArg.posY);
      }

      keyIdValue.value = gKeyListArr[keyId].userId+" - 0x"+ inArg.keyId.substr(-8,8);

      var exitCodeObj = {};
      var errorMsgObj = {};

      var sigList = enigmailSvc.getKeySig("0x"+keyId, exitCodeObj, errorMsgObj);

      if (exitCodeObj.value != 0) {
        EnigAlert(errorMsgObj.value);
        window.close();
        return;
      }


      var keySigList=document.getElementById("keySigList");
      var treeChildren=keySigList.getElementsByAttribute("id", "keySigListChildren")[0];
      var aSigList = sigList.split(/\n/);
      var aRevSig = [];
      var currUid="";

      for (var i=0; i<aSigList.length; i++) {
        var listRow=aSigList[i].split(/:/);
        if (listRow.length>=0) {
          if ((listRow[0] == "uid" || listRow[0] == "pub" || listRow[0] == "uat") && (listRow[USER_ID].length>0)) {
            var userRow=document.createElement("treerow");
            if (typeof(listRow[KEY_USE_FOR])!="string") {
              listRow[KEY_USE_FOR]="";
            }
            var keyValid = (KEY_NOT_VALID.indexOf(listRow[KEY_TRUST])<0 &&
                            listRow[KEY_USE_FOR].indexOf("D")<0);
            if (listRow[0] == "uat") {
              listRow[USER_ID]=EnigGetString("userAtt.photo");
            }

            if (listRow[0] == "uid" || listRow[0] == "uat") {
              currUid=listRow[UID_ID];
            }
            addCell(userRow, EnigConvertGpgToUnicode(listRow[USER_ID]), true, keyValid);
            var treeItem=document.createElement("treeitem");
            treeItem.appendChild(userRow);
            treeChildren.appendChild(treeItem);
          }
          else if (listRow[0] == "sig") {
            if (listRow[USER_ID].length == 0) {
              listRow[USER_ID] = "-";
            }
            if (listRow[SIG_TYPE].substr(0,2).toLowerCase()!="1f") {
              // ignore "revoker" signatures
              userRow=document.createElement("treerow");
              if (typeof(gKeyListArr[listRow[KEY_ID]]) == "object") {
                addCell(userRow, "   "+EnigConvertGpgToUnicode(listRow[USER_ID]));
              }
              else {
                addCell(userRow, "   "+EnigGetString("userIdNotFound"));
              }
              addCell(userRow, listRow[KEY_ID].substr(-8,8));
              if (listRow[SIG_TYPE].substr(2,1) == "x") {
                addCell(userRow, EnigGetString("keySignatureExportable"));
              }
              else {
                addCell(userRow, EnigGetString("keySignatureLocal"));
              }
              if (typeof(gKeyListArr[listRow[KEY_ID]]) == "object") {
                addCell(userRow, EnigGetString("signatureValid"));
              }
              else {
                addCell(userRow, EnigGetString("keySignatureNoKey"));
                userRow.setAttribute("noKey", "true");
              }

              userRow.setAttribute("keyID", listRow[KEY_ID]);
              userRow.setAttribute("sigID", currUid+"-"+listRow[KEY_ID]);
              addCell(userRow, EnigGetDateTime(listRow[CREATED], true, false));
              treeItem=document.createElement("treeitem");
              treeItem.appendChild(userRow);
              treeChildren.appendChild(treeItem);
            }
          }
          else if (listRow[0] == "sub") {
            break;
          }
          else if (listRow[0] == "rev") {
            aRevSig.push(currUid+"-"+listRow[KEY_ID]);
          }
        }
      }

      // mark revoked signatures
      for (i=0; i<aRevSig.length; i++) {
        var nodes = document.getElementsByAttribute("sigID", aRevSig[i]);
        for (var node=0; node < nodes.length; node++) {
          try {
            nodes[node].childNodes[3].setAttribute("label", EnigGetString("keyValid.revoked"));

            var cNode=nodes[node].firstChild;
            while (cNode) {
              cNode.setAttribute("properties", "enigKeyInactive");
              cNode=cNode.nextSibling;
            }
          }
          catch (ex){}
        }
      }

      keySigList.appendChild(treeChildren);
      return;
    }

    function addCell(row, label, subkeyRow, keyActive) {
      var cell = document.createElement("treecell");
      cell.setAttribute("label", label);
      if (subkeyRow) {
        if (keyActive) {
          cell.setAttribute("properties", "enigmailSubkeyTitle");
        }
        else {
          cell.setAttribute("properties", "enigmailSubkeyTitle enigKeyInactive");
        }
      }
      row.appendChild(cell);
      return cell;
    }

    function getSelectedRows()
    {
      var sigList = document.getElementById( "keySigList" );
      var numRanges = sigList.view.selection.getRangeCount();
      var selectedRows = new Array();
      var start = new Object();
      var end = new Object();

      for( var i = 0; i < numRanges; ++i )
      {
        sigList.view.selection.getRangeAt( i, start, end );
        for( var j = start.value; j <= end.value; ++j )
        {
          selectedRows.push( j );
        }
      }

      return( selectedRows );
    }

    function getRowByIndex( index )
    {
      var sigList = document.getElementById( "keySigList" );
      var item = sigList.view.getItemAtIndex( index );
      if( item )
      {
        return item.firstChild;
      }
      return null;
    }

    function getCurrRow() {
      var sigList = document.getElementById("keySigList");
      var item = sigList.view.getItemAtIndex(sigList.view.selection.currentIndex);
      if (item) {
        return item.firstChild;
      }
      return null;
    }

    function showSigCtxMenu()
    {
      var viewDetailsDisabled = "true";
      var importKeyDisabled = "true";
      var selectedRows = getSelectedRows();

      if( selectedRows.length == 1 )
      {
        var row = getRowByIndex( selectedRows[0] );
        if( row.hasAttribute( "keyID" ) )
        {
          if( row.hasAttribute( "noKey" ) )
          {
            importKeyDisabled = "false";
          }
          else
          {
            viewDetailsDisabled = "false";
          }
        }
      }
      else
      {
        /* We have more than one row. If any of them are importable, enable
         * the import menuitem.
         */
        for( var i = 0; i < selectedRows.length; ++i )
        {
          var row = getRowByIndex( selectedRows[i] );
          if( row.hasAttribute( "keyID" ) && row.hasAttribute( "noKey" ) )
          {
            importKeyDisabled = "false";
            break;
          }
        }
      }
      document.getElementById( "bcViewDetails" ).setAttribute( "disabled", viewDetailsDisabled );
      document.getElementById( "ctxImportKey" ).setAttribute( "disabled", importKeyDisabled );
    }

    function listSig() {
      var row = getCurrRow();
      var inputObj = {
        keyId: row.getAttribute("keyID"),
        keyListArr: gKeyListArr,
        posX: window.screenX+10,
        posY: window.screenY+10
      };
      var resultObj = {};

      window.openDialog("chrome://enigmail/content/enigmailViewKeySigDlg.xul",
             "", "dialog,modal,centerscreen,resizable=yes", inputObj, resultObj);
      if (resultObj.refresh) {
        window.arguments[1].refresh=true;
      }
    }

    function viewKeyDetails() {
      var row = getCurrRow();
      var keyId = row.getAttribute("keyID")

      var inputObj = {
        keyId:  keyId,
        keyListArr: gKeyListArr,
        secKey: gKeyListArr[keyId].secretAvailable
      };
      var resultObj = { refresh: true };
      window.openDialog("chrome://enigmail/content/enigmailKeyDetailsDlg.xul",
            "", "dialog,modal,centerscreen", inputObj, resultObj);
      if (resultObj.refresh) {
        window.arguments[1].refresh=true;
      }
    }

    function importKey()
    {
      var resultObj = new Object();
      var inputObj = new Object();
      inputObj.searchList = new Array();
      var selectedRows = getSelectedRows();
      for( var i = 0; i < selectedRows.length; ++i )
      {
        var row = getRowByIndex( selectedRows[i] );
        if( row.hasAttribute( "keyID" ) && row.hasAttribute( "noKey" ) )
        {
          inputObj.searchList.push( "0x" + row.getAttribute( "keyID" ).substr(-8,8) );
        }
      }

      EnigDownloadKeys( inputObj, resultObj );
      if( resultObj.importedKeys > 0 )
      {
        var treeChildren = document.getElementById("keySigListChildren");
        while (treeChildren.firstChild)
        {
          treeChildren.removeChild(treeChildren.firstChild);
        }
        var keyListObj = {};
        EnigLoadKeyList(true, keyListObj);
        gKeyListArr = keyListObj.keyList;
        window.arguments[1].refresh = true;
        loadList();
      }
    }

    function handleDblClick(event) {
      if (event) {
        if (event.button != 0) return;
      }
      var row = getCurrRow();
      if (row.hasAttribute("keyID")) {
        if (row.hasAttribute("noKey")) {
          if (EnigConfirm(EnigGetString("retrieveKeyConfirm"))) {
            importKey();
          }
        }
        else {
          listSig();
        }
      }
    }
  ]]>
  </script>

</dialog>

