# Shapes

Line
Lines are defined by a Start point and an End point, along with a configurable Thickness. As with many other shapes, you can set Thickness Space to various units, so you can specify Thickness in either meters, pixels or noots.

#### Geometry

Flat 2D lines are flat on the local space XY plane, ignoring Z. This is useful for making lines that are locked to a plane, such as in 2D games, or for a 2D surface in a 3D world such as a screen or minimap
Billboard lines are positioned in 3D space, still using a quad mesh, always trying to face the camera. Useful for a cheap way of drawing 3D lines without using much geometry
Volumetric 3D lines are using actual polygons to render a 3D line with the given Thickness

#### End Caps

No Caps - cuts off immediately at each endpoint
Square Caps - extends by half the Thickness at each endpoint
Round Caps - extends by half the Thickness at each endpoint, rounding the corners

#### Dashed Lines

Dash Size and Dash Spacing are either in meters, relative to thickness, or a fixed count across the shape, depending on what Dash Space is set to. Dash Offset is always relative to a single period, which means integer values always look the same. Here are some example dashes, when set to Relative dash spacing
size 1, spacing 1
size 2, spacing 1
size 2, spacing 0.5
size 3, spacing 3
size 3, spacing 3, offset 0.5

 Blend Mode What blend mode to use when drawing this shape
 Color Color of the line, or, the color of the starting point, when two colors are used
 Color End Color of the endpoint when two colors are used
 Thickness How thick this shape should be, in the given Thickness Space
 Thickness Space What space Thickness is defined in
 Start Local space starting point
 End Local space endpoint
 Geometry Flat 2D, Billboard, or Volumetric 3D
 Color Mode Single color, or a gradient from start to end
 End Caps No caps, Square caps or Round caps
 Dashed Dashed or solid
 Dash Space The space in which Size and Spacing is defined. MetersRelative (to Thickness), which means a dash size of 1 is always a square dashFixed Count, where Size is the number of repeating periods across the shape, and Spacing is the fraction (0 to 1) of which should be space
 Dash Snap Snap Dashes to the full length of the shape. OffTiling (ensures a repeating pattern, ends with space)End To End (ensures a dash is snapped at each end)
 Dash Size Length of a single dash. When Dash Space is set to fixed count, this is the repeat count
 Dash Spacing Size of the space between dashes. When Dash Space is set to fixed count, this is a value from 0 to 1, where 0.5 means dashes and spaces have the same size
 Dash Offset Offset of dashes, relative to the repeating period, where 1 = offset by the length of one dash+space, which means that it tiles/repeats at every integer
 Dash Type Type of dash, either Basic, Angled or Rounded
 Dash Modifier Changes the shape of certain dash types
Vertex & Triangle Count
4 verts3 trisFlat 2D or Billboard
Volumetric 3D lines triangle/vert count depends on your 3D primitive detail in the settings window

Polyline
Polylines describe a line drawn along a path made of multiple points. A Closed polyline means it's cyclical, its ends are connected. A non-Closed path on the other hand has two endpoints. The Polyline Points use both a global Color, as well as per-point colors, these are multiplied together! You can think of the color as a tint color.
Just like the lines, you can set Thickness and Thickness Space to various units, scaled by the per-point thickness.

#### Joins

 Simple - corners set thickness by vertex distance. Also known as Bad™ joins. These are the cheapest of all! Useful for when you have high point density and don't want mitering effects, or when you just want something cheap! Miter - corners are extended to the line's intersection point. Note that they may shoot off into infinity with very sharp corners. Don't cut yourself on these pointybois Bevel - corners are chipped off at their halfway angle, not sure who uses these joins to be honest but they're like always a thing Round - corners are rounded off all soft, cuddly and good~

#### Geometry

Flat 2D polylines are flat on the local space XY plane, ignoring Z. This is useful for making lines that are locked to a plane, such as in 2D games, or for a 2D surface in a 3D world such as a screen or minimap
Billboard polylines are positioned in 3D space, still using a flat mesh, always trying to face the camera. Useful for a cheap way of drawing 3D lines without using much geometry

 Blend Mode What blend mode to use when drawing this shape
 Color Uniform color, tinted by per-point color
 Thickness Uniform thickness, in the given Thickness Space, scaled by per-point thickness
 Thickness Space What space Thickness is defined in
 Closed Open ends or closed loop
 Geometry Flat 2D or billboard
 Joins Miter, round or bevel joins
 Points Points and their corresponding colors and thicknesses
