• Hey Guest! Ever feel like entering a Game Jam, but the time limit is always too much pressure? We get it... You lead a hectic life and dedicating 3 whole days to make a game just doesn't work for you! So, why not enter the GMC SLOW JAM? Take your time! Kick back and make your game over 4 months! Interested? Then just click here!

3D 3D rendering problem. Everything drawn on top of eachother

ikonhero

Member
I'm playing around with 3D in GMS2. What I'm aiming for is a basic "Wolfenstein 3D" FPS look.

I pieced together some information from the limited guides that are out there. Got basic FPS movement and wall collisions done.

However there's a problem with the rendering. everything is drawn on top of eachother, regardless if it should be visible or not.



As you can see from this image all sides of all walls, floortiles and ceilingtiles are visible at all times.


I know the obj_solid create event is rather unoptimized and could be improved using more scripts.

I'm probably missing something very simple. Any help would be very much appreciated!!


Here's some code that I'm using:

window_set_fullscreen(true);

gpu_set_zwriteenable(true);
gpu_set_ztestenable(true);
gpu_set_cullmode(cull_noculling);
/*
gpu_set_alphatestenable(true);
gpu_set_alphatestref(100);
*/

layer_force_draw_depth(false,0);

view_enabled = true;//Enable the use of views
view_set_visible(0, true);//Make this view visible

camera = camera_create();

projMat = matrix_build_projection_perspective_fov(-60, -view_get_wport(0)/view_get_hport(0), 0, 32000);

camera_set_proj_mat(camera, projMat);

view_set_camera(0, camera);

camera_set_update_script(view_camera[0], scr_camera_update_script());

z = 0;
size = 32;


vertex_format_begin();
vertex_format_add_position_3d();//Add 3D position info
vertex_format_add_normal();
vertex_format_add_color();//Add color info
vertex_format_add_textcoord();//Texture coordinate info
//End building the format, and assign the format to the variable "format"
format = vertex_format_end();


square1 = vertex_create_buffer();
vertex_begin(square1,format);

//1
scr_vertex_point_add(square1,x,y,z+size,0,0,1,c_white,1,1,0);
//2
scr_vertex_point_add(square1,x+size,y,z+size,0,0,1,c_white,1,0,0);
//3
scr_vertex_point_add(square1,x,y,z,0,0,1,c_white,1,1,1);

//2
scr_vertex_point_add(square1,x+size,y,z+size,0,0,1,c_white,1,0,0);
//3
scr_vertex_point_add(square1,x,y,z,0,0,1,c_white,1,1,1);
//4
scr_vertex_point_add(square1,x+size,y,z,0,0,1,c_white,1,0,1);

vertex_end(square1);
vertex_freeze(square1)


square2 = vertex_create_buffer();
vertex_begin(square2,format);
//1
scr_vertex_point_add(square2,x,y,z+size,0,0,1,c_white,1,0,0);
//5
scr_vertex_point_add(square2,x,y+size,z+size,0,0,1,c_white,1,1,0);
//3
scr_vertex_point_add(square2,x,y,z,0,0,1,c_white,1,0,1);

//5
scr_vertex_point_add(square2,x,y+size,z+size,0,0,1,c_white,1,1,0);
//3
scr_vertex_point_add(square2,x,y,z,0,0,1,c_white,1,0,1);
//6
scr_vertex_point_add(square2,x,y+size,z,0,0,1,c_white,1,1,1);

vertex_end(square2);
vertex_freeze(square2)


square3 = vertex_create_buffer();
vertex_begin(square3,format);
//2
scr_vertex_point_add(square3,x+size,y,z+size,0,0,-1,c_white,1,1,0);
//4
scr_vertex_point_add(square3,x+size,y,z,0,0,-1,c_white,1,1,1);
//7
scr_vertex_point_add(square3,x+size,y+size,z+size,0,0,-1,c_white,1,0,0);

//4
scr_vertex_point_add(square3,x+size,y,z,0,0,-1,c_white,1,1,1);
//7
scr_vertex_point_add(square3,x+size,y+size,z+size,0,0,-1,c_white,1,0,0);
//8
scr_vertex_point_add(square3,x+size,y+size,z,0,0,-1,c_white,1,0,1);

vertex_end(square3);
vertex_freeze(square3)

square4 = vertex_create_buffer();
vertex_begin(square4,format);
//5
scr_vertex_point_add(square4,x,y+size,z+size,0,0,-1,c_white,1,0,0);
//8
scr_vertex_point_add(square4,x+size,y+size,z,0,0,-1,c_white,1,1,1);
//6
scr_vertex_point_add(square4,x,y+size,z,0,0,-1,c_white,1,0,1);

//5
scr_vertex_point_add(square4,x,y+size,z+size,0,0,-1,c_white,1,0,0);
//7
scr_vertex_point_add(square4,x+size,y+size,z+size,0,0,-1,c_white,1,1,0);
//8
scr_vertex_point_add(square4,x+size,y+size,z,0,0,-1,c_white,1,1,1);

vertex_end(square4);
vertex_freeze(square4)
/// @param buffer
/// @param x
/// @param y
/// @param z
/// @param nx
/// @param ny
/// @param nz
/// @param color
/// @param alpha
/// @param xtex
/// @param ytex

vertex_position_3d(argument0,argument1,argument2,argument3);
vertex_normal(argument0,argument4,argument5,argument6);
vertex_color(argument0,argument7,argument8);
vertex_texcoord(argument0,argument9,argument10);

var matrix = matrix_build(0,0,0,0,0,0,1,1,1);
matrix_set(matrix_world,matrix);

vertex_submit(square1,pr_trianglelist,sprite_get_texture(spr_wall,0));
vertex_submit(square2,pr_trianglelist,sprite_get_texture(spr_wall,0));
vertex_submit(square3,pr_trianglelist,sprite_get_texture(spr_wall,0));
vertex_submit(square4,pr_trianglelist,sprite_get_texture(spr_wall,0));

matrix_set(matrix_world, matrix_build_identity());
 
Your near clipping distance must be greater than zero. Recheck the arguments to matrix_build_projection_perspective_fov.

Also, it's a really bad idea to use a seperate vertex buffer for every face of every object. You should be able to combine all of those faces into one vertex buffer. It will draw MUCH more efficiently.
 

Yal

šŸ§ *penguin noises*
GMC Elder
camera_set_update_script(view_camera[0], scr_camera_update_script());
You're setting the camera's update script to the result of the scr_camera_update_script, since you added ()s (which is a script call - the name on its own is a script resource reference). Not sure if it's the root cause, but it might lead to weird results - if the script doesn't return anything by default, script zero will be called to update the camera (since the default return value if none is given is 0) - i.e., the topmost script in the resource tree. Change that line to

camera_set_update_script(view_camera[0], scr_camera_update_script);
 

ikonhero

Member
Thanks so much, you really helped me out! Would never have found out about the clipping distance needing to be greater than zero.

Here's a quick video on what I got so far:
"

I also made a very simple billboarding system for enemy sprites. What do you think of this system?
rdir = point_direction(obj_player.x,obj_player.y,x,y);

xs = x-lengthdir_x(x,rdir-90);
ys = y-lengthdir_y(x,rdir-90);

matrix_set(matrix_world,matrix_build(xs,ys,y+1,90,0,rdir-90,1,1,1));

draw_self();

matrix_set(matrix_world, matrix_build_identity());

Again thanks!
 
Top