// Copyright 2013 the V8 project authors. All rights reserved. // Redistribution and use in source and binary forms, with or without // modification, are permitted provided that the following conditions are // met: // // * Redistributions of source code must retain the above copyright // notice, this list of conditions and the following disclaimer. // * Redistributions in binary form must reproduce the above // copyright notice, this list of conditions and the following // disclaimer in the documentation and/or other materials provided // with the distribution. // * Neither the name of Google Inc. nor the names of its // contributors may be used to endorse or promote products derived // from this software without specific prior written permission. // // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. var worker_scripts = [ "../csvparser.js", "../splaytree.js", "../codemap.js", "../consarray.js", "../profile.js", "../profile_view.js", "../logreader.js", "../arguments.js", "../tickprocessor.js", "composer.js", "gnuplot-4.6.3-emscripten.js" ]; function plotWorker() { var worker = null; function initialize() { ui.freeze(); worker = new Worker("worker.js"); running = false; worker.postMessage({ "call" : "load scripts", "args" : worker_scripts }); worker.addEventListener("message", function(event) { var call = delegateList[event.data["call"]]; call(event.data["args"]); }); } function scriptLoaded() { ui.thaw(); } // Public methods. this.run = function(filename, resx, resy, distortion, range_start, range_end) { var args = { 'file' : filename, 'resx' : resx, 'resy' : resy, 'distortion' : distortion, 'range_start' : range_start, 'range_end' : range_end } worker.postMessage({ 'call' : 'run', 'args' : args }); } this.reset = function() { if (worker) worker.terminate(); initialize(); } var delegateList = { "log" : log, "error" : logError, "displayplot" : displayplot, "displayprof" : displayprof, "range" : setRange, "script" : scriptLoaded, "reset" : this.reset } } function UIWrapper() { var input_elements = ["range_start", "range_end", "distortion", "start", "file"]; var other_elements = ["log", "plot", "prof", "instructions", "credits", "toggledisplay"]; for (var i in input_elements) { var id = input_elements[i]; this[id] = document.getElementById(id); } for (var i in other_elements) { var id = other_elements[i]; this[id] = document.getElementById(id); } this.freeze = function() { this.plot.style.webkitFilter = "grayscale(1)"; this.prof.style.color = "#bbb"; for (var i in input_elements) { this[input_elements[i]].disabled = true; } } this.thaw = function() { this.plot.style.webkitFilter = ""; this.prof.style.color = "#000"; for (var i in input_elements) { this[input_elements[i]].disabled = false; } } this.reset = function() { this.thaw(); this.log.value = ""; this.range_start.value = "automatic"; this.range_end.value = "automatic"; this.toggle("plot"); this.plot.src = ""; this.prof.value = ""; } this.toggle = function(mode) { if (mode) this.toggledisplay.next_mode = mode; if (this.toggledisplay.next_mode == "plot") { this.toggledisplay.next_mode = "prof"; this.plot.style.display = "block"; this.prof.style.display = "none"; this.toggledisplay.innerHTML = "Show profile"; } else { this.toggledisplay.next_mode = "plot"; this.plot.style.display = "none"; this.prof.style.display = "block"; this.toggledisplay.innerHTML = "Show plot"; } } this.info = function(field) { var down_arrow = "\u25bc"; var right_arrow = "\u25b6"; if (field && this[field].style.display != "none") field = null; // Toggle. this.credits.style.display = "none"; this.instructions.style.display = "none"; if (!field) return; this[field].style.display = "block"; } } function log(text) { ui.log.value += text; ui.log.scrollTop = ui.log.scrollHeight; } function logError(text) { if (ui.log.value.length > 0 && ui.log.value[ui.log.value.length-1] != "\n") { ui.log.value += "\n"; } ui.log.value += "ERROR: " + text + "\n"; ui.log.scrollTop = ui.log.scrollHeight; error_logged = true; } function displayplot(args) { if (error_logged) { log("Plot failed.\n\n"); } else { log("Displaying plot. Total time: " + (Date.now() - timer) / 1000 + "ms.\n\n"); var blob = new Blob([new Uint8Array(args.contents).buffer], { "type" : "image\/svg+xml" }); window.URL = window.URL || window.webkitURL; ui.plot.src = window.URL.createObjectURL(blob); } ui.thaw(); ui.toggle("plot"); } function displayprof(args) { if (error_logged) return; ui.prof.value = args; this.prof.style.color = ""; ui.toggle("prof"); } function start(event) { error_logged = false; ui.freeze(); try { var file = getSelectedFile(); var distortion = getDistortion(); var range = getRange(); } catch (e) { logError(e.message); display(); return; } timer = Date.now(); worker.run(file, kResX, kResY, distortion, range[0], range[1]); } function getSelectedFile() { var file = ui.file.files[0]; if (!file) throw Error("No valid file selected."); return file; } function getDistortion() { var input_distortion = parseInt(ui.distortion.value, 10); if (isNaN(input_distortion)) { input_distortion = ui.distortion.value = 4500; } return input_distortion / 1000000; } function getRange() { var input_start = parseInt(ui.range_start.value, 10); if (isNaN(input_start)) input_start = undefined; var input_end = parseInt(ui.range_end.value, 10); if (isNaN(input_end)) input_end = undefined; return [input_start, input_end]; } function setRange(args) { ui.range_start.value = args.start.toFixed(1); ui.range_end.value = args.end.toFixed(1); } function onload() { kResX = 1200; kResY = 600; error_logged = false; ui = new UIWrapper(); ui.reset(); ui.info(null); worker = new plotWorker(); worker.reset(); } var kResX; var kResY; var error_logged; var ui; var worker; var timer;