// Keep everything in anonymous function, called on window load.
if(window.addEventListener) {
window.addEventListener('load', function () {
  var canvas, context, canvaso, contexto;

  // Variables de herramientas.
  var tool;
  var flagRejilla = true;
  var undoHistory = new Array();//Matriz que guarda imagenes para el deshacer
  var redoHistory = new Array();//Matriz que guarda imagenes para el rehacer
  var tool_default = 'pencil';
  var imagenEncima = "imagenes/simetria/rejilla20px.png";
  var imagenFondo = "data:image/png;base64,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";
  rellenoR = 244;
  rellenoG = 237;
  rellenoB = 200;
  var fin = 'round';
  var grid = 20;//Tamaño de rejilla
  var colorFondo = '#f3f0e7';//color de fondo y del borrador
  var radioPuntos = 1.5;//radio de círculos en punteado
  var densidad = 5;//factor que marca la distancia entre puntos respecto al grosor del punto en punteado2 y pincelPluma
  var espaciado = densidad * 5;//separación entre pinceladas en pincel compuesto
  var pincel = 10;//radio del area donde se dibujan los puntos en pincel aleatorio y del borrador
  var anchopluma = 2;//en pincel pluma el ancho en el que hay trazos
  var grosorpluma = 1;//Grosor de los trazos en pincel pluma
  var canvasWidth;
  var canvasHeight;
 var cir_3px_sin = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABHNCSVQICAgIfAhkiAAAAFZJREFU GJWNkFEKwDAIQ1/KTtfcd9dzH7XQDTsa8EMM8SkRwSzAQGR5nSkNAEgS0LO9Yxm+jH9qkpxJpTRk Kp6Kux3tTXmybhIF+PiY6wvO5j0leHXgA0MzY7PnNfzfAAAAAElFTkSuQmCC "
 var cir_4px_sin = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABHNCSVQICAgIfAhkiAAAAE5JREFU GJWNkEsKwFAIA2feubw/eCq7sdCPpS+QVQZMpKo4DSRQ7bxlDzAaTiCumQ38aqmpxheghppMfabe a+tu61V8Grg/Zio+Dtx9+AG9HXKZXgI35AAAAABJRU5ErkJggg== "
 var cir_5px_sin = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABHNCSVQICAgIfAhkiAAAAEdJREFU GJWVkFEKACAIQx+ez+t7nvVTIVlggj/bZHNIQhKAAzrWN5+EBkQSBWCJxxcwxf7A6vXDpea55TY+ pm3de6ZdT7fwAabkfn9iz+3mAAAAAElFTkSuQmCC "
 var cir_6px_sin = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABHNCSVQICAgIfAhkiAAAAEZJREFU GJWVkFEKACAIQx99dsvO66HWj0SkggkiuMnmkIQkAAP0tB38Iq6EuC4cc9L0acUuXhcq0U/me/BR beneM+14uoFvi4aA5WGdJEwAAAAASUVORK5CYII= "
 var cir_7px_sin = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABHNCSVQICAgIfAhkiAAAAGlJREFU GJWN0NsJwzAMheHPoQ/dpKN0Eg/VUTqKJ2neTl9sSLADEQghoct/JAlU5MJrElsppaJhN9uO1nsE P3x6zKpWenFMv/HqecMXz7F+4llxbwuupT2uwA8CT6dviRnvOYFPAu8+/A9LH0hBQWduCgAAAABJ RU5ErkJggg== "
  var triangulo = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAQCAYAAAAvf+5AAAAABHNCSVQICAgIfAhkiAAAAKNJREFU KJGN0LENg0AQRNG/IHICeiCjBqeuhJhGiOmCDNfhzD04wLGFNE4OtAeH7ZVGOt28aEwS/szsCiDp FhWStgAF8Agpom4HO0AhXRICFTA7OANVCg4OrRkiCDTAkoAL0Hg4Aq+TjJKw/Txnl/2lgMzMLr/Q au5A7jfbbZsHg4D2C2yDQcATKBOoDN0GBfQJ2Lt+e7yB2qE6/B2ggMnByXcf2QLQMzDzTScAAAAA SUVORK5CYII= "
  var triangulo_20 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAmCAYAAADEO7urAAAABHNCSVQICAgIfAhkiAAAAVBJREFU SInt1K1uAkEUhuH3kDQhGBRuEySqCaI1CHwvAENSi8dhuAU8usFwAVQjUBUVvQGSuioMadKGnIrO NLQM87drmnaST+zMOU8muzsjqkpoiMgNgKreB2tDoIhcAE/m8VJV370NquoNMAbUZBysD2AtYHcE 7oBWGXB+hNnMs0CgCxwc4AHo5oBrB2azTgKBgQezGUSBQB3YRoBboB4DTiMwm6kXBApgnwDugcIH LhIwm4UTBHoZmE3POl9nWUTugGvyxoOq3kLE5ZA6apVqvwMUkauqMGttQpdmbIANfP5HwwqwobFQ 4BlolMAaxlD7UQpgUuL1TYyB3aECr0A7Y3dt02udb2dymQEufxgnB72fgPUd/ScTj0AtAquZ2iCo wCgCHJ3pdU6+AE0P1jQ10aACMw848/SdXXgDOg6sY9aSQQVWDnDl6/m/sf8C+AGAi5AGoUzTuwAA AABJRU5ErkJggg== "
  var triangulo_40 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACgAAABACAYAAABoWTVaAAAABHNCSVQICAgIfAhkiAAAAxJJREFU aIHtmr9PFEEUxz/vwGgCCVdoQWi4QsgVQkfoCA3E0BFKQksIVFBhCQ3VBf8OQiliQ2voRAuiFloo JmKhiUaUH89iZ+Oxd8fOzszuNnyTl9ztvXnvk7c7uzNvT1SVUBKRxwCq+jxYzFCAInIHeGO+PlLV 8xBxKyGCGK0Aw8ZWQgUNUkEReQC8B/rMoR/AQ1U99Y0dqoKb/IfDfN4MEllVvQwYBS4BTdglMOob P0QFn9L+TFTMb37yrN4crZVL2pxPDudJIiL3gGNgMMX1I1BX1TOXPD6neI10OIzPmmsSpwqKyADw FuixHPILGFbVz1lzuVZwC3s4jO+WUyaHiTEOXJE+OZJ2BYxnzpcRToBDB7jYDjGXVV6ACx5wsS3k Agj0AicBAE+A3jyeJE+A/gz+ndRvYtnJsno14Az/6sV2BtSCnWJgNyBcbLtBAIHJHOBim/QCBLqA oxwBj4AuH8ClHOFiW3ICBKrAaQGAp0DVBXC7ALjYtjMBAnXgvEDAc6I1ozXgfoFwse1bAQIzJcDF NpPk6aZVU8CLNseL0BTwrPlAsNZHXgrZ+shFt4C+ugX01S2gryoiMlQ2RCeJyFAFaJQNcoMaED0D p232B0UaMA2oGMBjYERVL0qrVZNEpBt4DdTjSVIHlstDatEyERNxBQG+E3Xmv5VFBSAi94neGFTh +m2mCmyUAZXQBgYuVvOC8YLoWixrYowYhmamllXtQYmAB2142i69Z0uAm23H0jxJmvWBaJf1x/eC spGI3CW61dWSv3V6FteA1TyhElqlDRxcv80k9RMYUtUveVEBiEg/8I6oQdqim1Yzvbh25rNpiw5w sW7ap14BYzlOjDHS3xikbqZfkrEzbwknJnZafqsd/3wOgPOWua2cPgE9AeF6TMzU3LZL/gFg3dLX RusmppVsGzu/gcEA1Rs0sWzzZuo+7QQA3MmYM5OzAhMecBMO+TIPeAVUHOAqZmzugAosOgAuOuZy GvQV6MsA12fGFAaoQCMDYMMjj/PAv0T/Q0iDGza+hQMqsGcBuOeT4x9j5Oaai6NJLgAAAABJRU5E rkJggg== "
  var elipse = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAUCAYAAACNiR0NAAAABHNCSVQICAgIfAhkiAAAAJZJREFU OI3NlcENgDAIRR/GPdzABdyhIziPi7mAid4dxOClB6O1Um0TSbiU8BLgQ1FVjg7MgBp9vuQHgD2w GWAb0D8CPdQBSwS2AC6UKx4QNBHpgBZo/NMKTKo63ubEgG+sykoDBBgwlBKFnFpjanbC8GxySJCX TbDWBcg+lOIlfx5Kdtn8f1PqWPDNcch+vsofWD5+ATuG8a+mdnoINAAAAABJRU5ErkJggg== "
  var estrella = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABHNCSVQICAgIfAhkiAAAAIFJREFU GJWNzzEKAlEMhOHvWVsJa2PjFay0EG/jIb2EYCHeQgRRUFjHZlfwsYKBQJgM+TMliX9qVAullNWg M8lX44Smm8eYJlFqdCnlggPOmGOd5NZfabDFDi8EDyx6Uv9j0HbLHtHi+SH9QO9xxQybJPehMEdM 6jBDxmWtDab+VW/DC26DHJtNZgAAAABJRU5ErkJggg== "
  var estrella_20 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAUCAYAAACNiR0NAAAABHNCSVQICAgIfAhkiAAAAPdJREFU OI2t1LtKBDEUANCTRRRLKxu11wULKys7QbC00dbK37AXtBUEK0t/wC9REEWw2EYr38jGwlkcx8k8 1rlwISQ3h1wSEmKMuoxep1oTMIQw3ymIkxDCdJfgIg6bgmKMlYlbRGyVrC1j+9dcA/A6Ax+xgD72 cYkX9NuCVxkY8ZQbR+z9qU8gE1jHMV4LyCjPS/fmkEls4hQPCWSUd5gpA4u3PMRnllXxkaxJtNzD mu/n8p445VllyxWXMsghbwV09z/gALNYxQFu8IylccAhNkrWVrAzDnhUV9cGvMBUUzBkm5IRQpiL Md7XPKOf+jqwbXT+Y38BH8Ds21K6c7YAAAAASUVORK5CYII= "
  var estrella_40 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACgAAAAoCAYAAACM/rhtAAAABHNCSVQICAgIfAhkiAAAAiZJREFU WIXtmDtoFFEUhr9/heAjSBpjYa8WIj5IJQk2xsZWBAMWghaSJoWFpSAmlYhWFimSRpNUVgqCCjY+ +6DGRxECCjZBxLjmWLiBmc3cnZ2555Ig/nCauef+++15wDAyMzazGhsNUKb/gLGKBpSU9E96mF92 8AjKA/C0pPMOPoXyAFwFbkna6+C1Tl6AO4B7knoc/HLyAgQ4DIw7+OXkCQgwJulkVQNJ+0Jn3oAC piT1dwF1RNKEpA/AQDDRzKICeApYWzwAVJB7CLgOvM/kTnf0dwB8XABowFjr/CBwDXhbkPMO6E0N +CgA+BOYD5ytnR8t8/eewax6gODwA1fM7E2pe0TleoEzwEfCVQpF4YxGtxjoA84B94EfNcAMWAL6 u/7NLqB2AReAh8BKTai1WAVOVCpKAGoPMAo8AZqRUNmYqDpKoSUx4Dfwi/AS1NHXyje6nLsRYA5Y Jq6CK8BAdIs7wG4FTgGTwJeakAvAziSAbbANYAj4VANyJjlgBvR5zUpejFmSKlLg+XfgW4d7NyUd KDNPCXgJ2A0MA3f4O7NZbQNmJW3v6O7Q4pesb9/dgrwtwHHgNrCYyZ1MPYOv2uA+A30ldwQcA260 8s+mBHydgWsCgzU89qdckqzGzexZ1UtmNh8681ySF8BVB7+cvACXgREzazr45eTV4lEzW3DyyskD cMbMph18CqXWFtU3kBpm5vlKlvePBUytf/8La2ptesA/dTPi5y51kRgAAAAASUVORK5CYII= "
  var cua_4_6 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABHNCSVQICAgIfAhkiAAAAD1JREFU GJWtkDEOACAIA6/G/3+5LhLFwTDQCZKDFmSbkKTTALYV9aAo3Ru/IODXJgE7Ttm6HywfM9NUxx8X O5oWCc0mDvgAAAAASUVORK5CYII= "
  var ajedrez_10_10 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAUCAYAAACNiR0NAAAABHNCSVQICAgIfAhkiAAAASVJREFU OI3lVDFyxCAMBIFlGuae4B9cyU/ySr+ElP6Bn5ChwAELpQkZn61Ul+JmohkVq5EWgVYopRSfHQDI OZc7DiHEGGNgZsXMKufsiAg6PjqoP7Z/SGgBoF1OAWjHuNaamVl33FqD1prYjEXEIhEOw1A7NsYQ EZmOa61Dz7sQbtvmJMJjB/u+W2vt3vE4jp+IWMTbSW0/YzaE8H4Oaq3ZGEMpJV9KwWma1nVdp9vt 9lFKwZSSN8aQ1povtTHGcA4ysyYi471PiFiWZbnP8/y2LMsdEYv3PhGROQ7qWHxxIoKcs+s4xhhC CFF9r6JzLgMAKWltn3+1RxOn3FqDWuvgnNuUkqd8VsIPoaTDc6Kkw1IKioSSlpR6FO1vmyIRvv7n 8PqEXzA22aszfDLnAAAAAElFTkSuQmCC "
  var ajedrez_20_20 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACgAAAAoCAYAAACM/rhtAAAABHNCSVQICAgIfAhkiAAAAFdJREFU WIXt18ENwAAMwkDo/jvTIZxKffgGQFZ+aZLl0LZe7j2XY18wkDKQMpAykDKQMpAykDKQMpDqdvqS pO3p4O8vaCBlIGUgZSBlIGUgZSBlIGUg9QJHyQhLIyBatgAAAABJRU5ErkJggg== "
  var ver_1_3 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAQAAAAKCAYAAACT+/8OAAAABHNCSVQICAgIfAhkiAAAABpJREFU CJljZGBg+P///39GBihgYkADg0UAAJd8BBHF/SdNAAAAAElFTkSuQmCC "
  var ver_2_2 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAgAAAAKCAYAAACJxx+AAAAABHNCSVQICAgIfAhkiAAAACVJREFU GJVjZGBg+M/AwMDw//9/RgYGBgZGRkYUPhMDATCqAAIA1v0IEbe0EMsAAAAASUVORK5CYII= "
  var ver_3_1 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAQAAAAKCAYAAACT+/8OAAAABHNCSVQICAgIfAhkiAAAABpJREFU CJljZGBg+M8ABf///2dkYkADg0UAAH+MBBHdQgvAAAAAAElFTkSuQmCC "
  var ver_4_4 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAgAAAAKCAYAAACJxx+AAAAABHNCSVQICAgIfAhkiAAAAB1JREFU GJVjZGBg+M+ABP7//8+IzGdiIABGFUAAAPiyBBG50ohbAAAAAElFTkSuQmCC "

  function init () {
    // Localiza el elemento canvas.
    canvaso = document.getElementById('imageView');
    if (!canvaso) {
      alert('Error: ¡No puedo encontrar el elemento canvas!');
      return;
    }
   altoNuevo = canvaso.height;
   anchoNuevo = canvaso.width;
    if (!canvaso.getContext) {
      alert('Error: no canvas.getContext!');
      return;
    }

    // Toma el 2D canvas context.
    contexto = canvaso.getContext('2d');
    if (!contexto) {
      alert('Error: failed to getContext!');
      return;
    }
	
    // Crea contexto para canvas que está encima de todo
	
    canvasTop = document.getElementById('imageTop');	
    contextTop = canvasTop.getContext('2d');
    if (!contextTop) {
      alert('Error: failed to getContext!');
      return;
    }	
	
	canvasWidth = canvaso.width;
	canvasHeight = canvaso.height;
	
	//Ponemos fondo color
	fondoColor();
	

    // Añade un canvas temporal.
    //var container = canvaso.parentNode;
    canvas = document.createElement('canvas');
    if (!canvas) {
    alert('¡Error: No puedo crar un nuevo lienzo!');
    return;
    }
    canvas.id     = 'imageTemp';
    canvas.width  = canvaso.width;
    canvas.height = canvasHeight - 22;
	contTemp = document.getElementById('contenedor1');
    contTemp.appendChild(canvas);
    context = canvas.getContext('2d');



    // Activa la herramienta por defecto.
    if (tools[tool_default]) {
      tool = new tools[tool_default]();
    }
	//Pone por defecto el cursor lápiz
	$('canvas').css("cursor","url(imagenes/cursores/cursor_lapiz.png),auto");
	

    // Coloca mousedown, mousemove and mouseup event listeners.
    canvas.addEventListener('mousedown', ev_canvas, false);
    canvas.addEventListener('mousemove', ev_canvas, false);
    canvas.addEventListener('mouseup',  ev_canvas, false);
	canvas.addEventListener('dblclick',  ev_canvas, false);
	canvas.addEventListener('mouseout',  ev_canvas, false);
	canvaso.addEventListener('mouseup',  ev_canvas, false);
	
	//Eventos cuando se presiona una tecla
	window.onkeydown = function(evt) {
	evt = evt || window.event;
	if (evt.keyCode === 17) {
		keyControl = true;
		}
	}
	window.onkeyup = function(evt) {
	evt = evt || window.event;
		if (evt.keyCode === 17) {
			keyControl = false;
		}else if(evt.keyCode === 90 &&(keyControl)){//Deshace al presionar Ctrl + z
		undoDraw();
		}
	}
	//Evita seleccion azul
	document.onselectstart = function() {
	return false;
	}
	
	//Aquí ponemos una imagen de fondo si queremos
	ponerFondo(imagenFondo);
	//Pone imagen por encima
	ponerRejilla();

}
	
	//Carga imagen para patrón y lo crea.
	$('.textura').click(function (){
	
		 var img = new Image();
			var direccion = $(this).css('backgroundImage');
		 	direccion = direccion.split("/");
			direccion = direccion[6].split(".");
			direccion = direccion[0];
			img.src =  eval(direccion);
			img.onload = function(){
			var ptrn = context.createPattern(img,'repeat');
			relleno = ptrn;
		}
	})
	
	
	//Abre ventana para escribir texto en canvas
	$('#texto').click( function() {
		document.getElementById('text-controls').style.display = 'block';
		var textE1 = document.getElementById('text');
		//textE1.focus();
	})
	//Coloca texto al aceptar
	$('#botonTexto').click(function (){
		saveActions();
		contexto.save();
		contexto.fillStyle = colorFondo;
		contexto.fillRect(0,523, canvaso.width, 22);//rellena con color de fondo Si fuera una imagen habría que recargarla
		contexto.restore();
		titulo = document.getElementById('text').value;
		contexto.font = "12pt Verdana";
		contexto.fillStyle = "black";
		contexto.fillText(titulo, 20, 540);
		saveLocalStorage();
		document.getElementById('text-controls').style.display = 'none';
	})
	//Cierra ventana de colocar texto
	$('#botonTexCan').click(function (){document.getElementById('text-controls').style.display = 'none'});
	
	// Controlador de evento general. Esta función determina la
	// posicion relativa del ratón respecto al elemento canvas.Da las coordenadas del raton dentro del canvas
	function ev_canvas (ev) {
		if (ev.layerX || ev.layerX == 0) { // Firefox
		  ev._x = Math.round(ev.layerX / canvasScale);//multiplicamos por canvasScale para conpensar zoom
		  ev._y = Math.round(ev.layerY / canvasScale);
		} else if (ev.offsetX || ev.offsetX == 0) { // Opera
		  ev._x = Math.round(ev.offsetX / canvasScale);
		  ev._y = Math.round(ev.offsetY / canvasScale);
		}

		// Llama al manejador del evento de la herramienta
		var func = tool[ev.type];
		if (func) {
		  func(ev);
		}
	}

	// Esta función dibuja #imageTemp canvas encima de #imageView, después
	// #imageTemp se limpia. Esto se realiza cada vez que el usuario
	// completa unaa operación de dibujo.
	function img_update () {
  		saveActions();//Guarda copia de la imagen
		contexto.drawImage(canvas, 0, 0);//copia imagen temporal en definitiva
		context.clearRect(0, 0, canvas.width, canvas.height);//Limpia la imagen temporal
		redoHistory = [];
		saveLocalStorage();

	}
	//Function guarda imagen en array para poder deshacer
	function saveActions() {
		var imgData = document.getElementById("imageView").toDataURL("image/png");
		undoHistory.push(imgData);//guarda imagen en matriz deshacer
	}
	//Guarda imagen en el cache del navegador
	function saveLocalStorage(){
		var imgData = document.getElementById("imageView").toDataURL("image/png");
		localStorage.dibujo_00 = imgData;//guarda imagen en el cache del navegador
	}
	
	//Función pone fondo de color
	function fondoColor(){
	contexto.save();
	contexto.fillStyle = colorFondo;
	contexto.fillRect(0,0, canvaso.width, canvaso.height);
	contexto.restore();
	}
	
	//Funcion deshacer
	function undoDraw(){
		if(undoHistory.length > 0){
		var imgData = document.getElementById("imageView").toDataURL("image/png");
		redoHistory.push(imgData);//Guarda la imagen actual en array rehacer
        var undoImg = new Image();
			undoImg.onload = function(){//funcion para que le de tiempo a cargar la imagen
			contexto.drawImage(undoImg, 0,0);//copia imagen rescatada en canvas
			var imgData = document.getElementById("imageView").toDataURL("image/png");
			localStorage.dibujo_00 = imgData;//guarda imagen en el cache del navegador
			};
			undoImg.src = undoHistory.pop();//saca ultima imagen guardada en el array y la guarda en undoImg
        } else if(undoHistory.length == 0){
		return
		}		
	}
	
	function redoDraw(){
		if(redoHistory.length > 0){
		saveActions();
        var redoImg = new Image();
			redoImg.onload = function(){//funcion para que le de tiempo a cargar la imagen
			contexto.drawImage(redoImg, 0,0);//copia imagen rescatada en canvas
			var imgData = document.getElementById("imageView").toDataURL("image/png");
			localStorage.dibujo_00 = imgData;//guarda imagen en el cache del navegador
			};
			redoImg.src = redoHistory.pop();//saca ultima imagen guardada en el array y la guarda en redoImg
		}
	}
	
	
		//si existe almacenada imagen de anterior trabajo en navegador la carga
	if (STORAGE){
		if (localStorage.dibujo_00){
			if (confirm('¿Quieres recuperar el último trabjo que se hizo con esta aplicación?')) {
				localStorageImage = new Image();
				localStorageImage.addEventListener("load", function(event){
					localStorageImage.removeEventListener(event.type, arguments.callee, false);
					contexto.drawImage(localStorageImage,0,0);
				}, false);
				localStorageImage.src = localStorage.dibujo_00;	
			}
		}
	}
	
	//Pone una imagen como fondo
	function ponerFondo (imagenUrl){
		var img = new Image();
		img.src = imagenUrl;
		img.onload = function(){
		//contexto = canvaso.getContext('2d');
		contexto.drawImage(img,0,0,750,545);
		}
	}
	//Pone una imagen por encima del canvas de dibujo.Por ejemplo para tener una rejilla
	function ponerRejilla(){
		var imgTop = new Image();
		imgTop.src = imagenEncima;
		imgTop.onload = function(){
		contextTop.drawImage(imgTop,0,0,750,545);
		}
	}
	//Control del boton limpiar
    $('#reset').click(function() {
        if (confirm('Se reiniciará el ejercicio y se perderá la imagen actual. ¿Estás seguro?')) {
		//canvaso.width = canvaso.width;
		undoHistory.length = 0;//vacia array con estados anteriores
		redoHistory.length = 0;
		contexto.save();
		contexto.fillStyle = colorFondo;
		contexto.fillRect(0,0, canvaso.width, canvaso.height);//rellena con color de fondo Si fuera una imagen habría que recargarla
		contexto.restore();
		//init();
		ponerFondo(imagenFondo);
        }
    })

	//controlamos el boton guardar imagen
	$('#guardar').click (function() {
	var imgData = document.getElementById("imageView").toDataURL("image/png");
			var ventana = window.open('','imagenGenerada', "toolbar=no,location=no,status=no,menubar=no,resizable=yes,scrollbars=1");
			ventana.document.write('<html><head><title>Imagen Generada</title><meta http-equiv="content-type" content="text/html; charset=iso-8859-1"><link rel="stylesheet" type="text/css" href="css/dibujo_00.css" /> ');
			ventana.document.write('</head>');
			ventana.document.write('<body style="background-color:#F4EDC8">');
			ventana.document.write('<div  style="position:absolute; top:40px; left:50%; margin-left: -375px;  width:750px; height:545px; box-shadow: -2px 2px 10px 1px #999;"><div style="position:relative"></div><div><img src="');
			ventana.document.write(imgData);
			ventana.document.write('"width="750" height="545">');
			ventana.document.write('</div><br><div style="border-width:1;border-color:#901420;border-style:dashed;border-radius:15px; margin-top: 50px;margin-left: 150px; margin-right: 150px; margin-bottom: 20px; padding-left:20px; padding-right:20px; font-family:Verdana;font-size:16px;background-color:#f3f0e7;text-align:center">');
			ventana.document.write('<br><br>Para guardar la imagen haz clic sobre ella con el botón derecho. En el menú que aparece selecciona: "Guardar imagen como..."');
			ventana.document.write('<br><br><button onclick="window.close();" class="botonVentana">Cerrar Ventana</button><br><br></div><br><br></div></body>');
			ventana.document.close();
	//window.open(document.getElementById("imageView").toDataURL("image/png"),'Canvas Export','height=450,width=625');
	})
	
	//Controla boton para poner o quitar la rejilla
	$('#rejilla').click (function(){
		if(flagRejilla == false){
			ponerRejilla();
			flagRejilla = true;
		}else{
			contextTop.clearRect(0,0,750,545);
			flagRejilla = false;
		}
	})

	// tools Contiene la implementacion de cada herramienta
	var tools = {};
	//Controles para saber que botón se ha seleccionado
	$('#lapiz').click(function (){
	tool = new tools['pencil']();
	$('canvas').css("cursor","url(imagenes/cursores/cursor_lapiz.png),auto");
	})
	$('#cubo_pintura').click (function (){
	tool = new tools['cubo_pintura']();
	$('canvas').css("cursor","url(imagenes/cursores/cursor_cubo.png),auto");
	})
	$('#rectangulo').click (function (){
	tool = new tools['rect']();
	$('canvas').css("cursor","crosshair");
	})
	$('#borrar').click(function (){
	tool = new tools['borrador']();
	$('canvas').css("cursor","url(imagenes/cursores/cursor_goma.png),auto");	
	})
	$('#circulo').click(function (){
	tool = new tools['circle']();
	$('canvas').css("cursor","crosshair");
	})
	$('#linea').click(function (){
	tool = new tools['linea']();
	$('canvas').css("cursor","url(imagenes/cursores/cursor_lapiz.png),auto");
	})
	$('#poly').click(function (){
	tool = new tools['poly']();
	$('canvas').css("cursor","url(imagenes/cursores/cursor_lapiz.png),auto");
	})
	$('#punteado3').click(function (){
	tool = new tools['punteado3']();
	$('canvas').css("cursor","url(imagenes/cursores/cursor_lapiz.png),auto");	
	})
	$('#colorPicker').click(function (){
	tool = new tools['cuentagotas']();
	$('canvas').css("cursor","url(imagenes/cursores/cursor_cuenta.png),auto");	
	})
	$('#deshacer').click (function() {
	undoDraw();
	})
	$('#rehacer').click (function() {
	redoDraw();
	})
	
    // Coloca una imagen encima
	function ponerImg(urlImg) {
	var img = new Image();
	img.src = urlImg;
		img.onload = function(){
		context = canvas.getContext('2d');
		context.drawImage(img,0,0,canvasWidth,canvasHeight);
		img_update();
		}
	}
	// Lapiz dibujo libre.
	tools.pencil = function () {
		var tool = this;
		this.started = false;

		// This is called when you start holding down the mouse button.
		// This starts the pencil drawing.
		this.mousedown = function (ev) {
			context.lineWidth = fileteAnc;
			context.lineJoin = "round";		
			context.lineCap = fin;
			context.strokeStyle = relleno;
			//context.strokeStyle = fileteCol;
			context.beginPath();
			context.moveTo(ev._x, ev._y);
			tool.started = true;
		};

		// This function is called every time you move the mouse. Obviously, it only
		// draws if the tool.started state is set to true (when you are holding down
		// the mouse button).
		this.mousemove = function (ev) {
		  if (tool.started) {
			context.lineTo(ev._x, ev._y);
			context.stroke();
		  }
		};

		// This is called when you release the mouse button.
		this.mouseup = function (ev) {
			if (tool.started) {
			tool.mousemove(ev);
			tool.started = false;
			img_update();
			}
		};
	};


	// Linea Pluma.
	tools.lineapluma = function () {
    var tool = this;
    this.started = false;

		this.mousedown = function (ev) {
		context.lineWidth = grosorpluma;
		context.strokeStyle = rellenoAlfa;
		context.lineCap = fin;
	    x = ev._x;
        y = ev._y;
        tool.started = true;
		};

		this.mousemove = function (ev) {
			if (tool.started) {
				for (i=0;i<densidad;i++){
				context.beginPath();
				context.moveTo(ev._x + (Math.random()*10-5)*anchopluma + Math.cos(x),ev._y+ (Math.random()*10-5)*anchopluma + Math.cos(y));
				//context.lineTo(x+Math.random()*i*4,y+Math.random()*i*4);
				context.lineTo(ev._x + (Math.random()*10-5)*anchopluma + Math.cos(x),ev._y+ (Math.random()*10-5)*anchopluma + Math.cos(y));
				context.stroke();
				context.closePath();
				x = ev._x;
				y = ev._y;
				}
			}
		};

		this.mouseup = function (ev) {
			if (tool.started) {
			tool.started = false;
			img_update();
			}
		};
	};


	// Herramienta Rectangulo.
	tools.rect = function () {
    var tool = this;
    this.started = false;

		this.mousedown = function (ev) {
		context.fillStyle = rellenoAlfa;
		context.strokeStyle = fileteCol;
		context.lineWidth = fileteAnc;
		context.lineCap = fin;
		tool.started = true;
		tool.x0 = Math.round(ev._x/grid)*grid;
		tool.y0 = Math.round(ev._y/grid)*grid;
		};

		this.mousemove = function (ev) {
			if (!tool.started) {
			return;
			}

		var x = Math.min((Math.round(ev._x/grid)*grid),  tool.x0),
		y = Math.min((Math.round(ev._y/grid)*grid),  tool.y0),
		w = Math.abs((Math.round(ev._x/grid)*grid) - tool.x0),
		h = Math.abs((Math.round(ev._y/grid)*grid) - tool.y0);

		context.clearRect(0, 0, canvas.width, canvas.height);

			if (!w || !h) {
			return;
			}
		context.fillRect(x, y, w, h);
		context.strokeRect(x, y, w, h);
		};

		this.mouseup = function (ev) {
			if (tool.started) {
				tool.mousemove(ev);
				tool.started = false;
				img_update();
			}
		};
  };

	// Punteado simple.
	tools.punteado = function () {
    var tool = this;

		this.mousemove = function (ev) {
		  context.fillStyle = rellenoAlfa;
		  context.clearRect(0, 0, canvas.width, canvas.height);
		  context.beginPath();
		  context.arc( ev._x, ev._y, radioPuntos*10, 0, Math.PI*2, true);
		  context.closePath();
		  context.fill();
		};

		this.mouseup = function (ev) {
			tool.mousemove(ev);
			img_update();
		};

		this.mouseout = function (ev) {
			context.clearRect(0, 0, canvas.width, canvas.height);
		};
	};

	// Cuadrícula. Dibuja cuadrados uno a uno cada vez que se hace clic.
   	/*tools.cuadricula = function () {
    var tool = this;
		this.mousemove = function (ev) {
		context.fillStyle = relleno;
		context.clearRect(0, 0, canvas.width, canvas.height);
		context.fillRect(Math.round(ev._x/grid)*grid - (grid/2), Math.round(ev._y/grid)*grid - (grid/2), grid, grid);
		};

		this.mouseup = function (ev) {
			tool.mousemove(ev);
			img_update();
		};

		this.mouseout = function (ev) {
			context.clearRect(0, 0, canvas.width, canvas.height);
		};
	};*/

    // Cuadrícula 2. Pinta cuadrados de forma contínua mientras está el botón del ratón apretado.
	tools.cuadricula = function () {
    var tool = this;
    this.started = false;

		this.mousedown = function (ev) {
		  context.fillStyle = relleno;
		  tool.started = true;
		};

		this.mousemove = function (ev) {
		  if (tool.started) {
		  context.fillRect(Math.round(ev._x/grid)*grid - (grid/2), Math.round(ev._y/grid)*grid - (grid/2), grid, grid)
		  }
		};

		this.mouseup = function (ev) {
		  if (tool.started) {
			tool.mousemove(ev);
			tool.started = false;
			img_update();
		  }
		};

	};

	
    // Cuentagotas
	tools.cuentagotas = function () {
    var tool = this;
		this.mousedown = function (ev) {
		  pixelColor = contexto.getImageData( ev._x,ev._y,1,1);
		  rellenoR = pixelColor.data[0];
		  rellenoG = pixelColor.data[1];
		  rellenoB = pixelColor.data[2];
		  alfaColor();
		  $('#paleta').css('backgroundColor', relleno);
		};

	};

// Punteado compuesto.
	tools.punteado2 = function () {
    var tool = this;
    this.started = false;

		this.mousedown = function (ev) {
			context.fillStyle = relleno;
			tool.started = true;
			tool.x0 = ev._x;
			tool.y0 = ev._y;
		};

		this.mousemove = function (ev) {
			if (tool.started) {
				  if (Math.abs(Math.sqrt((ev._x-tool.x0)*(ev._x-tool.x0)+(ev._y-tool.y0)*(ev._y-tool.y0))) > espaciado){
				  context.beginPath();
				  context.arc( ev._x, ev._y, radioPuntos, 0, Math.PI*2, true);
				  context.closePath();
				  context.fill();
				  context.beginPath()
				  context.arc( ev._x, ev._y + (radioPuntos*densidad), radioPuntos, 0, Math.PI*2, true);
				  context.closePath();
				  context.fill();
				  context.beginPath()
				  context.arc( ev._x, ev._y - (radioPuntos*densidad), radioPuntos, 0, Math.PI*2, true);
				  context.closePath();
				  context.fill();
				  context.beginPath()
				  context.arc( ev._x - (radioPuntos*densidad*Math.cos(Math.PI/6)), ev._y + (radioPuntos*densidad*Math.sin(Math.PI/6)), radioPuntos, 0, Math.PI*2, true);
				  context.closePath();
				  context.fill();
				  context.beginPath()
				  context.arc( ev._x - (radioPuntos*densidad*Math.cos(Math.PI/6)), ev._y - (radioPuntos*densidad*Math.sin(Math.PI/6)), radioPuntos, 0, Math.PI*2, true);
				  context.closePath();
				  context.fill();
				  context.beginPath()
				  context.arc( ev._x + (radioPuntos*densidad*Math.cos(Math.PI/6)), ev._y + (radioPuntos*densidad*Math.sin(Math.PI/6)), radioPuntos, 0, Math.PI*2, true);
				  context.closePath();
				  context.fill();
				  context.beginPath()
				  context.arc( ev._x + (radioPuntos*densidad*Math.cos(Math.PI/6)), ev._y - (radioPuntos*densidad*Math.sin(Math.PI/6)), radioPuntos, 0, Math.PI*2, true);
				  context.closePath();
				  context.fill();
				  tool.x0 = ev._x;
				  tool.y0 = ev._y;
				  }
			}
		};

		this.mouseup = function (ev) {
		  if (tool.started) {
			tool.mousemove(ev);
			tool.started = false;
			img_update();
		  }
		};
	};

// Punteado aleatorio.
	tools.punteado3 = function () {
    var tool = this;
    this.started = false;

		this.mousedown = function (ev) {
		  context.fillStyle = rellenoAlfa;
		  tool.started = true;
		};

		this.mousemove = function (ev) {
		  if (tool.started) {
		  context.beginPath();
		  context.arc( ev._x + Math.sin(Math.random()*Math.PI*2)*Math.random()*pincel, ev._y + Math.cos(Math.random()*Math.PI*2)*Math.random()*pincel, radioPuntos, 0, Math.PI*2, true);
		  context.closePath();
		  context.fill();
		  }
		};

		this.mouseup = function (ev) {
		  if (tool.started) {
			tool.mousemove(ev);
			tool.started = false;
			img_update();
		  }
		};

	};


	//Borrador. Si hubiera imagen de fondo habría que copiarla primero cada vez que se hace imgUpdate
	//o colocarla en otro canvas por debajo
	tools.borrador = function () {
    var tool = this;
    this.started = false;

	saveActions();

		this.mousedown = function (ev) {
		  context.lineWidth = 1;
		  pincel = fileteAnc*3;
		  context.strokeStyle = 'black';
		  contexto.fillStyle = colorFondo;
		  tool.started = true;
		};

		this.mousemove = function (ev) {
		  if (tool.started) {
		  context.clearRect(0, 0, canvas.width, canvas.height);
		  context.strokeRect( ev._x-pincel/2, ev._y-pincel/2, pincel, pincel);
		  // contexto.clearRect( ev._x-pincel/2, ev._y-pincel/2, pincel, pincel);//elimina fondo
		  contexto.fillRect( ev._x-pincel/2, ev._y-pincel/2, pincel, pincel);//pinta con color de fondo
		  }
		};

		this.mouseup = function (ev) {
		  if (tool.started) {
			tool.mousemove(ev);
			tool.started = false;
			context.clearRect(0, 0, canvas.width, canvas.height);
			saveActions();
		  }
		};

	};

	// The line tool.
	tools.line = function () {
    var tool = this;
    this.started = false;

		this.mousedown = function (ev) {
		context.lineCap = 'round';
		context.lineWidth = fileteAnc;
		context.strokeStyle = fileteCol;
		context.lineCap = fin;
		tool.started = true;
		tool.x0 = ev._x;
		tool.y0 = ev._y;
		context.beginPath();
		context.moveTo(Math.round(tool.x0/grid)*grid, Math.round(tool.y0/grid)*grid);
		};

		this.mousemove = function (ev) {
		  if (!tool.started) {
			return;
		  }

		  context.clearRect(0, 0, canvas.width, canvas.height);
		  context.beginPath();
		  context.moveTo(Math.round(tool.x0/grid)*grid, Math.round(tool.y0/grid)*grid);
		  context.lineTo(Math.round(ev._x/grid)*grid,  Math.round(ev._y/grid)*grid);
		  context.stroke();
		  context.closePath();
		};

		this.mouseup = function (ev) {
		  if (tool.started) {
			tool.mousemove(ev);
			tool.started = false;
			img_update();
		  }
		};
	};


    // The circle tool.
    tools.circle = function () {
    var tool = this;
    this.started = false;

		this.mousedown = function (ev) {
		context.fillStyle = rellenoAlfa;
		context.strokeStyle = fileteCol;
		context.lineWidth = fileteAnc*1.5;
		tool.started = true;
		tool.x0 = Math.round(ev._x/grid)*grid
		tool.y0 = Math.round(ev._y/grid)*grid
		};
		this.mousemove = function (ev) {
			if (!tool.started) {
			return;
			}
			dif_x = Math.round(ev._x/grid)*grid - tool.x0;
			dif_y = Math.round(ev._y/grid)*grid - tool.y0;
			radio = Math.sqrt(dif_y*dif_y+dif_x*dif_x);
			context.clearRect(0, 0, canvas.width, canvas.height);
			context.beginPath();
			context.arc( tool.x0, tool.y0, radio, 0, Math.PI*2, true);
			context.closePath();
			context.stroke();
			context.fill();
		}
		this.mouseup = function (ev) {
			if (tool.started) {
			tool.mousemove(ev);
			tool.started = false;
			img_update();
			}
		}
	}


	// The polígono tool.
	tools.poly = function () {
    var tool = this;
    this.started = false;
		this.mousedown = function (ev) {
		  context.lineWidth = fileteAnc;
		  context.strokeStyle = fileteCol;
		  contexto.lineWidth = fileteAnc;
		  contexto.strokeStyle = fileteCol;
		  contexto.fillStyle = rellenoAlfa;
		  context.lineJoin = 'round';
		  if (!tool.started){
		  tool.x0 = Math.round(ev._x/grid)*grid;
		  tool.y0 = Math.round(ev._y/grid)*grid;
		  tool.x1 = Math.round(ev._x/grid)*grid;//Guarda coordenadas del
		  tool.y1 = Math.round(ev._y/grid)*grid;//comienzo del poligono
		  context.beginPath();
		  contexto.beginPath();
		  context.moveTo(tool.x0, tool.y0);
		  contexto.moveTo(tool.x0, tool.y0);
		  tool.started = true;
		  saveActions();
		  }else if ((Math.abs(tool.x1-ev._x)<(grid/2))&&(Math.abs(tool.y1-ev._y)<(grid/2))){
				contexto.closePath();
				contexto.fill();
				contexto.stroke();
				tool.started = false;
				context.clearRect(0, 0, canvas.width, canvas.height);
				saveLocalStorage();
		  }else{
		  contexto.lineTo(Math.round(ev._x/grid)*grid,  Math.round(ev._y/grid)*grid);
		  contexto.stroke();
		  //contexto.fill();//Si el relleno es transparente se van superponiendo Usar relleno solido
		  tool.x0 = ev._x;
		  tool.y0 = ev._y;
		  }

		};
		this.mousemove = function (ev){
		  if (!tool.started) {
			return;
		  }
		  context.clearRect(0, 0, canvas.width, canvas.height);
		  context.beginPath();
		  context.moveTo(Math.round(tool.x0/grid)*grid, Math.round(tool.y0/grid)*grid);
		  context.lineTo(Math.round(ev._x/grid)*grid,  Math.round(ev._y/grid)*grid);
		  context.stroke();
		};

		this.dblclick = function (ev) {
		  if (tool.started) {
			contexto.closePath();
			contexto.fill();
			contexto.stroke();
			tool.started = false;
			saveLocalStorage();
			}
		};
	};

		// Dibuja línea sobre una red Isometrica .
		tools.linea_Iso = function () {
		var tool = this;
		this.started = false;


			this.mousedown = function (ev) {
			  context.lineWidth = fileteAnc;
			  context.strokeStyle = fileteCol;
			  context.lineCap = 'round';
			  grid_iso = Math.sqrt(3)/2*grid;
			  if (!tool.started){
			  tool.x0 = ev._x;
			  tool.y0 = ev._y;
			  context.beginPath();
			  context.moveTo(Math.round(tool.x0/grid_iso)*grid_iso, Math.round(tool.y0/grid*2)*grid/2);
			  tool.started = true;
			  }else{
			  tool.mousemove(ev);
			  img_update();
			  tool.started = false;
			  }
			 };

			this.mousemove = function (ev) {
			  if (!tool.started) {
				return;
			  }
			  context.clearRect(0, 0, canvas.width, canvas.height);
			  context.beginPath();
			  context.moveTo(Math.round(tool.x0/grid_iso)*grid_iso, Math.round(tool.y0/grid*2)*grid/2);
			  context.lineTo(Math.round(ev._x/grid_iso)*grid_iso, Math.round(ev._y/grid*2)*grid/2);
			  context.stroke();
			  context.closePath();
			};
		};

		// The línea tool. Dibuja lineas rectas siguiendo una cuadrícula de grid px
		tools.linea= function () {
		var tool = this;
		this.started = false;

			this.mousedown = function (ev) {
			  context.lineWidth = fileteAnc;
			  context.strokeStyle = fileteCol;
			  context.lineCap = fin;
			  if (!tool.started){
			  tool.x0 = ev._x;
			  tool.y0 = ev._y;
			  context.beginPath();
			  context.moveTo(Math.round(tool.x0/grid)*grid, Math.round(tool.y0/grid)*grid);
			  tool.started = true;
			  }else{
			  tool.mousemove(ev);
			  img_update();
			  tool.started = false;
			  }
			};

			this.mousemove = function (ev) {
			  if (!tool.started) {
				return;
			  }
			  context.clearRect(0, 0, canvas.width, canvas.height);
			  context.beginPath();
			  context.moveTo(Math.round(tool.x0/grid)*grid, Math.round(tool.y0/grid)*grid);
			  context.lineTo(Math.round(ev._x/grid)*grid,  Math.round(ev._y/grid)*grid);
			  context.stroke();
			  context.closePath();
			};
		};



		// Línea H y V. Dibuja polilineas rectas consecutivas horizontales o verticales
		tools.linea_4 = function () {
		var tool = this;
		this.started = false;

			this.mousedown = function (ev) {
			  context.lineWidth = fileteAnc;
			  context.strokeStyle = fileteCol;
			  context.lineJoin = 'round';
			  context.lineCap = fin;
			  if (!tool.started){
			  tool.x0 = ev._x;
			  tool.y0 = ev._y;
			  context.beginPath();
			  context.moveTo(tool.x0, tool.y0);
			  tool.started = true;
			  }else{
			  tool.mousemove(ev);
			  img_update();
			  if(control == 1){
			  tool.x0 = ev._x;
			  }else{
			  tool.y0 = ev._y;
			  }
			  context.beginPath();
			  context.moveTo(tool.x0, tool.y0);
			  }
			};

			this.mousemove = function (ev) {
			  if (!tool.started) {
				return;
			  }
			  context.clearRect(0, 0, canvas.width, canvas.height);
			  context.beginPath();
			  context.moveTo(tool.x0, tool.y0);
			  if (Math.atan(Math.abs(ev._y - tool.y0)/Math.abs(ev._x - tool.x0)) <= Math.PI/4){
			  context.lineTo(ev._x, tool.y0);
			  control = 1;
			  }else{
			  context.lineTo(tool.x0, ev._y);
			  control = 0;
			  }
			  context.closePath();
			  context.stroke();
			};

			this.dblclick = function (ev) {
			  if (tool.started) {
			  img_update();
			  tool.started = false;
			  }
			};
		};

	   // The línea3 tool. Dibuja líneas horizontales separadas 10 px.
		tools.linea_3 = function () {
		var tool = this;
		this.started = false;

			this.mousedown = function (ev) {
			  context.lineWidth = fileteAnc;
			  context.strokeStyle = fileteCol;
			  context.lineCap = fin;
			  if (!tool.started){
			  tool.x0 = ev._x;
			  tool.y0 = ev._y;
			  context.beginPath();
			  context.moveTo(tool.x0, Math.round(tool.y0/10)*10);//10 es la separación entre lineas paralelas
			  tool.started = true;
			  }else{
			  tool.mousemove(ev);
			  img_update();
			  tool.started = false;
			  }
			};

			this.mousemove = function (ev) {
			  if (!tool.started) {
				return;
			  }
			  context.clearRect(0, 0, canvas.width, canvas.height);
			  context.beginPath();
			  context.moveTo(tool.x0, Math.round(tool.y0/10)*10);
			  context.lineTo(ev._x,  Math.round(tool.y0/10)*10);
			  context.stroke();
			  context.closePath();
			};
		};


		//línea puntos
		tools.lineapuntos = function () {
		var tool = this;
		this.started = false;

			this.mousedown = function (ev) {
			  context.lineWidth = fileteAnc;
			  context.strokeStyle = fileteCol;
			  context.lineCap = fin;
			  if (!tool.started){
			  tool.x0 = ev._x;
			  tool.y0 = ev._y;
			  tool.started = true;
			  }else{
			  tool.mousemove(ev);
			  img_update();
			  tool.started = false;
			  }

			};

			this.mousemove = function (ev) {
			  if (!tool.started) {
				return;
			  }
			  context.clearRect(0, 0, canvas.width, canvas.height);
			  context.beginPath();
			  context.dashedLineTo(Math.round(tool.x0/grid)*grid , Math.round(tool.y0/grid)*grid , Math.round(ev._x/grid)*grid,  Math.round(ev._y/grid)*grid , [5,10]);
			  context.closePath();
			  context.stroke();
			};
		};


		//Cubo Pintura
		tools.cubo_pintura = function () {
		var tool = this;
		this.started = false;

			this.mousedown = function (ev) {
			curColor = { r:rellenoR, g:rellenoG, b:rellenoB};//toma color seleccionado en rgb
			saveActions();
			colorLayerData = contexto.getImageData(0, 0, canvasWidth, canvasHeight);//copia canvas a colorLayerData
			paintAt(ev._x, ev._y);
			saveLocalStorage();
			};
			floodFill = function (startX, startY, startR, startG, startB) {


					var newPos,
						x,
						y,
						pixelPos,
						reachLeft,
						reachRight,
						drawingBoundLeft = 0,
						drawingBoundTop = 0,
						drawingBoundRight = canvasWidth,
						drawingBoundBottom = canvasHeight-22;
						pixelStack = [[startX, startY]];

					while (pixelStack.length) {

						newPos = pixelStack.pop();
						x = newPos[0];
						y = newPos[1];

						// Get current pixel position
						pixelPos = (y * canvasWidth + x) * 4;

						// Go up as long as the color matches and are inside the canvas
						while (y >= drawingBoundTop && matchStartColor(pixelPos, startR, startG, startB)) {
							y -= 1;
							pixelPos -= canvasWidth * 4;
						}

						pixelPos += canvasWidth * 4;
						y += 1;
						reachLeft = false;
						reachRight = false;

						// Go down as long as the color matches and in inside the canvas
						while (y <= drawingBoundBottom && matchStartColor(pixelPos, startR, startG, startB)) {
							y += 1;

							colorPixel(pixelPos, curColor.r, curColor.g, curColor.b);

							if (x > drawingBoundLeft) {
								if (matchStartColor(pixelPos - 4, startR, startG, startB)) {
									if (!reachLeft) {
										// Add pixel to stack
										pixelStack.push([x - 1, y]);
										reachLeft = true;
									}
								} else if (reachLeft) {
									reachLeft = false;
								}
							}

							if (x < drawingBoundRight) {
								if (matchStartColor(pixelPos + 4, startR, startG, startB)) {
									if (!reachRight) {
										// Add pixel to stack
										pixelStack.push([x + 1, y]);
										reachRight = true;
									}
								} else if (reachRight) {
									reachRight = false;
								}
							}

							pixelPos += canvasWidth * 4;
						}
					}

				},


			clearCanvas = function () {
			contexto.clearRect(0, 0,canvasWidth, canvasHeight);
			}

			matchStartColor = function (pixelPos, startR, startG, startB) {

				r = colorLayerData.data[pixelPos];
				g = colorLayerData.data[pixelPos + 1];
				b = colorLayerData.data[pixelPos + 2];

				// If the current pixel matches the clicked color
				if (r === startR && g === startG && b === startB) {
					return true;
				}

				// If current pixel matches the new color
				if (r === curColor.r && g === curColor.g && b === curColor.b) {
					return false;
				}
				// If current pixel has different colour
				return false;
			}

			colorPixel = function (pixelPos, r, g, b, a) {

				colorLayerData.data[pixelPos] = r;
				colorLayerData.data[pixelPos + 1] = g;
				colorLayerData.data[pixelPos + 2] = b;
				colorLayerData.data[pixelPos + 3] = a !== undefined ? a : 255;
			};
			paintAt = function (startX, startY) {

				var pixelPos = (startY * canvasWidth + startX) * 4,
					r = colorLayerData.data[pixelPos],
					g = colorLayerData.data[pixelPos + 1],
					b = colorLayerData.data[pixelPos + 2],
					a = colorLayerData.data[pixelPos + 3];

				if (r === curColor.r && g === curColor.g && b === curColor.b) {
					// Return because trying to fill with the same color
					return;
				};

				floodFill(startX, startY, r, g, b);
				contexto.putImageData(colorLayerData, 0, 0);
			}
		}; //fin cubo pintura
	
		//Aumenta de tamaño el escritorio
		document.getElementById('zoom_in').onclick = function() {
			if (canvasScale > 2) {
				return;	
			}
			canvasScale = canvasScale * scaleFactor;
			altoNuevo = Math.round(altoNuevo* scaleFactor);
			anchoNuevo = Math.round( anchoNuevo* scaleFactor);
			$('#imageView').css('height',altoNuevo);
			$('#imageView').css('width',anchoNuevo);
			$('.lienzo').css('height',altoNuevo);
			$('.lienzo').css('width',anchoNuevo);
			$('#imageTemp').css('height',altoNuevo-(22*canvasScale));
			$('#imageTemp').css('width',anchoNuevo);
			$('#imageTop').css('height',altoNuevo);
			$('#imageTop').css('width',anchoNuevo);
			objeto = document.getElementById('herram');
			objeto.style.height = altoNuevo +'px';
		}
	
		//Disminuye de tamaño el escritorio
		document.getElementById('zoom_out').onclick = function() {
			if (canvasScale < 0.9) {
				return;	
			}
			canvasScale = canvasScale / scaleFactor;
			altoNuevo = Math.round(altoNuevo * (1 / scaleFactor));
			anchoNuevo = Math.round(anchoNuevo * (1 / scaleFactor));
			$('#imageView').css('height',altoNuevo);
			$('#imageView').css('width',anchoNuevo);
			$('.lienzo').css('height',altoNuevo);
			$('.lienzo').css('width',anchoNuevo);
			$('#imageTemp').css('height',altoNuevo-(22 * canvasScale));
			$('#imageTemp').css('width',anchoNuevo);
			$('#imageTop').css('height',altoNuevo);
			$('#imageTop').css('width',anchoNuevo);
			objeto = document.getElementById('herram');
			objeto.style.height = altoNuevo +'px';
		}
	
	
		//Importa imagen desde archivo y la coloca como fondo del canvas fabric
		formEl = document.forms[0],
		fileEl = formEl.elements[0],

		formEl.onsubmit = fileEl.onchange = uploadHandler;
//
		function uploadHandler() {
		uploadFile(fileEl.files && fileEl.files[0]);
		return false;
		}		
		$('#subirArc').click(function(){fileEl.click()});
		
		//Sube archivo de imagen desde el ordenador
		function uploadFile(file) {
			if (file && file.type && file.type.match(/^image\/.*/)) {
				var fileReader = new FileReader();
				fileReader.onload = function(e) {
					var dataURL = e.target.result;
					var newImg = new Image();
					newImg.onload = ajustar();
					newImg.src = dataURL;
					
					function ajustar(){
						fondoColor();
						alto = newImg.height;
						ancho = newImg.width;
						altoCanvas =canvaso.height-22;
						if(ancho/alto >= canvaso.width/altoCanvas){
							yCoor = Math.floor((altoCanvas-canvaso.width*alto/ancho)/2);
							altoPNG = Math.floor(canvaso.width*alto/ancho);
							contexto.drawImage(newImg,0,yCoor,canvaso.width,altoPNG);
							return
						}else{
							xCoor = Math.floor((canvaso.width-altoCanvas*ancho/alto)/2);
							anchoPNG = Math.floor(altoCanvas*ancho/alto);
							contexto.drawImage(newImg,xCoor,0,anchoPNG,altoCanvas);
						}
					}
				}
			fileReader.readAsDataURL(file);
			}return
		}

	init();

}, false); }
