|
|
- // Copyright (c) 2014-17 Walter Bender
- // Copyright (c) Yash Khandelwal, GSoC'15
- // Copyright (c) 2016 Tymon Radzik
- //
- // This program is free software; you can redistribute it and/or
- // modify it under the terms of the The GNU Affero General Public
- // License as published by the Free Software Foundation; either
- // version 3 of the License, or (at your option) any later version.
- //
- // You should have received a copy of the GNU Affero General Public
- // License along with this library; if not, write to the Free Software
- // Foundation, 51 Franklin Street, Suite 500 Boston, MA 02110-1335 USA
- //
- // Note: This code is inspired by the Python Turtle Blocks project
- // (https://github.com/walterbender/turtleart), but implemented from
- // scratch. -- Walter Bender, October 2014.
-
- const _THIS_IS_MUSIC_BLOCKS_ = false;
- const _THIS_IS_TURTLE_BLOCKS_ = !_THIS_IS_MUSIC_BLOCKS_;
-
-
- function facebookInit() {
- window.fbAsyncInit = function () {
- FB.init({
- appId: '1496189893985945',
- xfbml: true,
- version: 'v2.1'
- });
-
- // ADD ADDITIONAL FACEBOOK CODE HERE
- };
- };
-
-
- try {
- (function (d, s, id) {
- var js, fjs = d.getElementsByTagName(s)[0];
- if (d.getElementById(id)) {
- return;
- }
-
- js = d.createElement(s);
- js.id = id;
- js.src = "https://connect.facebook.net/en_US/sdk.js";
- fjs.parentNode.insertBefore(js, fjs);
- }(document, 'script', 'facebook-jssdk'));
- } catch (e) {
- };
-
-
- var lang = document.webL10n.getLanguage();
- if (lang.indexOf('-') !== -1) {
- lang = lang.slice(0, lang.indexOf("-"));
- document.webL10n.setLanguage(lang);
- }
-
- if (_THIS_IS_MUSIC_BLOCKS_) {
- MYDEFINES = ["activity/sugarizer-compatibility", 'activity/platformstyle', 'easeljs-0.8.2.min', 'tweenjs-0.6.2.min', 'preloadjs-0.6.2.min', 'Tone.min', 'howler', 'p5.min', 'p5.sound.min', 'p5.dom.min', 'mespeak', 'Chart', 'activity/utils', 'activity/artwork', 'activity/status', 'activity/munsell', 'activity/trash', 'activity/boundary', 'activity/turtle', 'activity/palette', 'activity/protoblocks', 'activity/blocks', 'activity/block', 'activity/turtledefs', 'activity/logo', 'activity/clearbox', 'activity/utilitybox', 'activity/samplesviewer', 'activity/basicblocks', 'activity/blockfactory', 'activity/analytics', 'activity/modewidget', 'activity/soundsamples', 'activity/pitchtimematrix', 'activity/pitchdrummatrix', 'activity/rhythmruler', 'activity/pitchstaircase', 'activity/tempo', 'activity/pitchslider', 'activity/macros', 'activity/musicutils', 'activity/lilypond', 'prefixfree.min'];
- } else {
- MYDEFINES = ["activity/sugarizer-compatibility", 'activity/platformstyle', 'easeljs-0.8.2.min', 'tweenjs-0.6.2.min', 'preloadjs-0.6.2.min', 'howler', 'p5.min', 'p5.sound.min', 'p5.dom.min', 'mespeak', 'Chart', 'activity/utils', 'activity/artwork', 'activity/status', 'activity/munsell', 'activity/trash', 'activity/boundary', 'activity/turtle', 'activity/palette', 'activity/protoblocks', 'activity/blocks', 'activity/block', 'activity/turtledefs', 'activity/logo', 'activity/clearbox', 'activity/savebox', 'activity/utilitybox', 'activity/samplesviewer', 'activity/basicblocks', 'activity/blockfactory', 'activity/analytics', 'activity/macros', 'activity/musicutils', 'activity/lilypond', 'prefixfree.min'];
- }
-
- define(MYDEFINES, function (compatibility) {
-
- // Manipulate the DOM only when it is ready.
- requirejs(['domReady!','activity/sugarizer-compatibility'], function (doc) {
- if (sugarizerCompatibility.isInsideSugarizer()) {
- window.addEventListener('localized', function() {
- sugarizerCompatibility.loadData(function () {
- domReady(doc);
- });
- });
- document.webL10n.setLanguage(sugarizerCompatibility.getLanguage());
- } else {
- domReady(doc);
- }
- });
-
- function domReady(doc) {
- createDefaultStack();
- createHelpContent();
- // facebookInit();
- window.scroll(0, 0);
-
- try {
- meSpeak.loadConfig('lib/mespeak_config.json');
- var lang = document.webL10n.getLanguage();
- if (sugarizerCompatibility.isInsideSugarizer()) {
- lang = sugarizerCompatibility.getLanguage();
- }
- if (['es', 'ca', 'de', 'el', 'eo', 'fi', 'fr', 'hu', 'it', 'kn', 'la', 'lv', 'nl', 'pl', 'pt', 'ro', 'sk', 'sv', 'tr', 'zh'].indexOf(lang) !== -1) {
- meSpeak.loadVoice('lib/voices/' + lang + '.json');
- } else {
- meSpeak.loadVoice('lib/voices/en/en.json');
- }
- } catch (e) {
- console.log(e);
- }
-
- var canvas = docById('myCanvas');
-
- var queue = new createjs.LoadQueue(false);
-
- // Check for the various File API support.
- if (window.File && window.FileReader && window.FileList && window.Blob) {
- var files = true;
- } else {
- alert('The File APIs are not fully supported in this browser.');
- var files = false;
- }
-
- // Set up a file chooser for the doOpen function.
- var fileChooser = docById('myOpenFile');
- // Set up a file chooser for the doOpenPlugin function.
- var pluginChooser = docById('myOpenPlugin');
- // The file chooser for all files.
- var allFilesChooser = docById('myOpenAll');
-
- // Are we running off of a server?
- var server = true;
- var turtleBlocksScale = 1;
- var stage;
- var turtles;
- var palettes;
- var blocks;
- var logo;
- var clearBox;
- var utilityBox;
- var thumbnails;
- var buttonsVisible = true;
- var headerContainer = null;
- var toolbarButtonsVisible = true;
- var menuButtonsVisible = true;
- var menuContainer = null;
- var scrollBlockContainer = false;
- var currentKey = '';
- var currentKeyCode = 0;
- var lastKeyCode = 0;
- var pasteContainer = null;
- var pasteImage = null;
- var chartBitmap = null;
- if (_THIS_IS_TURTLE_BLOCKS_) {
- var saveBox;
- }
-
- // Calculate the palette colors.
- for (var p in PALETTECOLORS) {
- PALETTEFILLCOLORS[p] = getMunsellColor(PALETTECOLORS[p][0], PALETTECOLORS[p][1], PALETTECOLORS[p][2]);
- PALETTESTROKECOLORS[p] = getMunsellColor(PALETTECOLORS[p][0], PALETTECOLORS[p][1] - 30, PALETTECOLORS[p][2]);
- PALETTEHIGHLIGHTCOLORS[p] = getMunsellColor(PALETTECOLORS[p][0], PALETTECOLORS[p][1] + 10, PALETTECOLORS[p][2]);
- HIGHLIGHTSTROKECOLORS[p] = getMunsellColor(PALETTECOLORS[p][0], PALETTECOLORS[p][1] - 50, PALETTECOLORS[p][2]);
- }
-
- pluginObjs = {
- 'PALETTEPLUGINS': {},
- 'PALETTEFILLCOLORS': {},
- 'PALETTESTROKECOLORS': {},
- 'PALETTEHIGHLIGHTCOLORS': {},
- 'FLOWPLUGINS': {},
- 'ARGPLUGINS': {},
- 'BLOCKPLUGINS': {},
- 'ONLOAD': {},
- 'ONSTART': {},
- 'ONSTOP': {}
- };
-
- // Stacks of blocks saved in local storage
- var macroDict = {};
-
- var stopTurtleContainer = null;
- var stopTurtleContainerX = 0;
- var stopTurtleContainerY = 0;
- var homeButtonContainers = [];
- var homeButtonContainersX = 0;
- var homeButtonContainersY = 0;
-
- var cameraID = null;
- var toLang = null;
- var fromLang = null;
-
- // initial scroll position
- var scrollX = 0;
- var scrollY = 0;
-
- // default values
- const DEFAULTDELAY = 500; // milleseconds
- const TURTLESTEP = -1; // Run in step-by-step mode
-
- const BLOCKSCALES = [1, 1.5, 2, 3, 4];
- var blockscale = BLOCKSCALES.indexOf(DEFAULTBLOCKSCALE);
- if (blockscale === -1) {
- blockscale = 1;
- }
-
- // Time when we hit run
- var time = 0;
-
- // Used by pause block
- var waitTime = {};
-
- // Used to track mouse state for mouse button block
- var stageMouseDown = false;
- var stageX = 0;
- var stageY = 0;
-
- var onXO = (screen.width === 1200 && screen.height === 900) || (screen.width === 900 && screen.height === 1200);
-
- var cellSize = 55;
- if (onXO) {
- cellSize = 75;
- }
-
- var onscreenButtons = [];
- var onscreenMenu = [];
- var utilityButton = null;
- var saveButton = null;
-
- var helpContainer = null;
- var helpIdx = 0;
- var firstRun = true;
-
- pluginsImages = {};
-
- // Sometimes (race condition?) Firefox does not properly
- // initialize strings in musicutils. These methods ensure that
- // the names are never null.
- console.log('initing i18n for music terms');
- initDrumI18N();
- initModeI18N();
- initVoiceI18N();
-
- window.onblur = function () {
- logo.doStopTurtle();
- };
-
- function _findBlocks() {
- logo.showBlocks();
- blocksContainer.x = 0;
- blocksContainer.y = 0;
- palettes.initial_x = 55;
- palettes.initial_y = 55;
- palettes.updatePalettes();
- var x = 100 * turtleBlocksScale;
- var y = 100 * turtleBlocksScale;
- for (var blk in blocks.blockList) {
- if (!blocks.blockList[blk].trash) {
- var myBlock = blocks.blockList[blk];
- if (myBlock.connections[0] == null) {
- var dx = x - myBlock.container.x;
- var dy = y - myBlock.container.y;
- blocks.moveBlockRelative(blk, dx, dy);
- blocks.findDragGroup(blk);
- if (blocks.dragGroup.length > 0) {
- for (var b = 0; b < blocks.dragGroup.length; b++) {
- var bblk = blocks.dragGroup[b];
- if (b !== 0) {
- blocks.moveBlockRelative(bblk, dx, dy);
- }
- }
- }
- x += 200 * turtleBlocksScale;
- if (x > (canvas.width - 100) / (turtleBlocksScale)) {
- x = 100 * turtleBlocksScale;
- y += 100 * turtleBlocksScale;
- }
- }
- }
- }
-
- // Blocks are all home, so reset go-home-button.
- homeButtonContainers[0].visible = false;
- homeButtonContainers[1].visible = true;
- boundary.hide();
- };
-
- function _allClear() {
- if (chartBitmap != null) {
- stage.removeChild(chartBitmap);
- chartBitmap = null;
- }
-
- logo.boxes = {};
- logo.time = 0;
- hideMsgs();
- logo.setBackgroundColor(-1);
- logo.lilypondOutput = LILYPONDHEADER;
- for (var turtle = 0; turtle < turtles.turtleList.length; turtle++) {
- logo.turtleHeaps[turtle] = [];
- logo.lilypondStaging[turtle] = [];
- turtles.turtleList[turtle].doClear(true, true);
- }
-
- blocksContainer.x = 0;
- blocksContainer.y = 0;
-
- // Code specific to cleaning up music blocks
- Element.prototype.remove = function () {
- this.parentElement.removeChild(this);
- };
-
- NodeList.prototype.remove = HTMLCollection.prototype.remove = function () {
- for (var i = 0, len = this.length; i < len; i++) {
- if(this[i] && this[i].parentElement) {
- this[i].parentElement.removeChild(this[i]);
- }
- }
- };
-
- var table = document.getElementById("myTable");
- if(table != null) {
- table.remove();
- }
-
- /*
- var canvas = document.getElementById("music");
- var context = canvas.getContext("2d");
- context.clearRect(0, 0, canvas.width, canvas.height);
- */
- };
-
- function _doFastButton(env) {
- var currentDelay = logo.turtleDelay;
- var playingWidget = false;
- logo.setTurtleDelay(0);
- if (_THIS_IS_MUSIC_BLOCKS_) {
- if (docById('ptmDiv').style.visibility === 'visible') {
- playingWidget = true;
- logo.pitchTimeMatrix.playAll();
- }
-
- if (docById('pscDiv').style.visibility === 'visible') {
- playingWidget = true;
- pitchstaircase.playUpAndDown();
- }
-
- if (docById('rulerDiv').style.visibility === 'visible') {
- // If the tempo widget is open, sync it up with the
- // rhythm ruler.
- if (docById('tempoDiv').style.visibility === 'visible') {
- if (tempo.isMoving) {
- tempo.pause();
- }
- tempo.resume();
- }
-
- playingWidget = true;
- rhythmruler.playAll();
- }
-
- // We were using the run button to play a widget, not
- // the turtles.
- if (playingWidget) {
- return;
- }
-
- // Restart tempo widget and run blocks.
- if (docById('tempoDiv').style.visibility === 'visible') {
- if (tempo.isMoving) {
- tempo.pause();
- }
-
- tempo.resume();
- }
- }
-
- if (!turtles.running()) {
- console.log('running');
- logo.runLogoCommands(null, env);
- } else {
- if (currentDelay !== 0) {
- // keep playing at full speep
- console.log('running from step');
- logo.step();
- } else {
- // stop and restart
- console.log('stopping...');
- logo.doStopTurtle();
-
- setTimeout(function () {
- console.log('and running');
- logo.runLogoCommands(null, env);
- }, 500);
- }
- }
- };
-
- function _doSlowButton() {
- logo.setTurtleDelay(DEFAULTDELAY);
- if (_THIS_IS_MUSIC_BLOCKS_ && docById('ptmDiv').style.visibility === 'visible') {
- logo.pitchTimeMatrix.playAll();
- } else if (!turtles.running()) {
- logo.runLogoCommands();
- } else {
- logo.step();
- }
- };
-
- function _doStepButton() {
- var turtleCount = 0;
- for (var turtle in logo.stepQueue) {
- turtleCount += 1;
- }
-
- if (turtleCount === 0 || logo.turtleDelay !== TURTLESTEP) {
- // Either we haven't set up a queue or we are
- // switching modes.
- logo.setTurtleDelay(TURTLESTEP);
- // Queue and take first step.
- if (!turtles.running()) {
- logo.runLogoCommands();
- }
- logo.step();
- } else {
- logo.setTurtleDelay(TURTLESTEP);
- logo.step();
- }
- };
-
- function _doSlowMusicButton() {
- logo.setNoteDelay(DEFAULTDELAY);
-
- if (docById('ptmDiv').style.visibility === 'visible') {
- logo.pitchTimeMatrix.playAll();
- } else if (!turtles.running()) {
- logo.runLogoCommands();
- } else {
- logo.stepNote();
- }
- };
-
- function _doStepMusicButton() {
- var turtleCount = 0;
- for (var turtle in logo.stepQueue) {
- turtleCount += 1;
- }
-
- if (turtleCount === 0 || logo.TurtleDelay !== TURTLESTEP) {
- // Either we haven't set up a queue or we are
- // switching modes.
- logo.setTurtleDelay(TURTLESTEP);
- // Queue and take first step.
- if (!turtles.running()) {
- logo.runLogoCommands();
- }
- logo.stepNote();
- } else {
- logo.setTurtleDelay(TURTLESTEP);
- logo.stepNote();
- }
- };
-
- var stopTurtle = false;
-
- function doStopButton() {
- logo.doStopTurtle();
- };
-
- var cartesianVisible = false;
-
- function _doCartesian() {
- if (cartesianVisible) {
- _hideCartesian();
- cartesianVisible = false;
- } else {
- _showCartesian();
- cartesianVisible = true;
- }
- };
-
- var polarVisible = false;
-
- function _doPolar() {
- if (polarVisible) {
- _hidePolar();
- polarVisible = false;
- } else {
- _showPolar();
- polarVisible = true;
- }
- };
-
- function toggleScroller() {
- scrollBlockContainer = !scrollBlockContainer;
- };
-
- function closeAnalytics(chartBitmap, ctx) {
- var button = this;
- button.x = (canvas.width / (2 * turtleBlocksScale)) + (300 / Math.sqrt(2));
- button.y = 300.00 - (300.00 / Math.sqrt(2));
- this.closeButton = _makeButton('cancel-button', _('Close'), button.x, button.y, 55, 0);
- this.closeButton.on('click', function (event) {
- console.log('Deleting Chart');
- button.closeButton.visible = false;
- stage.removeChild(chartBitmap);
- logo.showBlocks();
- update = true;
- ctx.clearRect(0, 0, 600, 600);
- });
- };
-
- function _isCanvasBlank(canvas) {
- var blank = document.createElement('canvas');
- blank.width = canvas.width;
- blank.height = canvas.height;
- return canvas.toDataURL() == blank.toDataURL();
- };
-
- function doAnalytics() {
- var myChart = docById('myChart');
-
- if(_isCanvasBlank(myChart) == false) {
- return ;
- }
-
- var ctx = myChart.getContext('2d');
- document.body.style.cursor = 'wait';
- var myRadarChart = null;
- var scores = analyzeProject(blocks);
- console.log(scores);
- var data = scoreToChartData(scores);
- var Analytics = this;
- Analytics.close = closeAnalytics;
-
- var __callback = function () {
- var imageData = myRadarChart.toBase64Image();
- var img = new Image();
- img.onload = function () {
- var chartBitmap = new createjs.Bitmap(img);
- stage.addChild(chartBitmap);
- chartBitmap.x = (canvas.width / (2 * turtleBlocksScale)) - (300);
- chartBitmap.y = 0;
- chartBitmap.scaleX = chartBitmap.scaleY = chartBitmap.scale = 600 / chartBitmap.image.width;
- logo.hideBlocks();
- update = true;
- document.body.style.cursor = 'default';
- Analytics.close(chartBitmap, ctx);
- };
- img.src = imageData;
- };
-
- var options = getChartOptions(__callback);
- console.log('creating new chart');
- myRadarChart = new Chart(ctx).Radar(data, options);
- };
-
- function doBiggerFont() {
- if (blockscale < BLOCKSCALES.length - 1) {
- blockscale += 1;
- blocks.setBlockScale(BLOCKSCALES[blockscale]);
- }
- };
-
- function doSmallerFont() {
- if (blockscale > 0) {
- blockscale -= 1;
- blocks.setBlockScale(BLOCKSCALES[blockscale]);
- }
- };
-
- // Do we need to update the stage?
- var update = true;
-
- // The dictionary of action name: block
- var actions = {};
-
- // The dictionary of box name: value
- var boxes = {};
-
- // Coordinate grid
- var cartesianBitmap = null;
-
- // Polar grid
- var polarBitmap = null;
-
- // Msg block
- var msgText = null;
-
- // ErrorMsg block
- var errorMsgText = null;
- var errorMsgArrow = null;
- var errorArtwork = {};
- const ERRORARTWORK = ['emptybox', 'emptyheap', 'negroot', 'noinput', 'zerodivide', 'notanumber', 'nostack', 'notastring', 'nomicrophone'];
-
- // Get things started
- init();
-
- function init() {
- docById('loader').className = 'loader';
-
- stage = new createjs.Stage(canvas);
- createjs.Touch.enable(stage);
-
- createjs.Ticker.timingMode = createjs.Ticker.RAF_SYNCHED;
- createjs.Ticker.setFPS(30);
- createjs.Ticker.addEventListener('tick', stage);
- createjs.Ticker.addEventListener('tick', __tick);
-
- _createMsgContainer('#ffffff', '#7a7a7a', function (text) {
- msgText = text;
- }, 55);
-
- _createMsgContainer('#ffcbc4', '#ff0031', function (text) {
- errorMsgText = text;
- }, 110);
-
- _createErrorContainers();
-
- /* Z-Order (top to bottom):
- * menus
- * palettes
- * blocks
- * trash
- * turtles
- * logo (drawing)
- */
- palettesContainer = new createjs.Container();
- blocksContainer = new createjs.Container();
- trashContainer = new createjs.Container();
- turtleContainer = new createjs.Container();
-
- stage.addChild(turtleContainer, trashContainer, blocksContainer, palettesContainer);
- _setupBlocksContainerEvents();
-
- trashcan = new Trashcan();
- trashcan
- .setCanvas(canvas)
- .setStage(trashContainer)
- .setSize(cellSize)
- .setRefreshCanvas(refreshCanvas)
- .init();
-
- turtles = new Turtles();
- turtles
- .setCanvas(canvas)
- .setStage(turtleContainer)
- .setRefreshCanvas(refreshCanvas);
-
- // Put the boundary in the blocks container so it scrolls
- // with the blocks.
- boundary = new Boundary();
- boundary
- .setStage(blocksContainer)
- .init();
-
- blocks = new Blocks();
- blocks
- .setCanvas(canvas)
- .setStage(blocksContainer)
- .setRefreshCanvas(refreshCanvas)
- .setTrashcan(trashcan)
- .setUpdateStage(stage.update)
- .setGetStageScale(getStageScale)
- .setTurtles(turtles)
- .setErrorMsg(errorMsg);
- blocks.makeCopyPasteButtons(_makeButton, updatePasteButton);
-
- turtles.setBlocks(blocks);
-
- palettes = new Palettes();
- palettes
- .setCanvas(canvas)
- .setStage(palettesContainer)
- .setRefreshCanvas(refreshCanvas)
- .setSize(cellSize)
- .setTrashcan(trashcan)
- .setBlocks(blocks)
- .init();
-
- initPalettes(palettes);
-
- logo = new Logo();
- logo
- .setCanvas(canvas)
- .setBlocks(blocks)
- .setTurtles(turtles)
- .setStage(turtleContainer)
- .setRefreshCanvas(refreshCanvas)
- .setTextMsg(textMsg)
- .setErrorMsg(errorMsg)
- .setHideMsgs(hideMsgs)
- .setOnStopTurtle(onStopTurtle)
- .setOnRunTurtle(onRunTurtle)
- .setGetStageX(getStageX)
- .setGetStageY(getStageY)
- .setGetStageMouseDown(getStageMouseDown)
- .setGetCurrentKeyCode(getCurrentKeyCode)
- .setClearCurrentKeyCode(clearCurrentKeyCode)
- .setMeSpeak(meSpeak)
- .setSaveLocally(saveLocally);
-
- blocks.setLogo(logo);
-
- // Set the default background color...
- logo.setBackgroundColor(-1);
-
- clearBox = new ClearBox();
- clearBox
- .setCanvas(canvas)
- .setStage(stage)
- .setRefreshCanvas(refreshCanvas)
- .setClear(sendAllToTrash);
-
- if (_THIS_IS_TURTLE_BLOCKS_) {
- saveBox = new SaveBox();
- saveBox
- .setCanvas(canvas)
- .setStage(stage)
- .setRefreshCanvas(refreshCanvas)
- .setSaveTB(doSaveTB)
- .setSaveSVG(doSaveSVG)
- .setSavePNG(doSavePNG)
- .setSavePlanet(doUploadToPlanet)
- .setSaveFB(doShareOnFacebook);
- }
-
- utilityBox = new UtilityBox();
- utilityBox
- .setStage(stage)
- .setRefreshCanvas(refreshCanvas)
- .setBigger(doBiggerFont)
- .setSmaller(doSmallerFont)
- .setPlugins(doOpenPlugin)
- .setStats(doAnalytics)
- .setScroller(toggleScroller);
-
- thumbnails = new SamplesViewer();
- thumbnails
- .setStage(stage)
- .setRefreshCanvas(refreshCanvas)
- .setClear(sendAllToTrash)
- .setLoad(loadProject)
- .setLoadRaw(loadRawProject)
- .init();
-
- initBasicProtoBlocks(palettes, blocks);
-
- // Load any macros saved in local storage.
- macroData = storage.macros;
- if (macroData != null) {
- processMacroData(macroData, palettes, blocks, macroDict);
- }
-
- // Blocks and palettes need access to the macros dictionary.
- blocks.setMacroDictionary(macroDict);
- palettes.setMacroDictionary(macroDict);
-
- // Load any plugins saved in local storage.
- pluginData = storage.plugins;
- if (pluginData != null) {
- var obj = processPluginData(pluginData, palettes, blocks, logo.evalFlowDict, logo.evalArgDict, logo.evalParameterDict, logo.evalSetterDict, logo.evalOnStartList, logo.evalOnStopList);
- updatePluginObj(obj);
- }
-
- // Load custom mode saved in local storage.
- var custommodeData = storage.custommode;
- if (custommodeData != undefined) {
- customMode = JSON.parse(custommodeData);
- console.log('restoring custom mode: ' + customMode);
- }
-
- fileChooser.addEventListener('click', function (event) {
- this.value = null;
- });
-
- fileChooser.addEventListener('change', function (event) {
- // Read file here.
- var reader = new FileReader();
-
- reader.onload = (function (theFile) {
- // Show busy cursor.
- document.body.style.cursor = 'wait';
- setTimeout(function () {
- var rawData = reader.result;
- var cleanData = rawData.replace('\n', ' ');
- var obj = JSON.parse(cleanData);
- // First, hide the palettes as they will need updating.
- for (var name in blocks.palettes.dict) {
- blocks.palettes.dict[name].hideMenu(true);
- }
-
- refreshCanvas();
-
- blocks.loadNewBlocks(obj);
- // Restore default cursor.
- document.body.style.cursor = 'default';
- }, 200);
- });
-
- reader.readAsText(fileChooser.files[0]);
- }, false);
-
- allFilesChooser.addEventListener('click', function (event) {
- this.value = null;
- });
-
- pluginChooser.addEventListener('click', function (event) {
- window.scroll(0, 0);
- this.value = null;
- });
-
- pluginChooser.addEventListener('change', function (event) {
- window.scroll(0, 0);
-
- // Read file here.
- var reader = new FileReader();
-
- reader.onload = (function (theFile) {
- // Show busy cursor.
- document.body.style.cursor = 'wait';
- setTimeout(function () {
- obj = processRawPluginData(reader.result, palettes, blocks, errorMsg, logo.evalFlowDict, logo.evalArgDict, logo.evalParameterDict, logo.evalSetterDict, logo.evalOnStartList, logo.evalOnStopList);
- // Save plugins to local storage.
- if (obj != null) {
- var pluginObj = preparePluginExports(obj);
- console.log(pluginObj);
- storage.plugins = pluginObj; // preparePluginExports(obj));
- }
-
- // Refresh the palettes.
- setTimeout(function () {
- if (palettes.visible) {
- palettes.hide();
- }
- palettes.show();
- palettes.bringToTop();
- }, 1000);
-
- // Restore default cursor.
- document.body.style.cursor = 'default';
- }, 200);
- });
-
- reader.readAsText(pluginChooser.files[0]);
- }, false);
-
- // Workaround to chrome security issues
- // createjs.LoadQueue(true, null, true);
-
- // Enable touch interactions if supported on the current device.
- // FIXME: voodoo
- // createjs.Touch.enable(stage, false, true);
- // Keep tracking the mouse even when it leaves the canvas.
- stage.mouseMoveOutside = true;
- // Enabled mouse over and mouse out events.
- stage.enableMouseOver(10); // default is 20
-
- cartesianBitmap = _createGrid('images/Cartesian.svg');
-
- polarBitmap = _createGrid('images/polar.svg');
-
- var URL = window.location.href;
- var projectName = null;
- var runProjectOnLoad = false;
-
- _setupAndroidToolbar();
-
- // Scale the canvas relative to the screen size.
- _onResize();
-
- var urlParts;
- var env = [];
-
- if (!sugarizerCompatibility.isInsideSugarizer() && URL.indexOf('?') > 0) {
- var urlParts = URL.split('?');
- if (urlParts[1].indexOf('&') > 0) {
- var newUrlParts = urlParts[1].split('&');
- for (var i = 0; i < newUrlParts.length; i++) {
- if (newUrlParts[i].indexOf('=') > 0) {
- var args = newUrlParts[i].split('=');
- switch (args[0].toLowerCase()) {
- case 'file':
- projectName = args[1];
- break;
- case 'run':
- if (args[1].toLowerCase() === 'true')
- runProjectOnLoad = true;
- break;
- case 'inurl':
- var url = args[1];
- var getJSON = function (url) {
- return new Promise(function (resolve, reject) {
- var xhr = new XMLHttpRequest();
- xhr.open('get', url, true);
- xhr.responseType = 'json';
- xhr.onload = function () {
- var status = xhr.status;
- if (status === 200) {
- resolve(xhr.response);
- } else {
- reject(status);
- }
- };
- xhr.send();
- });
- };
- getJSON(url).then(function (data) {
- console.log('Your Json result is: ' + data.arg); //you can comment this, i used it to debug
- n = data.arg;
- env.push(parseInt(n));
- }, function (status) { //error detection....
- alert('Something went wrong.');
- });
- break;
- case 'outurl':
- var url = args[1];
- break;
- default:
- errorMsg("Invalid parameters");
- }
- }
- }
- } else {
- if (urlParts[1].indexOf('=') > 0)
- var args = urlParts[1].split('=');
- //File is the only arg that can stand alone
- if (args[0].toLowerCase() === 'file') {
- projectName = args[1];
- }
- }
- }
-
- if (projectName != null) {
- setTimeout(function () {
- console.log('loading ' + projectName);
- loadStartWrapper(loadProject, projectName, runProjectOnLoad, env);
- }, 2000);
- } else {
- setTimeout(function () {
- loadStartWrapper(_loadStart);
- }, 2000);
- }
-
- document.addEventListener('mousewheel', scrollEvent, false);
- document.addEventListener('DOMMouseScroll', scrollEvent, false);
-
- this.document.onkeydown = __keyPressed;
- _hideStopButton();
-
- };
-
- function _setupBlocksContainerEvents() {
- var moving = false;
-
- stage.on('stagemousemove', function (event) {
- stageX = event.stageX;
- stageY = event.stageY;
- });
-
- stage.on('stagemousedown', function (event) {
- stageMouseDown = true;
- if (stage.getObjectUnderPoint() != null | turtles.running()) {
- stage.on('stagemouseup', function (event) {
- stageMouseDown = false;
- });
- return;
- }
- moving = true;
- lastCords = {
- x: event.stageX,
- y: event.stageY
- };
-
- stage.on('stagemousemove', function (event) {
- if (!moving) {
- return;
- }
- if (blocks.inLongPress) {
- blocks.saveStackButton.visible = false;
- blocks.dismissButton.visible = false;
- blocks.inLongPress = false;
- }
- if (scrollBlockContainer) {
- blocksContainer.x += event.stageX - lastCords.x;
- blocksContainer.y += event.stageY - lastCords.y;
- lastCords = {
- x: event.stageX,
- y: event.stageY
- };
- refreshCanvas();
- }
- });
-
- stage.on('stagemouseup', function (event) {
- stageMouseDown = false;
- moving = false;
- }, null, true); // once = true
- });
- };
-
- function scrollEvent(event) {
- var data = event.wheelDelta || -event.detail;
- var delta = Math.max(-1, Math.min(1, (data)));
- var scrollSpeed = 30;
-
- if (event.clientX < cellSize) {
- palettes.menuScrollEvent(delta, scrollSpeed);
- palettes.hidePaletteIconCircles();
- } else {
- palette = palettes.findPalette(event.clientX / turtleBlocksScale, event.clientY / turtleBlocksScale);
- if (palette) {
- palette.scrollEvent(delta, scrollSpeed);
- }
- }
- };
-
- function getStageScale() {
- return turtleBlocksScale;
- };
-
- function getStageX() {
- return turtles.screenX2turtleX(stageX / turtleBlocksScale);
- };
-
- function getStageY() {
- return turtles.screenY2turtleY(stageY / turtleBlocksScale);
- };
-
- function getStageMouseDown() {
- return stageMouseDown;
- };
-
- function setCameraID(id) {
- cameraID = id;
- };
-
- function _createGrid(imagePath) {
- var img = new Image();
- img.src = imagePath;
- var container = new createjs.Container();
- stage.addChild(container);
-
- var bitmap = new createjs.Bitmap(img);
- container.addChild(bitmap);
- bitmap.cache(0, 0, 1200, 900);
-
- bitmap.x = (canvas.width - 1200) / 2;
- bitmap.y = (canvas.height - 900) / 2;
- bitmap.scaleX = bitmap.scaleY = bitmap.scale = 1;
- bitmap.visible = false;
- bitmap.updateCache();
-
- return bitmap;
- };
-
- function _createMsgContainer(fillColor, strokeColor, callback, y) {
- var container = new createjs.Container();
- stage.addChild(container);
- container.x = (canvas.width - 1000) / 2;
- container.y = y;
- container.visible = false;
-
- var img = new Image();
- var svgData = MSGBLOCK.replace('fill_color', fillColor).replace(
- 'stroke_color', strokeColor);
-
- img.onload = function () {
- var msgBlock = new createjs.Bitmap(img);
- container.addChild(msgBlock);
- var text = new createjs.Text('your message here', '20px Arial', '#000000');
- container.addChild(text);
- text.textAlign = 'center';
- text.textBaseline = 'alphabetic';
- text.x = 500;
- text.y = 30;
-
- var bounds = container.getBounds();
- container.cache(bounds.x, bounds.y, bounds.width, bounds.height);
-
- var hitArea = new createjs.Shape();
- hitArea.graphics.beginFill('#FFF').drawRect(0, 0, 1000, 42);
- hitArea.x = 0;
- hitArea.y = 0;
- container.hitArea = hitArea;
-
- container.on('click', function (event) {
- container.visible = false;
- // On the possibility that there was an error
- // arrow associated with this container
- if (errorMsgArrow != null) {
- errorMsgArrow.removeAllChildren(); // Hide the error arrow.
- }
- update = true;
- });
- callback(text);
- blocks.setMsgText(text);
- };
-
- img.src = 'data:image/svg+xml;base64,' + window.btoa(
- unescape(encodeURIComponent(svgData)));
- };
-
- function _createErrorContainers() {
- // Some error messages have special artwork.
- for (var i = 0; i < ERRORARTWORK.length; i++) {
- var name = ERRORARTWORK[i];
- _makeErrorArtwork(name);
- }
- };
-
- function _makeErrorArtwork(name) {
- var container = new createjs.Container();
- stage.addChild(container);
- container.x = (canvas.width - 1000) / 2;
- container.y = 110;
- errorArtwork[name] = container;
- errorArtwork[name].name = name;
- errorArtwork[name].visible = false;
-
- var img = new Image();
- img.onload = function () {
- // console.log('creating error message artwork for ' + img.src);
- var artwork = new createjs.Bitmap(img);
- container.addChild(artwork);
- var text = new createjs.Text('', '20px Sans', '#000000');
- container.addChild(text);
- text.x = 70;
- text.y = 10;
-
- var bounds = container.getBounds();
- container.cache(bounds.x, bounds.y, bounds.width, bounds.height);
-
- var hitArea = new createjs.Shape();
- hitArea.graphics.beginFill('#FFF').drawRect(0, 0, bounds.width, bounds.height);
- hitArea.x = 0;
- hitArea.y = 0;
- container.hitArea = hitArea;
-
- container.on('click', function (event) {
- container.visible = false;
- // On the possibility that there was an error
- // arrow associated with this container
- if (errorMsgArrow != null) {
- errorMsgArrow.removeAllChildren(); // Hide the error arrow.
- }
- update = true;
- });
- };
-
- img.src = 'images/' + name + '.svg';
- };
-
- function __keyPressed(event) {
- if (docById('labelDiv').classList.contains('hasKeyboard')) {
- return;
- }
-
- if (_THIS_IS_MUSIC_BLOCKS_) {
- if (docById('BPMInput').classList.contains('hasKeyboard')) {
- return;
- }
-
- if (docById('musicratio1').classList.contains('hasKeyboard')) {
- return;
- }
-
- if (docById('musicratio2').classList.contains('hasKeyboard')) {
- return;
- }
-
- if (docById('dissectNumber').classList.contains('hasKeyboard')) {
- return;
- }
- }
-
- const BACKSPACE = 8;
- const TAB = 9;
- if (event.keyCode === TAB || event.keyCode === BACKSPACE) {
- // Prevent browser from grabbing TAB key
- event.preventDefault();
- }
-
- const ESC = 27;
- const ALT = 18;
- const CTRL = 17;
- const SHIFT = 16;
- const RETURN = 13;
- const SPACE = 32;
- const HOME = 36;
- const PAGE_UP = 33;
- const PAGE_DOWN = 34;
- const KEYCODE_LEFT = 37;
- const KEYCODE_RIGHT = 39;
- const KEYCODE_UP = 38;
- const KEYCODE_DOWN = 40;
-
- if (event.altKey) {
- switch (event.keyCode) {
- case 69: // 'E'
- _allClear();
- break;
- case 82: // 'R'
- _doFastButton();
- break;
- case 83: // 'S'
- logo.doStopTurtle();
- break;
- }
- } else if (event.ctrlKey) {
- } else {
- switch (event.keyCode) {
- case KEYCODE_UP:
- if (blocks.activeBlock != null) {
- blocks.moveStackRelative(blocks.activeBlock, 0, -STANDARDBLOCKHEIGHT / 2);
- blocks.blockMoved(blocks.activeBlock);
- blocks.adjustDocks(blocks.activeBlock, true);
- } else if (palettes.mouseOver) {
- palettes.menuScrollEvent(1, 10);
- palettes.hidePaletteIconCircles();
- } else if (palettes.activePalette != null) {
- palettes.activePalette.scrollEvent(STANDARDBLOCKHEIGHT, 1);
- } else if (scrollBlockContainer) {
- blocksContainer.y -= 21;
- }
- break;
- case KEYCODE_DOWN:
- if (blocks.activeBlock != null) {
- blocks.moveStackRelative(blocks.activeBlock, 0, STANDARDBLOCKHEIGHT / 2);
- blocks.blockMoved(blocks.activeBlock);
- blocks.adjustDocks(blocks.activeBlock, true);
- } else if (palettes.mouseOver) {
- palettes.menuScrollEvent(-1, 10);
- palettes.hidePaletteIconCircles();
- } else if (palettes.activePalette != null) {
- palettes.activePalette.scrollEvent(-STANDARDBLOCKHEIGHT, 1);
- } else if (scrollBlockContainer) {
- blocksContainer.y += 21;
- }
- break;
- case KEYCODE_LEFT:
- if (blocks.activeBlock != null) {
- blocks.moveStackRelative(blocks.activeBlock, -STANDARDBLOCKHEIGHT / 2, 0);
- blocks.blockMoved(blocks.activeBlock);
- blocks.adjustDocks(blocks.activeBlock, true);
- } else if (scrollBlockContainer) {
- blocksContainer.x -= 21;
- }
- break;
- case KEYCODE_RIGHT:
- if (blocks.activeBlock != null) {
- blocks.moveStackRelative(blocks.activeBlock, STANDARDBLOCKHEIGHT / 2, 0);
- blocks.blockMoved(blocks.activeBlock);
- blocks.adjustDocks(blocks.activeBlock, true);
- } else if (scrollBlockContainer) {
- blocksContainer.x += 21;
- }
- break;
- case HOME:
- if (palettes.mouseOver) {
- var dy = Math.max(55 - palettes.buttons['rhythm'].y, 0);
- palettes.menuScrollEvent(1, dy);
- palettes.hidePaletteIconCircles();
- } else if (palettes.activePalette != null) {
- palettes.activePalette.scrollEvent(-palettes.activePalette.scrollDiff, 1);
- } else {
- _findBlocks();
- }
- break;
- case TAB:
- break;
- case ESC:
- // toggle full screen
- _toggleToolbar();
- break;
- case RETURN:
- // toggle run
- logo.runLogoCommands();
- break;
- default:
- // currentKey = String.fromCharCode(event.keyCode);
- // currentKeyCode = event.keyCode;
- break;
- }
- // Always store current key so as not to mask it from
- // the keyboard block.
- currentKey = String.fromCharCode(event.keyCode);
- currentKeyCode = event.keyCode;
- }
- };
-
- function getCurrentKeyCode() {
- return currentKeyCode;
- };
-
- function clearCurrentKeyCode() {
- currentKey = '';
- currentKeyCode = 0;
- };
-
- function _onResize() {
- if (docById('labelDiv').classList.contains('hasKeyboard')) {
- return;
- }
-
- if (!platform.androidWebkit) {
- var w = window.innerWidth;
- var h = window.innerHeight;
- } else {
- var w = window.outerWidth;
- var h = window.outerHeight;
- }
-
- var smallSide = Math.min(w, h);
-
- if (smallSide < cellSize * 11) {
- var mobileSize = true;
- if (w < cellSize * 10) {
- turtleBlocksScale = smallSide / (cellSize * 11);
- } else {
- turtleBlocksScale = Math.max(smallSide / (cellSize * 11), 0.75);
- }
- } else {
- var mobileSize = false;
- if (w / 1200 > h / 900) {
- turtleBlocksScale = w / 1200;
- } else {
- turtleBlocksScale = h / 900;
- }
- }
-
- stage.scaleX = turtleBlocksScale;
- stage.scaleY = turtleBlocksScale;
-
- stage.canvas.width = w;
- stage.canvas.height = h;
-
- /*
- console.log('Resize: scale ' + turtleBlocksScale +
- ', windowW ' + w + ', windowH ' + h +
- ', canvasW ' + canvas.width + ', canvasH ' + canvas.height +
- ', screenW ' + screen.width + ', screenH ' + screen.height);
- */
- turtles.setScale(turtleBlocksScale);
- blocks.setScale(turtleBlocksScale);
- boundary.setScale(w, h, turtleBlocksScale);
- palettes.setScale(turtleBlocksScale);
- trashcan.resizeEvent(turtleBlocksScale);
- _setupAndroidToolbar(mobileSize);
-
- // Reposition coordinate grids.
- cartesianBitmap.x = (canvas.width / (2 * turtleBlocksScale)) - (600);
- cartesianBitmap.y = (canvas.height / (2 * turtleBlocksScale)) - (450);
- polarBitmap.x = (canvas.width / (2 * turtleBlocksScale)) - (600);
- polarBitmap.y = (canvas.height / (2 * turtleBlocksScale)) - (450);
- update = true;
-
- // Setup help now that we have calculated turtleBlocksScale.
- _showHelp(true);
-
- // Hide palette icons on mobile
- if (mobileSize) {
- palettes.setMobile(true);
- palettes.hide();
- } else {
- palettes.setMobile(false);
- palettes.show();
- palettes.bringToTop();
- }
-
- for (var turtle = 0; turtle < turtles.turtleList.length; turtle++) {
- turtles.turtleList[turtle].doClear(false, false);
- }
-
- var artcanvas = document.getElementById("overlayCanvas");
- artcanvas.width = w;
- artcanvas.height = h;
- };
-
- window.onresize = function () {
- _onResize();
- };
-
- function _restoreTrash() {
- // Restore last stack pushed to trashStack.
- // First, hide the palettes as they will need updating.
- for (var name in blocks.palettes.dict) {
- blocks.palettes.dict[name].hideMenu(true);
- }
- refreshCanvas();
-
- var dx = 0;
- var dy = -cellSize * 3; // Reposition blocks about trash area.
-
- if (blocks.trashStacks.length === 0) {
- console.log('Trash is empty--nothing to do');
- return;
- }
-
- var thisBlock = blocks.trashStacks.pop();
-
- // Restore drag group in trash
- blocks.findDragGroup(thisBlock);
- for (var b = 0; b < blocks.dragGroup.length; b++) {
- var blk = blocks.dragGroup[b];
- // console.log('Restoring ' + blocks.blockList[blk].name + ' from the trash.');
- blocks.blockList[blk].trash = false;
- blocks.moveBlockRelative(blk, dx, dy);
- blocks.blockList[blk].show();
- }
-
- blocks.raiseStackToTop(thisBlock);
-
- if (blocks.blockList[thisBlock].name === 'start' || blocks.blockList[thisBlock].name === 'drum') {
- var turtle = blocks.blockList[thisBlock].value;
- turtles.turtleList[turtle].trash = false;
- turtles.turtleList[turtle].container.visible = true;
- } else if (blocks.blockList[thisBlock].name === 'action') {
- // We need to add a palette entry for this action.
- // But first we need to ensure we have a unqiue name,
- // as the name could have been taken in the interim.
- var actionArg = blocks.blockList[blocks.blockList[thisBlock].connections[1]];
- if (actionArg != null) {
- var oldName = actionArg.value;
- // Mark the action block as still being in the
- // trash so that its name won't be considered when
- // looking for a unique name.
- blocks.blockList[thisBlock].trash = true;
- var uniqueName = blocks.findUniqueActionName(oldName);
- blocks.blockList[thisBlock].trash = false;
-
- if (uniqueName !== actionArg) {
- console.log('renaming action when restoring from trash. old name: ' + oldName + ' unique name: ' + uniqueName);
-
- actionArg.value = uniqueName;
-
- var label = actionArg.value.toString();
- if (label.length > 8) {
- label = label.substr(0, 7) + '...';
- }
- actionArg.text.text = label;
-
- if (actionArg.label != null) {
- actionArg.label.value = uniqueName;
- }
-
- actionArg.container.updateCache();
-
- // Check the drag group to ensure any do
- // blocks are updated (in case of recursion).
- for (var b = 0; b < blocks.dragGroup.length; b++) {
- var me = blocks.blockList[blocks.dragGroup[b]];
- if (['nameddo', 'nameddoArg', 'namedcalc', 'namedcalcArg'].indexOf(me.name) !== -1 && me.privateData === oldName) {
- console.log('reassigning nameddo to ' + uniqueName);
- me.privateData = uniqueName;
- me.value = uniqueName;
-
- var label = me.value.toString();
- if (label.length > 8) {
- label = label.substr(0, 7) + '...';
- }
- me.text.text = label;
- me.overrideName = label;
- me.regenerateArtwork();
- me.container.updateCache();
- }
- }
- }
-
- var actionName = actionArg.value;
- if (actionName !== _('action')) {
- // blocks.checkPaletteEntries('action');
- console.log('FIXME: Check for unique action name here');
- }
- }
- }
-
- blocks.refreshCanvas();
- };
-
- function _deleteBlocksBox() {
- clearBox.show(turtleBlocksScale);
- };
-
- function _doUtilityBox() {
- utilityBox.init(turtleBlocksScale, utilityButton.x - 27, utilityButton.y, _makeButton);
- };
-
- function sendAllToTrash(addStartBlock, doNotSave) {
- // First, hide the palettes as they will need updating.
- for (var name in blocks.palettes.dict) {
- blocks.palettes.dict[name].hideMenu(true);
- }
- refreshCanvas();
-
- var dx = 0;
- var dy = cellSize * 3;
- for (var blk in blocks.blockList) {
- // If this block is at the top of a stack, push it
- // onto the trashStacks list.
- if (blocks.blockList[blk].connections[0] == null) {
- blocks.trashStacks.push(blk);
- }
-
- if (blocks.blockList[blk].name === 'start' || blocks.blockList[blk].name === 'drum') {
- console.log('start blk ' + blk + ' value is ' + blocks.blockList[blk].value)
- var turtle = blocks.blockList[blk].value;
- if (!blocks.blockList[blk].trash && turtle != null) {
- console.log('sending turtle ' + turtle + ' to trash');
- turtles.turtleList[turtle].trash = true;
- turtles.turtleList[turtle].container.visible = false;
- }
- } else if (blocks.blockList[blk].name === 'action') {
- if (!blocks.blockList[blk].trash) {
- blocks.deleteActionBlock(blocks.blockList[blk]);
- }
- }
-
- blocks.blockList[blk].trash = true;
- blocks.moveBlockRelative(blk, dx, dy);
- blocks.blockList[blk].hide();
- }
-
- if (addStartBlock) {
- blocks.loadNewBlocks(DATAOBJS);
- } else if (!doNotSave) {
- // Overwrite session data too.
- saveLocally();
- }
-
- update = true;
- };
-
- function _changePaletteVisibility() {
- if (palettes.visible) {
- palettes.hide();
- } else {
- palettes.show();
- palettes.bringToTop();
- }
- };
-
- function _changeBlockVisibility() {
- if (blocks.visible) {
- logo.hideBlocks();
- palettes.hide();
- } else {
- if (chartBitmap != null) {
- stage.removeChild(chartBitmap);
- chartBitmap = null;
- }
- logo.showBlocks();
- palettes.show();
- palettes.bringToTop();
- }
-
- // Combine block and palette visibility into one button.
- // _changePaletteVisibility();
- };
-
- function _toggleCollapsibleStacks() {
- if (blocks.visible) {
- console.log('calling toggleCollapsibles');
- blocks.toggleCollapsibles();
- }
- };
-
- function onStopTurtle() {
- // TODO: plugin support
- if (stopTurtleContainer.visible) {
- _hideStopButton();
- }
- };
-
- function onRunTurtle() {
- // TODO: plugin support
- // If the stop button is hidden, show it.
- if (!stopTurtleContainer.visible) {
- _showStopButton();
- }
- };
-
- function refreshCanvas() {
- update = true;
- };
-
- function __tick(event) {
- // This set makes it so the stage only re-renders when an
- // event handler indicates a change has happened.
- if (update) {
- update = false; // Only update once
- stage.update(event);
- }
- };
-
- function _doOpenSamples() {
- if (_THIS_IS_MUSIC_BLOCKS_) {
- localStorage.setItem('isMatrixHidden', docById('ptmDiv').style.visibility);
- localStorage.setItem('isStaircaseHidden', docById('pscDiv').style.visibility);
- localStorage.setItem('isPitchDrumMatrixHidden', docById('pdmDiv').style.visibility);
- localStorage.setItem('isRhythmRulerHidden', docById('rulerDiv').style.visibility);
- localStorage.setItem('isModeWidgetHidden', docById('modeDiv').style.visibility);
- localStorage.setItem('isSliderHidden', docById('sliderDiv').style.visibility);
- localStorage.setItem('isTempoHidden', docById('tempoDiv').style.visibility);
-
- if (docById('ptmDiv').style.visibility !== 'hidden') {
- docById('ptmDiv').style.visibility = 'hidden';
- docById('ptmTableDiv').style.visibility = 'hidden';
- docById('ptmButtonsDiv').style.visibility = 'hidden';
- }
-
- if (docById('pdmDiv').style.visibility !== 'hidden') {
- docById('pdmDiv').style.visibility = 'hidden';
- docById('pdmButtonsDiv').style.visibility = 'hidden';
- docById('pdmTableDiv').style.visibility = 'hidden';
- }
-
- if (docById('rulerDiv').style.visibility !== 'hidden') {
- docById('rulerDiv').style.visibility = 'hidden';
- docById('rulerTableDiv').style.visibility = 'hidden';
- docById('rulerButtonsDiv').style.visibility = 'hidden';
- }
-
- if (docById('pscDiv').style.visibility !== 'hidden') {
- docById('pscDiv').style.visibility = 'hidden';
- docById('pscTableDiv').style.visibility = 'hidden';
- docById('pscButtonsDiv').style.visibility = 'hidden';
- }
-
- if (docById('statusDiv').style.visibility !== 'hidden') {
- docById('statusDiv').style.visibility = 'hidden';
- docById('statusButtonsDiv').style.visibility = 'hidden';
- docById('statusTableDiv').style.visibility = 'hidden';
- }
-
- if (docById('sliderDiv').style.visibility !== 'hidden') {
- docById('sliderDiv').style.visibility = 'hidden';
- docById('sliderButtonsDiv').style.visibility = 'hidden';
- docById('sliderTableDiv').style.visibility = 'hidden';
- }
-
- if (docById('modeDiv').style.visibility !== 'hidden') {
- docById('modeDiv').style.visibility = 'hidden';
- docById('modeButtonsDiv').style.visibility = 'hidden';
- docById('modeTableDiv').style.visibility = 'hidden';
- }
-
- if (docById('tempoDiv').style.visibility !== 'hidden') {
- if (logo.tempo != null) {
- logo.tempo.hide();
- }
- }
- }
-
- localStorage.setItem('isStatusHidden', docById('statusDiv').style.visibility);
-
- logo.doStopTurtle();
- helpContainer.visible = false;
- docById('helpElem').style.visibility = 'hidden';
- console.log('save locally');
- saveLocally();
- thumbnails.show()
- };
-
- function doSave() {
- if (_THIS_IS_MUSIC_BLOCKS_) {
- console.log('Saving .tb file');
- var name = 'My Project';
- download(name + '.tb', 'data:text/plain;charset=utf-8,' + prepareExport());
- } else {
- saveBox.init(turtleBlocksScale, saveButton.x - 27, saveButton.y - 97, _makeButton);
- }
- };
-
- function doSaveTB() {
- var filename = prompt('Filename:', 'untitled.tb'); // default filename = untitled
- if (filename != null) {
- if (fileExt(filename) !== 'tb') {
- filename += '.tb';
- }
- download(filename, 'data:text/plain;charset=utf-8,' + encodeURIComponent(prepareExport()));
- }
- };
-
- function doSaveSVG() {
- var filename = prompt('Filename:', 'untitled.svg');
- if (filename != null) {
- if (fileExt(filename) !== 'svg') {
- filename += '.svg';
- }
- var svg = doSVG(logo.canvas, logo, logo.turtles, logo.canvas.width, logo.canvas.height, 1.0);
- download(filename, 'data:image/svg+xml;utf8,' + svg, filename, '"width=' + logo.canvas.width + ', height=' + logo.canvas.height + '"');
- }
- };
-
- function doSavePNG() {
- alert("Unavailable at the moment");
- //var filename = prompt('Filename:', 'untitled.png');
- //if (fileExt(filename) !== 'png') {
- // filename += '.png';
- //}
- //download(filename, 'data:text/plain;charset=utf-8,' + encodeURIComponent(prepareExport()));
- };
-
- function doUploadToPlanet() {
- saveLocally();
- thumbnails.show()
- };
-
- function doShareOnFacebook() {
- alert("Facebook Sharing : disabled"); // remove when add fb share link
- // add code for facebook share link
- };
-
- function doLoad() {
- console.log('Loading .tb file');
- document.querySelector('#myOpenFile').focus();
- document.querySelector('#myOpenFile').click();
- window.scroll(0, 0);
- };
-
- function _doLilypond() {
- // Show busy cursor.
- document.body.style.cursor = 'wait';
-
- console.log('Saving .ly file');
- // Suppress music and turtle output when generating
- // Lilypond output.
- logo.runningLilypond = true;
- logo.lilypondOutput = LILYPONDHEADER;
- logo.lilypondNotes = {};
- for (var turtle = 0; turtle < turtles.turtleList.length; turtle++) {
- logo.lilypondStaging[turtle] = [];
- turtles.turtleList[turtle].doClear(true, true);
- }
- logo.runLogoCommands();
- };
-
- window.prepareExport = prepareExport;
- window.saveLocally = saveLocally;
-
- function saveLocally() {
- if (sugarizerCompatibility.isInsideSugarizer()) {
- //sugarizerCompatibility.data.blocks = prepareExport();
- storage = sugarizerCompatibility.data;
- } else {
- storage = localStorage;
- }
-
- console.log('overwriting session data');
-
- if (storage.currentProject === undefined) {
- try {
- storage.currentProject = 'My Project';
- storage.allProjects = JSON.stringify(['My Project'])
- } catch (e) {
- // Edge case, eg. Firefox localSorage DB corrupted
- console.log(e);
- }
- }
-
- try {
- var p = storage.currentProject;
- storage['SESSION' + p] = prepareExport();
- } catch (e) {
- console.log(e);
- }
-
- // if (isSVGEmpty(turtles)) {
- // We will use the music icon in these cases.
- // return;
- // }
-
- var img = new Image();
- var svgData = doSVG(canvas, logo, turtles, 320, 240, 320 / canvas.width);
- img.onload = function () {
- var bitmap = new createjs.Bitmap(img);
- var bounds = bitmap.getBounds();
- bitmap.cache(bounds.x, bounds.y, bounds.width, bounds.height);
- try {
- storage['SESSIONIMAGE' + p] = bitmap.getCacheDataURL();
- } catch (e) {
- console.log(e);
- }
- };
-
- img.src = 'data:image/svg+xml;base64,' +
- window.btoa(unescape(encodeURIComponent(svgData)));
- // console.log(img.src);
- if (sugarizerCompatibility.isInsideSugarizer()) {
- sugarizerCompatibility.saveLocally();
- }
- };
-
- function runProject(env){
- console.log("Running Project from Event");
- document.removeEventListener("finishedLoading", runProject);
- setTimeout(function () {
- console.log("Run");
- _changeBlockVisibility();
- _doFastButton(env);
- }, 5000);
- }
-
- function loadProject(projectName, run, env) {
- //set default value of run
- run = typeof run !== 'undefined' ? run : false;
- // Show busy cursor.
- document.body.style.cursor = 'wait';
- // palettes.updatePalettes();
- setTimeout(function () {
- if (fileExt(projectName) !== 'tb')
- {
- projectName += '.tb';
- }
-
- try {
- try {
- httpGet(null);
- console.log('running from server or the user can access to examples.');
- server = true;
- } catch (e) {
- console.log('running from filesystem or the connection isnt secure');
- server = false;
- }
-
- if (server) {
- var rawData = httpGet(projectName);
- var cleanData = rawData.replace('\n', '');
- }
-
- // First, hide the palettes as they will need updating.
- for (var name in blocks.palettes.dict) {
- blocks.palettes.dict[name].hideMenu(true);
- }
-
- var obj = JSON.parse(cleanData);
- blocks.loadNewBlocks(obj);
- saveLocally();
- } catch (e) {
- console.log(e);
- loadStartWrapper(_loadStart);
- }
-
- // Restore default cursor
- document.body.style.cursor = 'default';
- update = true;
- }, 200);
-
- if (run && firstRun) {
- if (document.addEventListener) {
- document.addEventListener('finishedLoading', function (){runProject(env);}, false);
- } else {
- document.attachEvent('finishedLoading', function (){runProject(env);});
- }
- }
- firstRun = false;
- };
-
- function loadRawProject(data) {
- console.log('loadRawProject ' + data);
- document.body.style.cursor = 'wait';
- _allClear();
-
- // First, hide the palettes as they will need updating.
- for (var name in blocks.palettes.dict) {
- blocks.palettes.dict[name].hideMenu(true);
- }
-
- var obj = JSON.parse(data);
- blocks.loadNewBlocks(obj);
- document.body.style.cursor = 'default';
- };
-
- function saveProject(projectName) {
- // palettes.updatePalettes();
- // Show busy cursor.
- document.body.style.cursor = 'wait';
- setTimeout(function () {
- var punctuationless = projectName.replace(/['!"#$%&\\'()\*+,\-\.\/:;<=>?@\[\\\]\^`{|}~']/g, '');
- projectName = punctuationless.replace(/ /g, '_');
- if (fileExt(projectName) !== 'tb') {
- projectName += '.tb';
- }
- try {
- // Post the project
- var returnValue = httpPost('MusicBlocks_'+projectName, prepareExport());
- errorMsg('Saved ' + projectName + ' to ' + window.location.host);
-
- var img = new Image();
- var svgData = doSVG(canvas, logo, turtles, 320, 240, 320 / canvas.width);
- img.onload = function () {
- var bitmap = new createjs.Bitmap(img);
- var bounds = bitmap.getBounds();
- bitmap.cache(bounds.x, bounds.y, bounds.width, bounds.height);
- // and base64-encoded png
- httpPost(('MusicBlocks_'+projectName).replace('.tb', '.b64'), bitmap.getCacheDataURL());
- };
-
- img.src = 'data:image/svg+xml;base64,' + window.btoa(
- unescape(encodeURIComponent(svgData)));
- // Restore default cursor
- document.body.style.cursor = 'default';
- return returnValue;
- } catch (e) {
- console.log(e);
- // Restore default cursor
- document.body.style.cursor = 'default';
- return;
- }
- }, 200);
- };
-
- // Calculate time such that no matter how long it takes to
- // load the program, the loading animation will cycle at least
- // once.
- function loadStartWrapper(func, arg1, arg2, arg3) {
- var time1 = new Date();
- func(arg1, arg2, arg3);
-
- var time2 = new Date();
- var elapsedTime = time2.getTime() - time1.getTime();
- var timeLeft = Math.max(6000 - elapsedTime);
- setTimeout(showContents, timeLeft);
- };
-
- // Hides the loading animation and unhides the background.
- function showContents(){
- docById('loading-image-container').style.display = 'none';
- // docById('canvas').style.display = 'none';
- docById('hideContents').style.display = 'block';
- };
-
- function _loadStart() {
- // where to put this?
- // palettes.updatePalettes();
- console.log('LOAD START')
- justLoadStart = function () {
- console.log('loading start and a matrix');
- blocks.loadNewBlocks(DATAOBJS);
- };
-
- if (sugarizerCompatibility.isInsideSugarizer()) {
- storage = sugarizerCompatibility.data;
- }
- else {
- storage = localStorage;
- }
-
- sessionData = null;
- // Try restarting where we were when we hit save.
- var currentProject = storage.currentProject;
- sessionData = storage['SESSION' + currentProject];
- if (sessionData) {
- try {
- if (sessionData === 'undefined' || sessionData === '[]') {
- console.log('empty session found: loading start');
- justLoadStart();
- } else {
- console.log('restoring session: ' + sessionData);
- // First, hide the palettes as they will need updating.
- for (var name in blocks.palettes.dict) {
- blocks.palettes.dict[name].hideMenu(true);
- }
-
- blocks.loadNewBlocks(JSON.parse(sessionData));
- }
- } catch (e) {
- console.log(e);
- }
- } else {
- justLoadStart();
- }
-
- update = true;
-
-
- };
-
- function hideMsgs() {
- errorMsgText.parent.visible = false;
- if (errorMsgArrow != null) {
- errorMsgArrow.removeAllChildren();
- refreshCanvas();
- }
-
- msgText.parent.visible = false;
- for (var i in errorArtwork) {
- errorArtwork[i].visible = false;
- }
- };
-
- function textMsg(msg) {
- if (msgText == null) {
- // The container may not be ready yet... so do nothing
- return;
- }
- var msgContainer = msgText.parent;
- msgContainer.visible = true;
- msgText.text = msg;
- msgContainer.updateCache();
- stage.setChildIndex(msgContainer, stage.getNumChildren() - 1);
- };
-
- function errorMsg(msg, blk, text) {
- _hideStopButton(); //Hide the button, as the program is going to be terminated
- if (errorMsgText == null) {
- // The container may not be ready yet... so do nothing
- return;
- }
- if (blk !== undefined && blk != null && !blocks.blockList[blk].collapsed) {
- var fromX = (canvas.width - 1000) / 2;
- var fromY = 128;
- var toX = blocks.blockList[blk].container.x + blocksContainer.x;
- var toY = blocks.blockList[blk].container.y + blocksContainer.y;
-
- if (errorMsgArrow == null) {
- errorMsgArrow = new createjs.Container();
- stage.addChild(errorMsgArrow);
- }
-
- var line = new createjs.Shape();
- errorMsgArrow.addChild(line);
- line.graphics.setStrokeStyle(4).beginStroke('#ff0031').moveTo(fromX, fromY).lineTo(toX, toY);
- stage.setChildIndex(errorMsgArrow, stage.getNumChildren() - 1);
-
- var angle = Math.atan2(toX - fromX, fromY - toY) / Math.PI * 180;
- var head = new createjs.Shape();
- errorMsgArrow.addChild(head);
- head.graphics.setStrokeStyle(4).beginStroke('#ff0031').moveTo(-10, 18).lineTo(0, 0).lineTo(10, 18);
- head.x = toX;
- head.y = toY;
- head.rotation = angle;
- }
-
- switch (msg) {
- case NOMICERRORMSG:
- errorArtwork['nomicrophone'].visible = true;
- stage.setChildIndex(errorArtwork['nomicrophone'], stage.getNumChildren() - 1);
- break;
- case NOSTRINGERRORMSG:
- errorArtwork['notastring'].visible = true;
- stage.setChildIndex(errorArtwork['notastring'], stage.getNumChildren() - 1);
- break;
- case EMPTYHEAPERRORMSG:
- errorArtwork['emptyheap'].visible = true;
- stage.setChildIndex(errorArtwork['emptyheap'], stage.getNumChildren() - 1);
- break;
- case NOSQRTERRORMSG:
- errorArtwork['negroot'].visible = true;
- stage.setChildIndex(errorArtwork['negroot'], stage.getNumChildren() - 1);
- break;
- case NOACTIONERRORMSG:
- if (text == null) {
- text = 'foo';
- }
- errorArtwork['nostack'].children[1].text = text;
- errorArtwork['nostack'].visible = true;
- errorArtwork['nostack'].updateCache();
- stage.setChildIndex(errorArtwork['nostack'], stage.getNumChildren() - 1);
- break;
- case NOBOXERRORMSG:
- if (text == null) {
- text = 'foo';
- }
- errorArtwork['emptybox'].children[1].text = text;
- errorArtwork['emptybox'].visible = true;
- errorArtwork['emptybox'].updateCache();
- stage.setChildIndex(errorArtwork['emptybox'], stage.getNumChildren() - 1);
- break;
- case ZERODIVIDEERRORMSG:
- errorArtwork['zerodivide'].visible = true;
- stage.setChildIndex(errorArtwork['zerodivide'], stage.getNumChildren() - 1);
- break;
- case NANERRORMSG:
- errorArtwork['notanumber'].visible = true;
- stage.setChildIndex(errorArtwork['notanumber'], stage.getNumChildren() - 1);
- break;
- case NOINPUTERRORMSG:
- errorArtwork['noinput'].visible = true;
- stage.setChildIndex(errorArtwork['noinput'], stage.getNumChildren() - 1);
- break;
- default:
- var errorMsgContainer = errorMsgText.parent;
- errorMsgContainer.visible = true;
- errorMsgText.text = msg;
- stage.setChildIndex(errorMsgContainer, stage.getNumChildren() - 1);
- errorMsgContainer.updateCache();
- break;
- }
-
- update = true;
- };
-
- function _hideCartesian() {
- cartesianBitmap.visible = false;
- cartesianBitmap.updateCache();
- update = true;
- };
-
- function _showCartesian() {
- cartesianBitmap.visible = true;
- cartesianBitmap.updateCache();
- update = true;
- };
-
- function _hidePolar() {
- polarBitmap.visible = false;
- polarBitmap.updateCache();
- update = true;
- };
-
- function _showPolar() {
- polarBitmap.visible = true;
- polarBitmap.updateCache();
- update = true;
- };
-
- function pasteStack() {
- blocks.pasteStack();
- };
-
- function prepareExport() {
- // We don't save blocks in the trash, so we need to
- // consolidate the block list and remap the connections.
- var blockMap = [];
- var hasMatrixDataBlock = false;
- for (var blk = 0; blk < blocks.blockList.length; blk++) {
- var myBlock = blocks.blockList[blk];
- if (myBlock.trash) {
- // Don't save blocks in the trash.
- continue;
- }
- blockMap.push(blk);
- }
-
- var data = [];
- for (var blk = 0; blk < blocks.blockList.length; blk++) {
- var myBlock = blocks.blockList[blk];
- if (myBlock.trash) {
- // Don't save blocks in the trash.
- continue;
- }
-
- if (myBlock.isValueBlock() || myBlock.name === 'loadFile') {
- // FIX ME: scale image if it exceeds a maximum size.
- var args = {
- 'value': myBlock.value
- };
- } else if (myBlock.name === 'start' || myBlock.name === 'drum') {
- // Find the turtle associated with this block.
- var turtle = turtles.turtleList[myBlock.value];
- if (turtle == null) {
- var args = {
- 'collapsed': false,
- 'xcor': 0,
- 'ycor': 0,
- 'heading': 0,
- 'color': 0,
- 'shade': 50,
- 'pensize': 5,
- 'grey': 100
- };
- } else {
- var args = {
- 'collapsed': myBlock.collapsed,
- 'xcor': turtle.x,
- 'ycor': turtle.y,
- 'heading': turtle.orientation,
- 'color': turtle.color,
- 'shade': turtle.value,
- 'pensize': turtle.stroke,
- 'grey': turtle.chroma
- };
- }
- } else if (myBlock.name === 'action') {
- var args = {
- 'collapsed': myBlock.collapsed
- }
- } else if(myBlock.name === 'matrix') {
- var args = {
- 'collapsed' : myBlock.collapsed
- }
- } else if(myBlock.name === 'pitchdrummatrix') {
- var args = {
- 'collapsed' : myBlock.collapsed
- }
- } else if(myBlock.name === 'status') {
- var args = {
- 'collapsed' : myBlock.collapsed
- }
- } else if (myBlock.name === 'namedbox') {
- var args = {
- 'value': myBlock.privateData
- }
- } else if (myBlock.name === 'nameddo') {
- var args = {
- 'value': myBlock.privateData
- }
- } else if (myBlock.name === 'nameddoArg') {
- var args = {
- 'value': myBlock.privateData
- }
- } else if (myBlock.name === 'namedcalc') {
- var args = {
- 'value': myBlock.privateData
- }
- } else if (myBlock.name === 'namedcalcArg') {
- var args = {
- 'value': myBlock.privateData
- }
- } else if (myBlock.name === 'namedarg') {
- var args = {
- 'value': myBlock.privateData
- }
- } else if (myBlock.name === 'matrixData') {
- var args = {
- 'notes': window.savedMatricesNotes, 'count': window.savedMatricesCount
- }
- hasMatrixDataBlock = true;
- } else {
- var args = {}
- }
-
- connections = [];
- for (var c = 0; c < myBlock.connections.length; c++) {
- var mapConnection = blockMap.indexOf(myBlock.connections[c]);
- if (myBlock.connections[c] == null || mapConnection === -1) {
- connections.push(null);
- } else {
- connections.push(mapConnection);
- }
- }
- data.push([blockMap.indexOf(blk), [myBlock.name, args], myBlock.container.x, myBlock.container.y, connections]);
- }
-
- return JSON.stringify(data);
- };
-
- function doOpenPlugin() {
- // Click on the plugin open chooser in the DOM (.json).
- pluginChooser.focus();
- pluginChooser.click();
- };
-
- function saveToFile() {
- var filename = prompt('Filename:');
- if (fileExt(filename) !== 'tb') {
- filename += '.tb';
- }
- download(filename, 'data:text/plain;charset=utf-8,' + encodeURIComponent(prepareExport()));
- };
-
- function _hideStopButton() {
- // stopTurtleContainer.x = stopTurtleContainerX;
- // stopTurtleContainer.y = stopTurtleContainerY;
- stopTurtleContainer.visible = false;
- };
-
- function _showStopButton() {
- // stopTurtleContainer.x = onscreenButtons[0].x;
- // stopTurtleContainer.y = onscreenButtons[0].y;
- stopTurtleContainer.visible = true;
- };
-
- function blinkPasteButton(bitmap) {
- function handleComplete() {
- createjs.Tween.get(bitmap).to({alpha:1, visible:true}, 500);
- };
-
- createjs.Tween.get(bitmap).to({alpha:0, visible:false}, 1000).call(
- handleComplete);
- };
-
- function updatePasteButton() {
- if (pasteImage === null) {
-
- var img = new Image();
-
- img.onload = function () {
- var originalSize = 55; // this is the original svg size
- var halfSize = Math.floor(cellSize / 2);
-
- var bitmap = new createjs.Bitmap(img);
- if (cellSize !== originalSize) {
- bitmap.scaleX = cellSize / originalSize;
- bitmap.scaleY = cellSize / originalSize;
- }
- bitmap.regX = halfSize / bitmap.scaleX;
- bitmap.regY = halfSize / bitmap.scaleY;
- pasteContainer.addChild(bitmap);
- pasteImage = bitmap;
-
- update = true;
- };
-
- img.src = 'header-icons/paste-button.svg';
- } else {
- blinkPasteButton(pasteImage);
- }
- };
-
- function _setupAndroidToolbar(showPalettesPopover) {
- if (headerContainer !== undefined) {
- stage.removeChild(headerContainer);
- for (var i in onscreenButtons) {
- stage.removeChild(onscreenButtons[i]);
- }
- }
-
- headerContainer = new createjs.Shape();
- headerContainer.graphics.f(platformColor.header).r(0, 0, screen.width / turtleBlocksScale, cellSize);
-
- if (platformColor.doHeaderShadow) {
- headerContainer.shadow = new createjs.Shadow('#777', 0, 2, 2);
- }
-
- stage.addChild(headerContainer);
-
- // Buttons used when running turtle programs
- // name / onpress function / label / onlongpress function / onextralongpress function / onlongpress icon / onextralongpress icon
- if (_THIS_IS_MUSIC_BLOCKS_) {
- var buttonNames = [
- ['run', _doFastButton, _('Run fast / long press to run slowly / extra-long press to run music slowly'), _doSlowButton, _doSlowMusicButton, 'slow-button', 'slow-music-button'],
- ['step', _doStepButton, _('Run step by step'), null, null, null, null],
- ['step-music', _doStepMusicButton, _('Run note by note'), null, null, null, null],
- ['stop-turtle', doStopButton, _('Stop'), null, null, null, null],
- ['clear', _allClear, _('Clean'), null, null, null, null],
- // ['palette', _changePaletteVisibility, _('Show/hide palettes'), null, null, null, null],
- ['hide-blocks', _changeBlockVisibility, _('Show/hide blocks'), null, null, null, null],
- ['collapse-blocks', _toggleCollapsibleStacks, _('Expand/collapse collapsable blocks'), null, null, null, null],
- ['go-home', _findBlocks, _('Home'), null, null, null, null],
- ['help', _showHelp, _('Help'), null, null, null, null]
- ];
- } else {
- var buttonNames = [
- ['run', _doFastButton, _('Run fast / long press to run slowly'), _doSlowButton, null, 'slow-button', null],
- ['step', _doStepButton, _('Run step by step'), null, null, null, null],
- ['stop-turtle', doStopButton, _('Stop'), null, null, null, null],
- ['clear', _allClear, _('Clean'), null, null, null, null],
- ['hide-blocks', _changeBlockVisibility, _('Show/hide blocks'), null, null, null, null],
- ['collapse-blocks', _toggleCollapsibleStacks, _('Expand/collapse collapsable blocks'), null, null, null, null],
- ['go-home', _findBlocks, _('Home'), null, null, null, null],
- ['help', _showHelp, _('Help'), null, null, null, null]
- ];
- }
-
- if (sugarizerCompatibility.isInsideSugarizer()) {
- buttonNames.push(['sugarizer-stop', function () {
- sugarizerCompatibility.data.blocks = prepareExport();
- sugarizerCompatibility.saveLocally(function () {
- sugarizerCompatibility.sugarizerStop();
- });
- }, "Stop", null, null, null, null])
- }
-
- if (showPalettesPopover) {
- buttonNames.unshift(['popdown-palette', doPopdownPalette])
- }
-
- var btnSize = cellSize;
- var x = Math.floor(btnSize / 2);
- var y = x;
- var dx = btnSize;
- var dy = 0;
-
- for (var i = 0; i < buttonNames.length; i++) {
- if (!getMainToolbarButtonNames(buttonNames[i][0])) {
- console.log('continue');
- continue;
- }
-
- var container = _makeButton(buttonNames[i][0] + '-button', buttonNames[i][2], x, y, btnSize, 0);
- _loadButtonDragHandler(container, x, y, buttonNames[i][1], buttonNames[i][3], buttonNames[i][4], buttonNames[i][5], buttonNames[i][6]);
- onscreenButtons.push(container);
-
- if (buttonNames[i][0] === 'stop-turtle') {
- stopTurtleContainer = container;
- stopTurtleContainerX = x;
- stopTurtleContainerY = y;
- } else if (buttonNames[i][0] === 'go-home') {
- homeButtonContainers = [];
- homeButtonContainers.push(container);
- homeButtonContainersX = x;
- homeButtonContainersY = y;
- var container2 = _makeButton('go-home-faded-button', _('Home'), x, y, btnSize, 0);
- _loadButtonDragHandler(container2, x, y, buttonNames[i][1], null, null, null, null);
- homeButtonContainers.push(container2);
- onscreenButtons.push(container2);
- homeButtonContainers[0].visible = false;
- homeButtonContainers[1].visible = true;
- boundary.hide();
- blocks.setHomeContainers(homeButtonContainers, boundary);
- }
-
- x += dx;
- y += dy;
- }
-
- _setupRightMenu(turtleBlocksScale);
- };
-
- function _setupRightMenu(turtleBlocksScale) {
- if (menuContainer !== undefined) {
- stage.removeChild(menuContainer);
- for (var i in onscreenMenu) {
- stage.removeChild(onscreenMenu[i]);
- }
- }
-
- // Misc. other buttons
- if (_THIS_IS_MUSIC_BLOCKS_) {
- var menuNames = [
- ['planet', _doOpenSamples, _('Load samples from server')],
- ['open', doLoad, _('Load project from files')],
- ['save', doSave, _('Save project')],
- ['lilypond', _doLilypond, _('Save sheet music')],
- ['paste-disabled', pasteStack, _('Paste')],
- ['Cartesian', _doCartesian, _('Cartesian')],
- ['polar', _doPolar, _('Polar')],
- ['utility', _doUtilityBox, _('Settings')],
- ['empty-trash', _deleteBlocksBox, _('Delete all')],
- ['restore-trash', _restoreTrash, _('Undo')]
- ];
- } else {
- var menuNames = [
- ['planet', _doOpenSamples, _('Load samples from server')],
- ['open', doLoad, _('Load project from files')],
- ['save', doSave, _('Save project')],
- ['paste-disabled', pasteStack, _('Paste')],
- ['Cartesian', _doCartesian, _('Cartesian')],
- ['polar', _doPolar, _('Polar')],
- ['utility', _doUtilityBox, _('Settings')],
- ['empty-trash', _deleteBlocksBox, _('Delete all')],
- ['restore-trash', _restoreTrash, _('Undo')]
- ];
- }
-
- document.querySelector('#myOpenFile')
- .addEventListener('change', function (event) {
- thumbnails.model.controller.hide();
- });
-
- var btnSize = cellSize;
- var x = Math.floor(canvas.width / turtleBlocksScale) - btnSize / 2;
- var y = Math.floor(btnSize / 2);
-
- var dx = 0;
- var dy = btnSize;
-
- menuContainer = _makeButton('menu-button', '', x, y, btnSize, menuButtonsVisible ? 90 : undefined);
- _loadButtonDragHandler(menuContainer, x, y, _doMenuButton, null, null, null, null);
-
- for (var i = 0; i < menuNames.length; i++) {
- if (!getAuxToolbarButtonNames(menuNames[i][0])) {
- continue;
- }
-
- x += dx;
- y += dy;
- var container = _makeButton(menuNames[i][0] + '-button', menuNames[i][2], x, y, btnSize, 0);
- _loadButtonDragHandler(container, x, y, menuNames[i][1], null, null, null, null);
- onscreenMenu.push(container);
- if (menuNames[i][0] === 'utility') {
- utilityButton = container;
- } else if (menuNames[i][0] === 'save') {
- saveButton = container;
- }
-
- container.visible = false;
- }
-
- if (menuButtonsVisible) {
- for (var button in onscreenMenu) {
- onscreenMenu[button].visible = true;
- }
- }
- };
-
- function doPopdownPalette() {
- console.log('doPopdownPalette');
- var p = new PopdownPalette(palettes);
- p.popdown();
- };
-
- function _showHelp(firstTime) {
- helpIdx = 0;
-
- if (firstTime) {
- if (helpContainer == null) {
- helpContainer = new createjs.Container();
- stage.addChild(helpContainer);
- helpContainer.x = 65;
- helpContainer.y = 65;
-
- helpContainer.on('click', function (event) {
- var bounds = helpContainer.getBounds();
- if (event.stageY < helpContainer.y + bounds.height / 2) {
- helpContainer.visible = false;
- docById('helpElem').style.visibility = 'hidden';
- } else {
- helpIdx += 1;
- if (helpIdx >= HELPCONTENT.length) {
- helpIdx = 0;
- }
- var imageScale = 55 * turtleBlocksScale;
- helpElem.innerHTML = '<img src ="' + HELPCONTENT[helpIdx][2] + '" style="height:' + imageScale + 'px; width: auto"></img> <h2>' + HELPCONTENT[helpIdx][0] + '</h2><p>' + HELPCONTENT[helpIdx][1] + '</p>';
- }
- update = true;
- });
-
- var img = new Image();
- img.onload = function () {
- console.log(turtleBlocksScale);
- var bitmap = new createjs.Bitmap(img);
- /*
- if (turtleBlocksScale > 1) {
- bitmap.scaleX = bitmap.scaleY = bitmap.scale = turtleBlocksScale;
- } else {
- bitmap.scaleX = bitmap.scaleY = bitmap.scale = 1.125;
- }
- */
- if (helpContainer.children.length > 0) {
- console.log('delete old help container');
- helpContainer.removeChild(helpContainer.children[0]);
- }
- helpContainer.addChild(bitmap)
-
- var bounds = helpContainer.getBounds();
- var hitArea = new createjs.Shape();
- hitArea.graphics.beginFill('#FFF').drawRect(bounds.x, bounds.y, bounds.width, bounds.height);
- hitArea.x = 0;
- hitArea.y = 0;
- helpContainer.hitArea = hitArea;
-
- docById('helpElem').innerHTML = '<img src ="' + HELPCONTENT[helpIdx][2] + '"</img> <h2>' + HELPCONTENT[helpIdx][0] + '</h2><p>' + HELPCONTENT[helpIdx][1] + '</p>';
- if (!doneTour) {
- docById('helpElem').style.visibility = 'visible';
- }
- update = true;
- };
-
- img.src = 'images/help-container.svg';
- }
-
- var helpElem = docById('helpElem');
- helpElem.style.position = 'absolute';
- helpElem.style.display = 'block';
- helpElem.style.paddingLeft = 20 * turtleBlocksScale + 'px';
- helpElem.style.paddingRight = 20 * turtleBlocksScale + 'px';
- helpElem.style.paddingTop = '0px';
- helpElem.style.paddingBottom = 20 * turtleBlocksScale + 'px';
- helpElem.style.fontSize = 20 + 'px'; // * turtleBlocksScale + 'px';
- helpElem.style.color = '#000000'; // '#ffffff';
- helpElem.style.left = 65 * turtleBlocksScale + 'px';
- helpElem.style.top = 105 * turtleBlocksScale + 'px';
- var w = Math.min(300, 300); // * turtleBlocksScale);
- var h = Math.min(300, 300); // * turtleBlocksScale);
- helpElem.style.width = w + 'px';
- helpElem.style.height = h + 'px';
-
- if (turtleBlocksScale > 1) {
- var bitmap = helpContainer.children[0];
- if (bitmap != undefined) {
- // bitmap.scaleX = bitmap.scaleY = bitmap.scale = turtleBlocksScale;
- }
- }
-
- }
-
- doneTour = storage.doneTour === 'true';
-
- if (firstTime && doneTour) {
- docById('helpElem').style.visibility = 'hidden';
- helpContainer.visible = false;
- } else {
- if (sugarizerCompatibility.isInsideSugarizer()) {
- sugarizerCompatibility.data.doneTour = 'true';
- } else {
- storage.doneTour = 'true';
- }
- docById('helpElem').innerHTML = '<img src ="' + HELPCONTENT[helpIdx][2] + '"</img> <h2>' + HELPCONTENT[helpIdx][0] + '</h2><p>' + HELPCONTENT[helpIdx][1] + '</p>';
- docById('helpElem').style.visibility = 'visible';
- helpContainer.visible = true;
- update = true;
-
- // Make sure the palettes and the secondary menus are
- // visible while help is shown.
- palettes.show();
- if (!menuButtonsVisible) {
- doMenuAnimation(1);
- }
- }
- };
-
- function _doMenuButton() {
- _doMenuAnimation(1);
- };
-
- function _doMenuAnimation() {
- var bitmap = last(menuContainer.children);
- if (bitmap != null) {
- var r = bitmap.rotation;
- createjs.Tween.get(bitmap)
- .to({
- rotation: r
- })
- .to({
- rotation: r + 90
- }, 500);
- } else {
- // Race conditions during load
- setTimeout(_doMenuAnimation, 50);
- }
-
- setTimeout(function () {
- if (menuButtonsVisible) {
- menuButtonsVisible = false;
- for (var button in onscreenMenu) {
- onscreenMenu[button].visible = false;
- }
- } else {
- menuButtonsVisible = true;
- for (var button in onscreenMenu) {
- onscreenMenu[button].visible = true;
- }
- }
- update = true;
- }, 500);
- };
-
- function _toggleToolbar() {
- buttonsVisible = !buttonsVisible;
- menuContainer.visible = buttonsVisible;
- headerContainer.visible = buttonsVisible;
- for (var button in onscreenButtons) {
- onscreenButtons[button].visible = buttonsVisible;
- }
-
- for (var button in onscreenMenu) {
- onscreenMenu[button].visible = buttonsVisible;
- }
-
- update = true;
- };
-
- function _makeButton(name, label, x, y, size, rotation, parent) {
- var container = new createjs.Container();
- if (name === 'paste-disabled-button') {
- pasteContainer = container;
- }
-
- if (parent == undefined) {
- stage.addChild(container);
- } else {
- parent.addChild(container);
- }
-
- container.x = x;
- container.y = y;
-
- var text = new createjs.Text(label, '14px Sans', '#282828');
- if (container.y < 55) {
- if (container.x < 55) {
- text.textAlign = 'left';
- text.x = -14;
- } else {
- text.textAlign = 'center';
- text.x = 0;
- }
- text.y = 30;
- } else {
- text.textAlign = 'right';
- text.x = -28;
- text.y = 0;
- }
-
- text.visible = false;
-
- container.on('mouseover', function (event) {
- for (var c = 0; c < container.children.length; c++) {
- if (container.children[c].text != undefined) {
- container.children[c].visible = true;
- break;
- }
- }
- });
-
- container.on('mouseout', function (event) {
- for (var c = 0; c < container.children.length; c++) {
- if (container.children[c].text != undefined) {
- container.children[c].visible = false;
- break;
- }
- }
- });
-
- var img = new Image();
-
- img.onload = function () {
- var originalSize = 55; // this is the original svg size
- var halfSize = Math.floor(size / 2);
-
- var bitmap = new createjs.Bitmap(img);
- if (size !== originalSize) {
- bitmap.scaleX = size / originalSize;
- bitmap.scaleY = size / originalSize;
- }
-
- bitmap.regX = halfSize / bitmap.scaleX;
- bitmap.regY = halfSize / bitmap.scaleY;
- if (rotation !== undefined) {
- bitmap.rotation = rotation;
- }
-
- container.addChild(bitmap);
- var hitArea = new createjs.Shape();
- hitArea.graphics.beginFill('#FFF').drawEllipse(-halfSize, -halfSize, size, size);
- hitArea.x = 0;
- hitArea.y = 0;
- container.hitArea = hitArea;
- bitmap.cache(0, 0, size, size);
- bitmap.updateCache();
- update = true;
- };
-
- img.src = 'header-icons/' + name + '.svg';
- container.addChild(text);
-
- return container;
- };
-
- function _loadButtonDragHandler(container, ox, oy, action, longAction, extraLongAction, longImg, extraLongImg) {
- // Prevent multiple button presses (i.e., debounce).
- var locked = false;
-
- if (longAction === null) {
- longAction = action;
- }
-
- if (extraLongAction === null) {
- extraLongAction = longAction;
- }
-
- // Long and extra-long press variables declaration
- var pressTimer, pressTimerExtra, isLong = false, isExtraLong = false;
- var formerContainer = container;
-
- container.on('mousedown', function (event) {
- var moved = true;
- var offset = {
- x: container.x - Math.round(event.stageX / turtleBlocksScale),
- y: container.y - Math.round(event.stageY / turtleBlocksScale)
- };
-
- pressTimer = setTimeout(function () {
- isLong = true;
- if (longImg !== null) {
- container.visible = false;
- container = _makeButton(longImg, '', ox, oy, cellSize, 0);
- }
- }, 500);
-
- pressTimerExtra = setTimeout(function () {
- isExtraLong = true;
- if (extraLongImg !== null) {
- container.visible = false;
- container = _makeButton(extraLongImg, '', ox, oy, cellSize, 0);
- }
- }, 1000);
-
- var circles = showButtonHighlight(ox, oy, cellSize / 2, event, turtleBlocksScale, stage);
-
- container.on('pressup', function (event) {
- hideButtonHighlight(circles, stage);
- container.x = ox;
- container.y = oy;
-
- if (longImg !== null || extraLongImg !== null) {
- container.visible = false;
- container = formerContainer;
- container.visible = true;
- }
-
- if (action != null && moved && !locked) {
- locked = true;
-
- setTimeout(function () {
- locked = false;
- }, 500);
-
- clearTimeout(pressTimer);
- clearTimeout(pressTimerExtra);
-
- if (!isLong) {
- action();
- } else if (!isExtraLong) {
- longAction();
- } else {
- extraLongAction();
- }
- }
- moved = false;
- });
-
- isLong = false;
- isExtraLong = false;
- });
-
- };
- };
- });
|