Author Topic: Game Design Megathread  (Read 555952 times)

Messing around...


Super Murder Mystery: The Game? Looks good!

scientific breakthrough!



using tons of help from plastiware i managed to make my first character in gamemaker that moves in a way that isn't 'straight down and out of the screen'

yay

Super Murder Mystery: The Game
is SMM... not already a game??

is SMM... not already a game??
he meant a standalone game, mr. literal

So I have recently (within the past couple days) started on a massive game project - a universe exploration game.

"But BluetoothBoy, there are so many being made already!"

Yeah, well I want one that is trimmed down - no fluff like an advanced economy, stats, tons of upgrades, etc. I want it to be more like what you would experience in real life. Well, real life... if you were a robot.

Here's a basic rundown of what I have so far:
- Fully operable/animated humanoid robot character: Using Unity's Mecanim system. All that is left to do is recode crouching (forgot to before I went to bed).
- 3rd/1st person dynamic camera switching: Scroll out; 3rd (RPG style). Adjustable distance. Scroll in all the way; 1st.
- Intuitive character movement: Movement is the same in both views. However, it feels like FPS in 1st, and RPG-style controls in 3rd. I accomplished this by making the body rotate independently of the head. Since the character is a robot, its head can feasibily rotate 360°, no sweat. The camera and head face whichever way you point them, and when you move, the character's body follows.
- Planetary gravity/orientation: Not 100% complete, but it is to the point at which the character can walk on the surface of a sphere with planetary gravity, oriented to the surface of the planet. What's left to do is make it distinguish between the player and all other rigidbodies (which do not have to be rotated to the surface normal) and code in when to apply rotation and when not to. This (in combination with player movement) took me one and a half days of nearly nonstop problem-solving to work out. It wouldn't have take so long if I was only doing 1st person view, but I'm not, so it did.

So what's the next major step? Procedural planet generation. Hehe... wish me luck.

P.S. The mothership is in the works as well. :^)


It has begun...



Thank you based Perlin noise. <3

it's as if the bumpy wall textures in my house had become a ball of terror

It has begun...

Thank you based Perlin noise. <3
is that supposed to be a planet
yes...

u might want to look into geology a little bit js
« Last Edit: June 16, 2015, 03:05:55 PM by Foxscotch »

is that supposed to be a planet
yes...

u might want to look into geology a little bit js
Baby steps. This was just one of the first successful runs, lol. More natural looking terrain comes later - for now, I'm creating a script that generates a sphere of any size ans resolution (well, as large as the GE can handle) so I don't have to import a several-hundred megabyte mesh and crash stuff. The reason why this is complicated is because each mesh in Unity can have a maximum of ~65000 vertices. I need way more (millions) to create a nice looking planet. So not only do I have to create a sphere from scratch, I have to split it into separate meshes as it is created.

All that being said, all this is still going faster than I expected.

each mesh in Unity can have a maximum of ~65000 vertices.
the exact number is probably 65,536 (2^16) isn't it

the exact number is probably 65,536 (2^16) isn't it
Yes, I believe so. ;)

EDIT: Here's a sneak peak at our robotic friend.



So, I have a small problem. The code below outputs a sphere if the total vertices are less than 65000, however, once they are over that, it gives me a "Some indices are referencing out of bound vertices" error. Basically, I'm trying to create triangles with non-existent vertices. What the script attempts to do is check to see if a sphere with more than 65000 vertices is trying to be created, and if so, split the mesh into however many 65000-or-fewer-vertex meshes. I suspect this is just a simple math issue I'm overlooking. I dunno if anyone here would know the answer to fixing this, but I might as well try. I also asked on the Unity Answers site, but the question needs to be approved first, and it hasn't been yet...

