Jump to content

  • Log In with Google      Sign In   
  • Create Account


Member Since 28 Apr 2007
Offline Last Active Today, 12:40 AM

#5163369 decompositing and recompositing color (pixel)

Posted by HappyCoder on 27 June 2014 - 10:25 PM

I agree with Vortez. Optimize it when it becomes a problem. Unless you are doing some serious image processing it shouldn't be a big problem.


I would also recommend packing the color in struct

struct Color
    unsigned char r, g, b, a;

    // constructors, operators, ect

Behind the scenes, the compiler will be doing the bit mask and bit shifts for you but with much cleaner code.


EDIT: I assumed you are using c++. Is that correct?

#5162856 SOLVED: Render a vector to screen in opengl

Posted by HappyCoder on 25 June 2014 - 03:42 PM

There is glDrawPixels


Keep in mind this function is deprecated and I wouldn't do any image processing using glReadPixels with glDrawPixels in any production code.



You should use a shader program to process the render output. To do that, you render your scene to an offscreen framebuffer bound to a texture. You then use that texture as the input to drawing a quad over the entire screen.


Here is an example of how to do this.

Render to Texture

#5162489 Help on learning OpenGL! (Especially perspective projection)

Posted by HappyCoder on 24 June 2014 - 02:11 AM

You just about have it.


The projection matrix transforms points from view space to clip space. To get to NDC from clip space, you divide by w. The reason why its called clip space is because that is where graphics pipelines usually cut away the parts of triangles that fall outside the viewing frustum and therefore wont show up on the screen. This is done by comparing w to x,y and z.


So to recap

// keep in mind that the 'w' value of pointInViewCoordinates is 1
pointInClipCoordinates = perspectiveMatrix * pointInViewCoordinates
// hardware does clipping on geometry here
pointInNDC = pointInClipCoordinates * (1.0 / pointInClipCoordinates .w)

As for the divide by z. You will notice that perspective matrices usually the values 0, 0, -1, 0 along the bottom row in OpenGL. This means that multiplying a point 'v' by a matrix M will result in a point where the new 'w' value is equal -z

| x' |       | x |
| y' | = M * | y |
| z' |       | z |
| -z |       | 1 |

I would suggest going through a few example on paper by hand. Just write out a simple perspective matrix and transform some points. I honestly didn't understand perspective transforms that well until I sat down and did a few by hand.

#5162434 Direct3D 11 Swap-Chain Madness

Posted by HappyCoder on 23 June 2014 - 05:55 PM

Very strange bug. Have you tested it on other machines?

#5162425 OpenGL 2.1 - FBO render to texture 2D projection(?) problem

Posted by HappyCoder on 23 June 2014 - 05:20 PM

Based on the size of the squashed smiley face, your offscreen render target is 512x256 pixels. When you transfer the 512x256 pixel size texture onto the 320x240 screen the image gets squashed.


What code do you use to copy the offscreen texture to the screen?

#5161128 Share the most challenging problem you solved recently! What made you fee...

Posted by HappyCoder on 17 June 2014 - 12:31 PM

I just got a nice wrapper for GLSL shader programs working. Now, with just a single line of code, I can create a shader program.

#5160984 3d rotation speeds

Posted by HappyCoder on 16 June 2014 - 10:52 PM

In 3d, you can represent angular velocity as a 3d vector. The object rotates in the plane perpendicular to the vector at a rate equal to its magnitude.

#5160582 My MMORPG ideas

Posted by HappyCoder on 14 June 2014 - 08:45 PM

Something I learned when making games, ideas might sound good on paper, or might sound bad on paper but once you actually put it into a game you cant really know. There have been many times where I thought an idea sounded bad, and after trying it out it was pretty good and same with the opposite.


Don't make a huge list of ideas that you want to put into a single game and then try to make the game exactly how you envision it. Instead, take one of your ideas, and try it out in a simple prototype. Make the prototype quickly. Don't create any fancy graphics for it and use whatever tool is fastest to try out that one idea. Use Unity, RPG maker, the starcraft II map editor, or even prototype your ideas using physical objects if possible. See what is good about the idea, and what isn't. Then try to fix what is broken and take what is good and make it better.


By doing more small prototypes you begin to learn what is fun and what isn't. Then start combining your ideas in interesting ways. After you have had some time experimenting, then you can start to think how all of this fits into a larger game. But, when you start to craft your game, you need to identify what the core mechanic will be and capitalize on that. If the most enjoyable part of your game is out battling monsters, players will not want to spend most of their time trading and crafting for better weapon stats. I'm not saying you can't include some of those elements, you just need to make sure the game keeps a definitive focus. The side quests should add to the gameplay, not detract from it.


I say this out of experience. I used to think that all it took for a game to be fun is a world to play in and stuff to do. It turns out that there is a lot more to it then that. I know this may not be what you want to hear but hold on to your dreams, even if it may take longer to get there.

#5160524 Getting Plane Vertices

Posted by HappyCoder on 14 June 2014 - 11:08 AM

Two non-parallel planes intersect at at a line, three non parallel planes intersect at a point. Each plane is in the form


Ax + By + Cz + D = 0


Where (A, B, C) is the normal and D is the distance. (x, y, z) is any point on the plane. If you are given three planes you can find where the intersect by setting up a matrix equation.

The normals of the three planes arranged in a matrix
    |A1 B1 C1|
M = |A2 B2 C2|
    |A3 B3 C3|

The intersection point of the three planes
v = |y|

The distances of the three planes
N = |-D2|

M * v = N

So solving for v gives us

v = inverse(M) * N

