Highmap generation Problem (with image)
Hi, currently I''m having a small mathematical problem:
I need to generate a hightmap, where only the hight of the 4 border vertices are known. The resolution should be user defined and the x_res is always same as y_res.
For visualisation I uploaded a small image which represents a 4x4 highmap. The black border vertices are know. What I need is to generate the red vertices, so that the highmap is "smooth".
Here is the image:
http://www.josh.ch/phpmywebmin/_uploads/TCS/Problem.jpg
Is there anyone who could help me?
Thx in advance...
There are many different methods of doing this.
There''s one thing I''d like to know though. I assume the grid is larger than one square. Now if you want a smooth curve between squares and in fact you have more than one, then the problem is considerably more complicated. I''ve implemented it, but I did it from scratch and didn''t read up on it, so I don''t think I''m in a position to recommend anything, as my method of forming cubic equations may not be the best way.
If you just want it to be smooth for one square though, the best way I can think of is just simply using linear interpolation on each axis. That is simple and should give smooth results across one square.
There''s one thing I''d like to know though. I assume the grid is larger than one square. Now if you want a smooth curve between squares and in fact you have more than one, then the problem is considerably more complicated. I''ve implemented it, but I did it from scratch and didn''t read up on it, so I don''t think I''m in a position to recommend anything, as my method of forming cubic equations may not be the best way.
If you just want it to be smooth for one square though, the best way I can think of is just simply using linear interpolation on each axis. That is simple and should give smooth results across one square.
What does "smooth" mean?
As simple solution might be to linearly interpolate between black vertices on two opposite edges, then linearly interpolate between each oppsite pair of vertices on the edges you just generated.
A sightly more complicated method would be to limit (or adjust to get) an odd number of vertices per side, you could average the four corners to get a central vertex hight, then linearly or quadratically interpolate diagonals from the corners to the centre, then linearly interpolate between adjacent diagonals to fill in the rest.
There are also various more complicated methods, like weighted averages based on distance from each of the 4 known vertices or fitting to other 2D surfaces...
As simple solution might be to linearly interpolate between black vertices on two opposite edges, then linearly interpolate between each oppsite pair of vertices on the edges you just generated.
*-*-*-* Find - lines first| | | | * * * * Then find | lines between| | | | vertices * on - lines* * * *| | | |*-*-*-*
A sightly more complicated method would be to limit (or adjust to get) an odd number of vertices per side, you could average the four corners to get a central vertex hight, then linearly or quadratically interpolate diagonals from the corners to the centre, then linearly interpolate between adjacent diagonals to fill in the rest.
*-*-*-*-* Find \ and / lines first|\ /|* *-*-* * Then find | and - lines| |\ /| | between vertices * on* * * * * adjacent / and \ lines| |/ \| |* *-*-* *|/ \|*-*-*-*-*
There are also various more complicated methods, like weighted averages based on distance from each of the 4 known vertices or fitting to other 2D surfaces...
I''m not a great fan of terrain stuff, but here''s how I would do it (assuming that generation doesn''t have to be realtime):
Randomize every height except for the four corner values.
Then blur the heightmap several times without blurring the corner values. This results in a smooth heightmap where the corner values are the initial values you wanted.
With a good weighting kernel this corresponds to the finite difference approximation of the heat equation, of course.
- Mikko Kauppila
Randomize every height except for the four corner values.
Then blur the heightmap several times without blurring the corner values. This results in a smooth heightmap where the corner values are the initial values you wanted.
With a good weighting kernel this corresponds to the finite difference approximation of the heat equation, of course.
- Mikko Kauppila
Hi, thank you all for your help. This is now what I did, which seems to work great for me:
If there is something to improve, then please let me know. Anyway thanks for your great help...
#include "stdio.h"#define UINT unsigned int#define RESOLUTION 10int main(int argc, char* argv[]){ UINT res = RESOLUTION; float hmap[RESOLUTION][RESOLUTION]; float y0 = 200.0f; float y1 = 50.0f; float y2 = 300.0f; float y3 = -100.0f; hmap [0][0] = y0; hmap [0][RESOLUTION-1] = y1; hmap [RESOLUTION-1][0] = y2; hmap [RESOLUTION-1][RESOLUTION-1] = y3; for(UINT i = 0; i < RESOLUTION; i++) { for(UINT j = 0; j < RESOLUTION; j++) { float* tval = &hmap[i][j]; float k1 = (float)i / (float)(RESOLUTION-1); float k2 = (float)j / (float)(RESOLUTION-1); *tval = (1-k1)*(1-k2)*y0+k1*(1-k2)*y1+(1-k1)*k2*y2+k1*k2*y3; } } for(UINT i = 0; i < RESOLUTION; i++) { for(UINT j = 0; j < RESOLUTION; j++) { float* tval = &hmap[j][i]; printf("%.2lf\t", *tval); } printf("\n"); } return 0;}
If there is something to improve, then please let me know. Anyway thanks for your great help...
This topic is closed to new replies.
Advertisement
Popular Topics
Advertisement
Recommended Tutorials
Advertisement