aboutsummaryrefslogtreecommitdiffstats
path: root/nnp_cooperation.js
AgeCommit message (Collapse)Author
2008-10-21liberator -> liberator.modulesjanus_wel
- buffer - commandline - commands - hints - ..etc コマンド追加時に使う addUserCommand の第 3 引数に指定する関数の第 1 引数が String から Object に変更したのに対応 - ldrize_cooperation_fetch_flv.js - lookupDictionary.js - matanico.js - nicontroller.js - nnp_cooperation.js - reading.js - youtubeamp.js migemo_hint.js で一時的にグローバルオブジェクト plugins を定義 応急処置なのであとで削る必要あり git-svn-id: http://svn.coderepos.org/share/lang/javascript/vimperator-plugins/trunk@21797 d0d07461-0603-4401-acd4-de1884942a52
2008-10-14fix up thumbnail's URLjanus_wel
git-svn-id: http://svn.coderepos.org/share/lang/javascript/vimperator-plugins/trunk@21342 d0d07461-0603-4401-acd4-de1884942a52
2008-10-10fix up XML ( don't use   and image -> img )janus_wel
git-svn-id: http://svn.coderepos.org/share/lang/javascript/vimperator-plugins/trunk@21089 d0d07461-0603-4401-acd4-de1884942a52
2008-09-28bugfix: :nnpgetlist in ranking page.janus_wel
git-svn-id: http://svn.coderepos.org/share/lang/javascript/vimperator-plugins/trunk@20077 d0d07461-0603-4401-acd4-de1884942a52
2008-09-26 correspond mode toggling (fullscreen, random, loop).janus_wel
change caption: display now-playing title and mode's statuses. mode's statuses are displayed with the following word. R: random mode is on L: loop mode is on F: fullscreen mode is on git-svn-id: http://svn.coderepos.org/share/lang/javascript/vimperator-plugins/trunk@19949 d0d07461-0603-4401-acd4-de1884942a52
2008-09-26change XPath expression for NicoNicoPlaylist ver. 1.11janus_wel
git-svn-id: http://svn.coderepos.org/share/lang/javascript/vimperator-plugins/trunk@19945 d0d07461-0603-4401-acd4-de1884942a52
2008-09-23 * fixed regexes.drry
* et cetera. git-svn-id: http://svn.coderepos.org/share/lang/javascript/vimperator-plugins/trunk@19784 d0d07461-0603-4401-acd4-de1884942a52
2008-09-22import matanico.js, nicontroller.js, nnp_cooperation.jsjanus_wel
git-svn-id: http://svn.coderepos.org/share/lang/javascript/vimperator-plugins/trunk@19750 d0d07461-0603-4401-acd4-de1884942a52
ref='#n151'>151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189
// ==VimperatorPlugin==
// @name           Command-MainMenu
// @description-ja メインメニューとツールバーをコマンドで実行できる
// @license        Creative Commons 2.1 (Attribution + Share Alike)
// @version        1.3
// ==/VimperatorPlugin==
//
// Usage:
//    :menu ツール-アドオン
//    :toolbar 戻る
//    のようにメニュー/ツールバーの"-"区切りのパスを渡すことで、メニュー/ツールバーをクリックします。
//    Migemo必須。
//
// TODO:
//    ・一度開かないと生成されないようなメニュー(ラベル)に対処できる魔法があったらいいな!
//     (ScrapBook / ブックマークメニュー)
//    ・コンテクストメニューがうまくいかない。
//
// License:
//    http://creativecommons.org/licenses/by-sa/2.1/jp/
//    http://creativecommons.org/licenses/by-sa/2.1/jp/deed.en_CA

(function(){ try{

  const migemo = Components
                  .classes['@piro.sakura.ne.jp/xmigemo/factory;1']
                  .getService(Components.interfaces.pIXMigemoFactory)
                  .getService("ja");

  function id (v) v;

  function equal (x) function (y) x == y;

  function cloneArray (src) src.map(id);

  function matchPath (elem, path, getName) {
    for (var i = 0; i < path.length; i++) {
      if (!path[i](getName(elem)))
        break;
    }
    if (i) {
      var res = [];
      for (var j = i; j < path.length; j++)
        res.push(path[j]);
      return res;
    }
  }

  function getElementsByPath (elem, path, getName, isTarget, isEnabled) {
    try{
      function get (point, elem, path) {
        if (isTarget(elem)) {
          if (!isEnabled(elem))
            return [];
          var m = path[0](getName(elem, true));
          if (m) {
            if (path.length == 1)
              return [[point + m, elem]];
            (path = cloneArray(path)).shift();
          } else {
            return [];
          }
        }

        //elem.containerOpen = true;
        var res, cs = elem.childNodes, result = [];
        if (cs && cs.length) {
          for (var i = 0; i < cs.length; i++) {
            if (res = get(m + point, cs[i], path))
              res.map(function(it) it && result.push(it));
          }
        }
        //elem.containerOpen = false;

        return result;
      }

      return get(0, elem, path).sort().map(function (it) it[1]);
    }catch(e){ liberator.log(e); }
  }

  function getPathMatchers (args) {
    return args.split('-').map(function(it){
      let n = it.toLowerCase();
      let s = migemo.getRegExp(it.replace(/^\s+|\s+$/, ''));
      let re = new RegExp(s, 'i');
      return function (l) {
        if (!l)                               return 0;
        if (l == it)                          return 1;
        if (l.toLowerCase().indexOf(n) >= 0)  return 2;
        if (re.test(l))                       return 3;
        return 0; 
      }
    });
  }

  function getPathString (elem, isRoot, getName, isTarget) {
    var res = [];
    while (!isRoot(elem)) {
      isTarget(elem) && res.unshift(getName(elem));
      elem = elem.parentNode;
    }
    return res.join('-');

  }



  /*********************************************************************************
   * メインメニュー
   *********************************************************************************/

  const mainMenubar = document.getElementById('main-menubar');
  const toolbox = document.getElementById('navigator-toolbox');
  const contextmenu = document.getElementById('contentAreaContextMenu');

  function fixName (name) {
    return name ? name.replace(/^\s+|\s+$/, '').replace(/[\-\s]+/g, '_') : '';
  }

  function getElementName (elem, multi) {
    const f = function (it) { return fixName(it) || ''; }
    return multi ? [elem.label, elem.tooltipText].map(f).join('-') 
                 : fixName(elem.label || elem.tooltipText || '') ;
  }

  function isNotHidden (elem) {
    return !elem.hidden;
  }

  function isClickable (elem) {
    const re = /^(menu(item)?|toolbarbutton)$/i;
    return elem.nodeName.match(re);
  }

  function addCommand(cmds, name, root, action) {
    function _find (args, single) {
      var result =  getElementsByPath(root, 
                                      getPathMatchers(args), 
                                      getElementName, 
                                      isClickable,
                                      isNotHidden);
      return single ? result[0] : result;
    }

    if (!action) {
      action = function (elem) {
        if (!elem.click)
          return;
        elem.click();
        return true;
      };
    }

    liberator.commands.addUserCommand(
      cmds,
      name,
      function (args, _, num, extra) {
        var res = _find(args.replace(/-\s*$/,''), true);
        if (!(res && action(res)))
          liberator.echoerr('menu not found');
      },
      {
        completer: function (args) {
          const gps = function (it) getPathString(it, equal(root), getElementName, isClickable);
          const fp = function (it) [gps(it), it.tooltipText || ''];
          return [0, _find(args).map(fp)];
        }
      }
    );
  }

  addCommand(['me[nu]'], 'Command MainMenu', mainMenubar);
  addCommand(['toolbar', 'tb'], 'Command Toolbar', toolbox);
  addCommand(['conme', 'contextmenu'],
             'Context Menu', 
             contextmenu, 
             function (elem) {
               //contextmenu.openPopup(null, null, 0, 0, true);
               //contextmenu.hidePopup();
               elem.click();
               //elem.doCommand();
               return true;
             }
  );

}catch(e){ liberator.log(e);}
})();