Code archives/Algorithms/Normal Map
This code has been declared by its author to be Public Domain code.
Download source code
| |||||
| I hope someone finds it usefull... It loads an image called "heightmap.bmp". This is an image containing height information. Exactly the same as you would use for bumpmapping. This should be a grayscale image. If you use a color image, then only the blue channel is used. It's usefull for generating quick simple normal maps from just about any image. There are probably many progs out there that do the same but better. But if your like me and just getting into Dot3 bump mapping, then this little prog can help make you understand the normal map. (I hope to expand it so that you can load models instead of height maps and use this to generate a high quality and more accurate normal map.) Please leave feedback if you find it usefull or suggest improvments. Thanx | |||||
AppTitle "NormalMap"
Graphics 800,600,32,2
; this is a grayscale image. Each pixel is height information.
; White being the heighest and black being the lowest.
; you can use a color image but only the blue channel is used
heightmap = LoadImage("heightmap.bmp")
Global img_w = ImageWidth(heightmap)-1
Global img_h = ImageHeight(heightmap)-1
lightmap = CreateImage(img_w+1,img_h+1)
LockBuffer ImageBuffer(heightmap)
LockBuffer ImageBuffer(lightmap)
For y = 0 To img_h
If y>0 : ym1=y-1 : Else : ym1=0 : EndIf
If y<img_h : yp1=y+1 : Else : yp1=img_h : EndIf
For x = 0 To img_w
If x>0 : xm1=x-1 : Else : xm1=0 : EndIf
If x<img_w : xp1=x+1 : Else : xp1=img_w : EndIf
; get the pixel value for height info - up, down,
; left and right of current pixel
; And $0000FF restricts to blue channel
y_u = ReadPixelFast(x,yp1,ImageBuffer(heightmap)) And $0000FF
y_d = ReadPixelFast(x,ym1,ImageBuffer(heightmap)) And $0000FF
x_r = ReadPixelFast(xp1,y,ImageBuffer(heightmap)) And $0000FF
x_l = ReadPixelFast(xm1,y,ImageBuffer(heightmap)) And $0000FF
;calculate x and y gradient exactly the same as bumpmapping
nx = (x_l - x_r)
ny = (y_u - y_d)
; nx and ny can potentially fall into the range of -255 to 255,
; so we offest it To get rid of the negative value,
; Then half it To keep the value in the range of 255
red = (nx + 255)/2
green = (ny + 255)/2
blue = 255
; red is horizontal (x axis)
; red = 0 normal points left, red = 255 normal points right
; red = 128 normal points out of screen at you
;green is vertical (y axis)
; green = 0 normal points down, green = 255 normal points up
; green = 128 normal points out of screen at you
; shift the colors into the right place
cr = (red Shl 16) + (green Shl 8) + (blue)
WritePixelFast(x,y,cr,ImageBuffer(lightmap))
Next
Next
UnlockBuffer ImageBuffer(lightmap)
UnlockBuffer ImageBuffer(heightmap)
While Not KeyDown(1)
DrawImage heightmap,0,0
DrawImage lightmap,0,ImageHeight(heightmap)
Flip
Wend
SaveImage lightmap,"normal_map.bmp"
FreeImage heightmap
FreeImage lightmap
End |
Comments
| ||
| Thanks, it's espectacular code! |
Code Archives Forum