calculate an area based on x and y coordinates and width and height values in javascript -
i have problem i've been trying solve myself without success.
i have object represent rectangle, it's position (x,y) , size (width , height).
i have 2 lists, both contains object mentioned before, 1 list represents positive areas , other represents negative areas.
based in information, need total area results if add elements in both positive , negative lists. i'm interested in result if total area rectangle, otherwise it's irrelevant me.
for example: if positive list contains these 2 objects
{x:20, y:20, width:100, height:20} {x:20, y:40, width:80, height:80}
and negative list contains object
{x:100, y:20, width:20, height:20}
the result of adding these 3 objects be:
{x:20, y:20, width:80, height:100}
this image shows graphical representation of 3 objects in 2 lists , result.
example http://oi64.tinypic.com/i1wkeo.jpg
i appreciate bring.
edit: made small correction in 1 of 3 objects, , coordinate system i'm using cartesian system reversed y-axis (as can see in next figure)
this not simple question, , more algorithmic problem javascript problem.
this works example.
var pos = [{x:20, y:20, width:100, height:20}, {x:20, y:40, width:80, height:80}]; var neg = [{x:100, y:20, width:20, height:20}]; // fixed x: 80 -> x: 100 // create 1 single array of rectangles , add attribute indicating if // rectangle neg or pos var rects = pos.map(function(o){ return object.assign({pos: true}, o); }).concat(neg.map(function(o){ return object.assign({pos: false}, o); })); // combine 2 rectangles. function combine2rects(r1, r2, maintainorder){ // width addition if(r1.pos && r2.pos && r1.x === r2.x && r1.width === r2.width && r2.y === r1.y + r1.height){ return object.assign({}, r1, { height: r1.height + r2.height }); // height addition } else if(r1.pos && r2.pos && r1.y === r2.y && r2.x === r1.x + r1.width && r1.height === r2.height) { return object.assign({}, r1, { width: r1.width + r2.width }); // height bottom subtraction } else if(r1.pos && !r2.pos && r1.x === r2.x && r1.width === r2.width && r2.y === r1.y + r1.height - r2.height && r1.height - r2.height > 0){ return object.assign({}, r1, { height: r1.height - r2.height }); // height top subtraction } else if(r1.pos && !r2.pos && r1.x === r2.x && r1.width === r2.width && r2.y === r1.y && r1.height > r2.height){ return object.assign({}, r1, { height: r1.height - r2.height, y: r1.y + r2.height }); // width right subtraction } else if(r1.pos && !r2.pos && r1.y === r2.y && r1.height === r2.height && r2.x === r1.x + r1.width - r2.width && r1.width - r2.width > 0){ return object.assign({}, r1, { width: r1.width - r2.width }); // width left subtraction } else if(r1.pos && !r2.pos && r1.y === r2.y && r1.height === r2.height && r2.x === r1.x && r2.width < r1.width){ return object.assign({}, r1, { x: r1.x + r2.width, width: r1.width - r2.width }); // if 2 negative rectangle, treat them pos invert them again. } else if(!r1.pos && !r2.pos){ var invertedresult = combine2rects( object.assign({}, r1, { pos: true }), object.assign({}, r2, { pos: true }), maintainorder ); if(invertedresult){ invertedresult.pos = false; return invertedresult; } // try r2 @ place of r1 , vice-versa } else if(!maintainorder){ return combine2rects(r2, r1, true); } } function combinerects(rects){ var lastn = 0; var result = rects.slice(); // while still made @ least 1 combination debugger while(result.length !== lastn){ lastn = result.length; // each rectangle in list for(var i=0; i<result.length; i++){ var r1 = result[i]; // try combine 1 of following rectangles in list for(var j=i+1; j<result.length; j++){ var r2 = result[j]; var c = combine2rects(r1, r2); if(c){ // replace combined rectangle combination result[i] = c; // , remove rectangle has been combined result.splice(j, 1); break; } } } } return result; } document.write(json.stringify(combinerects(rects)));
Comments
Post a Comment