Page Positioning Buttons

Add links to go to top, bottom or a user specified position of each page.

Tendrás que instalar una extensión para tu navegador como Tampermonkey, Greasemonkey o Violentmonkey si quieres utilizar este script.

You will need to install an extension such as Tampermonkey to install this script.

Necesitarás instalar una extensión como Tampermonkey o Violentmonkey para instalar este script.

Necesitarás instalar una extensión como Tampermonkey o Userscripts para instalar este script.

Necesitará instalar una extensión como Tampermonkey para instalar este script.

Necesitarás instalar una extensión para administrar scripts de usuario si quieres instalar este script.

(Ya tengo un administrador de scripts de usuario, déjame instalarlo)

Necesitará instalar una extensión como Stylus para instalar este estilo.

Necesitará instalar una extensión como Stylus para instalar este estilo.

Necesitará instalar una extensión como Stylus para instalar este estilo.

Necesitará instalar una extensión del gestor de estilos de usuario para instalar este estilo.

Necesitará instalar una extensión del gestor de estilos de usuario para instalar este estilo.

Necesitará instalar una extensión del gestor de estilos de usuario para instalar este estilo.

(Ya tengo un administrador de estilos de usuario, déjame instalarlo)

// ==UserScript==
// @name           Page Positioning Buttons
// @author         Ziyu
// @namespace      http://userscripts.org/users/ziyu
// @description    Add links to go to top, bottom or a user specified position of each page.
// @include        *
// @grant          none
// @version        End
// ==/UserScript==

// "Forked" from http://userscripts.org/scripts/show/105473

(function (document, window) {
  'use strict';

  // USER VARIABLES

  var numberOfPositions = 3,  // Sets the number of recording positions
      bottomEdge = '40%',     // Sets the bottom edge position in % of the page height
      color = '#a8a8a8';

  // Extend object a with object b's properties.
  var extend = function (a, b) {
    for (var key in b) {
      if (b.hasOwnProperty(key)) {
        a[key] = b[key];
      }
    }
    return a;
  };

  var cssPropsCommon = {
    cursor : 'pointer',
    zIndex : '1000'
  };

  var cssPropsContainer = extend({
    borderTop   : '2px solid' + color,
    borderBottom: '2px solid' + color,
    width       : '24px',
    position    : 'fixed',
    right       : '10px',
    bottom      : bottomEdge
  }, cssPropsCommon);

  var cssPropsTopButton = extend({
    width       : '0',
    height      : '0',
    borderBottom: '12px solid' + color,
    borderLeft  : '12px solid transparent',
    borderRight : '12px solid transparent'
  }, cssPropsCommon);

  var cssPropsBtmButton = extend({
    transform : 'rotate(180deg)',
    marginTop : '4px'
  }, cssPropsTopButton);

  var cssPropsRecButton = extend({
    width       : '12px',
    height      : '12px',
    borderRadius: '50%',
    background  : color,
    marginLeft  : '6px',
    marginTop : '4px'
  }, cssPropsCommon);

  var cssPropsRwdButton = extend({
    width       : '0',
    height      : '0',
    borderRight : '12px solid' + color,
    borderTop   : '6px solid transparent',
    borderBottom: '6px solid transparent',
    marginLeft  : '5px',
    marginTop   : '4px'
  }, cssPropsCommon);

  // HELPER FUNCTIONS

  // pfx is a function that takes a standard CSS property name as a parameter
  // and returns it's prefixed version valid for current browser it runs in.
  // The code is heavily inspired by Modernizr http://www.modernizr.com/
  var pfx = (function () {

    var style = document.createElement('dummy').style,
    prefixes = 'Webkit Moz O ms Khtml'.split(' '),
    memory = {};

    return function ( prop ) {
      if ( typeof memory[ prop ] === "undefined" ) {

        var ucProp = prop.charAt(0).toUpperCase() + prop.substr(1),
        props = (prop + ' ' + prefixes.join(ucProp + ' ') + ucProp).split(' ');

        memory[ prop ] = null;
        for ( var i in props ) {
          if ( style[ props[i] ] !== undefined ) {
            memory[ prop ] = props[i];
            break;
          }
        }

      }

      return memory[ prop ];
    };

  })();

  // css function applies the styles given in `props` object to the element
  // given as `el`. It runs all property names through `pfx` function to make
  // sure proper prefixed version of the property is used.
  // If rm is set to true, it removes the properties from the element.
  var css = function ( el, props, rm ) {
    var key, pkey;
    for ( key in props ) {
      if ( props.hasOwnProperty(key) ) {
        pkey = pfx(key);
        if ( pkey !== null ) {
          el.style[pkey] = rm ? null : props[key];
        }
      }
    }
    return el;
  };

  // PAGE POSITIONING BUTTONS API

  var createPositionButton = function () {
    var position = 0,
        isset = 0,
        button = document.createElement('div');

    var setPosition = function (yOffset) {
      position = yOffset;
      isset = 1;

      return position;
    };

    var getPosition = function () {
      return position;
    };

    var rewind = function () {
      if(isset) {
        window.scrollTo(0, position);
      }
    };

    var record = function () {
      setPosition(window.pageYOffset);

      css(button, cssPropsRecButton, true);
      css(button, cssPropsRwdButton);
      button.removeEventListener('click', record, false);
      button.addEventListener('click', rewind, false);
    };

    css(button, cssPropsRecButton);
    button.addEventListener('click', record, false);

    return {
      button      : button,
      isset       : isset,
      getPosition : getPosition
    };
  };

  var buttons = function () {

    var intervalHandle = null,
        container = document.createElement('div'),
        positionButtonContainer = document.createElement('div');

    var pageGoToTop = function () {
      window.scrollTo(0, 0);
    };

    var pageGoToBottom = function () {
      window.scrollTo(0, 999999);
    };

    var pageScrollUp = function () {
      if (intervalHandle === null) {
        intervalHandle = setInterval(function(){window.scrollBy(0,-3);}, 60);
      }
    };

    var pageScrollDown = function () {
      if (intervalHandle === null) {
        intervalHandle = setInterval(function(){window.scrollBy(0,3);}, 60);
      }
    };

    var stopScroll = function () {
      clearInterval(intervalHandle);
      intervalHandle = null;
    };

    var addPos = function () {

      while (numberOfPositions--) {
        positionButtonContainer.appendChild(createPositionButton().button);
      }
    };

    var init = function () {

      var topButton = document.createElement('div'),
      btmButton = document.createElement('div');

      css(container, cssPropsContainer);
      css(topButton, cssPropsTopButton);
      css(btmButton, cssPropsBtmButton);

      topButton.addEventListener('click', pageGoToTop, false);
      topButton.addEventListener('mouseover', pageScrollUp, false);
      topButton.addEventListener('mouseout', stopScroll, false);

      btmButton.addEventListener('click', pageGoToBottom, false);
      btmButton.addEventListener('mouseover', pageScrollDown, false);
      btmButton.addEventListener('mouseout', stopScroll, false);

      container.appendChild(topButton);
      container.appendChild(positionButtonContainer);
      container.appendChild(btmButton);
      document.body.appendChild(container);

      addPos();
    };

    return {
      container : container,
      init      : init
    };
  };

  // START PAGE POSITIONING BUTTONS

  if (window.top == window.self) { // if not iframe

    var de = document.documentElement;
    if(de.scrollHeight > de.clientHeight && document.body) {
      buttons().init();
    }
  }

})(document, window);