- 
                Notifications
    
You must be signed in to change notification settings  - Fork 67
 
Primitive Shapes #12
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
          
     Merged
      
      
    
  
     Merged
                    Primitive Shapes #12
Changes from 5 commits
      Commits
    
    
            Show all changes
          
          
            59 commits
          
        
        Select commit
          Hold shift + click to select a range
      
      6a67443
              
                Create geometric-primitives.md
              
              
                aevyrie 3f4c7e0
              
                Correct typo
              
              
                aevyrie fa1fc1c
              
                Adding details
              
              
                aevyrie 7f5f21f
              
                Incremental updates
              
              
                aevyrie 9a890e7
              
                Update rfcs/geometric-primitives.md
              
              
                aevyrie 175b8a0
              
                Update rfcs/geometric-primitives.md
              
              
                aevyrie b43acde
              
                Update rfcs/geometric-primitives.md
              
              
                aevyrie 3533994
              
                Apply suggestions from code review
              
              
                aevyrie 68f5485
              
                Update all the things
              
              
                aevyrie 08565cc
              
                Merge branch 'patch-1' of https://github.com/aevyrie/rfcs into patch-1
              
              
                aevyrie 66d8c9d
              
                Add meshing section.
              
              
                aevyrie ceac06d
              
                Added plane
              
              
                aevyrie 88af32e
              
                Add primitives and use demonstration
              
              
                aevyrie e6a7275
              
                Update rfcs/geometric-primitives.md
              
              
                aevyrie f8c8fbe
              
                Update rfcs/geometric-primitives.md
              
              
                aevyrie 6c9cbfd
              
                Update rfcs/geometric-primitives.md
              
              
                aevyrie da6871e
              
                wip updates
              
              
                aevyrie 47ea3b6
              
                Update table and rename
              
              
                aevyrie 5e84667
              
                Rewrite all the things.
              
              
                aevyrie f663bd1
              
                Rename primitive-shapes.md to 12-primitive-shapes.md
              
              
                aevyrie cef33e9
              
                Update 12-primitive-shapes.md
              
              
                aevyrie 9dd6b67
              
                Update 12-primitive-shapes.md
              
              
                aevyrie b67f30e
              
                Update 12-primitive-shapes.md
              
              
                aevyrie 47bcc26
              
                Update 12-primitive-shapes.md
              
              
                aevyrie 7d58f91
              
                Correct Mat3 -> Mat2
              
              
                aevyrie a2aa8cf
              
                Fix AABB error in table
              
              
                aevyrie bd9d5e2
              
                Update 12-primitive-shapes.md
              
              
                aevyrie 0f25cfe
              
                Typo
              
              
                aevyrie b3fcd7d
              
                Add notes to bounding/collision
              
              
                aevyrie cede313
              
                Clarify traits as reference only
              
              
                aevyrie 5e381f6
              
                improve bounding/collision discussion
              
              
                aevyrie 019047e
              
                Add notes about Parry types
              
              
                aevyrie 24dbd0b
              
                Update 12-primitive-shapes.md
              
              
                aevyrie 9ef4d2e
              
                Merge branch 'bevyengine:main' into patch-1
              
              
                aevyrie f37352e
              
                Fix markdown lint violations
              
              
                Weibye c50b330
              
                Fixing typo
              
              
                Weibye bc99e5b
              
                Merge pull request #1 from Weibye/primitive-shapes
              
              
                aevyrie e164fa5
              
                Merge pull request #3 from Weibye/fix-typo
              
              
                aevyrie cc192cb
              
                Explicitly naming x2d or x3d where it makes sense
              
              
                Weibye 2ff5978
              
                Rename Box2d to Rectangle
              
              
                Weibye e88a42a
              
                Removing unresolved question
              
              
                Weibye 2a33756
              
                Fix typo
              
              
                Weibye 5222ee8
              
                Moving 2d shapes ontop
              
              
                Weibye fbcc8da
              
                Moving 2d shapes before 3d shapes
              
              
                Weibye bafe5a5
              
                Adding descriptions to table
              
              
                Weibye 3494f3a
              
                Collecting and rewording 2d / 3d section
              
              
                Weibye 2ac6358
              
                Update rfcs/12-primitive-shapes.md
              
              
                Weibye 5ec59ee
              
                2d before 3d consistency
              
              
                Weibye 550e522
              
                Merge pull request #2 from Weibye/name-consolidation
              
              
                aevyrie 46ae46c
              
                Removing point as a primitive type
              
              
                Weibye 7a5e2c1
              
                Remove angle as a component
              
              
                Weibye ca533b1
              
                merging 'bounding and collision' with 'where are the transforms'
              
              
                Weibye 957bfca
              
                Merge pull request #4 from Weibye/dev/remove-point
              
              
                aevyrie dc58497
              
                Merge pull request #5 from Weibye/remove-angle
              
              
                aevyrie be92586
              
                Merge pull request #6 from Weibye/where-transforms
              
              
                aevyrie 7981ae8
              
                Update rfcs/12-primitive-shapes.md
              
              
                aevyrie f632b2b
              
                Removing torus and placing non-convex in future work
              
              
                Weibye 69e3ab0
              
                Merge pull request #7 from Weibye/non-convex
              
              
                aevyrie 03eaf5f
              
                Update rfcs/12-primitive-shapes.md
              
              
                aevyrie File filter
