// ==UserScript==
// @name        Image Reloader for Opera 9.1
// @version     1.12
// @date        2007-09-30
// @author      Mike Samokhvalov <mikivanch@gmail.com>
// @idea        Vlad Pudovkin.com, Kildor (background images reloading)
// @description Image Reloader loads regular and background images in two ways:
//              1) Ctrl+left click on the image
//              2) Hover the cursor on the image, press and hold (one second by default)
//              mouse left button.
//
// @download    http://www.puzzleclub.ru/files/image_reloader_for_opera_9.1.js
// @include     *
// ==/UserScript==

(function(){

  ///////////////////////////////////////////////////////////////////
  // BEGIN OF SETTINGS
  
  // Reload images by holding the mouse left button
  var reloadByHoldingDownMouseButton = true;
  // Reload images using ctrl+left click
  var reloadByCtrlClick = true;
  
  // Delay: the number of milliseconds to hold the mouse button
  var delay = 750;
  
  // END OF SETTINGS
  ///////////////////////////////////////////////////////////////////
  
  var timerId = 0;
  
  if(reloadByHoldingDownMouseButton)
  {
    opera.addEventListener('BeforeEvent.mousedown', function(e){
      if(e.event.button == 0)
      {
        timerId = setTimeout(function(){reload(e.event, 1);}, delay);
      }
    }, false);
  }

  document.addEventListener('mouseup', function(e) {    
    clearTimeout(timerId);
    if(reloadByCtrlClick && e.button == 0 && e.ctrlKey && !e.shiftKey)
    {
      reload(e, 0);
    }
  }, false);
  
  var reload = function(e, mode)
  {    
    var restoreImage = function(src)
    {      
      var attSrc = obj.getAttribute('src', false);       
      var imgs = document.selectNodes("//img[@src='" + attSrc + "']");
      for(var i = imgs.length - 1; i >= 0; i--)
      {
        if(imgs[i].currentStyle.display != 'none')
        {
          var display = imgs[i].currentStyle.display;
          imgs[i].style.display = 'none';
          imgs[i].style.display = display;
        }
      }
    };
    
    var reloadImage = function(src, bBgImage)
    {
      var img = new Image();
      img.src = src;
      if(img.complete)
        return false;

      var f = document.createElement('iframe');
      f.src = src;
      f.width = 0;
      f.height = 0;
      f.frameBorder = 'no';
      f.scrolling = 'no';
      f.onload = function(){
        this.parentNode.removeChild(this);
        if(!bBgImage)
        {
          restoreImage(src);
        }
      };
      document.documentElement.appendChild(f);
      return true;
    };
    
    var reloadBackgroundImage = function(obj, bgImgStyle)
    {
      var bgi = bgImgStyle.replace(/^url\(\x22?\x27?|\x22?\x27?\)$/gi, '');
      reloadImage(bgi, true);
    }
    
    var preventAnchorClick = function(anchor)
    {    
      var html = anchor.outerHTML;
      anchor.innerHTML = '';
      anchor.outerHTML = html;
    };
    
    var obj = e.srcElement;    
    if(obj.tagName == 'IMG')
    {
      var parent = obj.parentNode;
      if(parent.tagName == 'A')
      {          
        reloadImage(obj.src, false);         
        preventAnchorClick(parent);
      }
      else
      {
        reloadImage(obj.src, false);
      }
    }
    else if(obj.tagName == 'INPUT' && obj.type.toLowerCase() == 'image')
    {
      reloadImage(obj.src);
      obj.outerHTML = obj.outerHTML;
    }
    else
    {
      if(mode == 1)
      {
        if(document.getSelection())
          return;
      }
    
      var bgi = obj.currentStyle.backgroundImage;
      if((obj.tagName != 'BODY') && (obj.tagName != 'HTML') && (!bgi || bgi == 'none'))
      {
        // check parent elements
        var parent = obj.parentNode;
        while(parent)
        {
          if(parent.tagName == 'HTML')
            return;

          bgi = parent.currentStyle.backgroundImage;
          if(bgi && bgi != 'none')
          {            
            reloadBackgroundImage(parent, bgi);            
            break;
          }
          
          if(parent.tagName == 'BODY')
            return;
            
          parent = parent.parentNode;
        }        
      }
      else
      {
        if(obj.tagName == 'A')
        {
          reloadBackgroundImage(obj, bgi);
          preventAnchorClick(obj);
        }
        else
        {
          reloadBackgroundImage(obj, bgi);
        }
      }
    }      
  };
})();