You would have to solve this equation 8 times for each set of three adjacent planes



However, if you want to find the corners of a frustum I would recommend using the projection and view matrix instead. You simply find the inverse of the view matrix multiplied by the projection matrix and then use that matrix to transform a set of constant points.


It would look something like this, I am just writing this out in pseudo code

// find the matrix that transforms from normalized space to world space
frustrumMatrix = inverse(viewMatrix * projectionMatrix);
// the corners of the frustrum in normalized space
cornerPoints = {
    Vector3(-1, -1, 1), Vector3(-1, 1, 1), 
    Vector3(1, 1, 1), Vector3(1, -1, 1), 
    Vector3(-1, -1, 0), Vector3(-1, 1, 0), 
    Vector3(1, 1, 0), Vector3(1, -1, 0)}

result = new Array();

foreach (Vector3 sourcePoint in cornerPoints)
    // extend the 3d sourcePoint to a 4d vector by making the 4th component 1
    // then transform the 4d point from normalized space, to world space
    Vector4 transPt = Vector4(sourcePoint, 1) * frustrumMatrix;

    // divide the 4d point by its 'w' value and turn it back into a 3d point
    // this point is a corner of the frustrum in world space
    result.Add(Vector3(transPt.x / transPt.w, transPt.y / transPt.w, transPt.z / transPt.w));

Let me explain why this works.


Some definitions first

world space - In world space, locations are measured relative to the world origin

camara space - Points measured relative to the camera

clipping space - Used by directx to cut out polygons or parts of polygons that aren't seen

normalized space - Points from -1 to 1 in the x and y and from 0 to 1 in the z are mapped to the screen.


Normally, the view matrix transforms points from the world space to the camera space. The projection matrix transforms from view space to clipping space. Any point that is transformed by a matrix has to be a 4D vector. So a 3D points is extended by adding a 4th component. For points, this extra value, called w, should be 1.


Multiplying the 4d vector by the view and projection matrix puts the point in clipping space. To get it to normalized coordinates, we need to divide the point by its w component. After that any point that was inside the frustum will be inside a cube ranging for -1 to 1 both the x and y and from 0 to 1 in the z. All points inside this range are mapped and drawn to the screen.


So that is the process that DirectX uses to transform geometry to the screen. The code above that I gave does the process in reverse starting in the normalized coordinates space.


This is an attempt to explain a fairly complicated subject very quickly, so it is understandable if you don't grasp it right away.

#5158797 OpenGL quaternions

Posted by HappyCoder on 06 June 2014 - 04:08 PM

To better understand how Quaternions work I would recommend learning how complex numbers can be used to represent rotation in 2D.



Complex numbers are kinda like the 2D equivalent of Quaternions. The same basic operations can be done with complex numbers as can be done with Quaternions only they are much simpler to comprehend. Once you understand how to manipulate 2D using complex numbers.

#5158520 Full Model Shader

Posted by HappyCoder on 05 June 2014 - 02:53 PM

Are you using an existing game engine?
If you are using your own game engine, are you using OpenGL or DirectX?

#5152590 Variable Size Array Of Structs GLSL

Posted by HappyCoder on 09 May 2014 - 02:14 PM

You can pass the entire array at once using glUniform3fv 
struct Data {
   Vector3 foo;
   Vector3 bar;

vector<Data> data;

// populate data

// 3 floats per vector
// 2 vectors per Data structure
float* floatBuffer = new float[data.size() * 3 * 2];

for (int i = 0; i < data.size(); ++i)
   floatBuffer[i * 6] = data[i].foo.x;
   floatBuffer[i * 6 + 1] = data[i].foo.y;
   floatBuffer[i * 6 + 2] = data[i].foo.z;
   floatBuffer[i * 6 + 3] = data[i].bar.x;
   floatBuffer[i * 6 + 4] = data[i].bar.y;
   floatBuffer[i * 6 + 5] = data[i].bar.z;

glUniform3fv(uniformLocation, data.size() * 2, floatBuffer);
This wont work if you ever mix in non floating point values into your glsl structure. In that case, you could just pass the uniforms in as seperate arrays instead of an array of structures.

#5152588 Fixed timestep + Box2D game loop

Posted by HappyCoder on 09 May 2014 - 02:04 PM

Good choice going for the fixed time step. To answer your questions.


1) You want to update Box2D inside the Logic update loop. Use 'dt' as the timestep in world.step()

2) Experiment with the physics time step and see what works best for you game. There isn't one right answer for all games.

3) No, you don't need to use a fixed timestep for those things, but why wouldn't you? Adding two types of udpates adds unneeded complexity to your code.

#5152584 Variable Size Array Of Structs GLSL

Posted by HappyCoder on 09 May 2014 - 01:54 PM

How much will the number of elements in your array vary? What is the average size?


If the number of elements doesn't vary much and there aren't that many of them. I would just allocate the array to be larger than what the average length is and just accept that there will be unused slots in that array.


If the size will generally be small but occasionally be larger, see if you could process the larger arrays in chunks. For example, say you allocate your shader to support up to 16 structures at once. When you get a batch of 48, you proccess three seperate batches, each of size 16. For more information on doing this, just look up mulit-pass rendering.

#5145759 How to make semi-transparent simple shadows not stack?

Posted by HappyCoder on 09 April 2014 - 02:08 PM

One option would be to render all of your shadows onto an off screen gray-scale texture using a normal blending mode. You then draw that texture to the screen using a multiply with alpha letting you control how dark the shadow is. Unfortunately, the game engine you are using might not have the features to allow you to do that. I am not familiar with HGE so I cannot tell you if it would support that or not.