Vertex & Triangle Count
2n verts2n-2 trisMiter, Open
2n verts2n trisMiter, Closed
8n-6 verts5n-6 trisBevel, Open
8n vertsn+4 trisBevel, Closed
10n-10 verts3n-2 trisRounded, Open
10n verts3n+4 trisRounded, Closed

Disc
The Disc is a versatile shape encapsulating various Disc Types, including pie, ring and arc.
When in ring or arc mode, Radius is not the distance to the outer edge, but rather distance to the center of a cross section of the ring. This is so that you can specify Thickness and Radius in separate units, with predictable results.
When drawing arcs or pies, you specify a Start Angle and an End Angle. You can select what angular unit you want to use in the inspector. Note that if you access the disc through code, angles are always in radians.

Disc
Pie 🥧
Ring
Arc

Single color

#### Dashed Rings & Arcs

Dash Size and Dash Spacing are either in meters, relative to thickness, or a fixed count across the shape, depending on what Dash Space is set to. Dash Offset is always relative to a single period, which means integer values always look the same. Here are some example dashes, when set to Relative dash spacing
size 1, spacing 1
size 2, spacing 1
size 2, spacing 0.5
size 3, spacing 3
size 3, spacing 3, offset 0.5

 Blend Mode What blend mode to use when drawing this shape
 Color Color of the disc, Radial Inner, Angular Start or Bilinear Inner Start
 Color Outer Start Color of Radial Inner or Bilinear Outer Start
 Color Inner End Color of Angular End or Bilinear Inner End
 Color Outer End Color of Bilinear Outer End
 Color Mode Single, Radial, Angular or Bilinear colors
 Geometry Flat 2D or Billboard
 Disc Type Disc, Pie, Ring or Arc
 Thickness Thickness of Ring & Arc
 Angle Start Start Angle for Pie & Arc, stored as radians in code
 Angle End End Angle for Pie & Arc, stored as radians in code
 Arc End Cap Whether or not the Arc ends should be rounded
 Dashed Dashed or solid
 Dash Space The space in which Size and Spacing is defined. MetersRelative (to Thickness), which means a dash size of 1 is always a square dashFixed Count, where Size is the number of repeating periods across the shape, and Spacing is the fraction (0 to 1) of which should be space
 Dash Snap Snap Dashes to the full length of the shape. OffTiling (ensures a repeating pattern, ends with space)End To End (ensures a dash is snapped at each end)
 Dash Size Length of a single dash. When Dash Space is set to fixed count, this is the repeat count
 Dash Spacing Size of the space between dashes. When Dash Space is set to fixed count, this is a value from 0 to 1, where 0.5 means dashes and spaces have the same size
 Dash Offset Offset of dashes, relative to the repeating period, where 1 = offset by the length of one dash+space, which means that it tiles/repeats at every integer
 Dash Type Type of dash, either Basic, Angled or Rounded
 Dash Modifier Changes the shape of certain dash types
Vertex & Triangle Count
4 verts2 tris

Rectangle
Rectangles have a Size in width and height, support rounded corners with a specific Radius, as well as optionally being hollow with a given Thickness. In addition, you can set the Pivot to be either in the bottom left or center of the rectangle
 Blend Mode What blend mode to use when drawing this shape
 Color Color (RGB) & opacity (A)
 Style Hard vs rounded corners & hollow vs solid
 Pivot Whether size should be relative to the center or bottom left
 Size Width and height
 Thickness How thick this shape should be, in the given Thickness Space
 Thickness Space What space Thickness is defined in
 Corner Radius Gets or sets the corner radius for all four corners, in meters
 Corner Radii Gets or sets each corner radius, in meters (Order is clockwise, starting bottom left)
 Dashed Dashed or solid
 Dash Space The space in which Size and Spacing is defined. MetersRelative (to Thickness), which means a dash size of 1 is always a square dashFixed Count, where Size is the number of repeating periods across the shape, and Spacing is the fraction (0 to 1) of which should be space
 Dash Snap Snap Dashes to the full length of the shape. OffTiling (ensures a repeating pattern, ends with space)End To End (ensures a dash is snapped at each end)
 Dash Size Length of a single dash. When Dash Space is set to fixed count, this is the repeat count
 Dash Spacing Size of the space between dashes. When Dash Space is set to fixed count, this is a value from 0 to 1, where 0.5 means dashes and spaces have the same size
 Dash Offset Offset of dashes, relative to the repeating period, where 1 = offset by the length of one dash+space, which means that it tiles/repeats at every integer
 Dash Type Type of dash, either Basic, Angled or Rounded
 Dash Modifier Changes the shape of certain dash types
