## The Shape

I was working on a project where I needed to arrange chairs around a pillar in a hotel or condo lobby. While I was contemplating the procedural layout, I thought it would be interesting to arrange objects based on various geometric shapes. I initially began with a circle and eventually developed concentric rings around a radius to create what could potentially be stadium seating.

## Blueprint Node

Determined to streamline the process when it came to working in the blueprint graph, I created blueprint function library functions for different types of potential shapes, each with the appropriate structs for parameters that correspond to those shapes. I plan to encapsulate this functionality into a component where you can simply select the specific shape via an enumerator, and the relevant settings will be displayed accordingly. I intend to revisit this concept in the near future. The idea is to enable artists to add objects or actors to the world in the form of a 2D or 3D layout. Furthermore, artists will have the capability to add objects around specific vector points, but I’ll discuss that in more detail in a separate post.

For now this is the result that we’re shooting for.

1. What are the uses
2. Usage

## Struct

```USTRUCT(BlueprintType)
struct FCageVectorSphereParams
{
GENERATED_BODY()
int32 LatitudeSegments;
int32 LongitudeSegments;
bool bTop;
bool bBottom;
};
```
```/** Create Vector Sphere */
UFUNCTION(BlueprintCallable, BlueprintPure, meta=(DisplayName = "Create Vector Sphere"), Category="CageTools|Object Placement")
static TArray CreateVectorSphere(int32 LatitudeSegments, int32 LongitudeSegments, float Radius, bool bTop, bool bBottom);
}```

## C++

```TArray UCageUtilities::CreateVectorSphere(int32 LatitudeSegments, int32 LongitudeSegments, float Radius, bool bTop, bool bBottom)
{
TArray SphereTransforms;
for (int32 lat = 0; lat <= LatitudeSegments; ++lat)
{
for (int32 lon = 0; lon <= LongitudeSegments; ++lon)
{
// Calculate the spherical coordinates
float Theta = 2 * PI * float(lon) / float(LongitudeSegments);
float Phi = PI * float(lat) / float(LatitudeSegments);
// Convert to Cartesian coordinates
float X = Radius * sin(Phi) * cos(Theta);
float Y = Radius * sin(Phi) * sin(Theta);
float Z = Radius * cos(Phi);
FVector Vertex(X, Y, Z);
if ((bTop && Vertex.Z >= 0.0f) || (bBottom && Vertex.Z <= 0.0f) || (!bTop && !bBottom))
{
// Create a transform with the forward vector pointing outward on the Z-axis
FTransform Transform(FRotator(0.0f, 0.0f, 0.0f), Vertex);