Why am I getting only a single circle in the canvas? - javascript

So I want my output something like this.
var circlePath = new Path.Circle(new Point(0, 0), 25);
circlePath.strokeColor = 'black';
var copy = [];
for(var i=0;i<=10;i++){
var j=100;
copy[i]= circlePath.clone();
copy[i].strokeColor = 'red';
copy[i].position = new Point(j, 0);
j=j+100;
}
Hence, I just used a variable to shift the copy to a new point. But it doesn't work and just displays a single circle.

Related

Paper.js use multiple moveTo commands on a path

I'm trying to do:
Using this code:
var p = new Path();
p.strokeColor = 'blue'
p.strokeWidth = 4
var size = 10
var o = new Point(100, 100)
p.moveTo (o.add ([-size, -size]))
p.lineTo (o.add ([size, size]))
p.moveTo (o.add ([size, -size]))
p.lineTo (o.add ([-size, size]))
But instead I get:
Apparently the second moveTo() is ignored. How could I make it work? I couldn't find anything in the documentation.
The solution in your case is to use CompoundPath instead of Path as you are intending to work on a group of paths.
There is a clue about that in the path.moveTo documentation:
On a normal empty Path, the point is simply added as the path’s first segment. If called on a CompoundPath, a new Path is created as a child and the point is added as its first segment.
Here is a sketch adapted from your initial code, demonstrating the solution.
var p = new CompoundPath();
p.strokeColor = 'blue';
p.strokeWidth = 4;
var size = 10;
var o = new Point(100, 100);
p.moveTo(o.add([-size, -size]));
p.lineTo(o.add([size, size]));
p.moveTo(o.add([size, -size]));
p.lineTo(o.add([-size, size]));
I ended up doing:
var s = 10 // size
var o = new Point(100, 100)
var p1 = new Path.Line (o.add ([-s, -s]), o.add ([s, s]))
var p2 = new Path.Line (o.add ([s, -s]), o.add ([-s, s]))
p2.strokeColor = p1.strokeColor = 'blue'
p2.strokeWidth = p1.strokeWidth = 4
Which is inelegant, but works. I have tried p1.unite (p2) but that also doesn't work.

Position Labels on a coordinate System Easeljs

