diff options
Diffstat (limited to 'public')
-rw-r--r-- | public/dye.html | 83 | ||||
-rw-r--r-- | public/js/mp/dye.js | 30 | ||||
-rw-r--r-- | public/js/mp/resource.js | 35 | ||||
-rw-r--r-- | public/playground.html | 13 |
4 files changed, 149 insertions, 12 deletions
diff --git a/public/dye.html b/public/dye.html new file mode 100644 index 0000000..f7ca177 --- /dev/null +++ b/public/dye.html @@ -0,0 +1,83 @@ +<!DOCTYPE html> +<html> + <head> + <title>Dyer</title> + <style type="text/css"> + .viewport { + border:solid 1px #000000; + display: inline-block; + height: 400px; + overflow: scroll; + width: 600px; + } + </style> + <script src="js/mp/dye.js"></script> + <script src="js/mp/resource.js"></script> + </head> + <body> + <div class="viewport" dropzone="link" ondrop="dyeDrop(event);" ondragover="event.preventDefault();"> + <canvas id="dyeCanvas"></canvas> + </div> + <div class="viewport" dropzone="link" ondrop="referenceDrop(event);" ondragover="event.preventDefault();"></div> + + <div style="display: none" > + <canvas id="rawCanvas"></canvas> + </div> + + <div><input type="text" id="dyeStringInput" size="100"/><button onclick="applyDye(event);">Apply</button></div> + + <script> + var dyeCanvas = document.getElementById("dyeCanvas"), + dyeStringInput = document.getElementById("dyeStringInput"); + + var loadedImage = null; + + function applyDye(event) { + if (loadedImage == null) { + return; + } + + var ctx = dyeCanvas.getContext("2d"); + ctx.clearRect(0, 0, dyeCanvas.width, dyeCanvas.height); + var clone = mp.resource.copyImageData(ctx, loadedImage); + mp.dye.dyeImage(clone.data, mp.dye.parseDyeString(dyeStringInput.value)); + ctx.putImageData(clone, 0, 0); + } + + function dyeDrop(event) { + event.stopPropagation(); + event.preventDefault(); + var file = event.dataTransfer.files[0], + reader = new FileReader(); + reader.onload = function (event) { + mp.resource.loadImage(event.target.result, function(err, imageData) { + if (!err) { + loadedImage = imageData; + dyeCanvas.width = loadedImage.width; + dyeCanvas.height = loadedImage.height; + applyDye(null); + } + }); + }; + reader.readAsDataURL(file); + + return false; + } + + function referenceDrop(event) { + event.stopPropagation(); + event.preventDefault(); + var file = event.dataTransfer.files[0], + reader = new FileReader(); + reader.onload = function (event) { + var img = new Image(); + img.src = event.target.result; + referenceViewport.innerHTML = ''; + referenceViewport.appendChild(img); + }; + reader.readAsDataURL(file); + return false; + } + </script> + </body> +</html> diff --git a/public/js/mp/dye.js b/public/js/mp/dye.js index 7cf8da5..e7af938 100644 --- a/public/js/mp/dye.js +++ b/public/js/mp/dye.js @@ -5,7 +5,12 @@ var mp = function(mp) { parseDyeString: parseDyeString, dyeImage: dyeImage }; + var channel = [null, "R", "G", "Y", "B", "M", "C", "W"]; + + /* + * Return the channel and intensity for the given RGB(A) array. + */ function getChannel(color) { var r = color[0], g = color[1], b = color[2], max = Math.max(r, g, b); @@ -28,12 +33,35 @@ var mp = function(mp) { return { channel: channel[idx], intensity: max }; } + /* * Return a dye specification from a dye string. */ function parseDyeString(dyeString) { - /* TODO */ + var channelStrings = dyeString.split("|"); + var dyeData = {}; + + for (var i = 0; i < channelStrings.length; i++) { + var channelStr = channelStrings[i]; + if (channelStr[1] != ":" || channelStr[2] != "#") { + // TODO error + } + + var channel = channelStr[0]; + var parts = channelStr.substring(3).split(","); + + var list = []; + + for (var j = 0; j < parts.length; j++) { + list.push(mp.resource.parseColor(parts[j])); + } + + dyeData[channel] = list; + } + + return dyeData; } + /* * Dye the internal image data based on the specification provided by dyeData. * The specification can be generated from a dyeString by parseDyeString. diff --git a/public/js/mp/resource.js b/public/js/mp/resource.js index f348a89..406222a 100644 --- a/public/js/mp/resource.js +++ b/public/js/mp/resource.js @@ -1,7 +1,9 @@ "use strict"; var mp = function(mp) { mp.resource = { - loadImage: loadImage + loadImage: loadImage, + copyImageData: copyImageData, + parseColor: parseColor }; /* @@ -32,5 +34,36 @@ var mp = function(mp) { }; image.src = url; } + + function copyImageData(ctx, src) { + var dst = ctx.createImageData(src.width, src.height); + dst.data.set(src.data); + return dst; + } + + /* + * Parses the given color string into an array of parts + */ + function parseColor(colorString) { + if (colorString[0] == "#") { + colorString = colorString.substring(1); + } + + if (colorString.length == 3) { + var r = colorString[0] + colorString[0]; + var g = colorString[1] + colorString[1]; + var b = colorString[2] + colorString[2]; + return [parseInt(r, 16), parseInt(g, 16), parseInt(b, 16)] + } + + if (colorString.length == 6) { + return [parseInt(colorString.substring(0,2), 16), parseInt(colorString.substring(2,4), 16), parseInt(colorString.substring(4,6), 16)] + } + + // TODO others? + + return null; + } + return mp; }(mp || {}); diff --git a/public/playground.html b/public/playground.html index 3099b83..10ac6c2 100644 --- a/public/playground.html +++ b/public/playground.html @@ -11,16 +11,9 @@ <script src="js/mp/dye.js"></script> <script src="js/mp/resource.js"></script> <script> -var dyeData = { - "R": [ - [0xed, 0xe5, 0xb2], - [0xff, 0xf7, 0xbf] - ], - "G": [ - [0xcc, 0xcc, 0xcc], - [0xff, 0xff, 0xff] - ] -}; +var dyeString = "R:#ede5b2,fff7bf|G:#cccccc,ffffff"; +var dyeData = mp.dye.parseDyeString(dyeString); + mp.resource.loadImage("bigcake.png", function(err, imageData) { var oContext = document.getElementById("original").getContext("2d"); var dContext = document.getElementById("dyed").getContext("2d"); |