From d7d78d4a4e8cf82c56379d25efbe679b3b823abc Mon Sep 17 00:00:00 2001 From: Pushkar Joshi Date: Thu, 1 Mar 2012 11:22:46 -0800 Subject: show feedback on mouseover on a part of the path where a new anchor will be added if clicked --- js/helper-classes/RDGE/GLSubpath.js | 147 ++++++++++++++++++++++++++++++------ 1 file changed, 124 insertions(+), 23 deletions(-) (limited to 'js/helper-classes') diff --git a/js/helper-classes/RDGE/GLSubpath.js b/js/helper-classes/RDGE/GLSubpath.js index f3d8ad36..2fb91d33 100755 --- a/js/helper-classes/RDGE/GLSubpath.js +++ b/js/helper-classes/RDGE/GLSubpath.js @@ -505,7 +505,6 @@ GLSubpath.prototype._isWithinBoundingBox = function(point, ctrlPts, radius) { GLSubpath.prototype.pickAnchor = function (pickX, pickY, pickZ, radius) { var numAnchors = this._Anchors.length; var selAnchorIndex = -1; - var retCode = this.SEL_NONE; var radSq = radius * radius; var minDistance = Infinity; //check if the clicked location is close to the currently selected anchor position @@ -515,9 +514,23 @@ GLSubpath.prototype.pickAnchor = function (pickX, pickY, pickZ, radius) { if (distSq < minDistance && distSq < radSq) { selAnchorIndex = this._selectedAnchorIndex; minDistance = distSq; - retCode = retCode | this.SEL_ANCHOR; + } else { + //check the prev and next of the selected anchor if the above did not register a hit + distSq = this._Anchors[this._selectedAnchorIndex].getPrevDistanceSq(pickX, pickY, pickZ); + if (distSq < minDistance && distSq < radSq){ + selAnchorIndex = this._selectedAnchorIndex; + minDistance = distSq; + } else { + //check the next for this anchor point + distSq = this._Anchors[this._selectedAnchorIndex].getNextDistanceSq(pickX, pickY, pickZ); + if (distSqx || this._BBoxMin[1]>y || this._BBoxMin[2]>z){ + return false; + } + if (this._BBoxMax[0]=0 && this._selectedAnchorIndex=0 && selAnchorIndex === -1) { + var distSq = this._Anchors[this._selectedAnchorIndex].getPrevDistanceSq(pickX, pickY, pickZ); + if (distSq < minDistance && distSq < radSq){ + selAnchorIndex = this._selectedAnchorIndex; + minDistance = distSq; + } else { + //check the next for this anchor point + distSq = this._Anchors[this._selectedAnchorIndex].getNextDistanceSq(pickX, pickY, pickZ); + if (distSq1) { + //if (numPoints>1) { + if (0){ var threshold = this._WETNESS_FACTOR*this._strokeWidth; var prevPt = this._Points[0]; var prevIndex = 0; @@ -331,7 +332,7 @@ function GLBrushStroke() { } */ - + /* var R2 = this._strokeWidth; var R = R2*0.5; var hardness = 0; //for a pencil, this is always 1 //TODO get hardness parameter from user interface @@ -359,6 +360,48 @@ function GLBrushStroke() { //ctx.globalCompositeOperation = 'source-in'; //ctx.rect(x-R, y-R, R2, R2); } + */ + + //todo test how to render the path as a bunch of moveTo and lineTos (for calligraphic brush styles) + var numTraces = this._strokeWidth; + var halfNumTraces = numTraces/2; + var deltaDisplacement = [1,0];//[this._strokeWidth/numTraces, 0]; //a horizontal line brush + var startPos = [-this._strokeWidth/2,0]; + for (var t=0;t1) { + var numInsertedPoints = 0; + var threshold = 5;//0.25*this._strokeWidth; //this determines whether a segment between two sample is too long + var prevPt = this._Points[0]; + for (var i=1;ithreshold){ + //build the control polygon for the Catmull-Rom spline (prev. 2 points and next 2 points) + var prev = (i===1) ? i-1 : i-2; + var next = (i===numPoints-1) ? i : i+1; + var ctrlPts = [this._Points[prev], this._Points[i-1], this._Points[i], this._Points[next]]; + //insert points along the prev. to current point + var numNewPoints = Math.floor(distance/threshold); + for (var j=0;j this._MAX_ALLOWED_SAMPLES){ + console.log("leaving the resampling because numPoints is greater than limit:"+this._MAX_ALLOWED_SAMPLES); + break; + } + } + console.log("Inserted "+numInsertedPoints+" additional CatmullRom points"); + } // *** compute the bounding box ********* this._BBoxMin = [Infinity, Infinity, Infinity]; this._BBoxMax = [-Infinity, -Infinity, -Infinity]; @@ -362,7 +404,6 @@ function GLBrushStroke() { } */ - //todo test how to render the path as a bunch of moveTo and lineTos (for calligraphic brush styles) var numTraces = this._strokeWidth; var halfNumTraces = numTraces/2; var deltaDisplacement = [1,0];//[this._strokeWidth/numTraces, 0]; //a horizontal line brush @@ -371,17 +412,20 @@ function GLBrushStroke() { var disp = [startPos[0]+t*deltaDisplacement[0], startPos[1]+t*deltaDisplacement[1]]; //ctx.globalCompositeOperation = 'source-over'; var distFromMiddle = Math.abs(halfNumTraces-t); - var alphaVal = 1.0 - (distFromMiddle/halfNumTraces); + var alphaVal = 1.0 - (100-this._strokeHardness)*(distFromMiddle/halfNumTraces)/100; ctx.save(); ctx.lineWidth=this._strokeWidth/10;//4; if (ctx.lineWidth<2) ctx.lineWidth=2; + if (t===numTraces-1){ + ctx.lineWidth = 1; + } ctx.lineJoin="bevel"; ctx.lineCap="butt"; if (t --- js/helper-classes/3D/snap-manager.js | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) (limited to 'js/helper-classes') diff --git a/js/helper-classes/3D/snap-manager.js b/js/helper-classes/3D/snap-manager.js index 596ba56a..5eef8b5c 100755 --- a/js/helper-classes/3D/snap-manager.js +++ b/js/helper-classes/3D/snap-manager.js @@ -1990,12 +1990,20 @@ var SnapManager = exports.SnapManager = Montage.create(Component, { }, setupDragPlanes : { - value: function( hitRec ) { + value: function( hitRec, inGlobalMode ) { // get the location of the point in stage world space var elt = hitRec.getElt(); var localPt = hitRec.getLocalPoint(); var planeMat = hitRec.getPlaneMatrix(); - var stageWorldPt = viewUtils.postViewToStageWorld( MathUtils.transformPoint(localPt,planeMat), elt ); + var stageWorldPt; + if(inGlobalMode) + { + stageWorldPt = MathUtils.transformPoint(localPt,planeMat); + } + else + { + stageWorldPt = viewUtils.postViewToStageWorld( MathUtils.transformPoint(localPt,planeMat), elt ); + } /* // get a working plane parallel to the current working plane through the stage world point -- cgit v1.2.3 From 264e3d8e6d3624083d2fab9fe2560234553bb2ad Mon Sep 17 00:00:00 2001 From: Pushkar Joshi Date: Tue, 6 Mar 2012 17:03:06 -0800 Subject: draw brush stroke as concentric paths overlaid on top of each other...allows us to simulate softness for circular brushes --- js/helper-classes/RDGE/GLBrushStroke.js | 135 +++++++++++++++++++++++--------- 1 file changed, 98 insertions(+), 37 deletions(-) (limited to 'js/helper-classes') diff --git a/js/helper-classes/RDGE/GLBrushStroke.js b/js/helper-classes/RDGE/GLBrushStroke.js index c1469977..26c922a3 100755 --- a/js/helper-classes/RDGE/GLBrushStroke.js +++ b/js/helper-classes/RDGE/GLBrushStroke.js @@ -81,7 +81,7 @@ function GLBrushStroke() { //add the point only if it is some epsilon away from the previous point var numPoints = this._Points.length; if (numPoints>0) { - var threshold = this._WETNESS_FACTOR*this._strokeWidth; + var threshold = 1;//this._WETNESS_FACTOR*this._strokeWidth; var prevPt = this._Points[numPoints-1]; var diffPt = [prevPt[0]-pt[0], prevPt[1]-pt[1]]; var diffPtMag = Math.sqrt(diffPt[0]*diffPt[0] + diffPt[1]*diffPt[1]); @@ -375,46 +375,58 @@ function GLBrushStroke() { */ /* - var R2 = this._strokeWidth; - var R = R2*0.5; - var hardness = 0; //for a pencil, this is always 1 //TODO get hardness parameter from user interface - var innerRadius = (hardness*R)-1; - if (innerRadius<1) - innerRadius=1; - - var r = ctx.createRadialGradient(0,0,innerRadius, 0,0,R); - var midColor = "rgba("+parseInt(255*this._strokeColor[0])+","+parseInt(255*this._strokeColor[1])+","+parseInt(255*this._strokeColor[2])+",1)"; - r.addColorStop(0, midColor); - var endColor = "rgba("+parseInt(255*this._strokeColor[0])+","+parseInt(255*this._strokeColor[1])+","+parseInt(255*this._strokeColor[2])+",0.0)"; - r.addColorStop(1, endColor); - ctx.fillStyle = r; - - for (var i = 0; i < numPoints; i++) { - var pt = this._Points[i]; - ctx.globalCompositeOperation = 'source-over'; - var x = pt[0]-bboxMin[0]; - var y = pt[1]-bboxMin[1]; - ctx.save(); - ctx.translate(x,y); - ctx.arc(0, 0, R, 0, 2 * Math.PI, false); - ctx.fill(); - ctx.restore(); - //ctx.globalCompositeOperation = 'source-in'; - //ctx.rect(x-R, y-R, R2, R2); - } - */ - + //build the stamp for the brush stroke + //todo get this directly from the UI + var t=0; var numTraces = this._strokeWidth; var halfNumTraces = numTraces/2; - var deltaDisplacement = [1,0];//[this._strokeWidth/numTraces, 0]; //a horizontal line brush var startPos = [-this._strokeWidth/2,0]; - for (var t=0;t");var f=this.def.shaders[a.vshader],g=this.def.shaders[a.fshader];this.ctx.useProgram(null);var h=null,l=null;f.indexOf("{")!=-1?l=f:(l=new XMLHttpRequest,l.open("GET",f,!1),l.send(null),l=l.responseText);h=this.buildShader(this.ctx.VERTEX_SHADER, -l);l=null;f.indexOf("{")!=-1?l=g:(l=new XMLHttpRequest,l.open("GET",g,!1),l.send(null),l=l.responseText);l=this.buildShader(this.ctx.FRAGMENT_SHADER,l);if(!h||!l)return null;this.compiledShaders[a.vshader]=h;this.compiledShaders[a.fshader]=l;f=this.ctx.createProgram();if(!f)return null;this.ctx.attachShader(f,h);this.ctx.attachShader(f,l);g=0;a.attribPairs=[];for(var n in a.attributes)a.attribPairs.push({loc:g,name:n}),this.ctx.bindAttribLocation(f,g++,n);this.ctx.linkProgram(f);return!this.ctx.getProgramParameter(f, -this.ctx.LINK_STATUS)?(a=this.ctx.getProgramInfoLog(f),window.console.log("Error in program linking:"+a),this.ctx.deleteProgram(f),this.ctx.deleteProgram(l),this.ctx.deleteProgram(h),null):f};this.setLightContext=function(a){for(t in this.technique)for(var f=this.technique.passes.length,g=0;g");var f=this.def.shaders[a.vshader],g=this.def.shaders[a.fshader];this.ctx.useProgram(null);var h=null,l=null;f.indexOf("{")!=-1? +l=f:(l=new XMLHttpRequest,l.open("GET",f,!1),l.send(null),l=l.responseText);h=this.buildShader(this.ctx.VERTEX_SHADER,l);l=null;f.indexOf("{")!=-1?l=g:(l=new XMLHttpRequest,l.open("GET",g,!1),l.send(null),l=l.responseText);l=this.buildShader(this.ctx.FRAGMENT_SHADER,l);if(!h||!l)return null;this.compiledShaders[a.vshader]=h;this.compiledShaders[a.fshader]=l;f=this.ctx.createProgram();if(!f)return null;this.ctx.attachShader(f,h);this.ctx.attachShader(f,l);g=0;a.attribPairs=[];for(var n in a.attributes)a.attribPairs.push({loc:g, +name:n}),this.ctx.bindAttribLocation(f,g++,n);this.ctx.linkProgram(f);return!this.ctx.getProgramParameter(f,this.ctx.LINK_STATUS)?(a=this.ctx.getProgramInfoLog(f),window.console.log("Error in program linking:"+a),this.ctx.deleteProgram(f),this.ctx.deleteProgram(l),this.ctx.deleteProgram(h),null):f};this.setLightContext=function(a){for(t in this.technique)for(var f=this.technique.passes.length,g=0;g