]> git.bts.cx Git - benzene.git/blob - src/bz/gfx/draw_queue.c
Fixed Aseprite rendering system
[benzene.git] / src / bz / gfx / draw_queue.c
1 #include <bz/gfx/draw_queue.h>
2
3 #include <bz/memory/allocator.h>
4 #include <bz/memory/arena_internal.h>
5 #include <string.h> // memcpy
6
7 static BZMemoryArena instructionArena;
8
9 struct BZDrawQueueInstruction {
10 //BZRect cullRect;
11 BZDrawQueueCall drawCall;
12 void *userParameter;
13
14 uint8_t sortIdx;
15 struct BZDrawQueueInstruction *sortedNextInstruction;
16 };
17 typedef struct BZDrawQueueInstruction BZDrawQueueInstruction;
18
19 // FIXME, make this better?? Dynamic??
20 #define kNumberDrawInstructions 512
21 #define kDrawInstructionMemory 32
22
23 struct BZDrawQueue {
24 size_t enqueuedInstructions;
25 BZDrawQueueInstruction instructions[kNumberDrawInstructions];
26 uint8_t *instructionMemory;
27 BZMemoryArena instructionArena;
28 BZDrawQueueInstruction *sortedFirstInstruction[kNumberDrawInstructions];
29 BZDrawQueueInstruction *sortedLastInstruction[kNumberDrawInstructions];
30 };
31
32 #define kInstructionMemorySize kNumberDrawInstructions * kDrawInstructionMemory
33
34 //static size_t numDrawQueues = 0;
35 //static BZDrawQueue drawQueues[300];
36
37 BZDrawQueueID bzGfxDrawQueueCreate(BZMemoryArenaID arena, const char *identifierFmt, ...) {
38 // bzLog("Creating queue size %d", sizeof(BZDrawQueue));
39 BZDrawQueueID drawQueue = (BZDrawQueueID)bzMemoryAlloc(arena, sizeof(BZDrawQueue));
40 bzAssert(drawQueue != NULL);
41 drawQueue->instructionMemory = bzMemoryAlloc(arena, kInstructionMemorySize);
42 bzMemoryArenaSetup(&drawQueue->instructionArena, drawQueue->instructionMemory, kInstructionMemorySize, false); // Don't zero this out because it's just some temp memory stuff
43 bzGfxDrawQueueClear(drawQueue);
44 return drawQueue;
45 // return &drawQueues[numDrawQueues++];
46 }
47
48 void bzGfxDrawQueueTeardown(BZDrawQueueID drawQueue) {
49
50 }
51
52 size_t bzGfxDrawQueueEnqueuedInstructionCount(BZDrawQueueID drawQueue) {
53 return drawQueue->enqueuedInstructions;
54 }
55
56 void bzGfxDrawQueueClear(BZDrawQueueID drawQueue) {
57 drawQueue->enqueuedInstructions = 0;
58
59 for (size_t i = 0; i < kNumberDrawInstructions; ++i) {
60 drawQueue->sortedFirstInstruction[i] = NULL;
61 drawQueue->sortedLastInstruction[i] = NULL;
62 }
63
64 bzMemoryArenaReset(&drawQueue->instructionArena);
65 }
66
67 /*void bzGfxDrawQueueEnqueue(BZDrawQueueID drawQueue, BZDrawQueueCall drawCall, void *userParameter) {
68 BZDrawQueueInstruction *instruction = &drawQueue->instructions[drawQueue->enqueuedInstructions++];
69 instruction->drawCall = drawCall;
70 instruction->userParameter = userParameter;
71 }*/
72
73
74 extern void *bzGfxDrawQueueEnqueue(BZDrawQueueID drawQueue, uint8_t sortIdx, BZDrawQueueCall drawCall, size_t userParameterSize) {
75 bzAssert(drawQueue->enqueuedInstructions < kNumberDrawInstructions);
76
77 BZDrawQueueInstruction *instruction = &drawQueue->instructions[drawQueue->enqueuedInstructions++];
78 instruction->sortedNextInstruction = NULL;
79 //instruction->cullRect = cullRect;
80 instruction->drawCall = drawCall;
81 instruction->userParameter = bzMemoryAlloc(&drawQueue->instructionArena, userParameterSize);
82
83 if (drawQueue->sortedFirstInstruction[sortIdx] == NULL) {
84 drawQueue->sortedFirstInstruction[sortIdx] = instruction;
85 drawQueue->sortedLastInstruction[sortIdx] = instruction;
86 } else {
87 drawQueue->sortedLastInstruction[sortIdx]->sortedNextInstruction = instruction;
88 drawQueue->sortedLastInstruction[sortIdx] = instruction;
89 }
90
91 return instruction->userParameter;
92 }
93
94 void bzGfxDrawQueueRun(BZDrawQueueID drawQueue) {
95 for (size_t i = 0; i < kNumberDrawInstructions; ++i) {
96 bzGfxDrawQueueRunSortBin(drawQueue, i);
97 }
98
99 // for (size_t i = 0; i < drawQueue->enqueuedInstructions; ++i) {
100 // //if (true) { // FIXME, cull
101 // drawQueue->instructions[i].drawCall(drawQueue->instructions[i].userParameter);
102 // //}
103 // }
104 }
105
106 void bzGfxDrawQueueRunSortBin(BZDrawQueueID drawQueue, uint8_t sortIdx) {
107 BZDrawQueueInstruction *instruction = drawQueue->sortedFirstInstruction[sortIdx];
108 while (instruction != NULL) {
109 instruction->drawCall(instruction->userParameter);
110 instruction = instruction->sortedNextInstruction;
111 }
112 }