diff --git a/support/client/lib/vwf/model/graphtool.js b/support/client/lib/vwf/model/graphtool.js index 791c6348d..46add0f52 100644 --- a/support/client/lib/vwf/model/graphtool.js +++ b/support/client/lib/vwf/model/graphtool.js @@ -20,7 +20,6 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili self = this; this.state.graphs = {}; this.state.objects = {}; - this.state.kernel = this.kernel.kernel.kernel; }, // == Model API ============================================================================ @@ -31,8 +30,7 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili childSource, childType, childIndex, childName, callback /* ( ready ) */ ) { var node = undefined; - var kernel = this.state.kernel; - var protos = getPrototypes.call( this, kernel, childExtendsID ); + var protos = this.kernel.prototypes( childID ); if ( protos && isGraph( protos ) ) { @@ -47,6 +45,7 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili "yAxisVisible": undefined, "zAxisVisible": undefined, "gridVisible": undefined, + "graphVisible": undefined, "axisOpacity": undefined, "gridOpacity": undefined, "renderTop": undefined @@ -85,6 +84,16 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili "renderTop": undefined }; break; + case "pointline": + node.objectProperties = { + "points": undefined, + "color": undefined, + "opacity": undefined, + "lineThickness": undefined, + "isLoop": undefined, + "renderTop": undefined + }; + break; case "plane": node.objectProperties = { "origin": undefined, @@ -109,6 +118,9 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili node.initialized = false; + } else if ( protos && isMaterial( protos ) && this.state.objects[ nodeID ] ) { + var obj = this.state.objects[ nodeID ]; + obj.materialObject = getThreeJSModel().state.nodes[ childID ]; } }, @@ -118,19 +130,14 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili childSource, childType, childIndex, childName ) { var node; - if ( this.state.graphs[ childID ] ) { - node = this.state.graphs[ childID ]; createGraph( node ); node.initialized = true; - } else if ( this.state.objects[ childID ] ) { - node = this.state.objects[ childID ]; createObject( node ); node.initialized = true; - } }, @@ -138,7 +145,7 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili deletingNode: function( nodeID ) { - if( nodeID ) { + if ( nodeID ) { var childNode = this.state.objects[ nodeID ]; if( childNode ) { var threeObject = childNode.threeObject; @@ -193,23 +200,22 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili settingProperty: function( nodeID, propertyName, propertyValue ) { var node; - if ( this.state.graphs[ nodeID ] ) { - node = this.state.graphs[ nodeID ]; - if ( node.graphProperties.hasOwnProperty( propertyName ) ) { - node.graphProperties[ propertyName ] = propertyValue; - if ( node.initialized ) { - switch ( propertyName ) { case "xAxisVisible": case "yAxisVisible": case "zAxisVisible": case "gridVisible": - setGraphVisibility( node, true ); + if ( propertyValue ) { + this.kernel.setProperty( nodeID, "graphVisible", true ); + } + break; + case "graphVisible": + setGraphVisibility( node, propertyValue ); break; case "graphScale": redrawGraph( node ); @@ -219,37 +225,26 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili redrawGraph( node ); break; } - } - } - } else if ( this.state.objects[ nodeID ] ) { - node = this.state.objects[ nodeID ]; - if ( node.objectProperties.hasOwnProperty( propertyName ) ) { - - node.objectProperties[ propertyName ] = propertyValue; - + switch ( propertyName ) { + default: + node.objectProperties[ propertyName ] = propertyValue; + break; + } if ( node.initialized ) { - redrawObject( node ); - } - } - } }, // -- gettingProperty ---------------------------------------------------------------------- gettingProperty: function( nodeID, propertyName, propertyValue ) { - var node = this.state.objects[ nodeID ]; - - if ( node ) { - } }, // -- creatingMethod ----------------------------------------------------------------------- @@ -264,15 +259,7 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili callingMethod: function( nodeID, methodName, methodParameters, methodValue ) { var node; - if ( this.state.graphs[ nodeID ] ) { - node = this.state.graphs[ nodeID ]; - - if ( methodName === "setGraphVisibility" ) { - var visible = methodParameters[0]; - setGraphVisibility( node, visible ); - } - - } else if ( this.state.objects[ nodeID ] ) { + if ( this.state.objects[ nodeID ] ) { node = this.state.objects[ nodeID ]; if ( methodName === "setGroupItemProperty" ) { @@ -318,18 +305,6 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili return threejs; } - - function getPrototypes( kernel, extendsID ) { - var prototypes = []; - var id = extendsID; - - while ( id !== undefined ) { - prototypes.push( id ); - id = kernel.prototype( id ); - } - - return prototypes; - } function isGraph( prototypes ) { @@ -352,6 +327,7 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili for ( var i = 0; i < prototypes.length && !foundObject; i++ ) { foundObject = ( prototypes[i] == "http://vwf.example.com/graphtool/graphline.vwf" ) || ( prototypes[i] == "http://vwf.example.com/graphtool/graphlinefunction.vwf" ) || + ( prototypes[i] == "http://vwf.example.com/graphtool/graphpointline.vwf" ) || ( prototypes[i] == "http://vwf.example.com/graphtool/graphplane.vwf" ) || ( prototypes[i] == "http://vwf.example.com/graphtool/graphgroup.vwf" ); } @@ -360,6 +336,18 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili return foundObject; } + function isMaterial( prototypes ) { + var foundMaterial = false; + if ( prototypes ) { + for ( var i = 0; i < prototypes.length && !foundMaterial; i++ ) { + foundMaterial = ( prototypes[i] == "http://vwf.example.com/material.vwf" ) || + ( prototypes[i] == "http://vwf.example.com/shaderMaterial.vwf" ); + } + } + + return foundMaterial; + } + function getObjectType( prototypes ) { if ( prototypes ) { @@ -368,6 +356,8 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili return "line"; } else if ( prototypes[i] == "http://vwf.example.com/graphtool/graphlinefunction.vwf" ) { return "function"; + } else if ( prototypes[i] == "http://vwf.example.com/graphtool/graphpointline.vwf" ) { + return "pointline"; } else if ( prototypes[i] == "http://vwf.example.com/graphtool/graphplane.vwf" ) { return "plane"; } else if ( prototypes[i] == "http://vwf.example.com/graphtool/graphgroup.vwf" ) { @@ -391,6 +381,7 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili props.yAxisVisible, props.zAxisVisible, props.gridVisible, + props.graphVisible, props.axisOpacity, props.gridOpacity, props.renderTop @@ -435,6 +426,19 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili ); break; + case "pointline": + obj = generatePointLine( + graphScale, + props.points, + props.color, + props.opacity, + props.lineThickness, + props.isLoop, + node.materialObject, + props.renderTop + ); + break; + case "plane": obj = generatePlane( graphScale, @@ -482,6 +486,7 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili function redrawObject( obj ) { var oldObj = obj.threeObject.children[ 0 ]; + var material = oldObj.material; obj.threeObject.remove( oldObj ); if ( oldObj.children.length > 0 ) { disposeObject( oldObj ); @@ -541,7 +546,7 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili } function generateGraph( graphScale, gridInterval, gridLineInterval, gridLength, xAxisVisible, - yAxisVisible, zAxisVisible, gridVisible, axisOpacity, gridOpacity, renderTop ) { + yAxisVisible, zAxisVisible, gridVisible, graphVisible, axisOpacity, gridOpacity, renderTop ) { var xAxis, yAxis, zAxis, gridX, gridY, axisLine; var thickness = 0.1; @@ -552,15 +557,15 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili xAxis = generateLine( graphScale, [ 1, 0, 0 ], -gridLength, gridLength, [ 255, 0, 0 ], axisOpacity, thickness, renderTop ); xAxis.name = "xAxis"; - xAxis.visible = xAxisVisible; + xAxis.visible = xAxisVisible && graphVisible; yAxis = generateLine( graphScale, [ 0, 1, 0 ], -gridLength, gridLength, [ 0, 0, 255 ], axisOpacity, thickness, renderTop ); yAxis.name = "yAxis"; - yAxis.visible = yAxisVisible; + yAxis.visible = yAxisVisible && graphVisible; zAxis = generateLine( graphScale, [ 0, 0, 1 ], -gridLength, gridLength, [ 0, 255, 0 ], axisOpacity, thickness, renderTop ); zAxis.name = "zAxis"; - zAxis.visible = zAxisVisible; + zAxis.visible = zAxisVisible && graphVisible; if ( renderTop ) { xAxis.renderDepth = yAxis.renderDepth = zAxis.renderDepth = DEPTH_AXES; @@ -583,11 +588,11 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili gridX = generateLine( graphScale, [ 1, 0, 0 ], -gridLength, gridLength, [ 255, 255, 255 ], gridOpacity, thickness, renderTop ); gridX.position.set( 0, i, 0 ); - gridX.visible = gridVisible; + gridX.visible = gridVisible && graphVisible; gridY = generateLine( graphScale, [ 0, 1, 0 ], -gridLength, gridLength, [ 255, 255, 255 ], gridOpacity, thickness, renderTop ); gridY.position.set( i, 0, 0 ); - gridY.visible = gridVisible; + gridY.visible = gridVisible && graphVisible; if ( renderTop ) { gridX.renderDepth = gridY.renderDepth = DEPTH_GRID; @@ -657,6 +662,8 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili geometry.faces.push( new THREE.Face3( last, last - 1, last - 3 ) ); geometry.faces.push( new THREE.Face3( last - 1, last - 2, last - 3 ) ); + calcUVs( geometry ); + var transparent = renderTop || opacity < 1; var vwfColor = new utility.color( color ); color = vwfColor.getHex(); @@ -718,6 +725,8 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili geometry.faces.push( new THREE.Face3( last, last - 1, last - 3 ) ); geometry.faces.push( new THREE.Face3( last - 1, last - 2, last - 3 ) ); + calcUVs( geometry ); + var transparent = renderTop || opacity < 1; var vwfColor = new utility.color( color ); color = vwfColor.getHex(); @@ -731,6 +740,103 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili } + function generatePointLine( graphScale, linepoints, color, opacity, thickness, isLoop, material, renderTop ) { + var geometry = new THREE.Geometry(); + var points = new Array(); + var point, direction, planePoints, i, j, lng; + lng = linepoints.length; + + for ( i = 0; i < lng; i++ ) { + point = new THREE.Vector3( + linepoints[ i ][ 0 ] * graphScale, + linepoints[ i ][ 1 ] * graphScale, + linepoints[ i ][ 2 ] * graphScale + ); + if ( i === lng - 1 ) { + if ( isLoop ) { + direction = new THREE.Vector3( + linepoints[ 0 ][ 0 ] * graphScale, + linepoints[ 0 ][ 1 ] * graphScale, + linepoints[ 0 ][ 2 ] * graphScale + ) + } else { + direction = point.clone(); + } + } else { + direction = new THREE.Vector3( + linepoints[ i + 1 ][ 0 ] * graphScale, + linepoints[ i + 1 ][ 1 ] * graphScale, + linepoints[ i + 1 ][ 2 ] * graphScale + ); + } + if ( i === 0 ) { + if ( isLoop ) { + direction.sub( new THREE.Vector3( + linepoints[ lng - 1 ][ 0 ] * graphScale, + linepoints[ lng - 1 ][ 1 ] * graphScale, + linepoints[ lng - 1 ][ 2 ] * graphScale + ) ); + } else { + direction.sub( point.clone() ); + } + } else { + direction.sub( new THREE.Vector3( + linepoints[ i - 1 ][ 0 ] * graphScale, + linepoints[ i - 1 ][ 1 ] * graphScale, + linepoints[ i - 1 ][ 2 ] * graphScale + ) ); + } + var planePoints = generateLineVertices( direction, point, thickness / 2 ); + for ( j = 0; j < planePoints.length; j++ ) { + points.push( planePoints[ j ] ); + } + } + + geometry.vertices = points; + + for ( i = 0; i < points.length; i++ ) { + if ( points[ i + 4 ] !== undefined ) { + geometry.faces.push( new THREE.Face3( i, i + 4, i + 1 ) ); + geometry.faces.push( new THREE.Face3( i, i + 3, i + 4 ) ); + } else if ( isLoop ) { + var i4, i3, i1; + i4 = i + 4 >= points.length ? i + 4 - points.length : i + 4; + i3 = i + 3 >= points.length ? i + 3 - points.length : i + 3; + i1 = i + 1 >= points.length ? i + 1 - points.length : i + 1; + geometry.faces.push( new THREE.Face3( i, i4, i1 ) ); + geometry.faces.push( new THREE.Face3( i, i3, i4 ) ); + } + } + + if ( !isLoop ) { + var last = points.length - 1; + geometry.faces.push( new THREE.Face3( 0, 1, 2 ) ); + geometry.faces.push( new THREE.Face3( 0, 2, 3 ) ); + geometry.faces.push( new THREE.Face3( last, last - 1, last - 3 ) ); + geometry.faces.push( new THREE.Face3( last - 1, last - 2, last - 3 ) ); + } + + calcUVs( geometry ); + + var meshMaterial, vwfColor, transparent, mesh; + + if ( material && material.threeObject ) { + meshMaterial = material.threeObject.clone(); + } else { + transparent = renderTop || opacity < 1; + vwfColor = new utility.color( color ); + color = vwfColor.getHex(); + meshMaterial = new THREE.MeshBasicMaterial( + { "color": color, "transparent": transparent, "opacity": opacity, "depthTest": !renderTop } + ); + } + + mesh = new THREE.Mesh( geometry, meshMaterial ); + mesh.renderDepth = renderTop ? DEPTH_OBJECTS : null; + + return mesh; + } + function generatePlane( graphScale, origin, normal, rotationAngle, size, color, opacity, doubleSided, renderTop ) { var geometry = new THREE.Geometry(); @@ -746,6 +852,8 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili geometry.faces.push( new THREE.Face3( 0, 1, 2 ) ); geometry.faces.push( new THREE.Face3( 0, 2, 3 ) ); + calcUVs( geometry ); + var transparent = renderTop || opacity < 1; var vwfColor = new utility.color( color ); color = vwfColor.getHex(); @@ -1000,4 +1108,25 @@ define( [ "module", "vwf/model", "vwf/utility" ], function( module, model, utili } )(); } + function calcUVs( geometry ) { + geometry.computeBoundingBox(); + var max = geometry.boundingBox.max; + var min = geometry.boundingBox.min; + var offset = new THREE.Vector2( 0 - min.x, 0 - min.y ); + var range = new THREE.Vector2( max.x - min.x, max.y - min.y ); + geometry.faceVertexUvs[ 0 ] = []; + var faces = geometry.faces; + for ( var i = 0; i < geometry.faces.length ; i++ ) { + var v1 = geometry.vertices[ faces[ i ].a ]; + var v2 = geometry.vertices[ faces[ i ].b ]; + var v3 = geometry.vertices[ faces[ i ].c ]; + geometry.faceVertexUvs[0].push( [ + new THREE.Vector2( ( v1.x + offset.x ) / range.x , ( v1.y + offset.y ) / range.y ), + new THREE.Vector2( ( v2.x + offset.x ) / range.x , ( v2.y + offset.y ) / range.y ), + new THREE.Vector2( ( v3.x + offset.x ) / range.x , ( v3.y + offset.y ) / range.y ) + ] ); + } + geometry.uvsNeedUpdate = true; + } + } ); \ No newline at end of file diff --git a/support/proxy/vwf.example.com/graphtool/graph.vwf.yaml b/support/proxy/vwf.example.com/graphtool/graph.vwf.yaml index 2ba83d0b6..abe74a12e 100644 --- a/support/proxy/vwf.example.com/graphtool/graph.vwf.yaml +++ b/support/proxy/vwf.example.com/graphtool/graph.vwf.yaml @@ -9,18 +9,11 @@ properties: yAxisVisible: undefined zAxisVisible: undefined gridVisible: undefined + graphVisible: undefined axisOpacity: undefined gridOpacity: undefined renderTop: undefined - graphIsVisible$: true methods: - setGraphVisibility: - parameters: - - visible - body: | - this.graphIsVisible$ = visible; - toggleGraphVisibility: | - this.setGraphVisibility( !this.graphIsVisible$ ); graphLine: parameters: - axis @@ -85,6 +78,33 @@ methods: } name = name || "function" + this.functioncount++; this.children.create( name, functionDef ); + graphPointLine: + parameters: + - points + - color + - opacity + - lineThickness + - renderTop + - name + - optionalProperties + body: | + var pointLineDef = { + "extends": "http://vwf.example.com/graphtool/graphpointline.vwf", + "properties": { + "points": points, + "color": color, + "opacity": opacity, + "lineThickness": lineThickness, + "renderTop": renderTop + } + } + if ( optionalProperties ) { + for ( var key in optionalProperties ) { + pointLineDef.properties[ key ] = optionalProperties[ key ]; + } + } + name = name || "pointLine" + this.pointLineCount++; + this.children.create( name, pointLineDef ); graphPlane: parameters: - origin @@ -142,5 +162,6 @@ methods: scripts: | this.lineCount = 0; this.functioncount = 0; + this.pointLineCount = 0; this.planecount = 0; this.groupcount = 0; \ No newline at end of file diff --git a/support/proxy/vwf.example.com/graphtool/graphpointline.vwf.yaml b/support/proxy/vwf.example.com/graphtool/graphpointline.vwf.yaml new file mode 100644 index 000000000..507356960 --- /dev/null +++ b/support/proxy/vwf.example.com/graphtool/graphpointline.vwf.yaml @@ -0,0 +1,19 @@ +--- +extends: http://vwf.example.com/node3.vwf +properties: + points: undefined + color: undefined + opacity: undefined + lineThickness: undefined + isLoop: undefined + renderTop: undefined +methods: + addPoint: + parameters: + - x + - y + - z + body: | + var points = this.points.slice(); + points.push( [ x, y, z ] ); + this.points = points; \ No newline at end of file