Opened 9 years ago

Closed 9 years ago

Last modified 9 years ago

#3435 closed defect (fixed)

Unexpected output from ST_AsX3D with PolyhedralSurfaceZ -rendering of concave geometries is wrong

Reported by: tomvantilburg Owned by: robe
Priority: medium Milestone: PostGIS 2.2.2
Component: postgis Version: 2.2.x
Keywords: x3d, history Cc: lr@…

Description

When extruding polygons as X3D the output with concave polygons (U shaped) will create a convex faceset on the top and bottom of the 3D structure whereas a concave faceset is expected.

When tesselated first, and therefore fom polyhedralsurfacez to TIN the output is allright.

Test with:

SELECT ST_AsX3D(ST_Tesselate(ST_Extrude(ST_GeometryFromText('Polygon((0 0, 0 10, 30 10, 30 0, 20 0, 20 5, 10 5, 10 0, 0 0))'),0,0,10)))

For completeness:

<X3D>
<Scene>
        <Viewpoint orientation='0.2 0 0 0.8' position='-10 -10 100'/> 
        <Background skyColor='1 1 1'/> 
        <Shape>
<!--PUT YOUR OUTPUT HERE, TESSELATED VERSION ALREADY INCLUDES SHAPE -->
</Shape>
    </Scene>
</X3D>

Attachments (3)

current_state.2.png (11.5 KB ) - added by robe 9 years ago.
current_state.png (11.5 KB ) - added by robe 9 years ago.
future_state_not_convex.png (12.3 KB ) - added by robe 9 years ago.

Download all attachments as: .zip

Change History (15)

comment:1 by robe, 9 years ago

Owner: changed from pramsey to robe

comment:2 by robe, 9 years ago

Just posting this so I can cut and paste into my x3d viewer:

{{{ SELECT ST_AsX3D(ST_Extrude(ST_GeometryFromText('Polygon((0 0, 0 10, 30 10, 30 0, 20 0, 20 5, 10 5, 10 0, 0 0))'),0,0,10)); }}}

<IndexedFaceSet  coordIndex='0 1 2 3 4 5 6 7 -1 8 9 10 11 12 13 14 15 -1 16 17 18 19 -1 20 21 22 23 -1 24 25 26 27 -1 28 29 30 31 -1 32 33 34 35 -1 36 37 38 39 -1 40 41 42 43 -1 44 45 46 47'><Coordinate point='0 0 0 0 10 0 30 10 0 30 0 0 20 0 0 20 5 0 10 5 0 10 0 0 0 0 10 10 0 10 10 5 10 20 5 10 20 0 10 30 0 10 30 10 10 0 10 10 0 0 0 0 0 10 0 10 10 0 10 0 0 10 0 0 10 10 30 10 10 30 10 0 30 10 0 30 10 10 30 0 10 30 0 0 30 0 0 30 0 10 20 0 10 20 0 0 20 0 0 20 0 10 20 5 10 20 5 0 20 5 0 20 5 10 10 5 10 10 5 0 10 5 0 10 5 10 10 0 10 10 0 0 10 0 0 10 0 10 0 0 10 0 0 0' /></IndexedFaceSet>

{{{ —current state — SELECT '<Shape><appearance>

<material ambientintensity="0.500" containerfield="material" shininess="1" diffusecolor="0.8 0.3 0.4" /> </appearance>'
ST_AsX3D(ST_Extrude(ST_GeometryFromText('Polygon((0 0, 0 10, 30 10, 30 0, 20 0, 20 5, 10 5, 10 0, 0 0))'),0,0,10)) '</Shape>'

}}}

Version 0, edited 9 years ago by robe (next)

comment:3 by robe, 9 years ago

tomvantilburg,

The problem seems to be that I need to specify if the polyhedral is convex or not. Seems the spec assumes convex if not stated so guess I have to come up with routine for that.

So before:

I redid mine using:

