UNPKG

react-planner-electron

Version:

react-planner-electron is a React Component for plans design. Draw a 2D floorplan and navigate it in 3D mode.

340 lines (260 loc) 10.8 kB
import * as Three from 'three'; import React from 'react'; const WIDTH = 70; const DEPTH = 50; const HEIGHT = 90; const CHAIR_WIDTH = 55; const CHAIR_DEPTH = 55; const CHAIR_HEIGHT = 50; const CHAIR_TRANSLATION = 30; const TOTAL_DEPTH = DEPTH + CHAIR_DEPTH / 2 - (CHAIR_TRANSLATION - CHAIR_DEPTH / 2); export default { name: "school-desk", prototype: "items", info: { tag: ['furnishings'], title: "School desk", description: "School desk", image: require('./school-desk.png') }, properties: { altitude: { label: "altitude", type: "length-measure", defaultValue: { length: 0, unit: 'cm' } } }, render2D: function (element, layer, scene) { let angle = element.rotation + 90; let textRotation = 0; if (Math.sin(angle * Math.PI / 180) < 0) { textRotation = 180; } let arrow_style = {stroke: element.selected ? '#0096fd' : null, strokeWidth: "2px", fill: "#84e1ce"}; return ( <g transform={`translate(${-WIDTH / 2},${-TOTAL_DEPTH / 2})`}> <rect key="1" x="0" y="0" width={WIDTH} height={TOTAL_DEPTH} style={{stroke: element.selected ? '#0096fd' : '#000', strokeWidth: "2px", fill: "#84e1ce"}}/> <line key="2" x1={WIDTH / 2} x2={WIDTH / 2} y1={DEPTH + DEPTH / 2} y2={1.5 * DEPTH + DEPTH / 2} style={arrow_style}/> <line key="3" x1={.25 * WIDTH} x2={WIDTH / 2} y1={1.2 * DEPTH + DEPTH / 2} y2={1.5 * DEPTH + DEPTH / 2} style={arrow_style}/> <line key="4" x1={WIDTH / 2} x2={.75 * WIDTH} y1={1.5 * DEPTH + DEPTH / 2} y2={1.2 * DEPTH + DEPTH / 2} style={arrow_style}/> <text key="5" x="0" y="0" transform={`translate(${WIDTH / 2}, ${TOTAL_DEPTH / 2}) scale(1,-1) rotate(${textRotation})`} style={{textAnchor: "middle", fontSize: "11px"}}> {element.type} </text> </g> ) }, render3D: function (element, layer, scene) { let makeChair = (altitude) => { let WIDTH = CHAIR_WIDTH; let DEPTH = CHAIR_DEPTH; let HEIGHT = CHAIR_HEIGHT; let chair = new Three.Object3D(); let geometry = new Three.CylinderGeometry(0.02, 0.02, 0.5, 32); let material = new Three.MeshLambertMaterial({color: 0xd9d7d7}); let p1 = new Three.Mesh(geometry, material); p1.rotation.x += Math.PI / 2; p1.position.z += 0.5 / 2; let p2 = new Three.Mesh(geometry, material); p2.rotation.x += Math.PI / 2; p2.position.z += 0.5 / 2; p2.position.y += 0.4; let p3 = new Three.Mesh(geometry, material); p3.rotation.x += Math.PI / 2; p3.position.z += 0.5 / 2; p3.position.x += 0.4; let p4 = new Three.Mesh(geometry, material); p4.rotation.x += Math.PI / 2; p4.position.z += 0.5 / 2; p4.position.y += 0.4; p4.position.x += 0.4; let p5 = new Three.Mesh(geometry, material); p5.rotation.x += Math.PI / 2; p5.position.z += 0.5 * 3 / 2; let p6 = new Three.Mesh(geometry, material); p6.rotation.x += Math.PI / 2; p6.position.z += 0.5 * 3 / 2; p6.position.x += 0.4; // material = new Three.MeshLambertMaterial({color: 0x9b8c75}); let texture = new Three.TextureLoader().load(require('./wood.jpg')); let materialTexture = new Three.MeshLambertMaterial({map: texture}); let roundedRectShape = new Three.Shape(); let x = 0; let y = 0; let width = .5; let height = .48; let radius = 0.05; roundedRectShape.moveTo(x, y + radius); roundedRectShape.lineTo(x, y + height - radius); roundedRectShape.quadraticCurveTo(x, y + height, x + radius, y + height); roundedRectShape.lineTo(x + width - radius, y + height); roundedRectShape.quadraticCurveTo(x + width, y + height, x + width, y + height - radius); roundedRectShape.lineTo(x + width, y + radius); roundedRectShape.quadraticCurveTo(x + width, y, x + width - radius, y); roundedRectShape.lineTo(x + radius, y); roundedRectShape.quadraticCurveTo(x, y, x, y + radius); let extrudeSettings = { steps: 2, depth: 0.03, bevelEnabled: false, bevelThickness: 1, bevelSize: 1, bevelSegments: 1 }; let geometry50 = new Three.ExtrudeGeometry(roundedRectShape, extrudeSettings); let plane = new Three.Mesh(geometry50, materialTexture); plane.position.x += -0.05; plane.position.y += -0.04; plane.position.z += 0.5; let roundedRectShape2 = new Three.Shape(); let x1 = 0; let y1 = 0; let width1 = .45; let height1 = .25; let radius1 = 0.05; roundedRectShape2.moveTo(x1, y1 + radius1); roundedRectShape2.lineTo(x1, y1 + height1 - radius1); roundedRectShape2.quadraticCurveTo(x1, y1 + height1, x1 + radius1, y1 + height1); roundedRectShape2.lineTo(x1 + width1 - radius1, y1 + height1); roundedRectShape2.quadraticCurveTo(x1 + width1, y1 + height1, x1 + width1, y1 + height1 - radius1); roundedRectShape2.lineTo(x1 + width1, y1 + radius1); roundedRectShape2.quadraticCurveTo(x1 + width1, y1, x1 + width1 - radius1, y1); roundedRectShape2.lineTo(x1 + radius1, y1); roundedRectShape2.quadraticCurveTo(x1, y1, x1, y1 + radius1); let extrudeSettings2 = { steps: 2, depth: 0.03, bevelEnabled: false, bevelThickness: 1, bevelSize: 1, bevelSegments: 1 }; let geometry22 = new Three.ExtrudeGeometry(roundedRectShape2, extrudeSettings2); let back = new Three.Mesh(geometry22, materialTexture); //geometry = new Three.BoxGeometry( 0.38, 0.02, 0.15); //let back = new Three.Mesh( geometry, material ); back.rotation.x += Math.PI / 2; back.position.z += 0.5 * 12 / 8; back.position.y += 0.03; back.position.x += -0.025; chair.add(back); chair.add(plane); chair.add(p1); chair.add(p2); chair.add(p3); chair.add(p4); chair.add(p5); chair.add(p6); let aa = new Three.Box3().setFromObject(chair); let deltaX = Math.abs(aa.max.x - aa.min.x); let deltaY = Math.abs(aa.max.y - aa.min.y); let deltaZ = Math.abs(aa.max.z - aa.min.z); // if (element.selected) { // let bbox = new Three.BoxHelper(chair, 0x99c3fb); // bbox.material.linewidth = 5; // bbox.renderOrder = 1000; // bbox.material.depthTest = false; // chair.add(bbox); // } chair.rotation.x += -Math.PI / 2; chair.position.y += altitude; chair.position.x += -WIDTH / 3.5; chair.position.z += DEPTH / 4; chair.scale.set(1.5 * WIDTH / deltaZ, DEPTH / 1.5 / deltaX, HEIGHT / deltaY); return chair; }; let newAltitude = element.properties.get('altitude').get('length'); let brown = new Three.MeshLambertMaterial({color: 0x9b8c75}); let grey = new Three.MeshLambertMaterial({color: 0xd9d7d7}); let black = new Three.MeshLambertMaterial({color: 0x000000}); let texture = new Three.TextureLoader().load(require('./wood.jpg')); let materialTexture = new Three.MeshLambertMaterial({map: texture}); let newDepth = .5; let newWidth = .9; let newHeight = 1; let raggio = .03; let banco = new Three.Object3D(); let geometry = new Three.BoxGeometry(newWidth + newWidth / 6, newHeight / 20, newDepth + newDepth / 4); let boxMaterials = [ new Three.MeshBasicMaterial({map: texture}), new Three.MeshBasicMaterial({map: texture}), new Three.MeshBasicMaterial({color: 0x669966}), //top new Three.MeshBasicMaterial({map: texture}), new Three.MeshBasicMaterial({map: texture}), new Three.MeshBasicMaterial({map: texture}) ]; let tMaterial = new Three.MultiMaterial(boxMaterials); let plane = new Three.Mesh(geometry, tMaterial); plane.position.y = newHeight; banco.add(plane); let geometry_legs = new Three.CylinderGeometry(raggio, raggio, newHeight, 32); let geometry2 = new Three.BoxGeometry(newWidth, newHeight / 20, newDepth); let plane2 = new Three.Mesh(geometry2, materialTexture); plane2.position.y = newHeight / 2 + newHeight / 4; banco.add(plane2); let geometry3 = new Three.BoxGeometry(newWidth, newHeight / 10, newDepth / 20); let plane3 = new Three.Mesh(geometry3, materialTexture); plane3.position.y = newHeight / 2 + newHeight / 4 + newHeight / 16; plane3.position.z = newDepth / 3 + newDepth / 5; banco.add(plane3); let p1 = new Three.Mesh(geometry_legs, grey); p1.position.x = newWidth / 2; p1.position.z = newDepth / 2; p1.position.y = newHeight / 2; banco.add(p1); let p2 = new Three.Mesh(geometry_legs, grey); p2.position.x = newWidth / 2; p2.position.z = -newDepth / 2; p2.position.y = newHeight / 2; banco.add(p2); let p3 = new Three.Mesh(geometry_legs, grey); p3.position.x = -newWidth / 2; p3.position.z = newDepth / 2; p3.position.y = newHeight / 2; banco.add(p3); let p4 = new Three.Mesh(geometry_legs, grey); p4.position.x = -newWidth / 2; p4.position.z = -newDepth / 2; p4.position.y = newHeight / 2; banco.add(p4); let valueObject = new Three.Box3().setFromObject(banco); let deltaX = Math.abs(valueObject.max.x - valueObject.min.x); let deltaY = Math.abs(valueObject.max.y - valueObject.min.y); let deltaZ = Math.abs(valueObject.max.z - valueObject.min.z); // if (element.selected) { // let bbox = new Three.BoxHelper(banco, 0x99c3fb); // bbox.material.linewidth = 5; // bbox.renderOrder = 1000; // bbox.material.depthTest = false; // banco.add(bbox); // } banco.rotation.y += Math.PI; banco.position.y += newAltitude; banco.scale.set(WIDTH / deltaX, HEIGHT / deltaY, DEPTH / deltaZ); let chair = makeChair(newAltitude); chair.position.z += CHAIR_TRANSLATION; let deskAndChair = new Three.Object3D(); deskAndChair.add(banco); deskAndChair.add(chair); if (element.selected) { let bbox = new Three.BoxHelper(deskAndChair, 0x99c3fb); bbox.material.linewidth = 5; bbox.renderOrder = 1000; bbox.material.depthTest = false; deskAndChair.add(bbox); } deskAndChair.position.z -= (CHAIR_DEPTH / 2 - (CHAIR_TRANSLATION - CHAIR_DEPTH / 2)) / 2; let boundingBoxDeskAndChair = new Three.Box3().setFromObject(deskAndChair); let deltaZDeskAndChair = Math.abs(boundingBoxDeskAndChair.max.z - boundingBoxDeskAndChair.min.z); deskAndChair.scale.set(1, 1, TOTAL_DEPTH / deltaZDeskAndChair); //Fix Depth problem with the chair return Promise.resolve(deskAndChair); } };