Hi All,
I need some help about the feasibility of a project.
The basic problem I want to solve is to create a screenshot from 3d application in vector format for printing. First I tried doing a simple bitmap screenshot and tracing. The results are fairly good, the image has large areas with the same color and sharp edges. But the parts with gradients and finer details are not right. So the result is not usable for me.
Then I thought, 3d is vector graphic, why not convert it directly to 2d vector graphic without rasterization and tracing?
All the 3d application does is drawing triangles to the screen, 2 kinds of them: type1 triangles have the same color all over the surface; type2 have different colors defined for all 3 corners and are semi-transparent. I thought of adding some new code to the application in the drawing routines to emit all triangle data in back to front order, and put these into an svg as path and fill.
This is the concept, before making any code do you think this is feasible? I see two problems:
- I'm not sure if it's possible to define colors for each point of the path in svg? (this limitation I can live with)
- the bigger problem seems to be edges appearing between neighboring triangles
For a quick test I created 2 semi transparent rectangles in Inkscape and aligned them next to each other with tools in "Align and Distribute" to have no gap and no overlap between. This is the alignment the program would emit for the triangles (neighboring triangles share 2 corner coordinates). But still there's a line visible between the 2 rectangles.
This is (I think) because of the fact that in 2d vector graphic a path always defines the boundary of an object, and in my case multiple triangles end up defining a shape.
Can this be solved somehow?
What do you think?
3D to SVG
Re: 3D to SVG
I looked around a bit and found many discussions about the line appearing between aligned shapes. It's the result of anti aliasing during the rasterization, and will stay as it is because it's way to complex to determine how to anti alias edges. The effect can be observed with the polyhedron rendering extension in Inkscape with stroking disabled.
One thing came to my mind about this: the lines are the side effect of the rasterization, converting the vector data to pixels on the monitor. It might be worth checking the actual printed version, because transforming to paper might be different from tranforming to pixels. Or the line might not be noticable in print.
I also found a tricks to slightly oversize triangles or enable 1px stroke, and this seems good for the opaque triangles, but results in the same lines for semi-transparent ones.
Another trick is to apply blur to the whole object (group of triangles), as it can be seen in one of Inkscape's demo svgs, if there are no sharp edges in the object that the blur ruins (sphere for example).
One question is still open, can I define triangles with 3 different corner colors in svg?
One thing came to my mind about this: the lines are the side effect of the rasterization, converting the vector data to pixels on the monitor. It might be worth checking the actual printed version, because transforming to paper might be different from tranforming to pixels. Or the line might not be noticable in print.
I also found a tricks to slightly oversize triangles or enable 1px stroke, and this seems good for the opaque triangles, but results in the same lines for semi-transparent ones.
Another trick is to apply blur to the whole object (group of triangles), as it can be seen in one of Inkscape's demo svgs, if there are no sharp edges in the object that the blur ruins (sphere for example).
One question is still open, can I define triangles with 3 different corner colors in svg?
-
- Posts: 626
- Joined: Wed Jun 06, 2007 2:37 am
Re: 3D to SVG
You cant define 1 shape with 3 colors like that no, you can do 2 with a gradient, but not 3 that are non linear. Think the best way to do them would be 3 co-located triangles that each have 1 corners color in a radial gradient going from colored to transparent.
Re: 3D to SVG
Before Doing any coding; it would probably be wise to check what others have done before (disclaimer, I have no idea if these work or not...)
http://severnclaystudio.wordpress.com/bluebeard/
http://wiki.blender.org/index.php/Exten ... aper_Model Probably not what you want...
http://www-etud.iro.umontreal.ca/~bouvi ... derscripts
Top
http://severnclaystudio.wordpress.com/bluebeard/
http://wiki.blender.org/index.php/Exten ... aper_Model Probably not what you want...
http://www-etud.iro.umontreal.ca/~bouvi ... derscripts
Top
Re: 3D to SVG
Thanks! VRM for blender is just what I want. It clearly shows possibilities and limitations of the vector rendering. I just need to export the scene from my app to some blender format.
The other solution I'm thinking of is modifying the rendering code to be able to handle very large resolutions suitable for printing. That's probably less work than the exporter.
Anyway thanks for all the info, I'll definitely use this in the future.
The other solution I'm thinking of is modifying the rendering code to be able to handle very large resolutions suitable for printing. That's probably less work than the exporter.
Anyway thanks for all the info, I'll definitely use this in the future.
Re: 3D to SVG
Did you take a look at the extension 'Render > 3D Polyhedrons' which can import (and draw as SVG paths) 3d objects from a Wavefront .obj 3D file stored in a local folder [1], with various settings (for appearance, lighting, rotation, etc.)?twinsen wrote:Then I thought, 3d is vector graphic, why not convert it directly to 2d vector graphic without rasterization and tracing?
The python script 'polyhedron_3d.py' is distributed with Inkscape and installed in the shared extensions directory.
[1] The current version of the extension doesn't allow to choose a local directory: custom *.obj file(s) need to be placed into 'share/extensions/Poly3DObjects' where the other polyhedron shape files are stored, and the file name entered in the extensions dialog (Object: Load from file, Filename: your_OBJ_file.obj)
Re: 3D to SVG
I already checked the polyhedron script and as I mentioned earlier it has the same light lines on the edges if stroke is set to 0px (practically disabled). 1px stroke with the fill color makes the lines disappear, and the result is very good, but it only works for full opaque surfaces. If the shape is semi-transparent the stroke makes an even stronger line.
-
- Posts: 215
- Joined: Thu Aug 21, 2008 4:08 am
- Location: Belgium
Re: 3D to SVG
Did you try the "Stitch together" filter ?
viewtopic.php?f=22&t=8579
It works well on Polyhedron extension results.
If you want make the triangles flat semi-transparent (not semi-transparent gradients) apply the filter before, then group them and apply the transparency. It works perfectly also for two adjacent rectangles.
ivan
viewtopic.php?f=22&t=8579
It works well on Polyhedron extension results.
If you want make the triangles flat semi-transparent (not semi-transparent gradients) apply the filter before, then group them and apply the transparency. It works perfectly also for two adjacent rectangles.
ivan
Re: 3D to SVG
Hey, this alpha multiplication filter is really cool! As I have uniform transparency for the whole object (not defined per triangle) the grouping trick works too.
My triangle rasterizer simply interpolates RGB values along the surface of the triangle, this is how it fills triangles with different colors for each corner. That can also be achieved in SVG with 3 co-located triangles and simple linear gradients. I attached an SVG with a red/green/blue cornered triangle. All I need to figure out is how to convert the 3 component values into gradient parameters, but that's just some math, I can hopefully solve it.
And that's all, I think I have all the functionality to convert my 3d scene to SVG representation.
My triangle rasterizer simply interpolates RGB values along the surface of the triangle, this is how it fills triangles with different colors for each corner. That can also be achieved in SVG with 3 co-located triangles and simple linear gradients. I attached an SVG with a red/green/blue cornered triangle. All I need to figure out is how to convert the 3 component values into gradient parameters, but that's just some math, I can hopefully solve it.
And that's all, I think I have all the functionality to convert my 3d scene to SVG representation.
- Attachments
-
- rgb.svg
- RGB triangle
- (8.84 KiB) Downloaded 463 times
-
- Posts: 1
- Joined: Sun Apr 01, 2012 6:14 pm
Re: 3D to SVG
Dear Twinsen!
At the moment I have almost same task as yours 1 year ago: convert output of my 3d app to 2d vector format.
Please can you explain the full pipeline of your solution so I will use it in my app?
At the moment I have almost same task as yours 1 year ago: convert output of my 3d app to 2d vector format.
Please can you explain the full pipeline of your solution so I will use it in my app?
Re: 3D to SVG
Hi pavelvasev,
First off, I would recommend the 2 plugins mentioned in this forum topic: the polyhedra renderer shipped with Inkscape and the VRM plugin for Blender (http://vrm.ao2.it/index.html). The source code of these also offer good opportunity to understand the concepts. If these plugins don't suit your needs then the only way I see is to implement it yourself, though it's not trivial.
In my application there are number of factors that make SVG export of a 3D scene simpler:
1 - all objects consist of triangle meshes
2 - all triangle meshes are convex
3 - there are no intersecting triangles or meshes
4 - there are no degenerate meshes (all meshes are valid solids)
5 - there are only 2 simple shading models: flat color shading, and linear color shading
6 - transparency is defined on object level (not per triangle or per vertex)
7 - no shadows, no textures, no reflections, no advanced stuff...
Point 1 is trivial, you'll render triangles in SVG just as you do in 3D. Points 2, 3, and 4 make your life easier; as there's no Z-Buffer is SVG , you have to do all hidden surface removal yourself. Basicly sorting all triangles of the scene from back-to-front (screen space Z) will work more or less fine. You can also drop back facing triangles of opaque objects, as these are always hidden, and only make rendering slower. Thinking of it points 2 and 3... these are not important regarding SVG export, but are important from other aspects of my code. Point 5: flat shaded triangles are simple (only define a fill color in SVG). Linear shaded triangles are a bit more tricky as you have 3 colors defined for the 3 corners of a tri and these have to be transformed into a gradient definition in SVG. Point 6 is important because most SVG renderers (including inkscape) draw a thin line between 2 perfectly aligned edges of anti aliased shapes. I never even thought of doing Point 7, SVG is a 2d vector format, you can do tricks to make it render something that looks like 3d, but it's still a bunch of tricks with serious tradeoffs.
The pipeline in my application looks like this:
- transform whole scene into screen space
- apply lighting on all triangles of flat shaded objects, and vertices of linear shaded objects
- sort all triangles of the scene from back-to-front
- discard all back facing triangles of opaque objects
- write SVG header, and generate a gradient definition for all linear shaded triangles
- dump all triangles into SVG file and close it.
Sometimes I had to do manual fixups with inkscape, because Z-sorting is not 100% correct, but the overall result was fine. Though, I only had to do 4-5 SVG's for a big poster.
The gradient definition as I wrote is a bit tricky, because you have to convert the 3 colors and 3 x,y coordinates of a triangle to a start/end color pair and start/end x,y coordinate of an SVG gradient. I have the code for (C++) it, and if you're interested I can post it here, but it's an ugly set of geometry equations and even I don't understand it anymore.
First off, I would recommend the 2 plugins mentioned in this forum topic: the polyhedra renderer shipped with Inkscape and the VRM plugin for Blender (http://vrm.ao2.it/index.html). The source code of these also offer good opportunity to understand the concepts. If these plugins don't suit your needs then the only way I see is to implement it yourself, though it's not trivial.
In my application there are number of factors that make SVG export of a 3D scene simpler:
1 - all objects consist of triangle meshes
2 - all triangle meshes are convex
3 - there are no intersecting triangles or meshes
4 - there are no degenerate meshes (all meshes are valid solids)
5 - there are only 2 simple shading models: flat color shading, and linear color shading
6 - transparency is defined on object level (not per triangle or per vertex)
7 - no shadows, no textures, no reflections, no advanced stuff...
Point 1 is trivial, you'll render triangles in SVG just as you do in 3D. Points 2, 3, and 4 make your life easier; as there's no Z-Buffer is SVG , you have to do all hidden surface removal yourself. Basicly sorting all triangles of the scene from back-to-front (screen space Z) will work more or less fine. You can also drop back facing triangles of opaque objects, as these are always hidden, and only make rendering slower. Thinking of it points 2 and 3... these are not important regarding SVG export, but are important from other aspects of my code. Point 5: flat shaded triangles are simple (only define a fill color in SVG). Linear shaded triangles are a bit more tricky as you have 3 colors defined for the 3 corners of a tri and these have to be transformed into a gradient definition in SVG. Point 6 is important because most SVG renderers (including inkscape) draw a thin line between 2 perfectly aligned edges of anti aliased shapes. I never even thought of doing Point 7, SVG is a 2d vector format, you can do tricks to make it render something that looks like 3d, but it's still a bunch of tricks with serious tradeoffs.
The pipeline in my application looks like this:
- transform whole scene into screen space
- apply lighting on all triangles of flat shaded objects, and vertices of linear shaded objects
- sort all triangles of the scene from back-to-front
- discard all back facing triangles of opaque objects
- write SVG header, and generate a gradient definition for all linear shaded triangles
- dump all triangles into SVG file and close it.
Sometimes I had to do manual fixups with inkscape, because Z-sorting is not 100% correct, but the overall result was fine. Though, I only had to do 4-5 SVG's for a big poster.
The gradient definition as I wrote is a bit tricky, because you have to convert the 3 colors and 3 x,y coordinates of a triangle to a start/end color pair and start/end x,y coordinate of an SVG gradient. I have the code for (C++) it, and if you're interested I can post it here, but it's an ugly set of geometry equations and even I don't understand it anymore.