Greasy Fork

Greasy Fork is available in English.

Sanskrit Tools - Toolbar

Sanskrit Language Tools - Quick access to Sanskrit dictionary, thesarus, news and other tools, on Firefox and Chrome browsers.

当前为 2016-03-21 提交的版本,查看 最新版本

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴Greasemonkey 油猴子Violentmonkey 暴力猴,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴Violentmonkey 暴力猴,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴Userscripts ,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展后才能安装此脚本。

(我已经安装了用户脚本管理器,让我安装!)

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

(我已经安装了用户样式管理器,让我安装!)

// ==UserScript==
// @name           Sanskrit Tools - Toolbar
// @namespace      stgeorge
// @description    Sanskrit Language Tools - Quick access to Sanskrit dictionary, thesarus, news and other tools, on Firefox and Chrome browsers.
// @require        http://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js
// @grant          GM_setValue
// @grant          GM_getValue
// @grant          GM_getResourceText
// @version        2.5
// @resource       lookup http://sanskrit.inria.fr/DICO/grammar.fr.html
// ==/UserScript==

(function() {

  // ===============================================================
  // Grammar stuff.
  // ===============================================================

  var SANSKRIT_SITE = 'spokensanskrit.de';

  // Options.
  // Set to the level number. 0 -> no logging; higher numbers -> more
  // verbose.
  var OPTION_DEBUG_LEVEL = 0;

  // Set to true true to change word completion list
  // to show up below the input field instead of on the side.
  var OPTION_IN_PLACE_MATCH = true;

  // Set to true if we want to assume verbs with no family
  // number to be family 1.
  // NOTE: Use this with caution. Often results in errors.
  var OPTION_DEF_GANA_1 = false;

  // Set to true to enable Amarakosha lookup.
  var OPT_AMARAKOSHA = false;
  
  // Set to true if we want to use split panes.
  var OPT_SPLIT_PANE = false;

  var verbMatch = /(verb)\s*(.*)/;
  var verbRootMatch = /{\s*(.*)\s*}/;
  var verbClassMatch = /\s*([0-9]+)\s*/g;
  var nounMatch = /\b([fmn](?=\.))/g;
  var nounRootMatch = /^\s*(.*)\s*$/;
  var vurl = 'http://sanskrit.inria.fr/cgi-bin/SKT/sktconjug?lex=SH%V%&q=%Q%&t=KH&c=%C%&font=deva';
  var nurl = 'http://sanskrit.inria.fr/cgi-bin/SKT/sktdeclin?lex=SH%V%&q=%Q%&t=KH&g=%G%&font=deva';
  var surl = 'http://sanskrit.uohyd.ernet.in/cgi-bin/scl/SHMT/generate.cgi?dic=amara&word=%Q%';
  var genders = { f: 'Fem', n: 'Neu', m: 'Mas' };
  var gender_names = { f: 'feminine', n: 'neuter', m: 'masculine' };

  var initDone = false;
  var paneSplit = false;
  var paneHeight;

  function isGrammarSupported() {
    if (document.URL.indexOf(SANSKRIT_SITE) == -1)
      return false;
    if (!initDone) {
      doc = $(GM_getResourceText('lookup'));
      v = $(GM_getResourceText('lookup')).find('[name="v"]:first').val();
      if (v) {
        v = '&v='+v;
      } else {
        v = '';
      }
      vurl = vurl.replace('%V%', v);
      nurl = nurl.replace('%V%', v);
      _debug(1, 'grammar code=' + v);
      _debug(1, 'vurl=' + vurl);
      _debug(1, 'nurl=' + nurl);
      initDone = true;
    }
    return true;
  }

  function initGrammarData() {
  }

  function buildGrammarUI() {
    fixSuggestBox();
    splitPane();
    setHandlers();
  }

  function fixSuggestBox() {
    if (OPTION_IN_PLACE_MATCH) {
      var ans = $('#answer');
      ans.bind('DOMSubtreeModified', function() {
        ans.children().first().attr('align', 'center');
      });
      ans.appendTo($('#tinput').parent());
    }
  }

  function splitPane() {
    if (!OPT_SPLIT_PANE)
      return;
    if (paneSplit) return;
    var body = $('body');
    var t = body.children('table').first();
    paneHeight = t.outerHeight(true);
    var t = t.detach();
    $('<div id="lp"></div><div id="rp"></div>').prependTo(body);
    $('#lp,#rp').css({
      'float': 'left',
      overflow: 'auto',
      height: paneHeight + 'px',
    });
    $('#lp').css({
      width: '45%',
    });
    $('#rp').css({
      marginLeft: '10px',
      width: '54%',
    });
    t.appendTo($('#lp'));
    paneSplit = true;
  }

  function setHandlers() {
    $('tr.bgcol2,tr.bgcol7,tr.highlight').each(function() {
      var tr = $(this);
      var ltd = tr.children().first();
      // Each line is of the form:
      // sans_text translit_text grammar_info meaning
      var sans = ltd.next();
      var xlit = sans.next();
      var grmr = xlit.next();
      var links = [];
      // grammar, in turn, can be of the forms:
      // m./f./n./adj. etc (for nouns)
      // verb N (for verbs)
      var a = grmr.text().match(verbMatch);
      var prefix = sans.text() + ';' + xlit.text() + ';' + grmr.text() + ': ';
      if (a && a[1] == 'verb') {
        // For verbs, xlit is of the form xlit_word (xlit_root).
        // We want the root.
        var b = xlit.text().match(verbRootMatch);
        if (!b || !b[1]) return true;
        b[1] = b[1].trim();
        if (b[1].match(/[^A-Za-z]/))
          return true;
        var n;
        // For verbs, see if grammar_info has the gaNA info.
        if (a[2])
          n = a[2].trim().match(verbClassMatch);
        if (!(n && n[0])) {
          // Use a default gaNa if opted.
          if (OPTION_DEF_GANA_1)
            n = ['1'];
          else
            return true;
        }
        var s = sans.text().match(verbRootMatch);
        // At this point, b[1] is the transliterated verb root,
        // s[1] is the devangari verb root, and n the gaNa.
        _debug(2, prefix);
        _debug(2, 'verb');
        _debug(2, b[1]);
        _debug(2, n);
        for (var i = 0; i < n.length; ++i) {
          links.push({
            tooltip: 'Inflections for ' + a[1] + '(' + n[i] + ') ' + s[1],
            url: vurl.replace('%Q%', b[1]).replace('%C%', n[i].trim()),
            sym: '&rtrif;',
            target: 'l_grammar',
          });
        }
      } else {
        a = grmr.text().match(nounMatch);
        if (!(a && a[0]))
          return true;
        var b = xlit.text().match(nounRootMatch);
        if (!b || !b[1]) return true;
        b[1] = b[1].trim();
        if (b[1].match(/[^A-Za-z]/))
          return true;
        s = sans.text().match(nounRootMatch);
        // At this point, b[1] is the xlit noun, s[1] is the
        // devanagari noun, and a is one or more lingas.
        _debug(2, prefix);
        _debug(2, 'noun=');
        _debug(2, b[1]);
        _debug(2, a);
        if (a.length > 0) {
          if (OPT_AMARAKOSHA) {
            links.push({
              url: surl.replace('%Q%', sans.text()),
              tooltip: 'Synonyms for ' + b[1] + '. (The thesarus may not have synonyms for all words.)',
              sym: '&lowast;',
              target: 'l_thes',
            });
          }
          for (var i = 0; i < a.length; ++i) {
            links.push({
              url: nurl.replace('%Q%', b[1]).replace('%G%', genders[a[i]]),
              tooltip: 'Inflections for ' + ' noun ' + s[1],
              sym: '&rtrif;',
              target: 'l_grammar',
            });
          }
        }
      }
      var html;
      if (links[0]) {
        html = '';
        for (var i in links) {
          l = links[i];
          ltd.attr('valign','top');
          html +=
            '<a data-id="' +i+
              '" class="def stil4" style="#96290e;font-weight:bold;font-size:x-large;" href="' +
              l.url + '" title="' + l.tooltip + '">'+l.sym+'</a>';
        }
        ltd.html(html);
        ltd.attr('align', 'left');
        if (OPT_SPLIT_PANE) {
          ltd.children('a').each(function(k,v) {
            $(this).on('click', function(e) {
              e.preventDefault();
              var url = $(this).attr('href');
              $('#rp').html('<iframe width="100%" border="none" frameborder="0" height="'+paneHeight+'px" src="' + url + '"></iframe>');
            });
          });
        }
      }
      return true;
    });
  }

  // ===============================================================
  // Toolbar stuff.
  // ===============================================================

  var IGNORES = [
    'mail.yahoo.com',
    'groups.yahoo.com',
    'spokensanskrit.de',
  ];
  var ALLOW_ANCHORS = [
    'sanskrit.uohyd.ernet.in/cgi-bin/scl/SHMT/generate.cgi',
  ];
  var TOOLBAR_HTML = '\
    <div id="s_toolbar">\
      <div style="float:left; display:inline-block">\
        <ul style="list-style:none;margin:0;padding:0">\
          <li class="st_li">\
            <a title="Doordarshan Sanskrit News/Magazine" class="st_common st_link" href="http://www.youtube.com/user/sanskritanews/videos" target="l_news">\
              &#2357;&#2366;&#2352;&#2381;&#2340;&#2366;&#2307;</a>\
          </li>\
          <li class="st_li">\
            <a title="\'Sambhaashana Sandesha\' Magazine" class="st_common st_link" href="http://www.sambhashanasandesha.in/" target="l_mag1">&#2360;&#2350;&#2381;&#2349;&#2366;&#2359;&#2339; &#2360;&#2344;&#2381;&#2342;&#2375;&#2358;&#2307;</a>\
          </li>\
          <li class="st_li">\
            <a title="\'Vishva Vani\' Magazine" class="st_common st_link" href="http://www.speaksanskrit.org/vishvavani.shtml" target="l_mag2">&#2357;&#2367;&#2358;&#2381;&#2357;&#2357;&#2366;&#2339;&#2368;</a>\
          </li>\
          <li class="st_li">\
            <a title="Books" class="st_common st_link" href="http://www.sanskrit.nic.in/ebook.htm" target="l_books">&#2346;&#2369;&#2360;&#2381;&#2340;&#2325;&#2366;&#2344;&#2367;</a>\
          </li>\
          <li class="st_li">\
            <a title="Wikipedia" class="st_common st_link" href="http://sa.wikipedia.org" target="l_wiki">\
              &#2357;&#2367;&#2325;&#2367;&#2346;&#2368;&#2337;&#2367;&#2351;&#2366</a>\
          </li>\
          <li class="st_li">\
            <a id="l_word" title="Show a random verb" class="st_common st_link" target="l_word">\&#2351;&#2342;&#2371;&#2330;&#2381;&#2331;&#2367;&#2325;&#2346;&#2342;&#2350;&#2381;</a>\
          </li>\
          <li class="st_li st_space">\
          </li>\
          <li class="st_li">\
            <a title="Maheshwara Sutras" class="st_common st_link" href="http://en.wikipedia.org/wiki/Siva_Sutra#Text" target="l_msutra">\
              &#2350;&#2366;&#2361;&#2375;&#2358;&#2381;&#2357;&#2352;&#2360;&#2370;&#2340;&#2381;&#2352;&#2366;&#2339;&#2367;</a>\
          </li>\
          <li class="st_li">\
            <a title="Noun/Verb Expansion" class="st_common st_link" href="http://sanskrit.inria.fr/DICO/grammar.fr.html" target="l_inria">\
              &#2358;&#2349;&#2381;&#2342;, &#2343;&#2366;&#2340;&#2369;&#2352;&#2370;&#2346;&#2366;&#2357;&#2354;&#2368;</a>\
          </li>\
          <li class="st_li">\
            <a title="Sandhi splitter" class="st_common st_link" href="http://tdil-dc.in/san/sandhi_splitter/index_dit.html" target="l_sandhi">\
              &#2360;&#2344;&#2381;&#2343;&#2367;&#2307;</a>\
          </li>\
          <li class="st_li st_space">\
          </li>\
          <li class="st_li">\
            <div title="Double-clicking a word will automatically launch the dictionary" class="st_common st_option">\
              <input type="checkbox" id="o_auto" class="st_common st_checkbox" title="Double-clicking a word will automatically launch the dictionary"/>\
              <label for="o_auto" class="st_label">Auto-dictionary</label>\
            </div>\
          </li>\
          <li class="st_li st_space">\
          </li>\
        </ul>\
      </div>\
    </div>\
    <a id="a_dict" style="display:none" href="" target="l_dict"></a>\
  </div>';
  var ICON_HTML = '\
      <div id="icon" title="Click to show/hide Sanskrit Toolbar">\u0938\
      </div>';
  var VERBS = [
'accept','account','achieve','act','add','admit','affect','afford','agree','aim','allow','answer','appear','apply','argue','arrange','arrive','ask','attack','avoid','base','be','beat','become','begin','believe','belong','break','build','burn','buy','call','can','care','carry','catch','cause','change','charge','check','choose','claim','clean','clear','climb','close','collect','come','commit','compare','complain','complete','concern','confirm','connect','consider','consist','contact','contain','continue','contribute','control','cook','copy','correct','cost','count','cover','create','cross','cry','cut','damage','dance','deal','decide','deliver','demand','deny','depend','describe','design','destroy','develop','die','disappear','discover','discuss','divide','do','draw','dress','drink','drive','drop','eat','enable','encourage','end','enjoy','examine','exist','expect','experience','explain','express','extend','face','fail','fall','fasten','feed','feel','fight','fill','find','finish','fit','fly','fold','follow','force','forget','forgive','form','found','gain','get','give','go','grow','handle','happen','hate','have','head','hear','help','hide','hit','hold','hope','hurt','identify','imagine','improve','include','increase','indicate','influence','inform','intend','introduce','invite','involve','join','jump','keep','kick','kill','knock','know','last','laugh','lay','lead','learn','leave','lend','let','lie','like','limit','link','listen','live','look','lose','love','make','manage','mark','matter','mean','measure','meet','mention','mind','miss','move','need','notice','obtain','occur','offer','open','order','own','pass','pay','perform','pick','place','plan','play','point','prefer','prepare','present','press','prevent','produce','promise','protect','prove','provide','publish','pull','push','put','raise','reach','read','realize','receive','recognize','record','reduce','refer','reflect','refuse','regard','relate','release','remain','remember','remove','repeat','replace','reply','report','represent','require','rest','result','return','reveal','ring','rise','roll','run','save','say','see','seem','sell','send','separate','serve','set','settle','shake','share','shoot','shout','show','shut','sing','sit','sleep','smile','sort','sound','speak','stand','start','state','stay','stick','stop','study','succeed','suffer','suggest','suit','supply','support','suppose','survive','take','talk','teach','tell','tend','test','thank','think','throw','touch','train','travel','treat','try','turn','understand','use','visit','vote','wait','walk','want','warn','wash','watch','wear','win','wish','wonder','work','worry','write'
  ];

  var icon;
  var cbs = {
    l_word : function(id) {
      showDict(VERBS[Math.floor(Math.random() * VERBS.length)],
        '&direction=ES'
      );
    }
  };
  var visible = {};
  var numClicks = 0;
  var vdiv = null;
  var allowAnchor = false;
  var selectedText = null;

  function isToolbarSupported() {
    for (var i in IGNORES) {
      if (document.URL.indexOf(IGNORES[i]) != -1) {
        return false;
      }
    }
    return true;
  }

  function initToolbarData() {
    for (var i in ALLOW_ANCHORS) {
      if (document.URL.indexOf(ALLOW_ANCHORS[i]) != -1) {
        allowAnchor = true;
        break;
      }
    }
  }

  function buildToolbarUI() {
    place('s_toolbar', TOOLBAR_HTML, {
      position: 'fixed',
      'top': 0,
      margin: 0,
      // minHeight: '30px',
      width: '100%',
      zIndex: 2999999999,
      paddingTop: '3px',
      paddingBottom: '3px',
      backgroundColor: 'white',
      borderBottom: '1px solid orange',
      float: 'left',
      display:'none'
    });
    for (var i in cbs) {
      (function(p) {
        $('#'+p).on('click', function(e) {
          e.preventDefault();
          e.stopPropagation();
          var cb = cbs[p];
          cb($(this).attr('id'));
        });
      })(i);
    }
    $('.st_li').css({
      background: 'none',
      border: 0,
      display:'inline',
      padding: 0,
    });
    $('.st_space').css({
      marginLeft:'20px',
    });
    $('.st_common').css({
      float: 'left',
      border: 0,
      margin: 0,
      padding: 0,
      // height: '30px',
      fontSize: '15px',
      verticalAlign:'middle',
    });
    $('.st_link').css({
      textDecoration: 'none',
      fontWeight: 'bolder',
      marginLeft:'5px',
      padding:'5px',
      cursor: 'pointer',
      backgroundColor: '#eeeeee',
      color: 'black',
    });
    $('.st_label').css({
      marginLeft: '5px',
    });
    $('.st_option').css({
      display: 'inline-block',
      margin: '5px'
    });
    $('.st_link').hover(function() {
      $(this).css({color:'orange'});
    }, function() {
      $(this).css({color:'black'});
    });
    $('.st_checkbox').css({
      margin: '5px'
    });
    $('.st_menutrigger').css({
      position: 'relative'
    });
    $('.st_menu').css({
      backgroundColor:'#eee',
      display:'none',
      listStyle: 'none',
      position:'absolute',
      width:'120px',
      // left:'50px',
      'top': '50px',
      boxShadow: '5px 5px 5px #888888',
      zIndex:'999',
    });
    $('.st_menu li').css({
      width:'100px',
      listStyle: 'none inside',
    });
    place('icon', ICON_HTML, {
      cursor:'pointer',
      'float':'right',
      padding: '0px 15px 18px',
      fontWeight:'bold',
      backgroundColor: 'transparent',
      color:'red',
      position:'fixed',
      right:0,
      bottom: 0,
      height:'10px',
      width:'10px',
      zIndex:9999
    });
    icon = $('#icon').get(0);

    $('#icon').on('click', function(e) {
      var tb = $('#s_toolbar');
      var v = tb.css('display');
      if (v == 'none') {
        tb.css({
          'display':'block',
        });
        $('body').css('marginTop', '50px');
        GM_setValue('status', 1);
      } else {
        tb.css({
          'display':'none',
        });
        $('body').css('marginTop', 0);
        GM_setValue('status', 0);
      }
    });
    $('#o_auto').on('change', function(e) {
      GM_setValue('auto', $(this).prop('checked'));
    });
    $('.st_menutrigger').on('click', function(e) {
      e.preventDefault();
      e.stopPropagation();
      var trigger = $(this);
      var tgt = trigger.attr('data-menu');
      var v = visible[tgt];
      if (v)
        $(tgt).css('display', 'none');
      else
        $(tgt).css('display', 'block');
      visible[tgt] = !v;
    });
    $(document).on('click', function(e) {
      $('.st_menu').css('display', 'none');
      for (var i in visible) {
        visible[i] = false;
      }
    });
    document.addEventListener('mouseup', function(e) {
      var node = (e.target || e.srcElement);
      if (e.button != 0 || (node.nodeName == 'A' && !allowAnchor)
        || node.nodeName == 'INPUT') {
        return;
      }
      var n = node;
      while (n) {
        if (n == icon) {
          return;
        }
        if (n.getAttribute) {
          var ce = n.getAttribute('contenteditable');
          if (ce) {
            return;
          }
        }
        n = n.parentNode;
      }
      if (++numClicks == 1) {
        window.setTimeout(function() {
          selectedText = getSelectedText(true);
          if (selectedText != null && selectedText.length > 0) {
            if (selectedText.indexOf(' ') != -1) {
              selectedText = null;
              return;
            }
            if ($('#o_auto').prop('checked')) {
              showDict(selectedText);
            }
          } else {
            hideDict();
          }
          numClicks = 0;
        }, 300);
      }
    }, false);

    if (GM_getValue('status', 0))
      show();
  }

  function place(id, html, css) {
    $('body').prepend(html);
    $('#'+id).css(css);
  }

  function getSelectedText(trim) {
    var text =
      (window.getSelection) ? window.getSelection().toString() :
      (document.getSelection) ? document.getSelection().toString() :
      (document.selection) ? document.selection.createRange().text : null;
    if (trim && text != null)
      text = text.trim();
    return text;
  }

  function showDict(text) {
    hideDict();
    var a = $('#a_dict');
    a.on('click', function(e) {
      a.attr('href',
        'http://spokensanskrit.de/index.php?trans=Translate&tinput='+text);
    });
    a.get(0).click();
  }
  
  function hideDict() {
    if (vdiv) {
      vdiv.close();
      vdiv = null;
    }
  }

  // ===============================================================
  // General stuff.
  // ===============================================================

  function _debug(level, s) {
    if (level < OPTION_DEBUG_LEVEL)
      console.log(s);
  }

  function isMainWindow() {
    return (window.top == window.self);
  }

  // Main:
  if (!isMainWindow())
    return;
  if (isGrammarSupported()) {
    initGrammarData();
    buildGrammarUI();
  }
  if (isToolbarSupported()) {
    initToolbarData();
    buildToolbarUI();
  }
})();