Vertex & Triangle Count
4 verts2 tris

Unlike the rectangle, the quad is positioned with each vertex at an arbitrary point in 3D space. The Quad supports four Color Modes, Single Color, Horizontal Gradient, Vertical Gradient and Per-Corner Colors. Color interpolation across a quad is surprisingly nontrivial though, so in light of that, you can configure quality level by changing Quad Interpolation Quality in Shapes settings if you want higher or lower quality depending on your needs
 Blend Mode What blend mode to use when drawing this shape
 Color Color of A, or color of the whole quad. Left color of h-gradient, bottom of v-gradient
 Color B Color of B, or top color for vertical gradients
 Color C Color of C, or right color for horizontal gradients
 Color D Color of D
 A Local space position of A
 B Local space position of B
 C Local space position of C
 D Local space position of D
 Auto-Set D Automatically position D based on the other points to form a planar rhombus/rhomboid
Vertex & Triangle Count
4 verts2 tris

Triangle
Similar to the Quad primitive, Triangles are positioned on a per-vertex basis. Its Color Mode is either Single Color or Per-Corner
 Blend Mode What blend mode to use when drawing this shape
 Color Color of A for per-corner colors, or color of the quad
 Color B Color of B for per-corner colors
 Color C Color of C for per-corner colors
 Color Mode Single color or per-corner colors
 A Local space position of A
 B Local space position of B
 C Local space position of C
 Border Whether it should outline the border or fill the shape
 Thickness How thick this shape should be, in the given Thickness Space
 Thickness Space What space Thickness is defined in
 Roundness A value from 0 to 1 that rounds off corners. 0 is completely sharp, 1 is a large round circle
Vertex & Triangle Count
3 verts1 tri

Regular Polygon
Regular Polygons have equal side lengths and angles. With this shape you can make equilateral triangles, pentagons, hexagons, and any other regular polygon!
 Blend Mode What blend mode to use when drawing this shape
 Color Color (RGB) & opacity (A)
 Geometry Flat 2D or Billboard
 Sides Number of sides
 Border Whether it should outline the border or fill the shape
 Thickness How thick this shape should be, in the given Thickness Space
 Thickness Space What space Thickness is defined in
 Roundness A value from 0 to 1 that rounds off corners. 0 is completely sharp, 1 is a large round circle
 Angle Angle of rotation, stored as radians in code
Vertex & Triangle Count
4 verts2 tris

Polygon
The Polygon shape is a 2D surface allowing for any number of points (within, you know, reason). The polygon allows for any non-self-intersecting simple polygons, including concave ones, as long as the Triangulation is set to Ear Clipping. While Polygons don't allow for per-vertex colors, it does have support gradient fills!
 Blend Mode What blend mode to use when drawing this shape
 Color Color (RGB) & opacity (A)
 Triangulation What method to use when triangulating this polygon. Fast Convex Only is a faster algorithm, but only allows for convex shapes. Ear Clipping supports concave shapes.
Vertex & Triangle Count
Vertex count = number of points
Triangle count = number of points - 2

Sphere
It's a sphere

 Blend Mode What blend mode to use when drawing this shape
 Color Color (RGB) & opacity (A)
Sphere triangle/vert count depends on your 3D primitive detail in the settings window

Torus
Torus with configurable Radius and Thickness, with separate units. This makes it possible to make a torus with a Radius in meters but a Thickness in, say, pixels, which can be useful for making gizmo-like shapes. The torus is oriented so that the axis of revolution / normal direction is along its Z axis

 Blend Mode What blend mode to use when drawing this shape
 Color Color (RGB) & opacity (A)
 Thickness How thick this shape should be, in the given Thickness Space
 Thickness Space What space Thickness is defined in
Torus triangle/vert count depends on your 3D primitive detail in the settings window

Cone
A cone with configurable Radius and Length. Optionally, you can toggle the bottom Cap on and off, in case you want a hollow cone
 Blend Mode What blend mode to use when drawing this shape
 Color Color (RGB) & opacity (A)
 Length Distance from base to tip
 Size Space What space to use when setting the size
 Fill Cap Filled or hollow base
Vertex & Triangle Count
Cone triangle/vert count depends on your 3D primitive detail in the settings window

