Text To link

把文字链接转换为可点击链接

目前为 2014-04-07 提交的版本。查看 最新版本

// ==UserScript==
// @name			Text To link
// @description		把文字链接转换为可点击链接
// @namespace		Lkytal
// @include			*
// @exclude			*pan.baidu.com/*
// @exclude			*.renren.com/*
// @exclude			*userscripts.org/scripts/review/*
// @version			2.3.5
// @icon			http://lkytal.qiniudn.com/ic.ico
// @grant			unsafeWindow
// ==/UserScript==// Generated by CoffeeScript 1.7.1


if (window != window.top || window.document.title == "")
	return;
var LinkPage, excludedTags, filter, linkify, observer, setLink, url_regexp, xpath;

url_regexp = new RegExp("((https?://|www\\.|magnet\\:\\?)[\x21-\x7e]+|([\x21-\x2e\x30-\x7e]+\\.(com|cn|org|net|info|tv)))(/[\x21-\x7e]*)?", "gi");

setLink = function(candidate) {
  var a, lastLastIndex, match, span, text, url;
  if ((candidate == null) || candidate.nodeName === "#cdata-section") {
    return;
  }
  text = candidate.textContent;
  lastLastIndex = 0;
  match = url_regexp.exec(text);
  if (match) {
    span = document.createElement("span");
    while (match) {
      span.appendChild(document.createTextNode(text.substring(lastLastIndex, match.index)));
      url = match[0];
      if (url.indexOf("http") !== 0 && url.indexOf("magnet") !== 0) {
        url = "http://" + url;
      }
      a = document.createElement("a");
      a.setAttribute("href", url);
      a.setAttribute("target", "_blank");
      a.appendChild(document.createTextNode(match[0]));
      span.appendChild(a);
      lastLastIndex = url_regexp.lastIndex;
      match = url_regexp.exec(text);
    }
    span.appendChild(document.createTextNode(text.substring(lastLastIndex)));
    return candidate.parentNode.replaceChild(span, candidate);
  }
};

excludedTags = "a,applet,input,button,area,embed,frame,frameset,head,iframe,img,map,meta,noscript,object,option,param,script,select,style,textarea,code".split(",");

xpath = "//text()[not(ancestor::" + excludedTags.join(') and not(ancestor::') + ")]";

filter = new RegExp("^(textarea|input|button|select|option|meta|link|noscript|a|html|head|object|embed|script|style|frameset|frame|iframe|img|code)$", "i");

linkify = function(doc) {
  var i, result, _i, _ref;
  result = document.evaluate(xpath, doc, null, XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE, null);
  for (i = _i = 0, _ref = result.snapshotLength; 0 <= _ref ? _i <= _ref : _i >= _ref; i = 0 <= _ref ? ++_i : --_i) {
    setLink(result.snapshotItem(i));
  }
};

LinkPage = function(root) {
  var tW;
  tW = document.createTreeWalker(root, NodeFilter.SHOW_TEXT, {
    acceptNode: function(a) {
      if (!filter.test(a.parentNode.localName)) {
        return NodeFilter.FILTER_ACCEPT;
      }
    }
  }, false);
  while (tW.nextNode()) {
    setLink(tW.currentNode);
  }
};

window._bodyHeight = document.body.clientHeight;

observer = new window.MutationObserver(function(mutations) {
  if (document.body.clientHeight < window._bodyHeight) {
    return;
  }
  window._bodyHeight = document.body.clientHeight;
  return mutations.forEach(function(mutation) {
    var Node, _i, _len, _ref;
    _ref = mutation.addedNodes;
    for (_i = 0, _len = _ref.length; _i < _len; _i++) {
      Node = _ref[_i];
      LinkPage(Node);
    }
  });
});

observer.observe(document.body, {
  childList: true,
  subtree: true
});

setTimeout((function() {
  return linkify(document.body);
}), 200);