Filter by extension
Conversations
          Failed to load comments.   
        
        
          
      Loading
        
  Jump to
        
          Jump to file
        
      
      
          Failed to load files.   
        
        
          
      Loading
        
  Diff view
Diff view
There are no files selected for viewing
  
    
      This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
      Learn more about bidirectional Unicode characters
    
  
  
    
              | Original file line number | Diff line number | Diff line change | 
|---|---|---|
| @@ -0,0 +1,162 @@ | ||
| # Feature Name: `geometric-primitives` | ||
| 
     | 
||
| ## Summary | ||
| 
     | 
||
| Lightweight geometric primitive types for use across bevy engine crates, and as interoperability types for external libraries. | ||
| 
     | 
||
| ## Motivation | ||
| 
     | 
||
| This would provide a standard way to model primitives across the bevy ecosystem to prevent ecosystem fragmentation amongst plugins. | ||
| 
     | 
||
| ## Guide-level explanation | ||
| 
     | 
||
| Geometric primitives are lightweight representations of geometry that describe the type of geometry as well as fully defined dimensions. These primitives are *not* discrete meshes, but the underlying precise geometric definition. For example, a circle is: | ||
| 
     | 
||
| ```rust | ||
| pub struct Circle { | ||
| origin: Point, | ||
| radius: f32, | ||
| } | ||
| ``` | ||
| 
     | 
||
| Geometric primitives have a defined shape, size, position, and orientation. Position and orientation are **not** handled by bevy's `Transform` systems. These are fundamental geometric primitives that must be usable and comparable as-is. | ||
| 
     | 
||
| TODO: | ||
| Explain the proposal as if it was already included in the engine and you were teaching it to another Bevy user. That generally means: | ||
| 
     | 
||
| - Introducing new named concepts. | ||
| - Explaining the feature, ideally through simple examples of solutions to concrete problems. | ||
| - Explaining how Bevy users should *think* about the feature, and how it should impact the way they use Bevy. It should explain the impact as concretely as possible. | ||
| - If applicable, provide sample error messages, deprecation warnings, or migration guidance. | ||
| - If applicable, explain how this feature compares to similar existing features, and in what situations the user would use each one. | ||
| 
     | 
||
| ## Reference-level explanation | ||
| 
     | 
||
| ### `bevy_geom::Shape2d` | ||
| 
     | 
||
| These types only exist in 2d space: their dimensions and location are only defined in `x` and `y` unlike their 3d counterparts. | ||
| 
     | 
||
| - `Point`: type alias of Vec2 | ||
| - `Direction`: Vec2 that is guaranteed to be normalized through its getter/setter | ||
| 
     | 
||
| #### Axis | ||
| 
     | 
||
| Line with infinite length on the x/y plane. | ||
| 
     | 
||
| 
     | 
||
| ```rust | ||
| struct Axis { point: Point, normal: Direction } | ||
| ``` | ||
| 
     | 
