Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

Create 10000+ cubes with Flyweight

Discussion in 'Scripting' started by PhilippBuxbaum, May 11, 2021.

  1. PhilippBuxbaum

    PhilippBuxbaum

    Joined:
    Mar 10, 2020
    Posts:
    3
    Hello,
    I want to render 10000 or more cubes using the Flyweight Design Pattern. I can´t find lot of content about this subject.
    Prefabs are already using some kind of Flyweight concepts or are only pure instances?
    Also Instanced rendering or DrawMeshInstancedindirect fall under Flyweight Design or are complety unrelated to this subject?
    I also read about scriptable Objects (which use Flyweight Design) but I guess there are not meant for this kind of work.

    public class FlyweightController : MonoBehaviour
    {

    private List<Flyweight> flyweightObjects = new List<Flyweight>();
    void Start()
    {
    int numberOfObjects = 1000000;

    }
    //Generate Flyweight objects
    //Generate the data that's being shared among all objects
    //Data data = new Data();
    //for (int i = 0; i < numberOfObjects; i++)
    //{
    // Flyweight newFlyweight = new Flyweight(data);
    // flyweightObjects.Add(newFlyweight);
    //}
    }

    I found this example in a git. That would already be Flyweight? In my case I would add the cube Gameobject instead of Data.
    Thank you for your time and help.
    Cheers
     
  2. APSchmidtOfOld

    APSchmidtOfOld

    Joined:
    Aug 8, 2016
    Posts:
    4,473
  3. PhilippBuxbaum

    PhilippBuxbaum

    Joined:
    Mar 10, 2020
    Posts:
    3
  4. exiguous

    exiguous

    Joined:
    Nov 21, 2010
    Posts:
    1,749
    In "normal" GameObject Unity having ten thousands of objects is a bad idea. No design pattern will help you with that. However, there is the new Data Oriented Tech Stack (DOTS) with an Entity Component System (ECS) in preview. This allows to have around 100.000 entities active.

    stress test
    comparison

    Data Oriented Design and the API around Unity ECS is an advanced topic and requires fundamental programming knowledge. If you can hardly code have you considered what you want to do to be above your skilllevel? There are also aproaches to combine the meshes of the cubes. Or do you aim in the direction of minecraft like voxels?
    So my advice is to rethink what you want to do and search for a way to "fake" it.
     
    Yoreki likes this.
  5. Yoreki

    Yoreki

    Joined:
    Apr 10, 2019
    Posts:
    2,590
    What is it you are actually trying to do?

    No matter what, having 10k invidivual gameobjects in a scene, performance wont be great. Thats why im asking what it is you are actually trying to accomplish. Usually for these kinds of topics, you rely on some optimization / trick to accomplish your goal. Like object pooling, to reuse previous instances, or only making one mesh look like it contains thousands of cubes, but really it doesnt (which is done in minecraft like voxel games), or if you actually need that many objects.. you just gotta implement them increadibly efficiently, for which the aforementioned DOTS would be a great starting place - but they wouldnt be gameobjects anymore.

    Each approach has advantages and downsides and which one is appropriate really depends on the use case.
     
    exiguous likes this.
  6. PhilippBuxbaum

    PhilippBuxbaum

    Joined:
    Mar 10, 2020
    Posts:
    3
    Thank you exiguous and Yoreki! It is intended only as an exercise to study game design patterns and their implementation. I thought Flyweight was intended for such operations. But I understand what you are saying. It was a misunderstanding on my part. But thanks for the examples. Looks very interesting and I'll look it up. cheers
     
  7. Owen-Reynolds

    Owen-Reynolds

    Joined:
    Feb 15, 2012
    Posts:
    1,921
    "Flyweight" really just means to factor data like a database designer would. It's one of those things which is totally obvious once you get it. Suppose your cubes have a type like in minecraft, and each type has 10 stats like hardness, texture, food value. The actual blocks have a few stats like like current Damage and current wetness. A crude way to do it is like this:

    Code (CSharp):
    1. class block_t {
    2.   int typeID;
    3.   string typeName;
    4.   int hardness;
    5.   Texture2D texture;
    6.   int foodValue;
    7.   ...
    8.   int currentDamage=0; // increases as it's hit
    9.   int wetness=0; // increased as water is poured on it
    10. }
    Seems fine, but when you instantiate 100 of these blocks you get 100 identical copies of of the name, hardness, food ... . Seems wasteful.

    You may have noticed the stats divide into "things all blocks of that type have in common" and "things that could be different for each block, even of the same type". Factoring it would look like:

    Code (CSharp):
    1. class blockType_t { // stored in a list somewhere
    2.   int typeID;
    3.   string name;
    4.   int hardness;
    5. ...
    6. }
    7.  
    8. class actualBlock { // this goes on the prefab
    9.   blockType_t myType; // hand-linked to the correct type
    10.   int currentDamage=0;
    11.   int wetness=0;
    12. }
    Each of your instantiated blocks has a lot less variables and smaller data tends to run faster since more fits in the high-speed cache part of memory.
     
    Yoreki and Bunny83 like this.