Code:
Code: [Select]
IEnumerator BuildPlanet()
 {
     noise = new Perlin();
     //Mesh mesh = new Mesh();
     MeshFilter filter = gameObject.AddComponent< MeshFilter >();
     //Mesh mesh = filter.mesh;
     //mesh.Clear();
     //Mesh[] mesh = new Mesh[];
     float radius = 1f;
     // Longitude |||
     int nbLong = 360;
     // Latitude ---
     int nbLat = 184;
    
     #region Vertices
     Vector3[] vertices = new Vector3[(nbLong+1) * nbLat + 2];
     //print (vertices.Length);
     float _pi = Mathf.PI;
     float _2pi = _pi * 2f;
     int obj = Mathf.CeilToInt((float)vertices.Length/65000);
 
     vertices[0] = Vector3.up * radius;
     //for(int m = 0; m < obj; m++)
     //{
 
         for( int lat = 0; lat < nbLat; lat++ )
         {
             float a1 = _pi * (float)(lat+1) / (nbLat+1);
             float sin1 = Mathf.Sin(a1);
             float cos1 = Mathf.Cos(a1);
            
             for( int lon = 0; lon <= nbLong; lon++ )
             {
                 float a2 = _2pi * (float)(lon == nbLong ? 0 : lon) / nbLong;
                 float sin2 = Mathf.Sin(a2);
                 float cos2 = Mathf.Cos(a2);
                
                 vertices[ lon + lat * (nbLong + 1) + 1] = new Vector3( sin1 * cos2, cos1, sin1 * sin2 ) * radius;
                 //vertices[ lon + lat * (nbLong + 1) + 1] = vertices[ lon + lat * (nbLong + 1) + 1].normalized*(float)(100+noise.GetValue(sin1*cos2, cos1, sin1*cos2)*2);
                 //vertices.normalized*(float)(100+noise.GetValue(pos.x, pos.y, pos.z)*2);
             }
         }
     //}
     vertices[vertices.Length-1] = Vector3.up * -radius;
 
     #endregion
    
     #region Normales        
     Vector3[] normales = new Vector3[vertices.Length];
     for( int n = 0; n < vertices.Length; n++ )
         normales[n] = vertices[n].normalized;
     #endregion
    
     #region UVs
     Vector2[] uvs = new Vector2[vertices.Length];
     uvs[0] = Vector2.up;
     uvs[uvs.Length-1] = Vector2.zero;
     for( int lat = 0; lat < nbLat; lat++ )
         for( int lon = 0; lon <= nbLong; lon++ )
             uvs[lon + lat * (nbLong + 1) + 1] = new Vector2( (float)lon / nbLong, 1f - (float)(lat+1) / (nbLat+1) );
     #endregion
    
     #region Triangles
     int nbFaces = vertices.Length;
     int nbTriangles = nbFaces * 2;
     int nbIndexes = nbTriangles * 3;
     int[] triangles = new int[ nbIndexes ];
    
     //Top Cap
     int i = 0;
     for( int lon = 0; lon < nbLong; lon++ )
     {
         triangles[i++] = lon+2;
         triangles[i++] = lon+1;
         triangles[i++] = 0;
     }
    
     //Middle
     for( int lat = 0; lat < nbLat - 1; lat++ )
     {
         for( int lon = 0; lon < nbLong; lon++ )
         {
             int current = lon + lat * (nbLong + 1) + 1;
             int next = current + nbLong + 1;
            
             triangles[i++] = current;
             triangles[i++] = current + 1;
             triangles[i++] = next + 1;
            
             triangles[i++] = current;
             triangles[i++] = next + 1;
             triangles[i++] = next;
         }
     }
    
     //Bottom Cap
     for( int lon = 0; lon < nbLong; lon++ )
     {
         triangles[i++] = vertices.Length - 1;
         triangles[i++] = vertices.Length - (lon+2) - 1;
         triangles[i++] = vertices.Length - (lon+1) - 1;
     }
 
     #endregion
 
     for(int m = 0; m < obj; m++)
     {
         int v = m*65000;
         Mesh mesh = new Mesh();
         mesh.Clear();
         GameObject gos = new GameObject("GO");
 
         Vector3[] verts = new Vector3[Mathf.Clamp (vertices.Length-v, 3, 65000)];
         Vector3[] norms = new Vector3[verts.Length];
         Vector2[] uv = new Vector2[verts.Length];
         int[] tris = new int[verts.Length*6];
 
 
         for(int a = 0; a < verts.Length; a++)
         {
             verts[a] = vertices[a+v];
         }
         for(int b = 0; b < norms.Length; b++)
         {
             norms[b] = normales[b+v];
         }
         for(int c = 0; c < uv.Length; c++)
         {
             uv[c] = uvs[c+v];
         }
         for(int d = 0; d < tris.Length; d++)
         {
             tris[d] = triangles[d+v];
         }
 
 
         mesh.vertices = verts;
         mesh.normals = norms;
         mesh.uv = uv;
         mesh.triangles = tris;
    
         mesh.RecalculateBounds();
         mesh.Optimize();
         gos.AddComponent<MeshFilter>();
         gos.AddComponent<MeshRenderer>();
         gos.AddComponent<MeshCollider>();
         gos.GetComponent<MeshFilter>().mesh = mesh;
         gos.GetComponent<MeshCollider>().sharedMesh = mesh;
         gos.transform.parent = transform;
         gos.GetComponent<MeshRenderer>().material = transform.GetComponent<MeshRenderer>().material;
 
     }
 
     yield return null;
 }
« Last Edit: June 16, 2015, 08:16:26 PM by BluetoothBoy »

So I won't actually be using the above code for sphere generation because UV mapping on a polar sphere is horrible.

Instead, I will be using quadspheres, which are basically subdivided cubes with all vertices normalized from the pivot times the radius of the desired sphere. This makes a sort of "six-sided" sphere which is far better for UVs.

Unfortunately, I haven't been able to yet find any code/math on creating the vertices of a subdivided cube, so I'm having to do it myself. Currently, I have it to the point at which I can generate the face vertices (not the corner or edge vertices) with any amount of subdivision (at least, as large as a Vector3 array will allow). The reason I haven't yet done the corner or edge vertices is to avoid overlapping. However, I realize now that if I generate the same two edges of every side and leave two off once each side has been rotated into the correct position, all the vectors will be in the right place.

I also just realized I can optimize my current code by generating the face verts of one side once and rotate six times instead of creating AND rotating six times. *facepalm*

Now, off to see if I can just find some quadsphere generation code, lol.

So I won't actually be using the above code for sphere generation because UV mapping on a polar sphere is horrible.

Instead, I will be using quadspheres, which are basically subdivided cubes with all vertices normalized from the pivot times the radius of the desired sphere. This makes a sort of "six-sided" sphere which is far better for UVs.

Unfortunately, I haven't been able to yet find any code/math on creating the vertices of a subdivided cube, so I'm having to do it myself. Currently, I have it to the point at which I can generate the face vertices (not the corner or edge vertices) with any amount of subdivision (at least, as large as a Vector3 array will allow). The reason I haven't yet done the corner or edge vertices is to avoid overlapping. However, I realize now that if I generate the same two edges of every side and leave two off once each side has been rotated into the correct position, all the vectors will be in the right place.

I also just realized I can optimize my current code by generating the face verts of one side once and rotate six times instead of creating AND rotating six times. *facepalm*

Now, off to see if I can just find some quadsphere generation code, lol.
Do it yourself, it's not that difficult. Though it becomes tricky when you try to split the terrain into patches to allow dynamic level of detail.