Cuboid
A cuboid! Equivalent to a cube if Size is the same along each axis
 Blend Mode What blend mode to use when drawing this shape
 Color Color (RGB) & opacity (A)
 Size Size along each axis, end to end
 Size Space What space to use when setting the size
Vertex & Triangle Count
8 verts12 tris

# Immediate-Mode Drawing

Drawing in immediate mode is useful when you want to draw from code, or for shapes that are only temporary, procedural, or where you don't want to deal with the overhead of GameObjects. Immediate mode is instantaneous - it renders only once in the camera you draw in, so if you want to continuously draw, you draw every frame! This means it's very easy to create dynamic setups where what is being drawn can always change with no overhead of destroying or creating GameObjects

### Example

``````[ExecuteAlways] public class MyScript : ImmediateModeShapeDrawer {

public override void DrawShapes( Camera cam ){

using( Draw.Command( cam ) ){

// set up static parameters. these are used for all following Draw.Line calls
Draw.LineGeometry = LineGeometry.Volumetric3D;
Draw.ThicknessSpace = ThicknessSpace.Pixels;
Draw.Thickness = 4; // 4px wide

// set static parameter to draw in the local space of this object
Draw.Matrix = transform.localToWorldMatrix;

// draw lines
Draw.Line( Vector3.zero, Vector3.right,   Color.red   );
Draw.Line( Vector3.zero, Vector3.up,      Color.green );
Draw.Line( Vector3.zero, Vector3.forward, Color.blue  );
}

}

}
``````
Attach this script to any object, and it will draw three 4px wide 3D lines along each axis at the center of the world, with different colors. Let's break it down:

#### ImmediateModeShapeDrawer

This is a helper class you can inherit from, that will make drawing in immediate mode a little bit easier when overriding the DrawShapes() method. This method is called once for every active camera, including the scene view if your script is marked with [ExecuteAlways]. Internally, this is just a wrapper for the camera OnPreRender callback, subscribed to in OnEnable and unsubscribed from in OnDisable. If you don't use this class, then it is highly recommended that you use the appropriate OnPreRender callback for your render pipeline when issuing draw commands

#### Draw.Command(...)

using( Draw.Command( myCamera ) ){} sets up a scope in which you can issue draw commands to the specified camera.
• Consecutive draw commands of the same type inside of this scope will be GPU instanced, so avoid alternating between types of shapes if you want to use less draw calls
• I highly recommended setting up draw commands in Camera.onPreRender or RenderPipelineManager.beginCameraRendering
• ImmediateModeShapeDrawer automatically hooks into these functions in a render pipeline agnostic way, so all you need to do is override DrawShapes() and set up the draw command in there
• While you can set up draw commands in Update(), it is not recommended. The reason for this is because it's important to not add more commands than you're rendering, as this will stack draw calls. If you're worried about this, you can always go to Shapes/Immediate Mode Monitor in Unity, to make sure nothing is leaking

#### Shapes.Draw (static properties)

Shapes.Draw is the main class for immediate mode drawing, and has two core parts. First, it contains static styling properties that will configure how all following Shapes should be drawn. For example:
• Draw.Color = Color.red; will make all following Shapes default to red
• Draw.LineGeometry = LineGeometry.Volumetric3D; will make lines be drawn using 3D geometry instead of flat quads
• Draw.ThicknessSpace = ThicknessSpace.Pixels; will set the thickness space of all shapes to use pixels instead of meters
• Draw.Thickness = 4; will make all shapes lines have a width of 4 (pixels, in this case)

The list above is just a handful of the many static properties in there that you may find useful! Your IDE should be able to show you all available properties to edit if you type Draw.

Note that when dealing with static properties, it's important to keep in mind that they are global. It's often useful to reset the static states right before issuing your draw commands, so that the states are guaranteed to be consistent, and not unintentionally use values that were set elsewhere
• Draw.ResetStyle() will reset all styling properties (but not the matrix)
• Draw.ResetMatrix() will reset the matrix (see below)
• Draw.ResetAllDrawStates() will reset everything

#### Shapes.Draw (drawing matrix)

You can also set the matrix to use when drawing. A matrix is like a transform - it contains position, rotation and scale, all in one type. In other words, this allows you to draw relative to something other than world space

#### Shapes.Draw (draw calls)

Shapes.Draw also contains the actual draw calls - in this case, we are using Draw.Line in order to draw simple line segments, but it contains lots of other shapes