Hey I am trying to build the following picture in canvas using the library:EaselJS.
My Picture components are:
two circles - yellow and red and a light green background
a coordinate system from 0 to 1 with all the necessary labels which appear in the picture.
I have succeeded in my two goals.
I have build a Coordinate System based on stackoverflow discussion:
How to draw a full coordinate system with Easeljs?.
I have left with 2 main problems which concern me a lot:
I need to draw a rectangle(or square) which fits the coordinate system, the current rectangle is just a background.
Also I need to add 3 labels: 'Critical Index' on the x axis, 'Long-term Severity Index' on the y axis and a headline of Long-term.
I would happy if someone could help me with this issues
I am adding the source code:
$(function(){
var stage = new createjs.Stage('canvas2d');
var circle1 = new createjs.Shape();
var circle2 = new createjs.Shape();
var rect = new createjs.Rectangle(0, 0, 100, 100);
circle2.graphics.beginFill("yellow").drawCircle(0, 0, 300);
circle2.x = 500;
circle2.y = 0;
stage.addChild(circle2);
circle1.graphics.beginFill("red").drawCircle(0, 0, 150);
circle1.x = 500;
circle1.y = 0;
stage.addChild(circle1);
//stage.addChild(rect);
stage.update();
var coord_xaxis = new createjs.Shape();
stage.addChild(coord_xaxis);
var coord_yaxis = new createjs.Shape();
stage.addChild(coord_yaxis);
var coord_arrow_x = new createjs.Shape();
//stage.addChild(coord_arrow_x);
var coord_arrow_y = new createjs.Shape();
//stage.addChild(coord_arrow_y);
var coord_xaxis_lines = new createjs.Shape();
stage.addChild(coord_xaxis_lines);
var coord_yaxis_lines = new createjs.Shape();
stage.addChild(coord_yaxis_lines);
/**$('#canvas2d').width()/15**/
var axis_center_x = $('#canvas2d').width()/15;
var axis_center_y = $('#canvas2d').height()/1.10;
var xaxis_width = $('#canvas2d').width()-0.05*$('#canvas2d').width();
var yaxis_width = $('#canvas2d').height()-0.05*$('#canvas2d').height();
var axis_start_x = ($('#canvas2d').width()-xaxis_width)/2;
var axis_start_y = ($('#canvas2d').height()-yaxis_width)/6;
var axis_strokewidth = 2;
coord_xaxis.graphics.setStrokeStyle(axis_strokewidth,'round').beginStroke('#000');
coord_xaxis.graphics.moveTo(axis_start_x, axis_center_y).lineTo(axis_start_x+xaxis_width, axis_center_y);
coord_yaxis.graphics.setStrokeStyle(axis_strokewidth,'round').beginStroke('#000');
coord_yaxis.graphics.moveTo(axis_center_x, axis_start_y).lineTo(axis_center_x, axis_start_y+yaxis_width);
// draw coordsys arrow for x-axis
var arrwidth = 5;
var arrxtnd = 5;
coord_arrow_x.graphics.beginFill('#000');
coord_arrow_x.graphics.setStrokeStyle(axis_strokewidth,'round').beginStroke('#000');
coord_arrow_x.graphics.moveTo(axis_center_x, axis_start_y-arrwidth/2).lineTo(axis_center_x+arrwidth, axis_start_y+arrwidth+arrxtnd).lineTo(axis_center_x-arrwidth, axis_start_y+arrwidth+arrxtnd).lineTo(axis_center_x, axis_start_y-arrwidth/2);
coord_arrow_x.graphics.endFill();
// draw coordsys arrow for y-axis
coord_arrow_y.graphics.beginFill('#000');
coord_arrow_y.graphics.beginStroke('#000');
coord_arrow_y.graphics.moveTo(axis_start_x+xaxis_width+arrwidth/2, axis_center_y).lineTo(axis_start_x+xaxis_width-arrwidth-arrxtnd, axis_center_y+arrwidth).lineTo(axis_start_x+xaxis_width-arrwidth-arrxtnd, axis_center_y-arrwidth).lineTo(axis_start_x+xaxis_width+arrwidth/2, axis_center_y);
coord_arrow_y.graphics.endFill();
var stepdist = xaxis_width/5.25;
var steplinew = 6;
// 10 horizontal lines
var xlines = 10;
var labels_x = [];
for(var i=xlines;i>=0;i--) {
// little black marker
coord_yaxis_lines.graphics.setStrokeStyle(1,'round').beginStroke('#000');
coord_yaxis_lines.graphics.moveTo(axis_center_x-steplinew, axis_center_y+(-i/2)*stepdist).lineTo(axis_center_x+steplinew, axis_center_y+(-i/2)*stepdist);
// labels
labels_x[i] = new createjs.Text('x', '14px Arial', '#333');
labels_x[i].x = axis_center_x-12;
labels_x[i].y = axis_center_y+(-i/2)*stepdist-6; // move up a bit
stage.addChild(labels_x[i]);
labels_x[i].text = (i/10);
labels_x[i].textAlign = 'right';
}
// 12 orthogonal lines
var stepdist2 = xaxis_width/6.5;
var steplinew2 = 6;
var ylines = 10;
var labels_y = [];
for(var i=ylines;i>=1;i--) {
// dont overdraw y-axis-line
// little black marker
coord_xaxis_lines.graphics.setStrokeStyle(1,'round').beginStroke('#000');
coord_xaxis_lines.graphics.moveTo(axis_center_x+(i/1.6)*stepdist2, axis_center_y-steplinew2).lineTo(axis_center_x+(i/1.6)*stepdist2, axis_center_y+steplinew2);
// labels
labels_y[i] = new createjs.Text('x', '14px Arial', '#333');
labels_y[i].x = axis_center_x+(i/1.6)*stepdist2; // move up a bit
labels_y[i].y = axis_center_y+12;
stage.addChild(labels_y[i]);
labels_y[i].text = (i/10);
labels_y[i].textAlign = 'center';
}
stage.update();
})
#canvas2d{
background-color: #32CD32;
}
<script src="https://code.createjs.com/createjs-2015.11.26.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<canvas id="canvas2d" width="500" height="500"></canvas>
The syntax for creating a rectangle in EaselJS is just the same as making a circle. The difference lies when calling drawRect instead of drawCircle in the graphics chain.
I've added a rectangle with arbitrary position and size values to match your overall code style, and because I couldn't find any criteria quickly. I also removed the background color on the CSS.
As for the addition of labels on each axis, I highly recommend you to use DOM instead. EaselJS support for text is almost unusable. Even EaselJS itself recommends you to use a DOMElement instead of the Text DisplayObj. More on DOMElement here.
Personally, I think it would be a lot easier to get to your desired result by using pure DOM instead of canvas work, unless you're doing some heavy user-interaction-based animation stuff.
$(function(){
var stage = new createjs.Stage('canvas2d');
var circle1 = new createjs.Shape();
var circle2 = new createjs.Shape();
var rect = new createjs.Shape();
rect.graphics.f("green").drawRect(33, 0, 500, 455);
stage.addChild(rect);
circle2.graphics.beginFill("yellow").drawCircle(0, 0, 300);
circle2.x = 500;
circle2.y = 0;
stage.addChild(circle2);
circle1.graphics.beginFill("red").drawCircle(0, 0, 150);
circle1.x = 500;
circle1.y = 0;
stage.addChild(circle1);
stage.update();
var coord_xaxis = new createjs.Shape();
stage.addChild(coord_xaxis);
var coord_yaxis = new createjs.Shape();
stage.addChild(coord_yaxis);
var coord_arrow_x = new createjs.Shape();
//stage.addChild(coord_arrow_x);
var coord_arrow_y = new createjs.Shape();
//stage.addChild(coord_arrow_y);
var coord_xaxis_lines = new createjs.Shape();
stage.addChild(coord_xaxis_lines);
var coord_yaxis_lines = new createjs.Shape();
stage.addChild(coord_yaxis_lines);
/**$('#canvas2d').width()/15**/
var axis_center_x = $('#canvas2d').width()/15;
var axis_center_y = $('#canvas2d').height()/1.10;
var xaxis_width = $('#canvas2d').width()-0.05*$('#canvas2d').width();
var yaxis_width = $('#canvas2d').height()-0.05*$('#canvas2d').height();
var axis_start_x = ($('#canvas2d').width()-xaxis_width)/2;
var axis_start_y = ($('#canvas2d').height()-yaxis_width)/6;
var axis_strokewidth = 2;
coord_xaxis.graphics.setStrokeStyle(axis_strokewidth,'round').beginStroke('#000');
coord_xaxis.graphics.moveTo(axis_start_x, axis_center_y).lineTo(axis_start_x+xaxis_width, axis_center_y);
coord_yaxis.graphics.setStrokeStyle(axis_strokewidth,'round').beginStroke('#000');
coord_yaxis.graphics.moveTo(axis_center_x, axis_start_y).lineTo(axis_center_x, axis_start_y+yaxis_width);
// draw coordsys arrow for x-axis
var arrwidth = 5;
var arrxtnd = 5;
coord_arrow_x.graphics.beginFill('#000');
coord_arrow_x.graphics.setStrokeStyle(axis_strokewidth,'round').beginStroke('#000');
coord_arrow_x.graphics.moveTo(axis_center_x, axis_start_y-arrwidth/2).lineTo(axis_center_x+arrwidth, axis_start_y+arrwidth+arrxtnd).lineTo(axis_center_x-arrwidth, axis_start_y+arrwidth+arrxtnd).lineTo(axis_center_x, axis_start_y-arrwidth/2);
coord_arrow_x.graphics.endFill();
// draw coordsys arrow for y-axis
coord_arrow_y.graphics.beginFill('#000');
coord_arrow_y.graphics.beginStroke('#000');
coord_arrow_y.graphics.moveTo(axis_start_x+xaxis_width+arrwidth/2, axis_center_y).lineTo(axis_start_x+xaxis_width-arrwidth-arrxtnd, axis_center_y+arrwidth).lineTo(axis_start_x+xaxis_width-arrwidth-arrxtnd, axis_center_y-arrwidth).lineTo(axis_start_x+xaxis_width+arrwidth/2, axis_center_y);
coord_arrow_y.graphics.endFill();
var stepdist = xaxis_width/5.25;
var steplinew = 6;
// 10 horizontal lines
var xlines = 10;
var labels_x = [];
for(var i=xlines;i>=0;i--) {
// little black marker
coord_yaxis_lines.graphics.setStrokeStyle(1,'round').beginStroke('#000');
coord_yaxis_lines.graphics.moveTo(axis_center_x-steplinew, axis_center_y+(-i/2)*stepdist).lineTo(axis_center_x+steplinew, axis_center_y+(-i/2)*stepdist);
// labels
labels_x[i] = new createjs.Text('x', '14px Arial', '#333');
labels_x[i].x = axis_center_x-12;
labels_x[i].y = axis_center_y+(-i/2)*stepdist-6; // move up a bit
stage.addChild(labels_x[i]);
labels_x[i].text = (i/10);
labels_x[i].textAlign = 'right';
}
// 12 orthogonal lines
var stepdist2 = xaxis_width/6.5;
var steplinew2 = 6;
var ylines = 10;
var labels_y = [];
for(var i=ylines;i>=1;i--) {
// dont overdraw y-axis-line
// little black marker
coord_xaxis_lines.graphics.setStrokeStyle(1,'round').beginStroke('#000');
coord_xaxis_lines.graphics.moveTo(axis_center_x+(i/1.6)*stepdist2, axis_center_y-steplinew2).lineTo(axis_center_x+(i/1.6)*stepdist2, axis_center_y+steplinew2);
// labels
labels_y[i] = new createjs.Text('x', '14px Arial', '#333');
labels_y[i].x = axis_center_x+(i/1.6)*stepdist2; // move up a bit
labels_y[i].y = axis_center_y+12;
stage.addChild(labels_y[i]);
labels_y[i].text = (i/10);
labels_y[i].textAlign = 'center';
}
stage.update();
})
<script src="https://code.createjs.com/createjs-2015.11.26.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<canvas id="canvas2d" width="500" height="500"></canvas>

