sketchucation logo sketchucation
    • Login
    ℹ️ Licensed Extensions | FredoBatch, ElevationProfile, FredoSketch, LayOps, MatSim and Pic2Shape will require license from Sept 1st More Info

    [Code] How do you compute weighted vertex normals?

    Scheduled Pinned Locked Moved Developers' Forum
    26 Posts 4 Posters 5.6k Views 4 Watching
    Loading More Posts
    • Oldest to Newest
    • Newest to Oldest
    • Most Votes
    Reply
    • Reply as topic
    Log in to reply
    This topic has been deleted. Only users with topic management privileges can see it.
    • thomthomT Offline
      thomthom
      last edited by

      This appear to work:

      <span class="syntaxdefault"><br />def&nbsp;self</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">vertex_normal</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">vertex&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">faces&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">vertex</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">faces<br />&nbsp;&nbsp;&nbsp;&nbsp;edges&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">vertex</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">edges<br />&nbsp;&nbsp;&nbsp;&nbsp;point&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">vertex</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">position<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxkeyword">return&nbsp;</span><span class="syntaxdefault">nil&nbsp;</span><span class="syntaxkeyword">if&nbsp;</span><span class="syntaxdefault">faces</span><span class="syntaxkeyword">.empty?<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">normal&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">Geom</span><span class="syntaxkeyword">;;</span><span class="syntaxdefault">Vector3d</span><span class="syntaxkeyword">.new(&nbsp;</span><span class="syntaxdefault">0</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">0</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">0&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">until&nbsp;faces</span><span class="syntaxkeyword">.empty?<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">face&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">faces</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">shift<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;e1</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">e2&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">face</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">edges&nbsp;</span><span class="syntaxkeyword">&&nbsp;</span><span class="syntaxdefault">edges<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pt1&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">e1</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">other_vertex</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">vertex&nbsp;</span><span class="syntaxkeyword">).</span><span class="syntaxdefault">position<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pt2&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">e2</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">other_vertex</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">vertex&nbsp;</span><span class="syntaxkeyword">).</span><span class="syntaxdefault">position<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;v1&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">point</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">vector_to</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">pt1&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">v2&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">point</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">vector_to</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">pt2&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">angle&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">v1</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">angle_between</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">v2&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">face_normal&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">face</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">normal<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;face_normal</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">length&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">angle<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;normal&nbsp;</span><span class="syntaxkeyword">+=&nbsp;</span><span class="syntaxdefault">face_normal<br />&nbsp;&nbsp;&nbsp;&nbsp;end<br />&nbsp;&nbsp;&nbsp;&nbsp;normal</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">normalize</span><span class="syntaxkeyword">!<br />&nbsp;&nbsp;</span><span class="syntaxdefault">end<br /></span>
      

      Thomas Thomassen — SketchUp Monkey & Coding addict
      List of my plugins and link to the CookieWare fund

      1 Reply Last reply Reply Quote 0
      • thomthomT Offline
        thomthom
        last edited by

        Though, the linked article seem to also take into account the face area... wonder what importance that has...

        Thomas Thomassen — SketchUp Monkey & Coding addict
        List of my plugins and link to the CookieWare fund

        1 Reply Last reply Reply Quote 0
        • thomthomT Offline
          thomthom
          last edited by

          hmm... it must be flawed. if a face is connected to the vertex then vector1.angle_between( vector2 ) won't give the correct angle, as it only return angles between 0 - 180 degrees. Either I need to deal with each triangle in each face, or I calculate the full angle.

          Thomas Thomassen — SketchUp Monkey & Coding addict
          List of my plugins and link to the CookieWare fund

          1 Reply Last reply Reply Quote 0
          • TIGT Offline
            TIG Moderator
            last edited by

            Stupid typo is my code should be norm ****+**** fnor not ' *********'... I've corrected the original - it should now work as expected - weighting vertex-normals dependent on the face's areas!

            TIG

            1 Reply Last reply Reply Quote 0
            • thomthomT Offline
              thomthom
              last edited by

              This seem to account for wide angle corners:

              <span class="syntaxdefault"><br />&nbsp;&nbsp;def&nbsp;self</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">vertex_normal</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">vertex&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">faces&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">vertex</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">faces<br />&nbsp;&nbsp;&nbsp;&nbsp;edges&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">vertex</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">edges<br />&nbsp;&nbsp;&nbsp;&nbsp;point&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">vertex</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">position<br />&nbsp;&nbsp;&nbsp;&nbsp;normal&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">Geom</span><span class="syntaxkeyword">;;</span><span class="syntaxdefault">Vector3d</span><span class="syntaxkeyword">.new(&nbsp;</span><span class="syntaxdefault">0</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">0</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">0&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">until&nbsp;faces</span><span class="syntaxkeyword">.empty?<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">face&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">faces</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">shift<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;e1</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">e2&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">face</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">edges&nbsp;</span><span class="syntaxkeyword">&&nbsp;</span><span class="syntaxdefault">edges<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pt1&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">e1</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">other_vertex</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">vertex&nbsp;</span><span class="syntaxkeyword">).</span><span class="syntaxdefault">position<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pt2&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">e2</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">other_vertex</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">vertex&nbsp;</span><span class="syntaxkeyword">).</span><span class="syntaxdefault">position<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;v1&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">point</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">vector_to</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">pt1&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">v2&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">point</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">vector_to</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">pt2&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">angle&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">self</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">full_angle_between</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">v1</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">v2</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">face</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">normal&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">face_normal&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">face</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">normal<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;face_normal</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">length&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">angle<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;normal&nbsp;</span><span class="syntaxkeyword">+=&nbsp;</span><span class="syntaxdefault">face_normal<br />&nbsp;&nbsp;&nbsp;&nbsp;end<br />&nbsp;&nbsp;&nbsp;&nbsp;normal</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">normalize</span><span class="syntaxkeyword">!<br />&nbsp;&nbsp;</span><span class="syntaxdefault">end<br />&nbsp;&nbsp;<br />&nbsp;&nbsp;def&nbsp;self</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">full_angle_between</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">vector1</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">vector2</span><span class="syntaxkeyword">,&nbsp;</span><span class="syntaxdefault">normal&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">cross&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">vector1&nbsp;</span><span class="syntaxkeyword">*&nbsp;</span><span class="syntaxdefault">vector2<br />&nbsp;&nbsp;&nbsp;&nbsp;direction&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">cross&nbsp;</span><span class="syntaxkeyword">%&nbsp;</span><span class="syntaxdefault">normal<br />&nbsp;&nbsp;&nbsp;&nbsp;angle&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">vector1</span><span class="syntaxkeyword">.</span><span class="syntaxdefault">angle_between</span><span class="syntaxkeyword">(&nbsp;</span><span class="syntaxdefault">vector2&nbsp;</span><span class="syntaxkeyword">)<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span class="syntaxdefault">angle&nbsp;</span><span class="syntaxkeyword">=&nbsp;</span><span class="syntaxdefault">360.degrees&nbsp;</span><span class="syntaxkeyword">-&nbsp;</span><span class="syntaxdefault">angle&nbsp;</span><span class="syntaxkeyword">if&nbsp;</span><span class="syntaxdefault">direction&nbsp;</span><span class="syntaxkeyword">>&nbsp;</span><span class="syntaxdefault">0.0<br />&nbsp;&nbsp;&nbsp;&nbsp;angle<br />&nbsp;&nbsp;end<br /></span>
              

              Thomas Thomassen — SketchUp Monkey & Coding addict
              List of my plugins and link to the CookieWare fund

              1 Reply Last reply Reply Quote 0
              • thomthomT Offline
                thomthom
                last edited by

                @tig said:

                Stupid typo is my code should be norm ****+**** fnorm not ' *********'... I've corrected the original - it should now work as expected !!!!

                I'll revisit your code again. http://www.bytehazard.com/code/vertnorm.html mentions that using the area still makes some faces weigh too much, but that it's not that notable. But since it looks to require less computing that checking the angles then it might be preferable.

                Thomas Thomassen — SketchUp Monkey & Coding addict
                List of my plugins and link to the CookieWare fund

                1 Reply Last reply Reply Quote 0
                • thomthomT Offline
                  thomthom
                  last edited by

                  hm... I added face area to the equations, but that yielded deviating normals depending how I divided the large face.
                  removing the face area appear to yield the exact same result.

                  VertexNormals.png
                  Weighted by angle:

                  1. Vector3d(0.419345, 0.0772543, 0.904534)
                  2. Vector3d(0.419345, 0.0772543, 0.904534)
                  3. Vector3d(0.419345, 0.0772543, 0.904534)

                  Weighted by area * angle:

                  1. Vector3d(0.324298, 0.116468, 0.938758)
                  2. Vector3d(0.706956, 0.253896, 0.660114)
                  3. Vector3d(0.770689, 0.276785, 0.573959)

                  Thomas Thomassen — SketchUp Monkey & Coding addict
                  List of my plugins and link to the CookieWare fund

                  1 Reply Last reply Reply Quote 0
                  • thomthomT Offline
                    thomthom
                    last edited by

                    I wonder if the linked article uses the face area because they computer the normals for lighting...

                    Thomas Thomassen — SketchUp Monkey & Coding addict
                    List of my plugins and link to the CookieWare fund

                    1 Reply Last reply Reply Quote 0
                    • TIGT Offline
                      TIG Moderator
                      last edited by

                      Several coplanar faces at a vertex are the same as one face of the same area as the bits? So the both area-weight-adjusted vertex-normals will be the same.
                      I think it is more for lighting...

                      TIG

                      1 Reply Last reply Reply Quote 0
                      • thomthomT Offline
                        thomthom
                        last edited by

                        @tig said:

                        Several coplanar faces at a vertex are the same as one face of the same area as the bits? So the both area-weight-adjusted vertex-normals will be the same.

                        But if a vertex is connected to three sides, one large and two small, then using the area would make the normal lean toward the large area, would it not?

                        Thomas Thomassen — SketchUp Monkey & Coding addict
                        List of my plugins and link to the CookieWare fund

                        1 Reply Last reply Reply Quote 0
                        • TIGT Offline
                          TIG Moderator
                          last edited by

                          Not if the two small areas were equivalent to the large one... then it'd be 'balanced'...
                          The large area pulls it over then the 1st small are pulls it back and then the 2nd small area pulls it back again.
                          IF there's a large and a small area the large one 'wins'.

                          TIG

                          1 Reply Last reply Reply Quote 0
                          • voljankoV Offline
                            voljanko
                            last edited by

                            By computer you mean compute?

                            SuSolid.com - solid check - solid repair- solid intersection check - weight plugin

                            1 Reply Last reply Reply Quote 0
                            • TIGT Offline
                              TIG Moderator
                              last edited by

                              @voljanko said:

                              By computer you mean compute?
                              A simple typo by tt in the original title - but we understood what he meant... 😉

                              TIG

                              1 Reply Last reply Reply Quote 0
                              • voljankoV Offline
                                voljanko
                                last edited by

                                I'm trying to follow your conversation,but not sure to understand what are you trying to do.
                                Do you want to align faces that are nearly aligned?

                                SuSolid.com - solid check - solid repair- solid intersection check - weight plugin

                                1 Reply Last reply Reply Quote 0
                                • thomthomT Offline
                                  thomthom
                                  last edited by

                                  @tig said:

                                  Not if the two small areas were equivalent to the large one... then it'd be 'balanced'...
                                  The large area pulls it over then the 1st small are pulls it back and then the 2nd small area pulls it back again.
                                  IF there's a large and a small area the large one 'wins'.

                                  Yes, but when they are not, which would be in any non-regular mesh. So I still wonder why one would use area to weigh the normals.

                                  Thomas Thomassen — SketchUp Monkey & Coding addict
                                  List of my plugins and link to the CookieWare fund

                                  1 Reply Last reply Reply Quote 0
                                  • thomthomT Offline
                                    thomthom
                                    last edited by

                                    @tig said:

                                    @voljanko said:

                                    By computer you mean compute?
                                    A simple typo by tt in the original title - but we understood what he meant... 😉

                                    Fixed! 😳

                                    Thomas Thomassen — SketchUp Monkey & Coding addict
                                    List of my plugins and link to the CookieWare fund

                                    1 Reply Last reply Reply Quote 0
                                    • thomthomT Offline
                                      thomthom
                                      last edited by

                                      @voljanko said:

                                      I'm trying to follow your conversation,but not sure to understand what are you trying to do.
                                      Do you want to align faces that are nearly aligned?

                                      No, I just want to compute the vertex normals.
                                      In this particular case I need it to be able to calculate some of the topographical characteristic of the mesh.

                                      Thomas Thomassen — SketchUp Monkey & Coding addict
                                      List of my plugins and link to the CookieWare fund

                                      1 Reply Last reply Reply Quote 0
                                      • thomthomT Offline
                                        thomthom
                                        last edited by

                                        My full_angle_between code seem to not work in all scenarios... back to the drawing table...

                                        Thomas Thomassen — SketchUp Monkey & Coding addict
                                        List of my plugins and link to the CookieWare fund

                                        1 Reply Last reply Reply Quote 0
                                        • thomthomT Offline
                                          thomthom
                                          last edited by

                                          Now I seemed to have corrected it. I had to ensure the vectors I used came in the same direction as the edge loop.

                                          Thomas Thomassen — SketchUp Monkey & Coding addict
                                          List of my plugins and link to the CookieWare fund

                                          1 Reply Last reply Reply Quote 0
                                          • 1
                                          • 2
                                          • 1 / 2
                                          • First post
                                            Last post
                                          Buy SketchPlus
                                          Buy SUbD
                                          Buy WrapR
                                          Buy eBook
                                          Buy Modelur
                                          Buy Vertex Tools
                                          Buy SketchCuisine
                                          Buy FormFonts

                                          Advertisement