• Draw.Line Draws a line between two points
• Draw.Polyline Draws a polyline along a path (see usage below)
• Draw.Disc Draws a solid disc/filled circle
• Draw.Ring Draws a ring/circle with a given thickness
• Draw.Pie Draws a pie/circle sector
• Draw.Arc Draws a circular arc
• Draw.Rectangle Draws a rectangle
• Draw.RectangleBorder Draws a rectangle border
• Draw.RegularPolygon Draws a regular n-sided polygon
• Draw.RegularPolygonBorder Draws a regular n-sided polygon border
• Draw.Polygon Draws a filled polygon (see usage below)
• Draw.Triangle Draws a triangle given 3 vertex locations in 3D
• Draw.TriangleBorder Draws a triangle border given 3 vertex locations in 3D
• Draw.Sphere Draws a sphere
• Draw.Cuboid Draws a cuboid with a given size along each axis
• Draw.Cube Draws a cube with a given size
• Draw.Cone Draws a cone with a given radius and length/height
• Draw.Torus Draws a torus with a given radius and thickness
• Draw.Text Draws text mesh pro text
• Draw.Texture Draws a texture within a rectangular region

Now, there are way too many overloads to list here, but all Draw functions follow the same pattern:
Draw.ShapeName( [Positioning], [Essentials], [Specials], [Coloring] )

• Any unspecified parameters will use the static properties
• The first few parameters are always for the positioning of the object
• Second we have the essentials, the most common parameters of the shape, such as the radius of a sphere
• Third, we have more special case parameters, that you might want to overload that you usually skip
• Finally, the color override of the shape is always at the very end

### Polylines & Polygons

Polylines and Polygons can be drawn in several ways. The first and most flexible one is to create a temporary PolylinePath/PolygonPath, then specify its points, and finally drawing it. This method will automatically dispose of mesh data at the end of its scope, since it's in a using block
``````using( Draw.Command( cam ) ){
using( var p = new PolylinePath() ){
Draw.Polyline( p, closed:true, thickness:0.1f, Color.red ); // Drawing happens here
} // Disposing of mesh data happens here
}``````