curved lines with EaselJS

I have a drawing canvas using EaselJS, the problem is that when I am drawing lines is working properly only the first one. Since second line is getting with some corners not with curved line as the first line, and it looks more like a polygon than a curved line. What is the best way to fix this?
I think here should to be something to correct
//containers
this.backgroundContainer = new createjs.Container();
this.stage.addChild(this.backgroundContainer);
var ss = new createjs.Shape();
ss.graphics.beginFill("#000000").drawRect(0, 0, 960, window.innerHeight);
this.stageArea = new createjs.Container();
this.stageArea.snapToPixel = true;
this.stageArea.hitArea = ss;
this.backgroundContainer.addChild(this.stageArea);
this.container = new createjs.Container();
this.stage.addChild(this.container);
this.stageArea.addEventListener("mousedown", this.handleMouseDown);
this.stage.addEventListener("stagemousemove" , this.handleMouseMove);
tick:function(){
if(app.mouseDOWN){
app.midPt = new createjs.Point(app.oldPt.x + app.stage.mouseX - app.stage.canvas.width/2>>1, app.oldPt.y+app.stage.mouseY - app.stage.canvas.height/2>>1);
app.lineArray[app.NUM_LINES].graphics
.beginStroke('#ffffff')
.moveTo(app.midPt.x, app.midPt.y)
.curveTo(app.oldPt.x, app.oldPt.y, app.oldMidPt.x, app.oldMidPt.y);
app.lineArray2[app.NUM_LINES].graphics
.beginStroke('#ffffff')
.moveTo(app.midPt.x, app.midPt.y)
.curveTo(app.oldPt.x, app.oldPt.y, app.oldMidPt.x, app.oldMidPt.y);
app.lineArray3[app.NUM_LINES].graphics
.beginStroke('#ffffff')
.moveTo(app.midPt.x, app.midPt.y)
.curveTo(app.oldPt.x, app.oldPt.y, app.oldMidPt.x, app.oldMidPt.y);
app.oldPt.x = app.stage.mouseX;
app.oldPt.y = app.stage.mouseY;
app.oldMidPt.x = app.midPt.x;
app.oldMidPt.y = app.midPt.y;
app.stage.update();
}
}