SELECT '<Shape><appearance>
  <material ambientintensity="0.500" containerfield="material" shininess="1" diffusecolor="0.8 0.3 0.4" /> </appearance>' || replace(ST_AsX3D(ST_Extrude(ST_GeometryFromText('Polygon((0 0, 0 10, 30 10, 30 0, 20 0, 20 5, 10 5, 10 0, 0 0))'),0,0,10)), 'IndexedFaceSet', 'IndexedFaceSet convex="false"') || '</Shape>'

so basically adding a convex="false" with

<IndexedFaceSet convex='false'  coordIndex='0 1 2 3 4 5 6 7 -1 8 9 10 11 12 13 14 15 -1 16 17 18 19 -1 20 21 22 23 -1 24 25 26 27 -1 28 29 30 31 -1 32 33 34 35 -1 36 37 38 39 -1 40 41 42 43 -1 44 45 46 47'><Coordinate point='0 0 0 0 10 0 30 10 0 30 0 0 20 0 0 20 5 0 10 5 0 10 0 0 0 0 10 10 0 10 10 5 10 20 5 10 20 0 10 30 0 10 30 10 10 0 10 10 0 0 0 0 0 10 0 10 10 0 10 0 0 10 0 0 10 10 30 10 10 30 10 0 30 10 0 30 10 10 30 0 10 30 0 0 30 0 0 30 0 10 20 0 10 20 0 0 20 0 0 20 0 10 20 5 10 20 5 0 20 5 0 20 5 10 10 5 10 10 5 0 10 5 0 10 5 10 10 0 10 10 0 0 10 0 0 10 0 10 0 0 10 0 0 0' /></IndexedFaceSet>

and output then looks correct:

So I guess solution is I've got to figure out if the polyhderal or polygon is convex or concave. I'm thinking if all polygons are convex (e.g. convexhull(polygon) = polygon) for all faces holds true then it's convex, otherwise concave.

Last edited 9 years ago by robe (previous) (diff)

by robe, 9 years ago

Attachment: current_state.2.png added

by robe, 9 years ago

Attachment: current_state.png added

by robe, 9 years ago

Attachment: future_state_not_convex.png added

comment:4 by robe, 9 years ago

Hmm probably more efficient to compute true / false based on angle of edges

http://stackoverflow.com/questions/471962/how-do-determine-if-a-polygon-is-complex-convex-nonconvex

rather than going thru the effort of computing the convexhull

comment:5 by tomvantilburg, 9 years ago

I've been looking at the possible drawbacks of setting the default to convex='false' (I would expect some penalty on calculation) but couldn't find any in the documentation. A quick test with just over 800 shapes (building footprints) didn't show any degradation in frame speed (both around 20 fps) when using a default of false.

Therefore I would suggest to set it to false, wouldn't break anything anyway. I can do a pull request if preferred.

comment:6 by robe, 9 years ago

Keywords: x3d added

comment:7 by robe, 9 years ago

(In [14755]) Use Tomvantilburg suggestion and just hard-code convex='false' for all IndexedFaceSets. Corrects the output of wrongly rendered without affecting true convex References #3435 for PostGIS 2.2 (fix).

comment:8 by robe, 9 years ago

Keywords: history added

comment:9 by robe, 9 years ago

Summary: Unexpected output from ST_AsX3D with PolyhedralSurfaceZUnexpected output from ST_AsX3D with PolyhedralSurfaceZ -rendering of concave geometries is wrong

comment:10 by robe, 9 years ago

(In [14756]) References #3435 for PostGIS 2.2 add to release notes

comment:11 by robe, 9 years ago

Resolution: fixed
Status: newclosed

(In [14757]) Use Tomvantilburg suggestion and just hard-code convex='false' for all IndexedFaceSets. Corrects the output of wrongly rendered without affecting true convex Closes #3435 for PostGIS 2.3 (trunk). Update Copyright info

comment:12 by robe, 9 years ago

(In [14758]) fix compile error introduced in X3D commeit references #3435

Note: See TracTickets for help on using tickets.