The above code will recreate the mesh every time you draw it. If you instead want a persistent one that you can modify instead of recreate all the time, you can create a PolylinePath/PolygonPath in, say, Awake, and then, importantly, dispose it when you're done with it, usually in OnDestroy or OnDisable. This ensures any mesh data is cleaned up properly.
(the following example below presumes you're using ImmediateModeShapeDrawer)
``````PolylinePath p;

void Awake(){
p = new PolylinePath();
}

override void DrawShapes( Camera cam ){
using( Draw.Command( cam ) ){
Draw.Polyline( p, closed:true, thickness:0.1f, Color.red ); // Drawing happens here
}
}

void OnDestroy() => p.Dispose(); // Disposing of mesh data happens here``````

### Drawing Text

Text can be drawn in two ways. The easiest is to use Draw.Text()/Draw.TextRect() directly.
The second method, is to pass a TextElement into the draw methods - this is much more performant.
Internally, TextElement will reserve a text cache for a specific string and style you're drawing, which will help Shapes only update the text data when necessary.

Below is an example implementation using the persistent text helpers
``````TextElement elemA, elemB;

void Awake(){
elemA = new TextElement();
elemB = new TextElement();
}

override void DrawShapes( Camera cam ){
using( Draw.Command( cam ) ){
Draw.Text( elemA, "Hello" ); // Draws text using the persistent element elemA
Draw.Translate( 0, 1 );
Draw.Text( elemB, "This is performant text", Color.red );
}
}

void OnDestroy(){
elemA.Dispose(); // Important - you have to dispose text elements when you are done with them
elemB.Dispose();
}``````

### Drawing without commands

In some special cases, you may want to draw without using Draw.Command. For example, if you want to draw gizmos using Shapes, you can issue draw calls directly:
``````void OnDrawGizmos(){
// set up all static parameters. these are used for all following Draw.Line calls
Draw.LineGeometry = LineGeometry.Volumetric3D;
Draw.ThicknessSpace = ThicknessSpace.Pixels;
Draw.Thickness = 4; // 4px wide

// draw lines
Draw.Line( Vector3.zero, Vector3.right,   Color.red   );
Draw.Line( Vector3.zero, Vector3.up,      Color.green );
Draw.Line( Vector3.zero, Vector3.forward, Color.blue  );
}``````

However, it's important to keep a few things in mind

• GPU instancing is not supported without Draw.Command, which means each draw corresponds 1:1 to draw calls on the GPU, which can get expensive with many shapes
• This will literally draw as soon as you call each draw call, which means that when during the render pipeline these draw calls happen is absolutely crucial, and in many cases they will simply not work, especially in HDRP and URP
• Drawing like this is equivalent to using Material.SetPass and Graphics.DrawMeshNow
• Generally, this is a bit of a legacy/advanced/bad way of drawing, so like, pls use Draw.Command instead~

# Anti-Aliasing

Shapes will look best across the board when your project is using some form of anti-aliasing. 8xMSAA is recommended! Some shapes however, also have built-in local anti-aliasing, which means that they will have smooth edges even when your project has no AA method enabled.

#### Local Anti-Aliasing

Local anti-aliasing or LAA, is when shapes themselves have built-in AA, even when your project/camera isn't using anti-aliasing as a whole. LAA is available for most 2D shapes when using a non-opaque blending mode. There are some exceptions, which can be found in the feature table below

You can disable or change the quality of local anti-aliasing in the Shapes settings window
 No LAA Fast LAA Corrected LAA
The difference between Fast and Corrected LAA is subtle - Fast LAA has a slight bias in the diagonal directions, making circular shapes appear ever so slightly rhombous and have a slightly sharper curvature in the orthogonal directions, especially when small. Sometimes the edges in the diagonals are slightly fuzzy as well. Corrected AA fixes both of these issues, but uses a slightly more expensive calculation.

All lines thinner than 1 pixel, will be locked at 1 pixel wide, and instead start fading opacity based on pixel coverage. This feature is always on, and is a very useful technique to ensure that thin lines don't get the pixelated wandering ants effect. Note that this is applied regardless of sizing methods - lines with thickness set in meters will also behave this way as soon as it's smaller than 1 pixel on screen.
Mind that this effect will only work if your blending mode supports fading. Opaque shapes will only be able to fade if you use MSAA. The higher the MSAA level, the more steps of fading you will have.
Together with MSAA or LAA, you can get very smooth looking lines. Here's a comparison of a billboard polyline arranged in a sphere, with various options toggled

# Blend Modes

Blend modes specify how the color of shapes should blend with the color behind it, and also whether or not it will write to the depth buffer.

• All blend modes use the alpha channel as opacity/strength
• All blend modes are order independent except Opaque & Transparent
• All blend modes support LAA with 2D shapes
• No blend modes write to the depth buffer, except Opaque

• ##### Opaque
writes to the depth buffer, and sorts properly even when intersecting other shapes. However, it does not support transparency, unless you have MSAA enabled, in which case it will use alpha to coverage to approximate alpha blending. This is especially useful for short alpha fades, such as the edges of the disc shape. Note that MSAA does not work in the scene view. Opaque shapes in the scene view with alpha less than 0.5 are completely invisible, and those above 0.5 are completely opaque
• Alpha-to-Coverage fading support with MSAA enabled
• The only blend mode that writes to the depth buffer
• Opaque 2D Shapes support LAA if MSAA is enabled

• ##### Transparent (Alpha Blended)
is standard "over"-operator blending, similar to having a layer on top of another in photoshop. The shape will affect the color more and more the higher the alpha channel is. A value of 1 means it will just show the color of the shape. A value of 0.5 means it's a halfway blend between the shape and the background, while a value of 0 will be completely invisible, showing only the background.
• Uses premultiplied alpha, which is useful when rendering to a render texture
• Order dependent, which means that intersecting and overlapping shapes using this blend mode may not sort properly

is good for glowing/brightening effects against dark backgrounds
##### Color Dodge
is a harsher non-linear version of additive that goes even brighter when blending with bright colors. Has somewhat unintuitive behaviors when blending with pure black
##### Screen
sometimes also called "soft additive", is the opposite operation of multiply, softly blending toward white instead of black
##### Lighten
outputs the lightest of the shape and its background
##### Linear Burn
darkens linearly. This is the opposite of additive. Unlike multiply, linear burn has a tendency to introduce hue shifting
##### Color Burn
is a harsher non-linear version of linear burn that goes even darker when blending with dark colors. Has somewhat unintuitive behaviors when blending with pure white
##### Multiply
is good for tinting/darkening effects against bright backgrounds. It will softly darken toward black, which is the opposite of screen blending which softly brighens to white
##### Darken
outputs the darkest of the shape and its background
##### Subtract
subtracts this color from the background. It's like linear burn but the colors are inverted and it's annoying to work with

# Draw Order & Depth Testing

#### Component Shapes

Shapes Components are, internally, mesh renderers, and so they will sort the same way any other mesh renderers in Unity would, respecting GameObject Layers, Sorting Layers, and the camera sorting settings in your project
• Shapes with the opaque blend mode render first, then all other blend modes render. Render Queue depends on the blend mode. The Opaque blend mode uses the ﻿Geometry (2450) render queue, all other blend modes use the Transparent (3000) render queue
• Shapes will also be sorted by Unity's Sorting Layers within the same render queue, and the sorting settings you have in your project, along with being sorted by camera depth
• All Shapes use depth testing by default (ie: they don't render if they are behind something), this can be changed at the top of components by changing Depth Test under Sorting & Depth. Note that component based shapes that override these values will not be able to use GPU instancing

#### Immediate Mode Shapes

Immediate mode shapes do not use sorting layers, render queues, or any other automatic sorting system, as they are raw draw commands being issued to the GPU. Instead, immediate mode shapes are drawn in the order you specify the draw commands, in the order you run each draw call. For the opaque blend mode, this matters less, but for any other blend mode, great care should be taken to issue all drawing in the order you want to draw them in.
• Draw Commands will be injected into the render pipeline at the point specified with the second parameter of Draw.Command(). By default, the injection point is:
• The ImmediateModeShapeDrawer component will subscribe to Unity's beginCameraRendering event in OnEnable
• As a result, the order of separate IM shape drawers, depend on the order they were enabled in
• You can explicitly set drawing order by either enabling the objects in a specific order, or changing script execution order in Unity, however...
• ...I recommend having only one central ImmediateModeShapeDrawer in your scene, then have that call functions in other objects, in order to have full control over draw order.
• Shapes drawn inside draw commands will draw in the order you issue the draw calls in
• Each draw call will render on top of the previous one, unless something opaque was in front of it
• Opaque shapes both write and read from the depth buffer, which means they are automatically rendered with correct depth no matter the order
• I recommend drawing all opaque shapes first, so that all following calls can take advantage of being culled by the depth buffer. For example, if you draw an opaque shape close to the camera, and then another shape, using any blend mode, further behind that line, the closer line will still be on top since it wrote to the depth buffer
• Draw.Text currently doesn't support custom depth/stencil settings, as of 4.2.0. More info in the changelog

# Meters, Pixels & Noots

Shapes with a given thickness, width or radius, generally have configurable units to specify in what space the thickness should be in

#### Meters, m

Meters relate to the scale of your world, rather than pixels or any other screen-space unit. A line with a thickness in meters, will look thinner when you're further away, just like any other geometry in your game

#### Pixels, px

Pixels are screen-space units, where 1 unit covers a single pixel on your screen. This means that the distance from the camera to the shape won't affect its thickness on screen, and will instead always have a consistent pixel size

#### Noots, nt

Noots are pixel-density independent screen-space units, defined as a fraction of the minimum dimension of your resolution.
By default, there are 100 noots across the shortest dimension of your resolution, so if you are running 1920x1080, then 1 noot will be min(1920,1080)/100 = 1080/100 = 10.8 pixels wide.
You can configure the number of noots across the screen in the Shapes settings window, if you want to change the default 100 to something else

For shapes that involve angles, you can specify the angles in three different units in the inspector

#### Degrees

define a full turn as 360°, meaning a quarter turn is the familiar 90° angle

#### Turns

define a full turn as 1, which is useful when thinking in fractions of a full turn, where 0.5 is halfway around the circle, 0.25 is a quarter way around, and so forth!

define a full turn as 6.28... = 2π = τ, which is useful in math formulas involving angles, arc lengths, and other relationships of the circle. Internally, angles are always in radians, across the entire library of Shapes. If you want to convert from degrees to radians, you can use degrees*Mathf.Deg2Rad, or turns to radians using turns*ShapesMath.TAU

# Performance

Shapes is designed to be as light on the CPU as possible, by offloading much of the work to the GPU, which means the CPU can focus on your game, while the GPU takes care of all the drawing.

#### General performance considerations

• Shapes is supported on all platforms that support GPU instancing
• Shapes works on mobile, though you need to keep general optimization things in mind
• Avoid having expensive shaders covering many pixels. The more feature rich a shape is, the more expensive it is in general. A good example is the Arc, if you enable end caps and use bilinear color and make it dashed, this means it's now more expensive to render, and you should avoid having them cover a large part of the screen
• Polygons and the Polylines both generate meshes on the fly when they are modified. They might be expensive on the CPU end in some cases, if you use a lot of points

• Now, performance will also vary depending on what side of the library you are using and what you are doing with Shapes:

#### Component Shapes

These will be part of Unity's regular render pipelines, which means they will gain all the benefits of instancing - most shapes of the same type will be a single draw call, since they can all share the same mesh! However, as a tradeoff, this means that Unity is not able to frustum cull Shapes automatically, so if you construct an entire game using shapes you might start running into performance issues, but in general they'll be very fast. Tweaking parameters like radius and colors and all of that, is essentially free, and all of these things are simple shader parameters in the end! With the exception of polyline, since that one requires a mesh to update if you change points. Though, even that mesh is generated without any heavy math on the CPU, as it's only passing data rather than doing complex miter join calcs etc.

• Shapes of the same type are GPU instanced
• Tweaking per-instance parameters like radius and color is free and doesn't break instancing
• Polylines and Polygons can't take advantage of GPU instancing
• #### Immediate Mode Shapes

When drawing using immediate mode, try to have Shapes of the same type issue their draw commands consecutively, that way they will be instanced together into a single draw call. However, if you don't use Draw.Command, then by nature of it drawing directly, each shape is a separate draw call on the GPU, which gets expensive quickly.

# UI

To use Shapes in UI, set your UI to either camera-based or world-space UI, this makes Shapes show up!
Another alternative is to render shapes into a render target, and display the render target in UI

Overlay UI mode is however, not supported, using canvas renderers, rect transforms and all, unfortunately.
It was never actually designed as a UI library, so it wasn't the primary use-case I was focusing on getting up and running, but it was a secondary use case I wanted. However, the reason it doesn't support overlay mode is because it's frankly a nightmare, so the workaround will have to do

# Shapes Feature Table

##### Vector Based
is when a shape has "infinite resolution", as in, it's not an approximation of the shape, and you can zoom in however much you want without loss of detail
##### LAA
is local anti-aliasing support
##### Cheap Edits
means that changing properties, such as color, radius, etc. of this shape is so cheap it's basically free
##### GPU Instancing
is whether or not these shapes will be instanced together to group multiple draw calls into one
##### Dashable
is whether or not it can be dashed (such as dashed lines or dashed rings)
is whether or not it supports color gradient fill. "yes" means it has gradients fit to that particular shape, "generic" means it only has a non-shape-specific gradient fill where you can make a linear or radial gradient, in either world space or local space
2D Shapes Vector Based LAA Cheap Edits GPU Instancing Dashable Gradient Fill
Disc yes yes yes yes n/a yes
Pie yes yes yes yes n/a yes
Ring yes yes yes yes yes yes
Arc yes yes yes yes yes yes
Line (flat/billboarded) yes yes yes yes yes yes
Regular Polygon yes yes yes yes yes generic
Rectangle yes yes yes yes yes generic
Triangle yes[V] yes yes yes yes yes
Quad yes[V] no yes yes n/a yes
Polygon yes[V] no depends[PG] no[I] n/a generic
Polyline yes yes depends[PL] no[I] no[DP] yes
Text yes yes n/a[T] no n/a n/a
Texture n/a n/a n/a no n/a n/a
3D Shapes
Line (volumetric) no no yes yes[IM] yes[L] yes
Sphere no no yes yes[IM] n/a no
Cuboid yes[V] no yes yes[IM] n/a no
Cone no no yes yes[IM] n/a no
Torus no no yes yes[IM] no no

 [V] This shape is inherently polygonal/not smooth, there are no curves to smooth out with vector based approaches [PG] Changing the polygon points retriangulates the mesh on the CPU, everything else is cheap [PL] Changing the polyline points or miter joins recalculates the mesh on the CPU, everything else is cheap [I] Polygons and Polylines use unique meshes, and so they cannot be GPU instanced with each other. The one exception is if you are drawing them in immediate mode using the same PolylinePath/PolygonPath in multiple consecutive calls [DP] Dashed polylines are surprisingly difficult, but may come in the future [T] Shapes doesn't have a text component since Unity already has that in the form of Text Mesh Pro text, but Shapes does have a wrapper for drawing TMP text in immediate mode, which can in some cases be expensive if you have lots of it [IM] shapes of the same type using the same detail level will be instanced together [L] 3D lines have limited dash support. No slanted or rounded dashes, and doesn't look very pretty when using a large thickness