Use multiple materials for merged geometries in Three.js

I want to create a Pine using 2 meshes, 1 for the trunk and another one for the bush, this what I've done:
var pine_geometry = new THREE.Geometry();
var pine_texture_1 = THREE.ImageUtils.loadTexture('./res/textures/4.jpg');
var pine_geometry_1 = new THREE.CylinderGeometry(25, 25, 50, 6);
var pine_material_1 = new THREE.MeshBasicMaterial({
map : pine_texture_1
});
var pine_1 = new THREE.Mesh(pine_geometry_1);
pine_1.position.x = x;
pine_1.position.y = y + 25;
pine_1.position.z = z;
pine_1.updateMatrix();
pine_geometry.merge(pine_1.geometry, pine_1.matrix);
var pine_texture_2 = THREE.ImageUtils.loadTexture('./res/textures/5.jpg');
var pine_geometry_2 = new THREE.CylinderGeometry(0, 70, 250, 8);
var pine_material_2 = new THREE.MeshBasicMaterial({
map : pine_texture_2
});
var pine_2 = new THREE.Mesh(pine_geometry_2);
pine_2.position.x = x;
pine_2.position.y = y + 175;
pine_2.position.z = z;
pine_2.updateMatrix();
pine_geometry.merge(pine_2.geometry, pine_2.matrix);
var pine = new THREE.Mesh(pine_geometry, new THREE.MeshFaceMaterial([pine_material_1, pine_material_2]));
pine.geometry.computeFaceNormals();
pine.geometry.computeVertexNormals();
Game.scene.add(pine);
The Pine is correctly positioned as I want, however, the whole merged shape only uses 1 material instead of the 2 (the whole shape is covered by the 1st) and I want that each mesh has it's respective material when mergin both.
What I'm doing wrong? any idea?
After a long research I discovered that I was missing an extra parameter for the method 'merge' from the Geometry object, the last parameter is the index of the material that the mesh must have from the materials array, ex: 0 -> first material in 'materials' array... and so on.
So, my final piece of code looks like:
pine_geometry.merge(pine_1.geometry, pine_1.matrix, 0);
var pine_texture_2 = THREE.ImageUtils.loadTexture('./res/textures/5.jpg');
var pine_geometry_2 = new THREE.CylinderGeometry(0, 70, 250, 8);
var pine_material_2 = new THREE.MeshBasicMaterial({
map : pine_texture_2
});
var pine_2 = new THREE.Mesh(pine_geometry_2);
pine_2.position.x = x;
pine_2.position.y = y + 175;
pine_2.position.z = z;
pine_2.updateMatrix();
pine_geometry.merge(pine_2.geometry, pine_2.matrix, 1);
(Note the last numbers I add to each merge).
However, I want to clarify that this practice only works when we are dealing with various geometries that are from the same type, in this case, we're merging two CylinderGeometry, but if we wanted to merge for example a Cylinder with a Box AND add the MeshFaceMaterial, it wouldn't be recognized properly and the console will throw us 'Cannot read property map/attributes from undefined', nevertheless we can still merge both geometries but not providing multiple materials (that's a terrible mistake I made).
Hope this helps to anyone.
Here's a general function to merge meshes with materials, You can also specify if you want it to return it as a buffer geometry.
function _mergeMeshes(meshes, toBufferGeometry) {
var finalGeometry,
materials = [],
mergedGeometry = new THREE.Geometry(),
mergeMaterial,
mergedMesh;
meshes.forEach(function(mesh, index) {
mesh.updateMatrix();
mesh.geometry.faces.forEach(function(face) {face.materialIndex = 0;});
mergedGeometry.merge(mesh.geometry, mesh.matrix, index);
materials.push(mesh.material);
});
mergedGeometry.groupsNeedUpdate = true;
mergeMaterial = new THREE.MeshFaceMaterial(materials);
if (toBufferGeometry) {
finalGeometry = new THREE.BufferGeometry().fromGeometry(mergedGeometry);
} else {
finalGeometry = mergedGeometry;
}
mergedMesh = new THREE.Mesh(finalGeometry, mergeMaterial);
mergedMesh.geometry.computeFaceNormals();
mergedMesh.geometry.computeVertexNormals();
return mergedMesh;
}
var mergedMesh = _mergeMeshes([trunkMesh, treeTopMesh], true);

How to draw circular segment using paper.js

How to draw circular segment using paper.js
I want to draw the circular segments as shown in the image. Each segment is independent and will later be used for interactive purposes.
I tried something like
//Temporary background circle
var keys = new Path.Circle(view.center, 130);
keys.fillColor = '#F1F1F1';
var home = new Path.Circle(view.center, 50);
home.fillColor = '#ee2a33';
var start = new Point(view.center.x, view.center.y-130);
var through = new Point(view.center.x-125, view.center.y-40);
var to = new Point(view.center.x-130, view.center.y);
var path = new Path.Arc(start, through, to);
path.strokeColor = 'black';
path.fillColor = 'green';
And it renders something like below
After several attempts, I came up with this. If anyone needs the same thing for whatever reason, maybe this will help.
//Creating keys
var arcOne = createSegment('#f1f1f1');
var arcTwo = createSegment('#666666');
var arcThree = createSegment('#333333');
var arcFour = createSegment('#666666');
var arcFive = createSegment('#999999');
var arcSix = createSegment('#000000');
arcTwo.rotate(-60, view.center);
arcThree.rotate(-120, view.center);
arcFour.rotate(60, view.center);
arcFive.rotate(120, view.center);
arcSix.rotate(180, view.center);
//center white
var center = new Path.Circle(view.center, 50);
center.fillColor = '#F1F1F1';
//Create Each segment
function createSegment(fillcolor){
//Segment One
var start = new Point(view.center.x, view.center.y-130);
var through = new Point(view.center.x-90, view.center.y-94);
var to = new Point(view.center.x-113, view.center.y-64);
var name = Path.Arc(start, through, to);
name.add(new Point(view.center.x, view.center.y));
name.add(new Point(view.center.x, view.center.y-130));
name.fillColor = fillcolor;
return name;
}

Categories