windmill-gint/src/windmill.hpp

263 lines
4.8 KiB
C++

#ifndef DEF_WINDMILL
#define DEF_WINDMILL
#include <math.h>
#include <gint/display.h> // pour affichage des coordonnées
#include <string.h>
#include <stdlib.h>
#include <gint/defs/util.h>
#include "camera.hpp"
#include "Geometry.hpp"
#include <stdio.h>
#define get_vram_address() ((char *)gint_vram)
// parametrage de Windmill
#define MIN_AREA_CLIP 5
#define MAX_DEPTH_Z_BUFFER 0xffff
enum {N, RX, RY, RZ, Z_BILLBOARD};
//#define N {0, 0, 0}
//#define RX {1, 0, 0}
//#define RY {0, 1, 0}
//#define RZ {0, 0, 1}
#define LB {0, 1}
#define RB {1, 1}
#define LT {0, 0}
#define RT {1, 0}
#define MB {0.5, 1}
#define MT {0.5, 0}
#define LM {0, 0.5}
#define RM {1, 0.5}
#define FRONT 1
#define BACK -1
#define INTERIEUR true
#define EXTERIEUR false
// pour la collision
#define INSIDE -1
#define ALL 127
#define NONE 0
//#define OUT 1
//#define IN 0
// definition des structures
struct Sphere
{
int x, y, z;
int radius;
int square_radius;
};
struct VertexPoint
{
int x, y, z;
};
struct TexturePoint
{
float u, v;
};
struct Texture
{
const unsigned char* sprite;
const unsigned char* mask;
const char pixel_width;
const char pixel_height;
const int real_height;
const int real_width;
};
struct Face
{
const Texture* texture_front;
const Texture* texture_back;
unsigned char v[3];
unsigned char t[3];
bool visible = true;
};
class Vertex
{
public:
int x, y, z;
float u, v;
int inv_z;
unsigned short z_normalized;
Vertex();
Vertex(int _x, int _y, int _z);
Vertex(int _x, int _y, int _z, float _u, float _v);
void set_texture(TexturePoint t);
void set_xyz(int _x, int _y, int _z);
};
struct Mesh
{
const VertexPoint* v;
const int v_length;
const TexturePoint* t;
const int t_length;
const Face* f;
const int f_length;
};
class WMesh
{
public:
Vertex* v;
int v_length;
int v_length_allocated;
TexturePoint* t;
int t_length;
int t_length_allocated;
Face* f;
int f_length;
int f_length_allocated;
void from_mesh(const Mesh* mesh, int margin);
void free_memory();
void add_vertex(Vertex vertex);
};
struct Object
{
// bool static = STATIC / DYNAMIC -> transform_model_to_world au chargement
const Mesh* mesh;
Point3D position;
//Vector3D rotation;
//short x, y, z;
char axe;
float angle;
//Vector3D rotation;
char collision = ALL;
bool visible = true;
Sphere sphere;
WMesh* shadow;
//bool on_screen;
};
struct Map
{
Object** object;
int object_length;
bool horizon;
bool ground;
// ajouter ici
};
struct Viewport
{
int x1, y1, x2, y2;
};
int compare_object(void const *a, void const *b);
class Windmill
{
public:
// initialisation, parametrage et pre calcul
Windmill();
void set_camera(Camera* _camera);
void set_viewport(int viewport_x1, int viewport_y1, int viewport_x2, int viewport_y2);
void set_map(Map* _map);
void set_objects();
void compute_bouding_sphere();
void compute_shadows();
void compute_shadows_hull(Point3D* points, int points_size);
int compute_shadows_hull_orientation(Point3D a, Point3D b, Point3D c);
// dessin
void draw();
void draw_horizon();
void draw_shadows();
void draw_ground();
void draw_objects();
void draw_post_treatment();
void draw_body();
// transformation 3D des vertex
void transform_model_to_world(Object* object, Vertex vertex[], int vertex_length);
void transform_world_to_camera(Vertex vertex[], int vertex_length);
void transform_camera_to_screen(Vertex vertex[], int vertex_length);
// test visiblilite
bool object_in_frustrum(Object* object);
void clip_frustrum(WMesh* mesh);
bool inside_frustrum(Vertex vertex, Plane plane, int offset = 0);
Vertex clip_plane(Vertex vertex[], int vertex_length);
Vertex clip_onto_plane(Vertex vertexA, Vertex vertexB, Plane plane);
bool inside_viewport(int x, int y);
int get_visible_face(Vertex* a, Vertex* b, Vertex* c);
// dessin des triangles
void render_triangles(WMesh mesh);
void render_triangle_texture(Vertex* vertex1, Vertex* vertex2, Vertex* vertex3, const Texture* texture);
void render_triangle_color(Vertex* vertex0, Vertex* vertex1, Vertex* vertex2, color_t color);
// divers
void copy_camera();
void sort_object();
void clear_z_buffer();
int edge(Vertex* a, Vertex* b, Vertex* c);
int edge_start(Vertex* a, Vertex* b, int px, int py);
int edge_step_x(Vertex* a, Vertex* b);
int edge_step_y(Vertex* a, Vertex* b);
float distance(float dx, float dy, float dz);
// utilitaires
void show_coordinates();
void show_repere();
// destructeur
~Windmill();
private:
// camera
Camera* camera2; // camera a suivre
Camera camera; // camera_temporaire
// carte
Map* map;
// liste objets triee
Object* objects;
// ombres
Point3D sun;
// z_buffer
int shift_x, shift_y;
unsigned short* z_buffer;
int z_buffer_size;
int z_buffer_offset;
int z_buffer_width;
// en cours
int i;
int j;
public:
// fenetre de visualisation
Viewport viewport;
// utilitaires
bool loading;
bool log = false;
};
#endif