From b9f8ef9951f2a534556925ad7a2776281f7e18c5 Mon Sep 17 00:00:00 2001 From: jmoenig Date: Wed, 8 Jan 2014 15:17:03 +0100 Subject: add mouseLeaveDragging() behavior to the paint editor, thanks, Kartik! All credit for fixing this goes to Kartik. This also seems to change just about every line ending for reasons known only to Xcode. Sorry Kartik, for not pulling your request because of those line endings, they are inevitable! --- paint.js | 1434 +++++++++++++++++++++++++++++++------------------------------- 1 file changed, 719 insertions(+), 715 deletions(-) (limited to 'paint.js') diff --git a/paint.js b/paint.js index 44585b2..15b4172 100644 --- a/paint.js +++ b/paint.js @@ -1,14 +1,14 @@ -/* +/* paint.js - - a paint editor for Snap! - inspired by the Scratch paint editor. - + + a paint editor for Snap! + inspired by the Scratch paint editor. + written by Kartik Chandra - Copyright (C) 2013 by Kartik Chandra - - This file is part of Snap!. - + Copyright (C) 2013 by Kartik Chandra + + This file is part of Snap!. + Snap! is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of @@ -50,186 +50,187 @@ May 16 - flat design adjustments (Jens) July 12 - pipette tool, code formatting adjustments (Jens) September 16 - flood fill freeze fix (Kartik) + Jan 08 - mouse leave dragging fix (Kartik) + + */ - */ - -/*global Point, Rectangle, DialogBoxMorph, fontHeight, AlignmentMorph, - FrameMorph, PushButtonMorph, Color, SymbolMorph, newCanvas, Morph, TextMorph, - CostumeIconMorph, IDE_Morph, Costume, SpriteMorph, nop, Image, WardrobeMorph, - TurtleIconMorph, localize, MenuMorph, InputFieldMorph, SliderMorph, +/*global Point, Rectangle, DialogBoxMorph, fontHeight, AlignmentMorph, + FrameMorph, PushButtonMorph, Color, SymbolMorph, newCanvas, Morph, TextMorph, + CostumeIconMorph, IDE_Morph, Costume, SpriteMorph, nop, Image, WardrobeMorph, + TurtleIconMorph, localize, MenuMorph, InputFieldMorph, SliderMorph, ToggleMorph, ToggleButtonMorph, BoxMorph, modules, radians, - MorphicPreferences, getDocumentPositionOf - */ - + MorphicPreferences, getDocumentPositionOf + */ + // Global stuff //////////////////////////////////////////////////////// -modules.paint = '2013-September-16'; +modules.paint = '2014-January-08'; // Declarations -var PaintEditorMorph; -var PaintCanvasMorph; -var PaintColorPickerMorph; - -// PaintEditorMorph ////////////////////////// - -// A complete paint editor - -PaintEditorMorph.prototype = new DialogBoxMorph(); -PaintEditorMorph.prototype.constructor = PaintEditorMorph; -PaintEditorMorph.uber = DialogBoxMorph.prototype; - -PaintEditorMorph.prototype.padding = 10; - -function PaintEditorMorph() { - this.init(); -} - -PaintEditorMorph.prototype.init = function () { - // additional properties: +var PaintEditorMorph; +var PaintCanvasMorph; +var PaintColorPickerMorph; + +// PaintEditorMorph ////////////////////////// + +// A complete paint editor + +PaintEditorMorph.prototype = new DialogBoxMorph(); +PaintEditorMorph.prototype.constructor = PaintEditorMorph; +PaintEditorMorph.uber = DialogBoxMorph.prototype; + +PaintEditorMorph.prototype.padding = 10; + +function PaintEditorMorph() { + this.init(); +} + +PaintEditorMorph.prototype.init = function () { + // additional properties: this.paper = null; // paint canvas - this.oncancel = null; - - // initialize inherited properties: - PaintEditorMorph.uber.init.call(this); - - // override inherited properties: - this.labelString = "Paint Editor"; - this.createLabel(); - - // build contents: - this.buildContents(); -}; - -PaintEditorMorph.prototype.buildContents = function () { - var myself = this; - + this.oncancel = null; + + // initialize inherited properties: + PaintEditorMorph.uber.init.call(this); + + // override inherited properties: + this.labelString = "Paint Editor"; + this.createLabel(); + + // build contents: + this.buildContents(); +}; + +PaintEditorMorph.prototype.buildContents = function () { + var myself = this; + this.paper = new PaintCanvasMorph(function () {return myself.shift; }); - this.paper.setExtent(new Point(480, 360)); - - this.addBody(new AlignmentMorph('row', this.padding)); - this.controls = new AlignmentMorph('column', this.padding); - this.controls.alignment = 'left'; - - this.edits = new AlignmentMorph('row', this.padding); - this.buildEdits(); - this.controls.add(this.edits); - - this.body.color = this.color; - - this.body.add(this.controls); - this.body.add(this.paper); - - this.toolbox = new BoxMorph(); - this.toolbox.color = SpriteMorph.prototype.paletteColor.lighter(8); + this.paper.setExtent(new Point(480, 360)); + + this.addBody(new AlignmentMorph('row', this.padding)); + this.controls = new AlignmentMorph('column', this.padding); + this.controls.alignment = 'left'; + + this.edits = new AlignmentMorph('row', this.padding); + this.buildEdits(); + this.controls.add(this.edits); + + this.body.color = this.color; + + this.body.add(this.controls); + this.body.add(this.paper); + + this.toolbox = new BoxMorph(); + this.toolbox.color = SpriteMorph.prototype.paletteColor.lighter(8); this.toolbox.borderColor = this.toolbox.color.lighter(40); if (MorphicPreferences.isFlat) { this.toolbox.edge = 0; - } - - this.buildToolbox(); - this.controls.add(this.toolbox); - - this.propertiesControls = { - colorpicker: null, - penSizeSlider: null, - penSizeField: null, - primaryColorButton: null, - primaryColorViewer: null, - constrain: null - }; - this.populatePropertiesMenu(); - - this.addButton("ok", "OK"); - this.addButton("cancel", "Cancel"); - - this.refreshToolButtons(); - this.fixLayout(); - this.drawNew(); -}; - -PaintEditorMorph.prototype.buildToolbox = function () { - var tools = { - brush: - "Paintbrush tool\n(free draw)", - rectangle: - "Stroked Rectangle\n(shift: square)", - circle: - "Stroked Ellipse\n(shift: circle)", - eraser: - "Eraser tool", - crosshairs: - "Set the rotation center", - - line: - "Line tool\n(shift: vertical/horizontal)", - rectangleSolid: - "Filled Rectangle\n(shift: square)", - circleSolid: - "Filled Ellipse\n(shift: circle)", - paintbucket: - "Fill a region", + } + + this.buildToolbox(); + this.controls.add(this.toolbox); + + this.propertiesControls = { + colorpicker: null, + penSizeSlider: null, + penSizeField: null, + primaryColorButton: null, + primaryColorViewer: null, + constrain: null + }; + this.populatePropertiesMenu(); + + this.addButton("ok", "OK"); + this.addButton("cancel", "Cancel"); + + this.refreshToolButtons(); + this.fixLayout(); + this.drawNew(); +}; + +PaintEditorMorph.prototype.buildToolbox = function () { + var tools = { + brush: + "Paintbrush tool\n(free draw)", + rectangle: + "Stroked Rectangle\n(shift: square)", + circle: + "Stroked Ellipse\n(shift: circle)", + eraser: + "Eraser tool", + crosshairs: + "Set the rotation center", + + line: + "Line tool\n(shift: vertical/horizontal)", + rectangleSolid: + "Filled Rectangle\n(shift: square)", + circleSolid: + "Filled Ellipse\n(shift: circle)", + paintbucket: + "Fill a region", pipette: "Pipette tool\n(pick a color anywhere)" - }, - myself = this, - left = this.toolbox.left(), - top = this.toolbox.top(), - padding = 2, - inset = 5, - x = 0, - y = 0; - - Object.keys(tools).forEach(function (tool) { - var btn = myself.toolButton(tool, tools[tool]); - btn.setPosition(new Point( - left + x, - top + y - )); - x += btn.width() + padding; - if (tool === "crosshairs") { - x = 0; - y += btn.height() + padding; - myself.paper.drawcrosshair(); - } - myself.toolbox[tool] = btn; - myself.toolbox.add(btn); - }); - - this.toolbox.bounds = this.toolbox.fullBounds().expandBy(inset * 2); - this.toolbox.drawNew(); -}; - -PaintEditorMorph.prototype.buildEdits = function () { - var paper = this.paper; - - this.edits.add(this.pushButton( - "undo", - function () {paper.undo(); } - )); - - this.edits.add(this.pushButton( - "clear", - function () {paper.clearCanvas(); } - )); - this.edits.fixLayout(); -}; - -PaintEditorMorph.prototype.openIn = function (world, oldim, oldrc, callback) { + }, + myself = this, + left = this.toolbox.left(), + top = this.toolbox.top(), + padding = 2, + inset = 5, + x = 0, + y = 0; + + Object.keys(tools).forEach(function (tool) { + var btn = myself.toolButton(tool, tools[tool]); + btn.setPosition(new Point( + left + x, + top + y + )); + x += btn.width() + padding; + if (tool === "crosshairs") { + x = 0; + y += btn.height() + padding; + myself.paper.drawcrosshair(); + } + myself.toolbox[tool] = btn; + myself.toolbox.add(btn); + }); + + this.toolbox.bounds = this.toolbox.fullBounds().expandBy(inset * 2); + this.toolbox.drawNew(); +}; + +PaintEditorMorph.prototype.buildEdits = function () { + var paper = this.paper; + + this.edits.add(this.pushButton( + "undo", + function () {paper.undo(); } + )); + + this.edits.add(this.pushButton( + "clear", + function () {paper.clearCanvas(); } + )); + this.edits.fixLayout(); +}; + +PaintEditorMorph.prototype.openIn = function (world, oldim, oldrc, callback) { // Open the editor in a world with an optional image to edit - this.oldim = oldim; - this.oldrc = oldrc.copy(); - this.callback = callback || nop; + this.oldim = oldim; + this.oldrc = oldrc.copy(); + this.callback = callback || nop; - this.processKeyUp = function () { - this.shift = false; - this.propertiesControls.constrain.refresh(); - }; + this.processKeyUp = function () { + this.shift = false; + this.propertiesControls.constrain.refresh(); + }; - this.processKeyDown = function () { - this.shift = this.world().currentKey === 16; - this.propertiesControls.constrain.refresh(); - }; + this.processKeyDown = function () { + this.shift = this.world().currentKey === 16; + this.propertiesControls.constrain.refresh(); + }; //merge oldim: if (this.oldim) { @@ -244,170 +245,170 @@ PaintEditorMorph.prototype.openIn = function (world, oldim, oldrc, callback) { this.paper.drawNew(); } - this.key = 'paint'; - this.popUp(world); -}; - + this.key = 'paint'; + this.popUp(world); +}; + PaintEditorMorph.prototype.fixLayout = function () { var oldFlag = Morph.prototype.trackChanges; - + this.changed(); oldFlag = Morph.prototype.trackChanges; Morph.prototype.trackChanges = false; if (this.paper) { this.paper.buildContents(); - this.paper.drawNew(); - } - if (this.controls) {this.controls.fixLayout(); } - if (this.body) {this.body.fixLayout(); } - PaintEditorMorph.uber.fixLayout.call(this); + this.paper.drawNew(); + } + if (this.controls) {this.controls.fixLayout(); } + if (this.body) {this.body.fixLayout(); } + PaintEditorMorph.uber.fixLayout.call(this); Morph.prototype.trackChanges = oldFlag; this.changed(); -}; - -PaintEditorMorph.prototype.refreshToolButtons = function () { - this.toolbox.children.forEach(function (toggle) { - toggle.refresh(); - }); -}; - -PaintEditorMorph.prototype.ok = function () { - this.callback( - this.paper.paper, - this.paper.rotationCenter - ); - this.destroy(); -}; +}; + +PaintEditorMorph.prototype.refreshToolButtons = function () { + this.toolbox.children.forEach(function (toggle) { + toggle.refresh(); + }); +}; + +PaintEditorMorph.prototype.ok = function () { + this.callback( + this.paper.paper, + this.paper.rotationCenter + ); + this.destroy(); +}; PaintEditorMorph.prototype.cancel = function () { if (this.oncancel) {this.oncancel(); } this.destroy(); }; - -PaintEditorMorph.prototype.populatePropertiesMenu = function () { - var c = this.controls, - myself = this, - pc = this.propertiesControls, - alpen = new AlignmentMorph("row", this.padding); - - pc.primaryColorViewer = new Morph(); - pc.primaryColorViewer.setExtent(new Point(180, 50)); - pc.primaryColorViewer.color = new Color(0, 0, 0); - pc.colorpicker = new PaintColorPickerMorph( - new Point(180, 100), - function (color) { - var ni = newCanvas(pc.primaryColorViewer.extent()), - ctx = ni.getContext("2d"), - i, - j; - myself.paper.settings.primarycolor = color; - if (color === "transparent") { - for (i = 0; i < 180; i += 5) { - for (j = 0; j < 15; j += 5) { - ctx.fillStyle = - ((j + i) / 5) % 2 === 0 ? - "rgba(0, 0, 0, 0.2)" : - "rgba(0, 0, 0, 0.5)"; - ctx.fillRect(i, j, 5, 5); - - } - } - } else { - ctx.fillStyle = color.toString(); - ctx.fillRect(0, 0, 180, 15); - } - ctx.strokeStyle = "black"; - ctx.lineWidth = Math.min(myself.paper.settings.linewidth, 20); - ctx.beginPath(); - ctx.lineCap = "round"; - ctx.moveTo(20, 30); - ctx.lineTo(160, 30); - ctx.stroke(); - pc.primaryColorViewer.image = ni; - pc.primaryColorViewer.changed(); - } - ); - pc.colorpicker.action(new Color(0, 0, 0)); - - pc.penSizeSlider = new SliderMorph(0, 20, 5, 5); - pc.penSizeSlider.orientation = "horizontal"; - pc.penSizeSlider.setHeight(15); - pc.penSizeSlider.setWidth(150); - pc.penSizeSlider.action = function (num) { - if (pc.penSizeField) { - pc.penSizeField.setContents(num); - } - myself.paper.settings.linewidth = num; - pc.colorpicker.action(myself.paper.settings.primarycolor); - }; - pc.penSizeField = new InputFieldMorph("5", true, null, false); - pc.penSizeField.contents().minWidth = 20; - pc.penSizeField.setWidth(25); - pc.penSizeField.accept = function () { - var val = parseFloat(pc.penSizeField.getValue()); - pc.penSizeSlider.value = val; - pc.penSizeSlider.drawNew(); - pc.penSizeSlider.updateValue(); - this.setContents(val); - myself.paper.settings.linewidth = val; - this.world().keyboardReceiver = myself; - pc.colorpicker.action(myself.paper.settings.primarycolor); - }; - alpen.add(pc.penSizeSlider); - alpen.add(pc.penSizeField); - alpen.color = myself.color; - alpen.fixLayout(); - pc.penSizeField.drawNew(); - pc.constrain = new ToggleMorph( - "checkbox", - this, - function () {myself.shift = !myself.shift; }, - "Constrain proportions of shapes?\n(you can also hold shift)", - function () {return myself.shift; } - ); - c.add(pc.colorpicker); - //c.add(pc.primaryColorButton); - c.add(pc.primaryColorViewer); - c.add(new TextMorph("Brush size")); - c.add(alpen); - c.add(pc.constrain); -}; - -PaintEditorMorph.prototype.toolButton = function (icon, hint) { - var button, myself = this; - - button = new ToggleButtonMorph( - null, + +PaintEditorMorph.prototype.populatePropertiesMenu = function () { + var c = this.controls, + myself = this, + pc = this.propertiesControls, + alpen = new AlignmentMorph("row", this.padding); + + pc.primaryColorViewer = new Morph(); + pc.primaryColorViewer.setExtent(new Point(180, 50)); + pc.primaryColorViewer.color = new Color(0, 0, 0); + pc.colorpicker = new PaintColorPickerMorph( + new Point(180, 100), + function (color) { + var ni = newCanvas(pc.primaryColorViewer.extent()), + ctx = ni.getContext("2d"), + i, + j; + myself.paper.settings.primarycolor = color; + if (color === "transparent") { + for (i = 0; i < 180; i += 5) { + for (j = 0; j < 15; j += 5) { + ctx.fillStyle = + ((j + i) / 5) % 2 === 0 ? + "rgba(0, 0, 0, 0.2)" : + "rgba(0, 0, 0, 0.5)"; + ctx.fillRect(i, j, 5, 5); + + } + } + } else { + ctx.fillStyle = color.toString(); + ctx.fillRect(0, 0, 180, 15); + } + ctx.strokeStyle = "black"; + ctx.lineWidth = Math.min(myself.paper.settings.linewidth, 20); + ctx.beginPath(); + ctx.lineCap = "round"; + ctx.moveTo(20, 30); + ctx.lineTo(160, 30); + ctx.stroke(); + pc.primaryColorViewer.image = ni; + pc.primaryColorViewer.changed(); + } + ); + pc.colorpicker.action(new Color(0, 0, 0)); + + pc.penSizeSlider = new SliderMorph(0, 20, 5, 5); + pc.penSizeSlider.orientation = "horizontal"; + pc.penSizeSlider.setHeight(15); + pc.penSizeSlider.setWidth(150); + pc.penSizeSlider.action = function (num) { + if (pc.penSizeField) { + pc.penSizeField.setContents(num); + } + myself.paper.settings.linewidth = num; + pc.colorpicker.action(myself.paper.settings.primarycolor); + }; + pc.penSizeField = new InputFieldMorph("5", true, null, false); + pc.penSizeField.contents().minWidth = 20; + pc.penSizeField.setWidth(25); + pc.penSizeField.accept = function () { + var val = parseFloat(pc.penSizeField.getValue()); + pc.penSizeSlider.value = val; + pc.penSizeSlider.drawNew(); + pc.penSizeSlider.updateValue(); + this.setContents(val); + myself.paper.settings.linewidth = val; + this.world().keyboardReceiver = myself; + pc.colorpicker.action(myself.paper.settings.primarycolor); + }; + alpen.add(pc.penSizeSlider); + alpen.add(pc.penSizeField); + alpen.color = myself.color; + alpen.fixLayout(); + pc.penSizeField.drawNew(); + pc.constrain = new ToggleMorph( + "checkbox", + this, + function () {myself.shift = !myself.shift; }, + "Constrain proportions of shapes?\n(you can also hold shift)", + function () {return myself.shift; } + ); + c.add(pc.colorpicker); + //c.add(pc.primaryColorButton); + c.add(pc.primaryColorViewer); + c.add(new TextMorph("Brush size")); + c.add(alpen); + c.add(pc.constrain); +}; + +PaintEditorMorph.prototype.toolButton = function (icon, hint) { + var button, myself = this; + + button = new ToggleButtonMorph( + null, this, function () { // action - myself.paper.currentTool = icon; - myself.paper.toolChanged(icon); + myself.paper.currentTool = icon; + myself.paper.toolChanged(icon); myself.refreshToolButtons(); if (icon === 'pipette') { myself.getUserColor(); - } - }, - new SymbolMorph(icon, 18), - function () {return myself.paper.currentTool === icon; } - ); - - button.hint = hint; - button.drawNew(); - button.fixLayout(); - return button; -}; - -PaintEditorMorph.prototype.pushButton = function (title, action, hint) { - return new PushButtonMorph( - this, - action, - title, - null, - hint - ); -}; + } + }, + new SymbolMorph(icon, 18), + function () {return myself.paper.currentTool === icon; } + ); + + button.hint = hint; + button.drawNew(); + button.fixLayout(); + return button; +}; + +PaintEditorMorph.prototype.pushButton = function (title, action, hint) { + return new PushButtonMorph( + this, + action, + title, + null, + hint + ); +}; PaintEditorMorph.prototype.getUserColor = function () { var myself = this, @@ -440,167 +441,167 @@ PaintEditorMorph.prototype.getUserColor = function () { hand.processMouseUp = mouseUpBak; }; }; - -// AdvancedColorPickerMorph ////////////////// - -// A large hsl color picker - -PaintColorPickerMorph.prototype = new Morph(); -PaintColorPickerMorph.prototype.constructor = PaintColorPickerMorph; -PaintColorPickerMorph.uber = Morph.prototype; - -function PaintColorPickerMorph(extent, action) { - this.init(extent, action); -} - -PaintColorPickerMorph.prototype.init = function (extent, action) { - this.setExtent(extent || new Point(200, 100)); - this.action = action || nop; - this.drawNew(); -}; - -PaintColorPickerMorph.prototype.drawNew = function () { - var x = 0, - y = 0, - can = newCanvas(this.extent()), - ctx = can.getContext("2d"), - colorselection, - r; - for (x = 0; x < this.width(); x += 1) { - for (y = 0; y < this.height() - 20; y += 1) { - ctx.fillStyle = "hsl(" + - (360 * x / this.width()) + - "," + - "100%," + - (y * 100 / (this.height() - 20)) + - "%)"; - ctx.fillRect(x, y, 1, 1); - } - } - for (x = 0; x < this.width(); x += 1) { - r = Math.floor(255 * x / this.width()); - ctx.fillStyle = "rgb(" + r + ", " + r + ", " + r + ")"; - ctx.fillRect(x, this.height() - 20, 1, 10); - } - colorselection = ["black", "white", "gray"]; - for (x = 0; x < colorselection.length; x += 1) { - ctx.fillStyle = colorselection[x]; - ctx.fillRect( - x * this.width() / colorselection.length, - this.height() - 10, - this.width() / colorselection.length, - 10 - ); - } - for (x = this.width() * 2 / 3; x < this.width(); x += 2) { - for (y = this.height() - 10; y < this.height(); y += 2) { - if ((x + y) / 2 % 2 === 0) { - ctx.fillStyle = "#DDD"; - ctx.fillRect(x, y, 2, 2); - } - } - } - this.image = can; -}; - -PaintColorPickerMorph.prototype.mouseDownLeft = function (pos) { - if ((pos.subtract(this.position()).x > this.width() * 2 / 3) && - (pos.subtract(this.position()).y > this.height() - 10)) { - this.action("transparent"); - } else { - this.action(this.getPixelColor(pos)); - } -}; - -PaintColorPickerMorph.prototype.mouseMove = + +// AdvancedColorPickerMorph ////////////////// + +// A large hsl color picker + +PaintColorPickerMorph.prototype = new Morph(); +PaintColorPickerMorph.prototype.constructor = PaintColorPickerMorph; +PaintColorPickerMorph.uber = Morph.prototype; + +function PaintColorPickerMorph(extent, action) { + this.init(extent, action); +} + +PaintColorPickerMorph.prototype.init = function (extent, action) { + this.setExtent(extent || new Point(200, 100)); + this.action = action || nop; + this.drawNew(); +}; + +PaintColorPickerMorph.prototype.drawNew = function () { + var x = 0, + y = 0, + can = newCanvas(this.extent()), + ctx = can.getContext("2d"), + colorselection, + r; + for (x = 0; x < this.width(); x += 1) { + for (y = 0; y < this.height() - 20; y += 1) { + ctx.fillStyle = "hsl(" + + (360 * x / this.width()) + + "," + + "100%," + + (y * 100 / (this.height() - 20)) + + "%)"; + ctx.fillRect(x, y, 1, 1); + } + } + for (x = 0; x < this.width(); x += 1) { + r = Math.floor(255 * x / this.width()); + ctx.fillStyle = "rgb(" + r + ", " + r + ", " + r + ")"; + ctx.fillRect(x, this.height() - 20, 1, 10); + } + colorselection = ["black", "white", "gray"]; + for (x = 0; x < colorselection.length; x += 1) { + ctx.fillStyle = colorselection[x]; + ctx.fillRect( + x * this.width() / colorselection.length, + this.height() - 10, + this.width() / colorselection.length, + 10 + ); + } + for (x = this.width() * 2 / 3; x < this.width(); x += 2) { + for (y = this.height() - 10; y < this.height(); y += 2) { + if ((x + y) / 2 % 2 === 0) { + ctx.fillStyle = "#DDD"; + ctx.fillRect(x, y, 2, 2); + } + } + } + this.image = can; +}; + +PaintColorPickerMorph.prototype.mouseDownLeft = function (pos) { + if ((pos.subtract(this.position()).x > this.width() * 2 / 3) && + (pos.subtract(this.position()).y > this.height() - 10)) { + this.action("transparent"); + } else { + this.action(this.getPixelColor(pos)); + } +}; + +PaintColorPickerMorph.prototype.mouseMove = PaintColorPickerMorph.prototype.mouseDownLeft; - + // PaintCanvasMorph /////////////////////////// /* - A canvas which reacts to drag events to + A canvas which reacts to drag events to modify its image, based on a 'tool' property. */ - -PaintCanvasMorph.prototype = new Morph(); -PaintCanvasMorph.prototype.constructor = PaintCanvasMorph; -PaintCanvasMorph.uber = Morph.prototype; - -function PaintCanvasMorph(shift) { - this.init(shift); -} - -PaintCanvasMorph.prototype.init = function (shift) { - this.rotationCenter = new Point(240, 180); - this.dragRect = null; - this.previousDragPoint = null; - this.currentTool = "brush"; - this.dragRect = new Rectangle(); - // rectangle with origin being the starting drag position and + +PaintCanvasMorph.prototype = new Morph(); +PaintCanvasMorph.prototype.constructor = PaintCanvasMorph; +PaintCanvasMorph.uber = Morph.prototype; + +function PaintCanvasMorph(shift) { + this.init(shift); +} + +PaintCanvasMorph.prototype.init = function (shift) { + this.rotationCenter = new Point(240, 180); + this.dragRect = null; + this.previousDragPoint = null; + this.currentTool = "brush"; + this.dragRect = new Rectangle(); + // rectangle with origin being the starting drag position and // corner being the current drag position - this.mask = newCanvas(this.extent()); // Temporary canvas - this.paper = newCanvas(this.extent()); // Actual canvas - this.erasermask = newCanvas(this.extent()); // eraser memory - this.background = newCanvas(this.extent()); // checkers - this.settings = { - "primarycolor": new Color(0, 0, 0, 255), // usually fill color - "secondarycolor": new Color(0, 0, 0, 255), // (unused) - "linewidth": 3 // stroke width - }; - this.brushBuffer = []; - this.undoBuffer = []; - this.isShiftPressed = shift || function () { - var key = this.world().currentKey; - return (key === 16); + this.mask = newCanvas(this.extent()); // Temporary canvas + this.paper = newCanvas(this.extent()); // Actual canvas + this.erasermask = newCanvas(this.extent()); // eraser memory + this.background = newCanvas(this.extent()); // checkers + this.settings = { + "primarycolor": new Color(0, 0, 0, 255), // usually fill color + "secondarycolor": new Color(0, 0, 0, 255), // (unused) + "linewidth": 3 // stroke width }; - this.buildContents(); -}; - -PaintCanvasMorph.prototype.cacheUndo = function () { - var cachecan = newCanvas(this.extent()); - this.merge(this.paper, cachecan); - this.undoBuffer.push(cachecan); -}; - -PaintCanvasMorph.prototype.undo = function () { - if (this.undoBuffer.length > 0) { - this.paper = newCanvas(this.extent()); - this.mask.width = this.mask.width + 1 - 1; - this.merge(this.undoBuffer.pop(), this.paper); - this.drawNew(); - this.changed(); - } -}; - -PaintCanvasMorph.prototype.merge = function (a, b) { - b.getContext("2d").drawImage(a, 0, 0); + this.brushBuffer = []; + this.undoBuffer = []; + this.isShiftPressed = shift || function () { + var key = this.world().currentKey; + return (key === 16); + }; + this.buildContents(); +}; + +PaintCanvasMorph.prototype.cacheUndo = function () { + var cachecan = newCanvas(this.extent()); + this.merge(this.paper, cachecan); + this.undoBuffer.push(cachecan); +}; + +PaintCanvasMorph.prototype.undo = function () { + if (this.undoBuffer.length > 0) { + this.paper = newCanvas(this.extent()); + this.mask.width = this.mask.width + 1 - 1; + this.merge(this.undoBuffer.pop(), this.paper); + this.drawNew(); + this.changed(); + } +}; + +PaintCanvasMorph.prototype.merge = function (a, b) { + b.getContext("2d").drawImage(a, 0, 0); }; - -PaintCanvasMorph.prototype.centermerge = function (a, b) { - b.getContext("2d").drawImage( - a, - (b.width - a.width) / 2, - (b.height - a.height) / 2 - ); -}; - + +PaintCanvasMorph.prototype.centermerge = function (a, b) { + b.getContext("2d").drawImage( + a, + (b.width - a.width) / 2, + (b.height - a.height) / 2 + ); +}; + PaintCanvasMorph.prototype.clearCanvas = function () { - this.buildContents(); - this.drawNew(); - this.changed(); -}; - -PaintCanvasMorph.prototype.toolChanged = function (tool) { - this.mask = newCanvas(this.extent()); - if (tool === "crosshairs") { - this.drawcrosshair(); - } - this.drawNew(); - this.changed(); -}; - -PaintCanvasMorph.prototype.drawcrosshair = function (context) { - var ctx = context || this.mask.getContext("2d"), - rp = this.rotationCenter; + this.buildContents(); + this.drawNew(); + this.changed(); +}; + +PaintCanvasMorph.prototype.toolChanged = function (tool) { + this.mask = newCanvas(this.extent()); + if (tool === "crosshairs") { + this.drawcrosshair(); + } + this.drawNew(); + this.changed(); +}; + +PaintCanvasMorph.prototype.drawcrosshair = function (context) { + var ctx = context || this.mask.getContext("2d"), + rp = this.rotationCenter; ctx.lineWidth = 1; ctx.strokeStyle = 'black'; @@ -646,32 +647,32 @@ PaintCanvasMorph.prototype.drawcrosshair = function (context) { ctx.moveTo(rp.x, 0); ctx.lineTo(rp.x, this.mask.height); ctx.stroke(); - - this.drawNew(); - this.changed(); -}; - + + this.drawNew(); + this.changed(); +}; + PaintCanvasMorph.prototype.floodfill = function (sourcepoint) { - var width = this.paper.width, - height = this.paper.height, - ctx = this.paper.getContext("2d"), - img = ctx.getImageData(0, 0, width, height), - data = img.data, - stack = [Math.round(sourcepoint.y) * width + sourcepoint.x], - currentpoint, - read, - sourcecolor, - checkpoint; - read = function (p) { - var d = p * 4; - return [data[d], data[d + 1], data[d + 2], data[d + 3]]; - }; - sourcecolor = read(stack[0]); - checkpoint = function (p) { - return p[0] === sourcecolor[0] && - p[1] === sourcecolor[1] && - p[2] === sourcecolor[2] && - p[3] === sourcecolor[3]; + var width = this.paper.width, + height = this.paper.height, + ctx = this.paper.getContext("2d"), + img = ctx.getImageData(0, 0, width, height), + data = img.data, + stack = [Math.round(sourcepoint.y) * width + sourcepoint.x], + currentpoint, + read, + sourcecolor, + checkpoint; + read = function (p) { + var d = p * 4; + return [data[d], data[d + 1], data[d + 2], data[d + 3]]; + }; + sourcecolor = read(stack[0]); + checkpoint = function (p) { + return p[0] === sourcecolor[0] && + p[1] === sourcecolor[1] && + p[2] === sourcecolor[2] && + p[3] === sourcecolor[3]; }; // if already filled, abort @@ -690,201 +691,204 @@ PaintCanvasMorph.prototype.floodfill = function (sourcepoint) { } while (stack.length > 0) { - currentpoint = stack.pop(); - if (checkpoint(read(currentpoint))) { - if (currentpoint % 480 > 1) { - stack.push(currentpoint + 1); - stack.push(currentpoint - 1); - } - if (currentpoint > 0 && currentpoint < 360 * 480) { - stack.push(currentpoint + width); - stack.push(currentpoint - width); - } - } - if (this.settings.primarycolor === "transparent") { - data[currentpoint * 4 + 3] = 0; - } else { - data[currentpoint * 4] = this.settings.primarycolor.r; - data[currentpoint * 4 + 1] = this.settings.primarycolor.g; - data[currentpoint * 4 + 2] = this.settings.primarycolor.b; - data[currentpoint * 4 + 3] = this.settings.primarycolor.a; - } - } + currentpoint = stack.pop(); + if (checkpoint(read(currentpoint))) { + if (currentpoint % 480 > 1) { + stack.push(currentpoint + 1); + stack.push(currentpoint - 1); + } + if (currentpoint > 0 && currentpoint < 360 * 480) { + stack.push(currentpoint + width); + stack.push(currentpoint - width); + } + } + if (this.settings.primarycolor === "transparent") { + data[currentpoint * 4 + 3] = 0; + } else { + data[currentpoint * 4] = this.settings.primarycolor.r; + data[currentpoint * 4 + 1] = this.settings.primarycolor.g; + data[currentpoint * 4 + 2] = this.settings.primarycolor.b; + data[currentpoint * 4 + 3] = this.settings.primarycolor.a; + } + } ctx.putImageData(img, 0, 0); this.drawNew(); this.changed(); -}; - -PaintCanvasMorph.prototype.mouseDownLeft = function (pos) { - this.cacheUndo(); - this.dragRect.origin = pos.subtract(this.bounds.origin); - this.dragRect.corner = pos.subtract(this.bounds.origin); - this.previousDragPoint = this.dragRect.corner.copy(); +}; + +PaintCanvasMorph.prototype.mouseDownLeft = function (pos) { + this.cacheUndo(); + this.dragRect.origin = pos.subtract(this.bounds.origin); + this.dragRect.corner = pos.subtract(this.bounds.origin); + this.previousDragPoint = this.dragRect.corner.copy(); if (this.currentTool === 'crosshairs') { this.rotationCenter = pos.subtract(this.bounds.origin); this.drawcrosshair(); return; } - if (this.currentTool === "paintbucket") { - return this.floodfill(pos.subtract(this.bounds.origin)); - } - if (this.settings.primarycolor === "transparent" && - this.currentTool !== "crosshairs") { - this.erasermask = newCanvas(this.extent()); - this.merge(this.paper, this.erasermask); - } -}; - + if (this.currentTool === "paintbucket") { + return this.floodfill(pos.subtract(this.bounds.origin)); + } + if (this.settings.primarycolor === "transparent" && + this.currentTool !== "crosshairs") { + this.erasermask = newCanvas(this.extent()); + this.merge(this.paper, this.erasermask); + } +}; + PaintCanvasMorph.prototype.mouseMove = function (pos) { if (this.currentTool === "paintbucket") { return; } - - var relpos = pos.subtract(this.bounds.origin), - mctx = this.mask.getContext("2d"), - pctx = this.paper.getContext("2d"), - x = this.dragRect.origin.x, // original drag X - y = this.dragRect.origin.y, // original drag y - p = relpos.x, // current drag x - q = relpos.y, // current drag y - w = (p - x) / 2, // half the rect width - h = (q - y) / 2, // half the rect height - i; // iterator number - mctx.save(); - function newW() { - return Math.max(Math.abs(w), Math.abs(h)) * (w / Math.abs(w)); - } - function newH() { - return Math.max(Math.abs(w), Math.abs(h)) * (h / Math.abs(h)); - } - this.brushBuffer.push([p, q]); - mctx.lineWidth = this.settings.linewidth; - mctx.clearRect(0, 0, this.bounds.width(), this.bounds.height()); // mask - - this.dragRect.corner = relpos.subtract(this.dragRect.origin); // reset crn - - if (this.settings.primarycolor === "transparent" && - this.currentTool !== "crosshairs") { - this.merge(this.erasermask, this.mask); - pctx.clearRect(0, 0, this.bounds.width(), this.bounds.height()); - mctx.globalCompositeOperation = "destination-out"; - } else { - mctx.fillStyle = this.settings.primarycolor.toString(); - mctx.strokeStyle = this.settings.primarycolor.toString(); - } - switch (this.currentTool) { - case "rectangle": - if (this.isShiftPressed()) { - mctx.strokeRect(x, y, newW() * 2, newH() * 2); - } else { - mctx.strokeRect(x, y, w * 2, h * 2); - } - break; - case "rectangleSolid": - if (this.isShiftPressed()) { - mctx.fillRect(x, y, newW() * 2, newH() * 2); - } else { - mctx.fillRect(x, y, w * 2, h * 2); - } - break; - case "brush": - mctx.lineCap = "round"; - mctx.lineJoin = "round"; - mctx.beginPath(); - mctx.moveTo(this.brushBuffer[0][0], this.brushBuffer[0][1]); - for (i = 0; i < this.brushBuffer.length; i += 1) { - mctx.lineTo(this.brushBuffer[i][0], this.brushBuffer[i][1]); - } - mctx.stroke(); - break; - case "line": - mctx.beginPath(); - mctx.moveTo(x, y); - if (this.isShiftPressed()) { - if (Math.abs(h) > Math.abs(w)) { - mctx.lineTo(x, q); - } else { - mctx.lineTo(p, y); - } - } else { - mctx.lineTo(p, q); - } - mctx.stroke(); - break; - case "circle": - case "circleSolid": - mctx.beginPath(); - if (this.isShiftPressed()) { - mctx.arc( - x, - y, - new Point(x, y).distanceTo(new Point(p, q)), - 0, - Math.PI * 2, - false - ); - } else { - for (i = 0; i < 480; i += 1) { - mctx.lineTo( - i, - (2 * h) * Math.sqrt(2 - Math.pow( - (i - x) / (2 * w), - 2 - )) + y - ); - } - for (i = 480; i > 0; i -= 1) { - mctx.lineTo( - i, - -1 * (2 * h) * Math.sqrt(2 - Math.pow( - (i - x) / (2 * w), - 2 - )) + y - ); - } - } - mctx.closePath(); - if (this.currentTool === "circleSolid") { - mctx.fill(); - } else { - if (this.currentTool === "circle") { - mctx.stroke(); - } - } - break; + + var relpos = pos.subtract(this.bounds.origin), + mctx = this.mask.getContext("2d"), + pctx = this.paper.getContext("2d"), + x = this.dragRect.origin.x, // original drag X + y = this.dragRect.origin.y, // original drag y + p = relpos.x, // current drag x + q = relpos.y, // current drag y + w = (p - x) / 2, // half the rect width + h = (q - y) / 2, // half the rect height + i; // iterator number + mctx.save(); + function newW() { + return Math.max(Math.abs(w), Math.abs(h)) * (w / Math.abs(w)); + } + function newH() { + return Math.max(Math.abs(w), Math.abs(h)) * (h / Math.abs(h)); + } + this.brushBuffer.push([p, q]); + mctx.lineWidth = this.settings.linewidth; + mctx.clearRect(0, 0, this.bounds.width(), this.bounds.height()); // mask + + this.dragRect.corner = relpos.subtract(this.dragRect.origin); // reset crn + + if (this.settings.primarycolor === "transparent" && + this.currentTool !== "crosshairs") { + this.merge(this.erasermask, this.mask); + pctx.clearRect(0, 0, this.bounds.width(), this.bounds.height()); + mctx.globalCompositeOperation = "destination-out"; + } else { + mctx.fillStyle = this.settings.primarycolor.toString(); + mctx.strokeStyle = this.settings.primarycolor.toString(); + } + switch (this.currentTool) { + case "rectangle": + if (this.isShiftPressed()) { + mctx.strokeRect(x, y, newW() * 2, newH() * 2); + } else { + mctx.strokeRect(x, y, w * 2, h * 2); + } + break; + case "rectangleSolid": + if (this.isShiftPressed()) { + mctx.fillRect(x, y, newW() * 2, newH() * 2); + } else { + mctx.fillRect(x, y, w * 2, h * 2); + } + break; + case "brush": + mctx.lineCap = "round"; + mctx.lineJoin = "round"; + mctx.beginPath(); + mctx.moveTo(this.brushBuffer[0][0], this.brushBuffer[0][1]); + for (i = 0; i < this.brushBuffer.length; i += 1) { + mctx.lineTo(this.brushBuffer[i][0], this.brushBuffer[i][1]); + } + mctx.stroke(); + break; + case "line": + mctx.beginPath(); + mctx.moveTo(x, y); + if (this.isShiftPressed()) { + if (Math.abs(h) > Math.abs(w)) { + mctx.lineTo(x, q); + } else { + mctx.lineTo(p, y); + } + } else { + mctx.lineTo(p, q); + } + mctx.stroke(); + break; + case "circle": + case "circleSolid": + mctx.beginPath(); + if (this.isShiftPressed()) { + mctx.arc( + x, + y, + new Point(x, y).distanceTo(new Point(p, q)), + 0, + Math.PI * 2, + false + ); + } else { + for (i = 0; i < 480; i += 1) { + mctx.lineTo( + i, + (2 * h) * Math.sqrt(2 - Math.pow( + (i - x) / (2 * w), + 2 + )) + y + ); + } + for (i = 480; i > 0; i -= 1) { + mctx.lineTo( + i, + -1 * (2 * h) * Math.sqrt(2 - Math.pow( + (i - x) / (2 * w), + 2 + )) + y + ); + } + } + mctx.closePath(); + if (this.currentTool === "circleSolid") { + mctx.fill(); + } else { + if (this.currentTool === "circle") { + mctx.stroke(); + } + } + break; case "crosshairs": this.rotationCenter = relpos.copy(); this.drawcrosshair(mctx); - break; - case "eraser": - this.merge(this.paper, this.mask); - mctx.save(); - mctx.globalCompositeOperation = "destination-out"; - mctx.beginPath(); - mctx.moveTo(this.brushBuffer[0][0], this.brushBuffer[0][1]); - for (i = 0; i < this.brushBuffer.length; i += 1) { - mctx.lineTo(this.brushBuffer[i][0], this.brushBuffer[i][1]); - } - mctx.stroke(); - mctx.restore(); - this.paper = newCanvas(this.extent()); - this.merge(this.mask, this.paper); - break; - default: - nop(); - } - this.previousDragPoint = relpos; - this.drawNew(); - this.changed(); - mctx.restore(); -}; - + break; + case "eraser": + this.merge(this.paper, this.mask); + mctx.save(); + mctx.globalCompositeOperation = "destination-out"; + mctx.beginPath(); + mctx.moveTo(this.brushBuffer[0][0], this.brushBuffer[0][1]); + for (i = 0; i < this.brushBuffer.length; i += 1) { + mctx.lineTo(this.brushBuffer[i][0], this.brushBuffer[i][1]); + } + mctx.stroke(); + mctx.restore(); + this.paper = newCanvas(this.extent()); + this.merge(this.mask, this.paper); + break; + default: + nop(); + } + this.previousDragPoint = relpos; + this.drawNew(); + this.changed(); + mctx.restore(); +}; + PaintCanvasMorph.prototype.mouseClickLeft = function () { - if (this.currentTool !== "crosshairs") { - this.merge(this.mask, this.paper); - } - this.brushBuffer = []; -}; + if (this.currentTool !== "crosshairs") { + this.merge(this.mask, this.paper); + } + this.brushBuffer = []; +}; + +PaintCanvasMorph.prototype.mouseLeaveDragging + = PaintCanvasMorph.prototype.mouseClickLeft; PaintCanvasMorph.prototype.buildContents = function () { this.background = newCanvas(this.extent()); @@ -903,47 +907,47 @@ PaintCanvasMorph.prototype.buildContents = function () { } } }; - -PaintCanvasMorph.prototype.drawNew = function () { - var can = newCanvas(this.extent()); - this.merge(this.background, can); - this.merge(this.paper, can); - this.merge(this.mask, can); - this.image = can; - this.drawFrame(); -}; - -PaintCanvasMorph.prototype.drawFrame = function () { - var context, borderColor; - - context = this.image.getContext('2d'); - if (this.parent) { - this.color = this.parent.color.lighter(this.contrast * 0.75); - borderColor = this.parent.color; - } else { - borderColor = new Color(120, 120, 120); - } - context.fillStyle = this.color.toString(); - - // cache my border colors - this.cachedClr = borderColor.toString(); - this.cachedClrBright = borderColor.lighter(this.contrast) - .toString(); - this.cachedClrDark = borderColor.darker(this.contrast).toString(); - this.drawRectBorder(context); -}; - -PaintCanvasMorph.prototype.drawRectBorder - = InputFieldMorph.prototype.drawRectBorder; - -PaintCanvasMorph.prototype.edge - = InputFieldMorph.prototype.edge; - -PaintCanvasMorph.prototype.fontSize - = InputFieldMorph.prototype.fontSize; - -PaintCanvasMorph.prototype.typeInPadding - = InputFieldMorph.prototype.typeInPadding; - -PaintCanvasMorph.prototype.contrast - = InputFieldMorph.prototype.contrast; + +PaintCanvasMorph.prototype.drawNew = function () { + var can = newCanvas(this.extent()); + this.merge(this.background, can); + this.merge(this.paper, can); + this.merge(this.mask, can); + this.image = can; + this.drawFrame(); +}; + +PaintCanvasMorph.prototype.drawFrame = function () { + var context, borderColor; + + context = this.image.getContext('2d'); + if (this.parent) { + this.color = this.parent.color.lighter(this.contrast * 0.75); + borderColor = this.parent.color; + } else { + borderColor = new Color(120, 120, 120); + } + context.fillStyle = this.color.toString(); + + // cache my border colors + this.cachedClr = borderColor.toString(); + this.cachedClrBright = borderColor.lighter(this.contrast) + .toString(); + this.cachedClrDark = borderColor.darker(this.contrast).toString(); + this.drawRectBorder(context); +}; + +PaintCanvasMorph.prototype.drawRectBorder + = InputFieldMorph.prototype.drawRectBorder; + +PaintCanvasMorph.prototype.edge + = InputFieldMorph.prototype.edge; + +PaintCanvasMorph.prototype.fontSize + = InputFieldMorph.prototype.fontSize; + +PaintCanvasMorph.prototype.typeInPadding + = InputFieldMorph.prototype.typeInPadding; + +PaintCanvasMorph.prototype.contrast + = InputFieldMorph.prototype.contrast; -- cgit v1.3.1 From fa88fdc761faa224d307e833f74163df48cedb0c Mon Sep 17 00:00:00 2001 From: jmoenig Date: Thu, 9 Jan 2014 18:50:38 +0100 Subject: validated all source files against the latest JSLint version and pushed to this date --- README.md | 2 +- blocks.js | 2 +- byob.js | 4 ++-- cloud.js | 7 ++----- gui.js | 6 +++--- history.txt | 3 ++- lang-de.js | 2 +- lists.js | 4 ++-- locale.js | 2 +- objects.js | 2 +- paint.js | 4 ++-- store.js | 4 ++-- threads.js | 2 +- widgets.js | 4 ++-- 14 files changed, 23 insertions(+), 25 deletions(-) (limited to 'paint.js') diff --git a/README.md b/README.md index 8564d27..cf17e18 100644 --- a/README.md +++ b/README.md @@ -9,7 +9,7 @@ inspired by Scratch written by Jens Mönig and Brian Harvey jens@moenig.org, bh@cs.berkeley.edu -Copyright (C) 2013 by Jens Mönig and Brian Harvey +Copyright (C) 2014 by Jens Mönig and Brian Harvey Snap! is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as diff --git a/blocks.js b/blocks.js index 9997d70..0ce1478 100644 --- a/blocks.js +++ b/blocks.js @@ -9,7 +9,7 @@ written by Jens Mönig jens@moenig.org - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. diff --git a/byob.js b/byob.js index 8093266..aff32ad 100644 --- a/byob.js +++ b/byob.js @@ -9,7 +9,7 @@ written by Jens Mönig jens@moenig.org - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. @@ -106,7 +106,7 @@ SymbolMorph, isNil*/ // Global stuff //////////////////////////////////////////////////////// -modules.byob = '2013-November-26'; +modules.byob = '2014-January-09'; // Declarations diff --git a/cloud.js b/cloud.js index 5ff2f77..17fc76b 100644 --- a/cloud.js +++ b/cloud.js @@ -6,7 +6,7 @@ written by Jens Mönig - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. @@ -29,7 +29,7 @@ /*global modules, IDE_Morph, SnapSerializer, hex_sha512, alert, nop*/ -modules.cloud = '2013-November-26'; +modules.cloud = '2014-January-09'; // Global stuff @@ -37,9 +37,6 @@ var Cloud; var SnapCloud = new Cloud( 'https://snapcloud.miosoft.com/miocon/app/login?_app=SnapCloud' - //'192.168.2.110:8087/miocon/app/login?_app=SnapCloud' - //'192.168.186.146:8087/miocon/app/login?_app=SnapCloud' - // 'localhost/miocon/app/login?_app=SnapCloud' ); // Cloud ///////////////////////////////////////////////////////////// diff --git a/gui.js b/gui.js index d7f562e..0adc325 100644 --- a/gui.js +++ b/gui.js @@ -9,7 +9,7 @@ written by Jens Mönig jens@moenig.org - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. @@ -68,7 +68,7 @@ sb, CommentMorph, CommandBlockMorph, BlockLabelPlaceHolderMorph*/ // Global stuff //////////////////////////////////////////////////////// -modules.gui = '2013-November-07'; +modules.gui = '2014-January-09'; // Declarations @@ -2391,7 +2391,7 @@ IDE_Morph.prototype.aboutSnap = function () { world = this.world(); aboutTxt = 'Snap! 4.0\nBuild Your Own Blocks\n\n--- beta ---\n\n' - + 'Copyright \u24B8 2013 Jens M\u00F6nig and ' + + 'Copyright \u24B8 2014 Jens M\u00F6nig and ' + 'Brian Harvey\n' + 'jens@moenig.org, bh@cs.berkeley.edu\n\n' diff --git a/history.txt b/history.txt index 2411d8f..f0569ff 100755 --- a/history.txt +++ b/history.txt @@ -2062,4 +2062,5 @@ ______ * Blocks, Objects, Threads: Collapse old STOP primitives into a single one with a dropdown of options * German translation update for new (migrated) STOP block * Morphic: Fixed updateReferences() (how could nobody notice so long?!) -* Store: resolved unexpected assignment expressions (conform to the latest JSLint quibbles) +* XML: resolved unexpected assignment expressions (conform to the latest JSLint quibbles) +* validated all source files against the latest JSLint version diff --git a/lang-de.js b/lang-de.js index 2013833..0b438b5 100644 --- a/lang-de.js +++ b/lang-de.js @@ -6,7 +6,7 @@ written by Jens Mönig - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. diff --git a/lists.js b/lists.js index 60cd7e3..3166bf1 100644 --- a/lists.js +++ b/lists.js @@ -7,7 +7,7 @@ written by Jens Mönig and Brian Harvey jens@moenig.org, bh@cs.berkeley.edu - Copyright (C) 2013 by Jens Mönig and Brian Harvey + Copyright (C) 2014 by Jens Mönig and Brian Harvey This file is part of Snap!. @@ -61,7 +61,7 @@ PushButtonMorph, SyntaxElementMorph, Color, Point, WatcherMorph, StringMorph, SpriteMorph, ScrollFrameMorph, CellMorph, ArrowMorph, MenuMorph, snapEquals, Morph, isNil, localize, MorphicPreferences*/ -modules.lists = '2013-December-04'; +modules.lists = '2014-January-09'; var List; var ListWatcherMorph; diff --git a/locale.js b/locale.js index eb79862..3b65ec9 100644 --- a/locale.js +++ b/locale.js @@ -6,7 +6,7 @@ written by Jens Mönig - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. diff --git a/objects.js b/objects.js index 3f3df76..af482b1 100644 --- a/objects.js +++ b/objects.js @@ -9,7 +9,7 @@ written by Jens Mönig jens@moenig.org - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. diff --git a/paint.js b/paint.js index 15b4172..1929f95 100644 --- a/paint.js +++ b/paint.js @@ -5,7 +5,7 @@ inspired by the Scratch paint editor. written by Kartik Chandra - Copyright (C) 2013 by Kartik Chandra + Copyright (C) 2014 by Kartik Chandra This file is part of Snap!. @@ -64,7 +64,7 @@ // Global stuff //////////////////////////////////////////////////////// -modules.paint = '2014-January-08'; +modules.paint = '2014-January-09'; // Declarations diff --git a/store.js b/store.js index 640f2d1..343dca6 100644 --- a/store.js +++ b/store.js @@ -7,7 +7,7 @@ written by Jens Mönig jens@moenig.org - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. @@ -61,7 +61,7 @@ SyntaxElementMorph*/ // Global stuff //////////////////////////////////////////////////////// -modules.store = '2013-December-19'; +modules.store = '2014-January-09'; // XML_Serializer /////////////////////////////////////////////////////// diff --git a/threads.js b/threads.js index 79af3b9..722ce6b 100644 --- a/threads.js +++ b/threads.js @@ -9,7 +9,7 @@ written by Jens Mönig jens@moenig.org - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. diff --git a/widgets.js b/widgets.js index 566d60c..c8dbd03 100644 --- a/widgets.js +++ b/widgets.js @@ -7,7 +7,7 @@ written by Jens Mönig jens@moenig.org - Copyright (C) 2013 by Jens Mönig + Copyright (C) 2014 by Jens Mönig This file is part of Snap!. @@ -74,7 +74,7 @@ HTMLCanvasElement, fontHeight, SymbolMorph, localize, SpeechBubbleMorph, ArrowMorph, MenuMorph, isString, isNil, SliderMorph, MorphicPreferences, ScrollFrameMorph*/ -modules.widgets = '2013-November-26'; +modules.widgets = '2014-January-09'; var PushButtonMorph; var ToggleButtonMorph; -- cgit v1.3.1