// encoding ='UTF-8'

/*
  # File : xnote-overlay.js
  # Author : Hugo Smadja, Pierre-Andre Galmes, Lorenz Froihofer, Klaus Buecher
  # Description : functions associated to the "xnote-overlay.xul" overlay file.
*/

/* 
 This overlay only deals with the context menu entries and should be replaced by
 menus API in background entirely.

 When a context menu entry closes a note window, it does not update xnote_displayed,
 so when this moves into background it should be more simple
 
 Tag management principles and thoughts
 - When should labels be applied?
    - When a new post-it is saved.
    - When XNote notes are imported from a PC to another PC (cf TODO: import
      procedure).

 - When should the XNote label related to a message be removed?
    - When the message is empty (no text in it).
    - When the message is removed.

 - What should happened when XNote is removed?
  - Remove the XNote tag ? No
  - Remove the XNote labels associated to messages? No
*/
//console.log("start xnote-overlay");

var { xnote } = ChromeUtils.import ? ChromeUtils.import("resource://xnote/modules/xnote.jsm")
  : ChromeUtils.importESModule("resource://xnote/modules/xnote.sys.mjs");

//var { MessageListTracker, MessageTracker, MessageManager } =
//  ChromeUtils.importESModule("resource:///modules/ExtensionMessages.sys.mjs");

var logException = function (exc, unknown) {
  try {
    Services.console.logStringMessage(exc.toString() + "\n" + exc.stack);
  } catch (x) { };
};



