Creating Stunning Procedural City
Table of Contents
- Introduction
- Procedurally Generated City
- Using Perlin Noise for Height Map
- Neighborhood Blocks and Grid Formation
- Alleyways for added Variation
- Building Placement
- Positioning Buildings in Grid
- Calculating Building Facing Direction
- Alleyway Generation Algorithm
- Rules for Generating Alleyways
- Blender and Unity Integration
- Creating Cube Prefabs in Blender
- Swapping Building Parts for Variation
- Custom Corner Buildings
- Building Specific Corner Shapes
- Configurable Corner Buildings
- Building Heights and Illusion of Variation
- Swapping Roof and Adding Sections
- Interchangeable Building Heights
- Code Refactoring and Performance Optimization
- Tidying up the Code
- Optimizing Window Rendering
- Improving Geometry Efficiency
- Conclusion
Procedurally Generating a City in Unity
Welcome to a new indie devlog about my game, "Riotown". In this devlog, I will be showcasing the process of creating a procedurally generated city in Unity. I will be using Perlin noise to generate a height map for the buildings, as well as implementing neighborhood blocks and alleyways for added variation. So let's dive in!
Procedurally Generated City
To begin with, I wanted to create a city that feels alive and bustling with activity. My city will be made up of various neighborhood blocks, each consisting of a 10x10 grid. These blocks can contain either buildings or streets and will be joined together to form the entire city.
Using Perlin Noise for Height Map
In order to give the buildings some pseudo-randomness and create a realistic cityscape, I decided to use Perlin noise to generate a height map. This height map will determine the varying heights of the buildings, adding visual interest to the city skyline.
Neighborhood Blocks and Grid Formation
Each neighborhood block is essentially a grid, with each grid cell representing a specific tile. These tiles can either be a building or a street. By organizing the city into these blocks, I can easily manage and generate different sections of the city.
Alleyways for added Variation
To add further variety and realism to the city, I decided to incorporate alleyways into the neighborhood blocks. These alleyways will act as connections between different blocks and will only be positioned once the layout of the blocks and streets has been established. This will give the city a more organic and dynamic feel.
Building Placement
Now that I had the basic structure of the city in place, it was time to start placing the buildings. I created a few cube prefabs of different sizes and added visual indicators to determine their facing direction towards the streets.
Positioning Buildings in Grid
The initial step in building placement was to position the buildings in the bottom left corner of each neighborhood block. Since the pivot point of the tiles was bottom left, this alignment made the positioning simple and straightforward.
Calculating Building Facing Direction
However, when it came to positioning buildings on the right-hand side of the grid, I needed to rotate them 180 degrees to ensure they faced the streets correctly. This required repositioning the buildings accordingly, considering the pivot points and rotation angles.
Alleyway Generation Algorithm
To generate the alleyways within the city, I developed an algorithm that follows specific rules and considerations. These rules ensure that the alleyways are correctly placed and maintain a natural flow throughout the city blocks.
Rules for Generating Alleyways
The algorithm starts by selecting a suitable starting tile at the edge of the neighborhood block. It then checks if the adjacent tiles meet certain criteria, such as being vacant and properly aligned with the previous tile. The algorithm also considers restrictions on multiple changes in direction and prevents alleyways from starting in corners.
Blender and Unity Integration
To enhance the visual appeal of the buildings, I used Blender, a 3D modeling software, to create unique building structures. By swapping out different parts and textures, I could create the illusion of various building types without creating separate assets for each.
Creating Cube Prefabs in Blender
In Blender, I designed cube prefabs with customizable features, such as shop fronts and windows. These prefabs allowed for easy customization and the creation of diverse building designs.
Swapping Building Parts for Variation
To add more visual variation to the city, I implemented a system that swaps out specific parts of the buildings. For example, a one-by-one grid building can have its front section removed and replaced with different types of shops, giving the appearance of multiple unique buildings.
Custom Corner Buildings
To further enhance the realism of the city, I wanted to create custom corner buildings instead of reusing the same one-by-one buildings for the edges. These corner buildings add a touch of uniqueness and architectural realism to the cityscape.
Building Specific Corner Shapes
Using Blender, I quickly created one-by-one and two-by-two corner shapes that can be added to the city blocks. These custom corner buildings provide more variety and contribute to the authenticity of the city layout.
Configurable Corner Buildings
Although the current corner buildings are not configurable in terms of their appearances, they serve as a starting point for further customization. With additional modifications, I can allow users to have more control over the corner building designs and ensure a greater level of diversity.
Building Heights and Illusion of Variation
To create an illusion of diverse building heights, I decided to change the height of the buildings by removing the roofs and adding sections between them. This approach, combined with the interchangeable parts, gives the impression of a multitude of unique buildings, even though there are a limited number of prefab templates.
Swapping Roof and Adding Sections
Using the Blender models, I detached the roof section from each building, allowing for the addition of sections of various heights. By lifting the roof and inserting the sections, I created the illusion of different building heights within the city.
Interchangeable Building Heights
Similar to the modular system used for creating variations in building types, the heights of the buildings can be easily adjusted. By swapping out the sections and rearranging the roof, I can create the perception of a diverse cityscape, even with a limited number of building designs.
Code Refactoring and Performance Optimization
As the development progressed, I realized the need for code refactoring and performance optimization. I wanted to improve the efficiency and overall performance of the city generation process.
Tidying up the Code
To ensure clean and organized code, I refactored and commented out unnecessary parts. This allowed for better readability and maintainability, making it easier to implement future enhancements.
Optimizing Window Rendering
One major performance issue was the detailed rendering of individual windows, which took a toll on the processor. To address this, I replaced the complex window models with simpler cubes adorned with textures. This optimization significantly improved performance without compromising the overall visual quality.
Improving Geometry Efficiency
To further optimize performance and reduce wasted geometry, I implemented a mechanism to hide or cull unnecessary building sides that are not visible to the player. By doing so, I reduced the number of triangles rendered, resulting in improved frame rates, especially when zooming out to view the entire city.
Conclusion
In this devlog, I showcased the process of procedurally generating a city in Unity for my game, "Riotown". I explained the techniques used, such as using Perlin noise for height maps, creating neighborhood blocks, generating alleyways, and optimizing building placement. Additionally, I discussed the integration of Blender for customized building designs and the illusion of variation in building heights. By implementing code refactoring and performance optimization strategies, I aimed to create a visually appealing and efficient city generation system. Stay tuned for more updates and improvements to "Riotown"!