||
| #### Line | ||
| 
     | 
||
| - `Line`: (start: Point, end: Point) line bounded by two points | ||
| - `Arc`: (start: Point, end: Point, radius_origin: Point) segment of a circle | ||
| 
     | 
||
| ```rust | ||
| struct Circle` { origin: Point, radius: f32 } | ||
| ``` | ||
| - `Triangle` | ||
| - `AABBCentered` origin and half-extents | ||
| - `AabbExtents` minimum and maximum extents | ||
| - `OBB` origin, orthonormal basis, and half-extents | ||
| 
     | 
||
| ### `bevy_geom::Shape3d` | ||
| 
     | 
||
| These types are fully defined in 3d space. | ||
| 
     | 
||
| - `Point`: type alias of Vec3 | ||
| - `Direction`: Vec3 that is guaranteed to be normalized through its getter/setter | ||
| - `Axis` | ||
| - `Line` | ||
| - `Plane` | ||
| - `Quad` | ||
| - `Sphere` | ||
| - `Cylinder` | ||
| - `Capsule` | ||
| - `Torus` | ||
| - `Cone` | ||
| - `Frustum`: defined with 6 planes | ||
| - `AabbCentered` | ||
| - `AabbExtents` | ||
| - `OBB` | ||
| 
     | 
||
| ### Bounding Boxes | ||
| 
     | 
||
| This section is based off of prototyping work done in [bevy_mod_bounding](https://github.com/aevyrie/bevy_mod_bounding). | ||
| 
     | 
||
| Because bounding boxes are fully defined in world space, this leads to the natural question of how they are kept in sync with their parent. | ||
| 
     | 
||
| ### Frustum Culling | ||
| 
     | 
||
| This section is based off of prototyping work done in [bevy_frustum_culling](https://github.com/aevyrie/bevy_frustum_culling). | ||
| 
     | 
||
| ### Ray Casting | ||
| 
     | 
||
| This section is based off of prototyping work done in [bevy_mod_picking](https://github.com/aevyrie/bevy_mod_picking). | ||
| 
     | 
||
| ## Drawbacks | ||
| 
     | 
||
| An argument could be made to use an external crate for this, however these types are so fundamental I think it's important that they are optimized for the engine's uses, and are not from a generalized solution. | ||
| 
     | 
||
| This is also a technically simple addition that shouldn't present maintenance burden. The real challenge is upfront in ensuring the API is designed well, and the primitives are performant for their most common use cases. If anything, this furthers the argument for not using an external crate. | ||
| 
     | 
||
| ## Rationale and alternatives | ||
| 
     | 
||
| ### Lack of `Transform`s | ||
| 
     | 
||
| Primitives are fully defined in space, and do not use `Transform` or `GlobalTransform`. This is an intentional decision. | ||
| 
     | 
||
| It's unsurprisingly much simpler to use these types when the primitives are fully defined internally, but maybe somewhat surprisingly, more efficient. | ||
| 
     | 
||
| #### Cache Efficiency | ||
| 
     | 
||
| - Some primitives such as AABB and Sphere don't need a rotation to be fully defined. | ||
| - By using a `GlobalTransform`, not only is this an unused Quat that fills the cache line, it would also cause redundant change detection on rotations. | ||
| - This is especially important for AABBs and Spheres, because they are fundamental to collision detection and BV(H), and as such need to be as efficient as possible. | ||
| - I still haven't found a case where you would use a `Primitive3d` without needing this positional information that fully defines the primitive in space. If this holds true, it means that storing the positional data inside the primitive is _not_ a waste of cache, which is normally why you would want to separate the transform into a separate component. | ||
| 
     | 
||
| #### CPU Efficiency | ||
                
      
                  aevyrie marked this conversation as resolved.
               
              
                Outdated
          
            Show resolved
            Hide resolved
         | 
||
| 
     | 
||
| - Storing the primitive's positional information internally serves as a form of memoization. | ||
| - Because you need the primitive to be fully defined in world space to run useful operations, this means that with a `GlobalTransform` you would need to apply the transform to the primitive every time you need to use it. | ||
| - By applying this transformation only once (e.g. during transform propagation), we only need to do this computation a single time. | ||
| 
     | 
||
| #### Ergonomics | ||
                
      
                  aevyrie marked this conversation as resolved.
               
              
                Outdated
          
            Show resolved
            Hide resolved
         | 
||
| 
     | 
||
| - As I've already mentioned a few times, primitives need to be fully defined in world space to do anything useful with them. | ||
| - By making the primitive components fully defined and standalone, computing operations is as simple as: `primitive1.some_function(primitive_2)`, instead of also having query and pass in 2 `GlobalTransform`s in the correct order. | ||
| 
     | 
||
| #### Use with Transforms | ||
                
      
                  aevyrie marked this conversation as resolved.
               
              
                Outdated
          
            Show resolved
            Hide resolved
         | 
||
| 
     | 
||
| - For use cases such as oriented bounding boxes, a primitive should be defined relative to its parent. | ||
| - In this case, the primitive would still be fully defined internally, but we would need to include primitive updates analogous to the transform propagation system. | ||
| - For example, a bounding sphere entity would be a child of a mesh, with a `Sphere` primitive and a `Transform`. On updates to the parent's `GlobalTransform`, the bounding sphere's `Transform` component would be used to update the `Sphere`'s position and radius by applying the scale and translation to a unit sphere. This could be applied to all primitives, with the update system being optimized for each primitive. | ||
| 
     | 
||
| - What other designs have been considered and what is the rationale for not choosing them? | ||
| - What is the impact of not doing this? | ||
| - Why is this important to implement as a feature of Bevy itself, rather than an ecosystem crate? | ||
| 
     | 
||
| ## \[Optional\] Prior art | ||
                
      
                  aevyrie marked this conversation as resolved.
               
              
                Outdated
          
            Show resolved
            Hide resolved
         | 
||
| 
     | 
||
| Unity `PrimitiveObjects`: https://docs.unity3d.com/Manual/PrimitiveObjects.html | ||
| Godot `PrimitiveMesh`: https://docs.godotengine.org/en/stable/classes/class_primitivemesh.html#class-primitivemesh | ||
| 
     | 
||
| These examples intermingle primitive geometry with the meshes themselves. This RFC makes these distinct. | ||
| 
     | 
||
                
      
                  aevyrie marked this conversation as resolved.
               
              
                Outdated
          
            Show resolved
            Hide resolved
         | 
||
| 
     | 
||
| ## Unresolved questions | ||
| 
     | 
||
                
      
                  aevyrie marked this conversation as resolved.
               
              
                Outdated
          
            Show resolved
            Hide resolved
         | 
||
| - What parts of the design do you expect to resolve through the RFC process before this gets merged? | ||
| - What parts of the design do you expect to resolve through the implementation of this feature before the feature PR is merged? | ||
| 
     | 
||
| ### Out of Scope | ||
| 
     | 
||
| - Value types, e.g. float vs. fixed is out of scope. This RFC is focused on the core geometry types and is intended to use Bevy's common rendering value types such as `f32`. | ||
| 
     | 
||
| ## Future possibilities | ||
                
      
                  aevyrie marked this conversation as resolved.
               
              
                Outdated
          
            Show resolved
            Hide resolved
         | 
||
| 
     | 
||
| - Bounding boxes | ||
| - Collisions | ||
| - Frustum Culling | ||
| - Debug Rendering | ||
  Add this suggestion to a batch that can be applied as a single commit.
  This suggestion is invalid because no changes were made to the code.
  Suggestions cannot be applied while the pull request is closed.
  Suggestions cannot be applied while viewing a subset of changes.
  Only one suggestion per line can be applied in a batch.
  Add this suggestion to a batch that can be applied as a single commit.
  Applying suggestions on deleted lines is not supported.
  You must change the existing code in this line in order to create a valid suggestion.
  Outdated suggestions cannot be applied.
  This suggestion has been applied or marked resolved.
  Suggestions cannot be applied from pending reviews.
  Suggestions cannot be applied on multi-line comments.
  Suggestions cannot be applied while the pull request is queued to merge.
  Suggestion cannot be applied right now. Please check back later.
  
    
  
    
Uh oh!
There was an error while loading. Please reload this page.