diff options
Diffstat (limited to 'js/tools/BrushTool.js')
-rw-r--r-- | js/tools/BrushTool.js | 174 |
1 files changed, 131 insertions, 43 deletions
diff --git a/js/tools/BrushTool.js b/js/tools/BrushTool.js index 4ce9976a..f7f0e4bf 100644 --- a/js/tools/BrushTool.js +++ b/js/tools/BrushTool.js | |||
@@ -16,6 +16,9 @@ var snapManager = require("js/helper-classes/3D/snap-manager").SnapManager; | |||
16 | 16 | ||
17 | var BrushStroke = require("js/lib/geom/brush-stroke").BrushStroke; | 17 | var BrushStroke = require("js/lib/geom/brush-stroke").BrushStroke; |
18 | 18 | ||
19 | //whether or not we want the mouse move to be handled all the time (not just while drawing) inside the brush tool | ||
20 | var g_DoBrushToolMouseMove = true; | ||
21 | |||
19 | exports.BrushTool = Montage.create(ShapeTool, { | 22 | exports.BrushTool = Montage.create(ShapeTool, { |
20 | hasReel: { value: false }, | 23 | hasReel: { value: false }, |
21 | _toolID: { value: "brushTool" }, | 24 | _toolID: { value: "brushTool" }, |
@@ -36,6 +39,7 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
36 | //view options | 39 | //view options |
37 | _brushStrokeCanvas: {value: null, writable: true}, | 40 | _brushStrokeCanvas: {value: null, writable: true}, |
38 | _brushStrokePlaneMat: {value: null, writable: true}, | 41 | _brushStrokePlaneMat: {value: null, writable: true}, |
42 | _draggingPlane: {value: null, writable: true}, | ||
39 | 43 | ||
40 | //the current brush stroke | 44 | //the current brush stroke |
41 | _selectedBrushStroke: {value: null, writable: true}, | 45 | _selectedBrushStroke: {value: null, writable: true}, |
@@ -61,9 +65,8 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
61 | } | 65 | } |
62 | 66 | ||
63 | this.startDraw(event); | 67 | this.startDraw(event); |
64 | if (this._brushStrokePlaneMat === null) { | 68 | this._brushStrokePlaneMat = this.mouseDownHitRec.getPlaneMatrix(); |
65 | this._brushStrokePlaneMat = this.mouseDownHitRec.getPlaneMatrix(); | 69 | |
66 | } | ||
67 | //start a new brush stroke | 70 | //start a new brush stroke |
68 | if (this._selectedBrushStroke === null){ | 71 | if (this._selectedBrushStroke === null){ |
69 | this._selectedBrushStroke = new BrushStroke(); | 72 | this._selectedBrushStroke = new BrushStroke(); |
@@ -73,6 +76,7 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
73 | if (this.application.ninja.colorController.colorToolbar.fill.webGlColor){ | 76 | if (this.application.ninja.colorController.colorToolbar.fill.webGlColor){ |
74 | this._selectedBrushStroke.setSecondStrokeColor(this.application.ninja.colorController.colorToolbar.fill.webGlColor); | 77 | this._selectedBrushStroke.setSecondStrokeColor(this.application.ninja.colorController.colorToolbar.fill.webGlColor); |
75 | } | 78 | } |
79 | |||
76 | //add this point to the brush stroke in case the user does a mouse up before doing a mouse move | 80 | //add this point to the brush stroke in case the user does a mouse up before doing a mouse move |
77 | var currMousePos = this._getUnsnappedPosition(event.pageX, event.pageY); | 81 | var currMousePos = this._getUnsnappedPosition(event.pageX, event.pageY); |
78 | this._selectedBrushStroke.addPoint(currMousePos); | 82 | this._selectedBrushStroke.addPoint(currMousePos); |
@@ -85,7 +89,7 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
85 | 89 | ||
86 | var strokeHardness = 100; | 90 | var strokeHardness = 100; |
87 | if (this.options.strokeHardness){ | 91 | if (this.options.strokeHardness){ |
88 | strokeHardness = ShapesController.GetValueInPixels(this.options.strokeHardness.value, this.options.strokeHardness.units); | 92 | strokeHardness = this.options.strokeHardness.value; |
89 | } | 93 | } |
90 | this._selectedBrushStroke.setStrokeHardness(strokeHardness); | 94 | this._selectedBrushStroke.setStrokeHardness(strokeHardness); |
91 | 95 | ||
@@ -94,7 +98,10 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
94 | doSmoothing = this.options.doSmoothing; | 98 | doSmoothing = this.options.doSmoothing; |
95 | } | 99 | } |
96 | this._selectedBrushStroke.setDoSmoothing(doSmoothing); | 100 | this._selectedBrushStroke.setDoSmoothing(doSmoothing); |
97 | 101 | if (doSmoothing){ | |
102 | this._selectedBrushStroke.setSmoothingAmount(this.options.smoothingAmount.value); | ||
103 | } | ||
104 | |||
98 | var useCalligraphic = false; | 105 | var useCalligraphic = false; |
99 | if (this.options.useCalligraphic){ | 106 | if (this.options.useCalligraphic){ |
100 | useCalligraphic = this.options.useCalligraphic; | 107 | useCalligraphic = this.options.useCalligraphic; |
@@ -103,15 +110,16 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
103 | this._selectedBrushStroke.setStrokeUseCalligraphic(true); | 110 | this._selectedBrushStroke.setStrokeUseCalligraphic(true); |
104 | var strokeAngle = 0; | 111 | var strokeAngle = 0; |
105 | if (this.options.strokeAngle){ | 112 | if (this.options.strokeAngle){ |
106 | strokeAngle= ShapesController.GetValueInPixels(this.options.strokeAngle.value, this.options.strokeAngle.units); | 113 | strokeAngle= this.options.strokeAngle.value; |
107 | } | 114 | } |
108 | this._selectedBrushStroke.setStrokeAngle(Math.PI * -strokeAngle/180); | 115 | this._selectedBrushStroke.setStrokeAngle(Math.PI * strokeAngle/180); |
109 | } else { | 116 | } else { |
110 | this._selectedBrushStroke.setStrokeUseCalligraphic(false); | 117 | this._selectedBrushStroke.setStrokeUseCalligraphic(false); |
111 | } | 118 | } |
112 | 119 | ||
113 | } | 120 | } |
114 | NJevent("enableStageMove");//stageManagerModule.stageManager.enableMouseMove(); | 121 | if (!g_DoBrushToolMouseMove) |
122 | NJevent("enableStageMove");//stageManagerModule.stageManager.enableMouseMove(); | ||
115 | } //value: function (event) { | 123 | } //value: function (event) { |
116 | }, //HandleLeftButtonDown | 124 | }, //HandleLeftButtonDown |
117 | 125 | ||
@@ -126,7 +134,9 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
126 | snapManager.enableSnapAlign(false); | 134 | snapManager.enableSnapAlign(false); |
127 | 135 | ||
128 | var point = webkitConvertPointFromPageToNode(this.application.ninja.stage.canvas, new WebKitPoint(x,y)); | 136 | var point = webkitConvertPointFromPageToNode(this.application.ninja.stage.canvas, new WebKitPoint(x,y)); |
137 | //todo fix this function to allow us to get the correct location (in 3D) for the mouse position | ||
129 | var unsnappedpos = DrawingToolBase.getHitRecPos(snapManager.snap(point.x, point.y, false)); | 138 | var unsnappedpos = DrawingToolBase.getHitRecPos(snapManager.snap(point.x, point.y, false)); |
139 | this._draggingPlane = snapManager.getDragPlane(); | ||
130 | 140 | ||
131 | snapManager.enableElementSnap(elemSnap); | 141 | snapManager.enableElementSnap(elemSnap); |
132 | snapManager.enableGridSnap(gridSnap); | 142 | snapManager.enableGridSnap(gridSnap); |
@@ -147,13 +157,15 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
147 | return; | 157 | return; |
148 | } | 158 | } |
149 | 159 | ||
160 | var currMousePos = this._getUnsnappedPosition(event.pageX, event.pageY); | ||
150 | if (this._isDrawing) { | 161 | if (this._isDrawing) { |
151 | var currMousePos = this._getUnsnappedPosition(event.pageX, event.pageY); | ||
152 | if (this._selectedBrushStroke && this._selectedBrushStroke.getNumPoints()<1000){ | 162 | if (this._selectedBrushStroke && this._selectedBrushStroke.getNumPoints()<1000){ |
153 | this._selectedBrushStroke.addPoint(currMousePos); | 163 | this._selectedBrushStroke.addPoint(currMousePos); |
154 | } | 164 | } |
155 | this.ShowCurrentBrushStrokeOnStage(); | 165 | this.ShowCurrentBrushStrokeOnStage(); |
156 | } //if (this._isDrawing) { | 166 | } else { |
167 | this.ShowCurrentBrushIconOnStage(currMousePos); | ||
168 | } | ||
157 | 169 | ||
158 | //this.drawLastSnap(); //TODO.. is this line necessary if we're not snapping? // Required cleanup for both Draw/Feedbacks | 170 | //this.drawLastSnap(); //TODO.. is this line necessary if we're not snapping? // Required cleanup for both Draw/Feedbacks |
159 | 171 | ||
@@ -164,27 +176,69 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
164 | 176 | ||
165 | HandleLeftButtonUp: { | 177 | HandleLeftButtonUp: { |
166 | value: function (event) { | 178 | value: function (event) { |
167 | /*var drawData = this.getDrawingData(); | ||
168 | if (drawData) { | ||
169 | if (this._brushStrokePlaneMat === null) { | ||
170 | this._brushStrokePlaneMat = drawData.planeMat; | ||
171 | } | ||
172 | } | ||
173 | if (this._isDrawing) { | ||
174 | this.doDraw(event); | ||
175 | }*/ | ||
176 | this.endDraw(event); | 179 | this.endDraw(event); |
177 | 180 | ||
178 | this._isDrawing = false; | 181 | this._isDrawing = false; |
179 | this._hasDraw = false; | 182 | this._hasDraw = false; |
180 | 183 | ||
181 | 184 | //finish giving enough info. to the brush stroke | |
185 | this._selectedBrushStroke.setPlaneMatrix(this._brushStrokePlaneMat); | ||
186 | this._selectedBrushStroke.setPlaneMatrixInverse(glmat4.inverse(this._brushStrokePlaneMat,[])); | ||
187 | this._selectedBrushStroke.setDragPlane(this._draggingPlane); | ||
188 | |||
182 | //display the previously drawn stroke in a separate canvas | 189 | //display the previously drawn stroke in a separate canvas |
183 | this.RenderCurrentBrushStroke(); | 190 | this.RenderCurrentBrushStroke(); |
184 | 191 | ||
185 | this._selectedBrushStroke = null; | 192 | this._selectedBrushStroke = null; |
186 | this._brushStrokeCanvas = null; | 193 | this._brushStrokeCanvas = null; |
187 | NJevent("disableStageMove"); | 194 | if (!g_DoBrushToolMouseMove) |
195 | NJevent("disableStageMove"); | ||
196 | } | ||
197 | }, | ||
198 | |||
199 | ShowCurrentBrushIconOnStage:{ | ||
200 | value: function(currMousePos) { | ||
201 | //clear the canvas before we draw anything else | ||
202 | this.application.ninja.stage.clearDrawingCanvas(); | ||
203 | //display the brush icon of proper size (query the options bar) | ||
204 | var strokeSize = 1; | ||
205 | if (this.options.strokeSize) { | ||
206 | strokeSize = ShapesController.GetValueInPixels(this.options.strokeSize.value, this.options.strokeSize.units); | ||
207 | } | ||
208 | var useCalligraphic = false; | ||
209 | if (this.options.useCalligraphic){ | ||
210 | useCalligraphic = this.options.useCalligraphic; | ||
211 | } | ||
212 | var ctx = this.application.ninja.stage.drawingContext;//stageManagerModule.stageManager.drawingContext; | ||
213 | if (ctx === null) | ||
214 | throw ("null drawing context in Brushtool::ShowCurrentBrushStrokeOnStage"); | ||
215 | ctx.save(); | ||
216 | |||
217 | var horizontalOffset = this.application.ninja.stage.userContentLeft; | ||
218 | var verticalOffset = this.application.ninja.stage.userContentTop; | ||
219 | var halfStrokeWidth = 0.5*strokeSize; | ||
220 | ctx.beginPath(); | ||
221 | if (!useCalligraphic) { | ||
222 | //for round brushes, draw a circle at the current mouse position | ||
223 | ctx.arc(currMousePos[0] + horizontalOffset, currMousePos[1]+ verticalOffset, halfStrokeWidth, 0, 2 * Math.PI, false); | ||
224 | } else { | ||
225 | //draw an angled stroke to represent the brush tip | ||
226 | var strokeAngle = 0; | ||
227 | if (this.options.strokeAngle){ | ||
228 | strokeAngle= this.options.strokeAngle.value; | ||
229 | } | ||
230 | strokeAngle = Math.PI * strokeAngle/180; | ||
231 | var deltaDisplacement = [Math.cos(strokeAngle),Math.sin(strokeAngle)]; | ||
232 | deltaDisplacement = VecUtils.vecNormalize(2, deltaDisplacement, 1); | ||
233 | var startPos = VecUtils.vecSubtract(2, currMousePos, [-horizontalOffset+halfStrokeWidth*deltaDisplacement[0],-verticalOffset+halfStrokeWidth*deltaDisplacement[1]]); | ||
234 | ctx.moveTo(startPos[0], startPos[1]); | ||
235 | var endPos = VecUtils.vecAdd(2, startPos, [strokeSize*deltaDisplacement[0], strokeSize*deltaDisplacement[1]]); | ||
236 | ctx.lineTo(endPos[0], endPos[1]); | ||
237 | ctx.lineWidth = 2; | ||
238 | } | ||
239 | ctx.strokeStyle = "black"; | ||
240 | ctx.stroke(); | ||
241 | ctx.restore(); | ||
188 | } | 242 | } |
189 | }, | 243 | }, |
190 | 244 | ||
@@ -193,30 +247,16 @@ exports.BrushTool = Montage.create(ShapeTool, { | |||
193 | //clear the canvas before we draw anything else | 247 | //clear the canvas before we draw anything else |
194 | this.application.ninja.stage.clearDrawingCanvas(); | 248 | this.application.ninja.stage.clearDrawingCanvas(); |
195 | if (this._selectedBrushStroke && this._selectedBrushStroke.getNumPoints()>0){ | 249 | if (this._selectedBrushStroke && this._selectedBrushStroke.getNumPoints()>0){ |
196 | //this._selectedBrushStroke.computeMetaGeometry(); | ||
197 | var ctx = this.application.ninja.stage.drawingContext;//stageManagerModule.stageManager.drawingContext; | 250 | var ctx = this.application.ninja.stage.drawingContext;//stageManagerModule.stageManager.drawingContext; |
198 | if (ctx === null) | 251 | if (ctx === null) |
199 | throw ("null drawing context in Brushtool::ShowCurrentBrushStrokeOnStage"); |