var xnoteOverlayObj = function () {
  var pub = {};
  Services.scriptloader.loadSubScript("chrome://xnote/content/scripts/notifyTools.js", pub, "UTF-8");

  // Variables related to the XNote context menu.
  var noteForContextMenu;
  var currentIndex;

  /** Contains the note for the current message */
  // This state variable is used by the Experiment, if this file goes away, the state could move into
  // a window map stored in the Experiment.
  var note;

  /** Contains the XNote window instance. */
  // This state variable is used by the Experiment, if this file goes away, the state could move into
  // a window map stored in the Experiment.
  var xnoteWindow;

  //msgHdr of the currently selected message
  var msgHdr;

  pub.GetThreadTree = function () {
    let mainWindow = Services.wm.getMostRecentWindow("mail:3pane");
    let threadTree1 = mainWindow.gTabmail.currentAbout3Pane.threadTree;
    let threadTree = mainWindow.gTabmail.tabInfo[0].chromeBrowser.contentWindow.threadTree;
    //  console.log("" ,threadTree ,threadTree1);
    return threadTree1;
  
  }
  


  /**
   * CALLER XUL
   * Type: event command element XUL <menuitem>
   * Id: context-addition
   * FUNCTION
   * Creation and modification of notes uses the same function, that is context_modifierNote()
   */
  pub.context_createNote = function (clicked = false, msgId = null) {
    // console.log("create hdr", pub.msgHdr);
    pub.context_modifyNote(false, clicked, msgId);
  }

  /**
   * CALLER XUL
   * Type: event command element XUL <menuitem>
   * Id: context-modif
   * FUNCTION
   */


  pub.getDBView = function () {
    let mainWindow = Services.wm.getMostRecentWindow("mail:3pane");
    //console.log("about3",mainWindow.gTabmail.currentAbout3Pane, mainWindow.gTabmail.currentTabInfo.chromeBrowser.contentWindow, mainWindow.gTabmail.tabInfo[0].chromeBrowser.contentWindow );
    //      this.mail3PaneWindow = mainWindow.gTabmail.currentAbout3Pane;
    let gDBView = mainWindow.gTabmail.currentAbout3Pane?.gDBView;//mainWindow.gDBView  ;//this.mail3PaneWindow.gDBView;
    //     this.threadTree = mainWindow.gTabmail.currentAbout3Pane.threadTree ;
    //     this.threadTree.addEventListener("select", mainWindow.NostalgyDefLabel, false);
    return gDBView;


  }


  pub.context_modifyNote = function (defaultSize, clicked = false, msgId = null) {
    //  console.log("modifynote");
    let gDBView = pub.getDBView();
    // debugger;
    //  console.log( "context_modifyNote wnd", window, window.document.title, gDBView.msgFolder.name, gDBView);
    if (msgId || clicked || (gDBView.selection.currentIndex == currentIndex)) {
      //Closes the note (if any) of the old (deselected) message.
      pub.closeNote();
    
let messageId = msgId ||  pub.getMessageID();
      //Initialize note for the newly selected message.
      note = new xnote.ns.Note(messageId);
      pub.updateTag(note.text);
      //          console.log("note", note, "wnd", window);
      if (defaultSize) {
        note.x = note.DEFAULT_X;
        note.y = note.DEFAULT_Y;
        //        note.width = note.DEFAULT_XNOTE_WIDTH;
        //        note.height = note.DEFAULT_XNOTE_HEIGHT;

      }

      /*
       xnoteWindow = window.openDialog(
         'chrome://xnote/content/testwin.xhtml',
         'XNote',
         'chrome=yes,dependent=yes,resizable=yes,titlebar=no, modal=no,left=' + (window.screenX + note.x) + ',top=' + (window.screenY + note.y) + ',width=' + note.width + ',height=' + note.height + "50px",
         note, true
       );
       */
      xnoteWindow = window.openDialog(
        'chrome://xnote/content/xnote-window.xhtml',
        'XNote',
        'chrome=yes,dependent=yes,resizable=yes,titlebar=yes, modal=no,left=' + (window.screenX + note.x) + ',top=' + (window.screenY + note.y) + ',width=' + note.width + ',height=' + (note.height + 50),
        note, true
      );
      //was titlebar=no

      //   console.log("xnotewnd in modify_note", xnoteWindow, window, window.document.title);
    }
    else {
      gDBView.selection.select(currentIndex);
      gDBView.selectionChanged();
      // The following prevents the previous message selection from
      // being restored during closing of the context menu.
      // Variable not present in SeaMonkey --> check to prevent errors.
      if (xnote.ns.Commons.isInThunderbird) {
        //115?       gRightMouseButtonSavedSelection.realSelection.select(currentIndex);
      }
    }
  }

  /**
   * CALLER XUL
   * Type: event command element XUL &lt;menuitem&gt;
   * Id: context-suppr
   * FUNCTION
   * Delete the note associated with the selected e-mail.
   */
  pub.context_deleteNote = function () {
    let gDBView = pub.getDBView();
    //   console.log("context_deleteNote", noteForContextMenu);
    if ( (gDBView.selection.currentIndex == currentIndex)) {
      //Closes the note (if any) of the old (deselected) message.
      pub.closeNote();
    };
    pub.closeNote();
    note = new xnote.ns.Note(pub.getMessageID());
    note.deleteNote();
//    if (noteForContextMenu) noteForContextMenu.deleteNote(); else note.deleteNote();
    //pub.notifyTools.notifyBackground({ command: "deleteXNote" });  //done in XNote class

    pub.updateTag("");


    pub.closeNote();
  }

  pub.context_resetNoteWindow = function () {
    if (gDBView.selection.currentIndex == currentIndex) {
      pub.context_modifyNote(true);
      /*      
            xnoteWindow.resizeTo(noteForContextMenu.DEFAULT_XNOTE_WIDTH, noteForContextMenu.DEFAULT_XNOTE_HEIGHT);
            xnoteWindow.moveTo(noteForContextMenu.DEFAULT_X, noteForContextMenu.DEFAULT_Y)
            note.modified = true;
          */
    }
    else {
      noteForContextMenu.x = noteForContextMenu.DEFAULT_X;
      noteForContextMenu.y = noteForContextMenu.DEFAULT_Y;
      noteForContextMenu.width = noteForContextMenu.DEFAULT_XNOTE_WIDTH;
      noteForContextMenu.height = noteForContextMenu.DEFAULT_XNOTE_HEIGHT;
      noteForContextMenu.modified = true;
      noteForContextMenu.saveNote();
    }
  }

  /**
   * Closes the XNote window.
   */
  pub.closeNote = function () {
    //  console.log("close xnotewnd", xnoteWindow, xnoteOverlayObj.xnoteWindow);
    if (xnoteWindow != null) {//115? && xnoteWindow.document) {
      //  setTimeout(xnoteWindow.close,500);
      //  pub.notifyTools.notifyBackground({ command: "closeNote" });

      xnoteWindow.close();
    }
  }

  /**
   * FUNCTION
   * Applies the XNote tag to the selected message.
   * (Choice of tag in the preferences.)
   */
  pub.updateTag = function (noteText) {
    //    console.log("updateTag", xnote.ns.Commons.useTag, noteText, pub.msgHdr);
    if (xnote.ns.Commons.useTag) {
      //    let gDBView = pub.getDBView();
      //    console.log("gDBView",gDBView, window.WL);
      //    let msgHdr = gDBView.hdrForFirstSelectedMessage;
      let msgId = xnote.ns.Commons.context.extension.messageManager.convert(pub.msgHdr);
      // If the note isn't empty,
      if (noteText != '') {
        // Add the XNote Tag.
        //       ToggleMessageTag("xnote", true);
        pub.notifyTools.notifyBackground({ command: "updateTag", info: { msgId: msgId.id, addTag: true, removeTag: false } });
        //      console.log("addTag", noteText);
      }
      // If the note is empty,
      else {
        // Remove the XNote Tag.
        //        ToggleMessageTag("xnote", false);
        pub.notifyTools.notifyBackground({ command: "updateTag", info: { msgId: msgId.id, addTag: false, removeTag: true } });
        //     console.log("removeTag", noteText);
      }
    }
  }

  function updateContextMenu() {
    noteForContextMenu = new xnote.ns.Note(pub.getMessageID());
    //  console.log("contextmenu", noteForContextMenu);
    let noteExists = noteForContextMenu.exists();
    /* Commented until button will be re-enabled in manifest.json 
      ("message_display_action" removed in earlier commit).
    if (noteExists) xnote.WL.messenger.messageDisplayAction.disable(); else 
         xnote.WL.messenger.messageDisplayAction.enable(); */
    window.gTabmail.currentAbout3Pane.document.getElementById('xnote-context-create').setAttribute('hidden', noteExists);
    window.gTabmail.currentAbout3Pane.document.getElementById('xnote-context-modify').setAttribute('hidden', !noteExists);
    window.gTabmail.currentAbout3Pane.document.getElementById('xnote-context-delete').setAttribute('hidden', !noteExists);
    window.gTabmail.currentAbout3Pane.document.getElementById('xnote-context-separator-after-delete').setAttribute('hidden', !noteExists);
    window.gTabmail.currentAbout3Pane.document.getElementById('xnote-context-reset-note-window').setAttribute('hidden', !noteExists);
    var messageArray = pub.getDBView().getSelectedMsgHdrs(); //115  gFolderDisplay.selectedMessages;
    if (messageArray && messageArray.length == 1) {
      window.gTabmail.currentAbout3Pane.document.getElementById('xnote-mailContext-xNote').setAttribute('disabled', false);
    }
    else {
      window.gTabmail.currentAbout3Pane.document.getElementById('xnote-mailContext-xNote').setAttribute('disabled', true);
    }
  }

  /**
   * FUNCTION
   * For right click in message pane:
   *   - Instantiates an object notes for the message on which was clicked
   *   - Functions that are not currently possible are greyed out in the context
   *     menu, e.g., modify or delete a note for a message not containing a note.
   */
  pub.messageListClicked = function (e) {
    if (e.button == 2) {
      updateContextMenu();
    }
    let t = e.originalTarget;
    if (true) { //t.className == "thread-container") {
      let tree = pub.GetThreadTree();
      //   let treeCellInfo = tree.getCellAt(e.clientX, e.clientY);
      currentIndex = tree._selection._currentIndex;
      //  let gDBView = pub.getDBView();
      // pub.msgHdr = gDBView.
      //          console.log("currInd/messlistclicked", currentIndex);//, gDBView); //115treeCellInfo.row;
    };
  }

  pub.getCurrentRow = function (e) {
    /*102
       let t = e.originalTarget;
       if (t.localName == 'treechildren') {
         let tree = pub.GetThreadTree();
         let treeCellInfo = tree.getCellAt(e.clientX, e.clientY);
         currentIndex = treeCellInfo.row;
       }
     */
    //   console.log("click", e);
    let t = e.originalTarget;
    //TB115  if (t.localName == 'treechildren') {
    if (true) { //t.className == "thread-container") {
      let tree = pub.GetThreadTree();
      //   let treeCellInfo = tree.getCellAt(e.clientX, e.clientY);
      currentIndex = tree._selection._currentIndex;
      //    console.log("currInd", currentIndex); //115treeCellInfo.row;
      //or tree.selectedIndex

    };
  }


  pub.messagePaneClicked = function (e) {
    if (e.button == 2) {
      updateContextMenu();
    }
    //  currentIndex = gDBView.selection.currentIndex;
  }

  /**
   * Get message id from selected message
   */
  pub.getMessageID = function () {
    /*
      let message = gFolderDisplay.selectedMessage;
      if (message != null) return message.messageId;
    */
    //    console.log("hdr-id", pub.getDBView(), pub.getDBView().getSelectedMsgHdrs());
    let message = pub.getDBView().hdrForFirstSelectedMessage;
    //  console.log("hdr", message.messageId);
    pub.msgHdr = message;

    //  let message = null; //TB115 gFolderDisplay.selectedMessage;
    if (message != null) return message.messageId;
    return null;
  }

  /**
   * At each boot of the extension, associate events such as selection of mails,
   * files, or right click on the list of messages. On selection show the associated
   * note.
   */
  pub.onLoad = function (e) {
    //  console.log("onload xn overlay");
    try {
      let m3pane = window;//.gTabmail.tabInfo[0].chromeBrowser.contentWindow;//window.gTabmail.currentAbout3Pane
      //      let tree = m3pane.threadTree;//document.getElementById('threadTree');
      //      console.log("pane",m3pane.threadTree ,m3pane.threadTree );
      /*
       let tree = pub.GetThreadTree();
       //    console.log("pane",m3pane ,m3pane.threadTree , tree);
       //    tree.addEventListener('contextmenu', pub.messageListClicked, false);
       //    tree.addEventListener('mouseover', pub.getCurrentRow, false);
 
       //let messagePane = document.getElementById("messagepane");
       //      m3pane.messagePane.addEventListener("contextmenu", pub.messagePaneClicked, false);
       //  tree = pub.GetThreadTree();
       if (tree) {
         tree.addEventListener('click', pub.getCurrentRow, false);
         tree.addEventListener('contextmenu', pub.messageListClicked, false);
 
       }
 */
    }
    catch (e) {
      logException(e, false);
    }
  }

  pub.onUnload = function (e) {
    //  console.log("close xn-overlay");
    try {
      let m3pane = window;//.gTabmail.currentAbout3Pane
      //     let tree = m3pane.threadTree;// document.getElementById('threadTree');
      //   tree = pub.GetThreadTree();
      //115!!     tree.removeEventListener('mouseover', pub.getCurrentRow);

      // let messagePane = document.getElementById("messagepane");
      //115!!    m3pane.messagePane.removeEventListener("contextmenu", pub.messagePaneClicked);
      //     tree = pub.GetThreadTree();
      //     if (tree) {
      //        tree.removeEventListener('click', pub.getCurrentRow);
      //        tree.removeEventListener('contextmenu', pub.messageListClicked);
      //
      //     }
    }
    catch (e) {
      logException(e, false);
    };
    //  console.log("close xn-overlay, unloaded");
  }

  return pub;
}();
