diff --git a/src/draw.c b/src/draw.c new file mode 100644 index 0000000..c3c99a0 --- /dev/null +++ b/src/draw.c @@ -0,0 +1,31 @@ +#include +#include +#include +#include +#include + +#include +#include + +#include "types.h" +#include "game.h" +#include "draw.h" + +void draw_workers(Workers *workers){ + for(int i = 0; i < workers->worker_n; i++){ + DrawRectangleV(workers->worker_stack[i].pos, (V2d){.x=32,.y=32}, WHITE); + } +} + +void draw_machines(Machines *machines){ + for(int i = 0; i < machines->machine_n; i++){ + DrawRectangleV(machines->machine_stack[i].pos, (V2d){.x=64,.y=64}, BLUE); + } +} + +void draw(Game *game){ + draw_machines(&game->machines); + draw_workers(&game->workers); +} + + diff --git a/src/draw.h b/src/draw.h new file mode 100644 index 0000000..ea00af4 --- /dev/null +++ b/src/draw.h @@ -0,0 +1,15 @@ +#include +#include +#include +#include +#include + +#include +#include + +#include "types.h" +#include "game.h" + +#pragma once + +void draw(Game *game); diff --git a/src/game.c b/src/game.c new file mode 100644 index 0000000..aafe410 --- /dev/null +++ b/src/game.c @@ -0,0 +1,256 @@ +#include +#include +#include +#include +#include + +#include +#include + +#include "types.h" +#include "game.h" + +MachineDef machine_dict[] = { + {{}, 0, R_Coal, 4}, // MT_CoalMine + {{}, 0, R_Iron, 4}, // MT_IronMine + {{R_Coal, R_Iron}, 2, R_Steel, 0}, // MT_Furnace +}; + +int init_machines(Machines *machines){ + machines->machine_n = 0; + machines->machine_id = 0; + + machines->machine_stack = malloc(sizeof(Worker)*W_ALLOC_BLOCK); + if(!machines->machine_stack) + return 1; + + return 0; +} + +int init_workers(Workers *workers){ + workers->worker_n = 0; + + workers->worker_stack = malloc(sizeof(Worker)*W_ALLOC_BLOCK); + if(!workers->worker_stack) + return 1; + + return 0; +} + +int init_game(Game *game){ + int err = init_machines(&game->machines); + err |= init_workers(&game->workers); + if(err){ + printf("Failed to init game. Error : %x\n", err); + return 1; + } + return 0; +} + +void clean_machines(Machines *machines){ + free(machines->machine_stack); +} + +void clean_workers(Workers *workers){ + free(workers->worker_stack); +} + +void clean_game(Game *game){ + clean_machines(&game->machines); + clean_workers(&game->workers); +} + +Worker *add_worker(Workers *workers, V2d pos){ + if((workers->worker_n%W_ALLOC_BLOCK)+1 >= W_ALLOC_BLOCK){ + void *tmp = realloc(workers->worker_stack, + (workers->worker_n+W_ALLOC_BLOCK)*sizeof(Worker)); + if(!tmp){ + printf("Failed to extend worker stack !\n"); + return NULL; + } + + workers->worker_stack = tmp; + } + + Worker *work = &workers->worker_stack[workers->worker_n++]; + work->pos = pos; + work->ai = (AiInternal){S_Idle, 0, 0, 0, -1, -1, {.x=0,.y=0}}; + + return work; +} + +Machine *add_machine(Machines *machines, V2d pos){ + if((machines->machine_n%M_ALLOC_BLOCK)+1 >= M_ALLOC_BLOCK){ + void *tmp = realloc(machines->machine_stack, + (machines->machine_n+W_ALLOC_BLOCK)*sizeof(Machine)); + if(!tmp){ + printf("Failed to extend machine stack !\n"); + return NULL; + } + + machines->machine_stack = tmp; + } + + Machine *mach = &machines->machine_stack[machines->machine_n++]; + mach->id = machines->machine_id++; + mach->pos = pos; + mach->assign_workers = 0; + + return mach; +} + +int id_cmpfunc(const void *a_, const void *b_){ + Machine *a = a_; + Machine *b = b_; + return a->id - b->id; +} + +Machine *get_machine_from_id(Machines *machines, int id){ + Machine tmach = {.id = id}; + Machine *match = bsearch(&tmach, machines->machine_stack, machines->machine_n, + sizeof(Machine), &id_cmpfunc); + return match; +} + +int get_machine_localres(Machine *machine, int globalres){ + MachineDef *def = &machine_dict[machine->type]; + for(int i = 0; i < 4; i++){ + if(def->inputs[i] == globalres) + return i; + } + return -1; +} + +void update_worker(Game *game, Worker *worker){ + AiInternal *ai = &worker->ai; + if(ai->assigned_machine < 0 && ai->assigned_machine1 < 0) + ai->status = S_Idle; + + Machine *mach[2]; + MachineDef *defs[2]; + + if(ai->assigned_machine > -1){ + mach[0] = get_machine_from_id(&game->machines, ai->assigned_machine); + if(!mach[0]) + ai->assigned_machine = -1; + else + defs[0] = &machine_dict[mach[0]->type]; + } + if(ai->assigned_machine1 > -1){ + mach[1] = get_machine_from_id(&game->machines, ai->assigned_machine1); + if(!mach[1]) + ai->assigned_machine1 = -1; + else + defs[1] = &machine_dict[mach[1]->type]; + } + + if(ai->assigned_machine < 0 && ai->assigned_machine1 < 0) + ai->status = S_Idle; + + //TODO : Move ! + switch(ai->status){ + default: + break; + case S_Loading: + if(!Vector2Equals(worker->pos,mach[0]->pos)){ + ai->status = S_Transporting; + ai->going_to = 0; + ai->dest = mach[0]->pos; + break; + } + if(ai->carrying <= 50 && mach[0]->storage[4]){ + ai->carrying++; + mach[0]->storage[4]--; + } + else { + ai->status = S_Transporting; + ai->dest = mach[1]->pos; + ai->going_to = 1; + } + break; + case S_Unloading: + int localres = get_machine_localres(mach[1], ai->carry_type); + if(localres != (int)ai->carry_type){ + ai->status = S_Idle; + break; + } + if(!Vector2Equals(worker->pos, mach[1]->pos)){ + ai->status = S_Transporting; + ai->dest = mach[1]->pos; + ai->going_to = 1; + break; + } + if(ai->carrying && mach[1]->storage[localres] <= 200){ + ai->carrying--; + mach[1]->storage[localres]++; + } + else{ + ai->status = S_Transporting; + ai->dest = mach[0]->pos; + ai->going_to = 0; + } + break; + case S_Operating: + worker->pos = mach[0]->pos; + break; + case S_Transporting: + case S_Walking: + worker->pos = ai->dest; + if(Vector2Equals(worker->pos, mach[0]->pos)) + ai->status = S_Loading; + else if(Vector2Equals(worker->pos, mach[1]->pos)) + ai->status = S_Unloading; + break; + } +} + +void update_workers(Game *game){ + for(int i = 0; i < game->workers.worker_n; i++){ + update_worker(game, &game->workers.worker_stack[i]); + } +} + +void update_machine(Game *game, Machine *machine){ + MachineDef *def = &machine_dict[machine->type]; + bool can_output = machine->assign_workers == def->workers_required; + can_output = can_output && (machine->storage[4] <= 200); + for(int i = 0; i < def->input_n; i++){ + if(!machine->storage[i]) + can_output = false; + } + if(can_output){ + for(int i = 0; i < def->input_n; i++){ + machine->storage[i]--; + } + machine->storage[4]++; + } +} + +void update_machines(Game *game){ + for(int i = 0; i < game->machines.machine_n; i++){ + update_machine(game, &game->machines.machine_stack[i]); + } +} + +void update(Game *game){ + update_machines(game); + update_workers(game); +} + +int assign_worker_machine(Machine *machine, Worker *worker){ + machine->assign_workers++; + AiInternal *ai = &worker->ai; + ai->assigned_machine = machine->id; + ai->assigned_machine1 = -1; + ai->status = S_Operating; + return 0; +} + +int assign_worker_fetch(Machine *a, Machine *b, Worker *worker){ + AiInternal *ai = &worker->ai; + ai->carry_type = machine_dict[a->id].output; + ai->assigned_machine = a->id; + ai->assigned_machine1 = b->id; + ai->status = S_Loading; + return 0; +} diff --git a/src/game.h b/src/game.h new file mode 100644 index 0000000..5fc7a0d --- /dev/null +++ b/src/game.h @@ -0,0 +1,34 @@ +#include +#include +#include +#include +#include + +#include +#include + +#include "types.h" + +#pragma once + +#define W_ALLOC_BLOCK 256 +#define M_ALLOC_BLOCK 64 + +extern MachineDef machine_dict[]; + +int init_game(Game *game); + +void clean_game(Game *game); + +Worker *add_worker(Workers *workers, V2d pos); + +Machine *add_machine(Machines *machines, V2d pos); + +Machine *get_machine_from_id(Machines *machines, int id); + +void update(Game *game); + +int assign_worker_machine(Machine *machine, Worker *worker); + +// prends de a et emmène à b +int assign_worker_fetch(Machine *a, Machine *b, Worker *worker); diff --git a/src/main.c b/src/main.c index 7bc1d99..a33488f 100644 --- a/src/main.c +++ b/src/main.c @@ -7,368 +7,13 @@ #include #include -#define V2d Vector2 +#include "types.h" +#include "game.h" +#include "draw.h" //Idées : // - Drogues -enum Status { - S_Idle = 0, - S_Transporting = 1, - S_Loading = 2, - S_Unloading = 3, - S_Operating = 4, - S_Walking -}; - -enum WorkerTraits { - pass2 -}; - -enum MachineTypes { - MT_CoalMine = 0, - MT_IronMine = 1, - MT_Furnace = 2 -}; - -enum Ressources { - R_Coal = 0, - R_Iron = 1, - R_Steel = 2 -}; - -typedef struct { - - uint8_t status; - uint8_t carrying; //Quantity - uint8_t carry_type; //Global type - uint8_t going_to; - int16_t assigned_machine; // Machine if working - int16_t assigned_machine1; // 2nd machine if carrying - V2d dest; - -} AiInternal; - -typedef struct { - - V2d pos; - uint16_t traits; - uint8_t fatigue; - uint8_t satisf; - AiInternal ai; - uint8_t __padding[4]; - -} Worker; - -typedef struct { - - int worker_n; - Worker *worker_stack; - -} Workers; - -typedef struct { - - V2d pos; - uint8_t type; - uint8_t assign_workers; - uint8_t rot; // Rotation - uint8_t storage[5]; // <=> inputs ; 4 is out storage - int16_t id; - -} Machine; - -typedef struct { - - uint8_t inputs[4]; - uint8_t input_n; - uint8_t output; - uint8_t workers_required; - -} MachineDef; - -typedef struct { - - int machine_n; - int machine_id; - Machine *machine_stack; - -} Machines; - -typedef struct { - - Machines machines; - Workers workers; - - int64_t cash; - -} Game; - -MachineDef machine_dict[] = { - {{}, 0, R_Coal, 4}, // MT_CoalMine - {{}, 0, R_Iron, 4}, // MT_IronMine - {{R_Coal, R_Iron}, 2, R_Steel, 0}, // MT_Furnace -}; - -#define W_ALLOC_BLOCK 256 -#define M_ALLOC_BLOCK 64 - -int init_machines(Machines *machines){ - machines->machine_n = 0; - machines->machine_id = 0; - - machines->machine_stack = malloc(sizeof(Worker)*W_ALLOC_BLOCK); - if(!machines->machine_stack) - return 1; - - return 0; -} - -int init_workers(Workers *workers){ - workers->worker_n = 0; - - workers->worker_stack = malloc(sizeof(Worker)*W_ALLOC_BLOCK); - if(!workers->worker_stack) - return 1; - - return 0; -} - -int init_game(Game *game){ - int err = init_machines(&game->machines); - err |= init_workers(&game->workers); - if(err){ - printf("Failed to init game. Error : %x\n", err); - return 1; - } - return 0; -} - -void clean_machines(Machines *machines){ - free(machines->machine_stack); -} - -void clean_workers(Workers *workers){ - free(workers->worker_stack); -} - -void clean_game(Game *game){ - clean_machines(&game->machines); - clean_workers(&game->workers); -} - -Worker *add_worker(Workers *workers, V2d pos){ - if((workers->worker_n%W_ALLOC_BLOCK)+1 >= W_ALLOC_BLOCK){ - void *tmp = realloc(workers->worker_stack, - (workers->worker_n+W_ALLOC_BLOCK)*sizeof(Worker)); - if(!tmp){ - printf("Failed to extend worker stack !\n"); - return NULL; - } - - workers->worker_stack = tmp; - } - - Worker *work = &workers->worker_stack[workers->worker_n++]; - work->pos = pos; - work->ai = (AiInternal){S_Idle, 0, 0, 0, -1, -1, {.x=0,.y=0}}; - - return work; -} - -Machine *add_machine(Machines *machines, V2d pos){ - if((machines->machine_n%M_ALLOC_BLOCK)+1 >= M_ALLOC_BLOCK){ - void *tmp = realloc(machines->machine_stack, - (machines->machine_n+W_ALLOC_BLOCK)*sizeof(Machine)); - if(!tmp){ - printf("Failed to extend machine stack !\n"); - return NULL; - } - - machines->machine_stack = tmp; - } - - Machine *mach = &machines->machine_stack[machines->machine_n++]; - mach->id = machines->machine_id++; - mach->pos = pos; - mach->assign_workers = 0; - - return mach; -} - -int id_cmpfunc(const void *a_, const void *b_){ - Machine *a = a_; - Machine *b = b_; - return a->id - b->id; -} - -Machine *get_machine_from_id(Machines *machines, int id){ - Machine tmach = {.id = id}; - Machine *match = bsearch(&tmach, machines->machine_stack, machines->machine_n, - sizeof(Machine), &id_cmpfunc); - return match; -} - -int get_machine_localres(Machine *machine, int globalres){ - MachineDef *def = &machine_dict[machine->type]; - for(int i = 0; i < 4; i++){ - if(def->inputs[i] == globalres) - return i; - } - return -1; -} - -void update_worker(Game *game, Worker *worker){ - AiInternal *ai = &worker->ai; - if(ai->assigned_machine < 0 && ai->assigned_machine1 < 0) - ai->status = S_Idle; - - Machine *mach[2]; - MachineDef *defs[2]; - - if(ai->assigned_machine > -1){ - mach[0] = get_machine_from_id(&game->machines, ai->assigned_machine); - if(!mach[0]) - ai->assigned_machine = -1; - else - defs[0] = &machine_dict[mach[0]->type]; - } - if(ai->assigned_machine1 > -1){ - mach[1] = get_machine_from_id(&game->machines, ai->assigned_machine1); - if(!mach[1]) - ai->assigned_machine1 = -1; - else - defs[1] = &machine_dict[mach[1]->type]; - } - - if(ai->assigned_machine < 0 && ai->assigned_machine1 < 0) - ai->status = S_Idle; - - //TODO : Move ! - switch(ai->status){ - default: - break; - case S_Loading: - if(!Vector2Equals(worker->pos,mach[0]->pos)){ - ai->status = S_Transporting; - ai->going_to = 0; - ai->dest = mach[0]->pos; - break; - } - if(ai->carrying <= 50 && mach[0]->storage[4]){ - ai->carrying++; - mach[0]->storage[4]--; - } - else { - ai->status = S_Transporting; - ai->dest = mach[1]->pos; - ai->going_to = 1; - } - break; - case S_Unloading: - int localres = get_machine_localres(mach[1], ai->carry_type); - if(localres != (int)ai->carry_type){ - ai->status = S_Idle; - break; - } - if(!Vector2Equals(worker->pos, mach[1]->pos)){ - ai->status = S_Transporting; - ai->dest = mach[1]->pos; - ai->going_to = 1; - break; - } - if(ai->carrying && mach[1]->storage[localres] <= 200){ - ai->carrying--; - mach[1]->storage[localres]++; - } - else{ - ai->status = S_Transporting; - ai->dest = mach[0]->pos; - ai->going_to = 0; - } - break; - case S_Operating: - worker->pos = mach[0]->pos; - break; - case S_Transporting: - case S_Walking: - worker->pos = ai->dest; - if(Vector2Equals(worker->pos, mach[0]->pos)) - ai->status = S_Loading; - else if(Vector2Equals(worker->pos, mach[1]->pos)) - ai->status = S_Unloading; - break; - } -} - -void update_workers(Game *game){ - for(int i = 0; i < game->workers.worker_n; i++){ - update_worker(game, &game->workers.worker_stack[i]); - } -} - -void update_machine(Game *game, Machine *machine){ - MachineDef *def = &machine_dict[machine->type]; - bool can_output = machine->assign_workers == def->workers_required; - can_output = can_output && (machine->storage[4] <= 200); - for(int i = 0; i < def->input_n; i++){ - if(!machine->storage[i]) - can_output = false; - } - if(can_output){ - for(int i = 0; i < def->input_n; i++){ - machine->storage[i]--; - } - machine->storage[4]++; - } -} - -void update_machines(Game *game){ - for(int i = 0; i < game->machines.machine_n; i++){ - update_machine(game, &game->machines.machine_stack[i]); - } -} - -void update(Game *game){ - update_machines(game); - update_workers(game); -} - -void draw_workers(Workers *workers){ - for(int i = 0; i < workers->worker_n; i++){ - DrawRectangleV(workers->worker_stack[i].pos, (V2d){.x=32,.y=32}, WHITE); - } -} - -void draw_machines(Machines *machines){ - for(int i = 0; i < machines->machine_n; i++){ - DrawRectangleV(machines->machine_stack[i].pos, (V2d){.x=64,.y=64}, BLUE); - } -} - -void draw(Game *game){ - draw_machines(&game->machines); - draw_workers(&game->workers); -} - -int assign_worker_machine(Machine *machine, Worker *worker){ - machine->assign_workers++; - AiInternal *ai = &worker->ai; - ai->assigned_machine = machine->id; - ai->assigned_machine1 = -1; - ai->status = S_Operating; - return 0; -} - -int assign_worker_fetch(Machine *a, Machine *b, Worker *worker){ - AiInternal *ai = &worker->ai; - ai->carry_type = machine_dict[a->id].output; - ai->assigned_machine = a->id; - ai->assigned_machine1 = b->id; - ai->status = S_Loading; - return 0; -} - int try_interface(Game *game){ return 0; } diff --git a/src/types.h b/src/types.h new file mode 100644 index 0000000..52f2f12 --- /dev/null +++ b/src/types.h @@ -0,0 +1,106 @@ +#include +#include +#include +#include +#include + +#include +#include + +#pragma once + +#define V2d Vector2 + +enum Status { + S_Idle = 0, + S_Transporting = 1, + S_Loading = 2, + S_Unloading = 3, + S_Operating = 4, + S_Walking +}; + +enum WorkerTraits { + pass2 +}; + +enum MachineTypes { + MT_CoalMine = 0, + MT_IronMine = 1, + MT_Furnace = 2 +}; + +enum Ressources { + R_Coal = 0, + R_Iron = 1, + R_Steel = 2 +}; + +typedef struct { + + uint8_t status; + uint8_t carrying; //Quantity + uint8_t carry_type; //Global type + uint8_t going_to; + int16_t assigned_machine; // Machine if working + int16_t assigned_machine1; // 2nd machine if carrying + V2d dest; + +} AiInternal; + +typedef struct { + + V2d pos; + uint16_t traits; + uint8_t fatigue; + uint8_t satisf; + AiInternal ai; + uint8_t __padding[4]; + +} Worker; + +typedef struct { + + int worker_n; + Worker *worker_stack; + +} Workers; + +typedef struct { + + V2d pos; + uint8_t type; + uint8_t assign_workers; + uint8_t rot; // Rotation + uint8_t storage[5]; // <=> inputs ; 4 is out storage + int16_t id; + +} Machine; + +typedef struct { + + uint8_t inputs[4]; + uint8_t input_n; + uint8_t output; + uint8_t workers_required; + +} MachineDef; + +typedef struct { + + int machine_n; + int machine_id; + Machine *machine_stack; + +} Machines; + +typedef struct { + + Machines machines; + Workers workers; + + int64_t cash; + +} Game; + +