remove stdbool dependency + destroy count tweak
parent
01d1848b11
commit
25cdbf7d09
134
src/Silkworm2.c
134
src/Silkworm2.c
|
@ -89,12 +89,12 @@ typedef struct Silkworm_Node
|
||||||
float mass;
|
float mass;
|
||||||
float friction;
|
float friction;
|
||||||
float radius;
|
float radius;
|
||||||
bool pinned;
|
uint8_t pinned;
|
||||||
float pushFactor;
|
float pushFactor;
|
||||||
float windFactor;
|
float windFactor;
|
||||||
bool destroyable;
|
uint8_t destroyable;
|
||||||
|
|
||||||
bool markedForDestroy; /* mutual recursion on nodes/links so this makes it easier to track destroys */
|
uint8_t markedForDestroy; /* mutual recursion on nodes/links so this makes it easier to track destroys */
|
||||||
|
|
||||||
Silkworm_Link** links;
|
Silkworm_Link** links;
|
||||||
uint32_t linkCount;
|
uint32_t linkCount;
|
||||||
|
@ -110,7 +110,7 @@ struct Silkworm_Link
|
||||||
float distance;
|
float distance;
|
||||||
float tearThreshold;
|
float tearThreshold;
|
||||||
|
|
||||||
bool markedForDestroy; /* mutual recursion on nodes/links so this makes it easier to track destroys */
|
uint8_t markedForDestroy; /* mutual recursion on nodes/links so this makes it easier to track destroys */
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef enum Silkworm_ClothTriangleOrientation
|
typedef enum Silkworm_ClothTriangleOrientation
|
||||||
|
@ -192,7 +192,7 @@ static inline void NodeTriangleHashTable_Insert(
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
uint64_t hashcode = NodeTriangleHashTable_GetHashCode(key);
|
uint64_t hashcode = NodeTriangleHashTable_GetHashCode(key);
|
||||||
NodeTriangleHashArray* arr = &table->buckets[hashcode % NUM_NODE_TRIANGLE_HASH_BUCKETS];
|
NodeTriangleHashArray* arr = &table->buckets[hashcode % NUM_NODE_TRIANGLE_HASH_BUCKETS];
|
||||||
bool foundKey = false;
|
uint8_t foundKey = 0;
|
||||||
|
|
||||||
for (i = 0; i < arr->count; i += 1)
|
for (i = 0; i < arr->count; i += 1)
|
||||||
{
|
{
|
||||||
|
@ -201,7 +201,7 @@ static inline void NodeTriangleHashTable_Insert(
|
||||||
arr->elements[i].indexArray = Silkworm_realloc(arr->elements[i].indexArray, sizeof(uint32_t) * (arr->elements[i].indexArrayCount + 1));
|
arr->elements[i].indexArray = Silkworm_realloc(arr->elements[i].indexArray, sizeof(uint32_t) * (arr->elements[i].indexArrayCount + 1));
|
||||||
arr->elements[i].indexArray[arr->elements[i].indexArrayCount] = index;
|
arr->elements[i].indexArray[arr->elements[i].indexArrayCount] = index;
|
||||||
arr->elements[i].indexArrayCount += 1;
|
arr->elements[i].indexArrayCount += 1;
|
||||||
foundKey = true;
|
foundKey = 1;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -274,7 +274,7 @@ static inline void LinkTriangleHashTable_Insert(
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
uint64_t hashcode = LinkTriangleHashTable_GetHashCode(key);
|
uint64_t hashcode = LinkTriangleHashTable_GetHashCode(key);
|
||||||
LinkTriangleHashArray* arr = &table->buckets[hashcode % NUM_LINK_TRIANGLE_HASH_BUCKETS];
|
LinkTriangleHashArray* arr = &table->buckets[hashcode % NUM_LINK_TRIANGLE_HASH_BUCKETS];
|
||||||
bool foundKey = false;
|
uint8_t foundKey = 0;
|
||||||
|
|
||||||
for (i = 0; i < arr->count; i += 1)
|
for (i = 0; i < arr->count; i += 1)
|
||||||
{
|
{
|
||||||
|
@ -283,7 +283,7 @@ static inline void LinkTriangleHashTable_Insert(
|
||||||
arr->elements[i].indexArray = Silkworm_realloc(arr->elements[i].indexArray, sizeof(uint32_t) * (arr->elements[i].indexArrayCount + 1));
|
arr->elements[i].indexArray = Silkworm_realloc(arr->elements[i].indexArray, sizeof(uint32_t) * (arr->elements[i].indexArrayCount + 1));
|
||||||
arr->elements[i].indexArray[arr->elements[i].indexArrayCount] = index;
|
arr->elements[i].indexArray[arr->elements[i].indexArrayCount] = index;
|
||||||
arr->elements[i].indexArrayCount += 1;
|
arr->elements[i].indexArrayCount += 1;
|
||||||
foundKey = true;
|
foundKey = 1;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -363,14 +363,9 @@ typedef struct Silkworm_Context
|
||||||
|
|
||||||
float timeElapsed;
|
float timeElapsed;
|
||||||
|
|
||||||
/* keep track of these so can do callbacks */
|
/* keep track of these so we can query */
|
||||||
Silkworm_Vector2* nodeDestructionData;
|
uint32_t destroyedNodeCount;
|
||||||
uint32_t nodeDestructionDataCount;
|
uint32_t destroyedLinkCount;
|
||||||
uint32_t nodeDestructionDataCapacity;
|
|
||||||
|
|
||||||
Silkworm_Vector2* linkDestructionData;
|
|
||||||
uint32_t linkDestructionDataCount;
|
|
||||||
uint32_t linkDestructionDataCapacity;
|
|
||||||
|
|
||||||
Silkworm_Vertex* vertexBuffer;
|
Silkworm_Vertex* vertexBuffer;
|
||||||
uint32_t vertexCapacity;
|
uint32_t vertexCapacity;
|
||||||
|
@ -411,13 +406,8 @@ void Silkworm_Init()
|
||||||
context->clothDensity = 4;
|
context->clothDensity = 4;
|
||||||
context->timeElapsed = 0;
|
context->timeElapsed = 0;
|
||||||
|
|
||||||
context->nodeDestructionDataCapacity = 16;
|
context->destroyedNodeCount = 0;
|
||||||
context->nodeDestructionData = Silkworm_malloc(sizeof(Silkworm_Vector2) * context->nodeDestructionDataCapacity);
|
context->destroyedLinkCount = 0;
|
||||||
context->nodeDestructionDataCount = 0;
|
|
||||||
|
|
||||||
context->linkDestructionDataCapacity = 16;
|
|
||||||
context->linkDestructionData = Silkworm_malloc(sizeof(Silkworm_Vector2) * context->nodeDestructionDataCapacity);
|
|
||||||
context->linkDestructionDataCount = 0;
|
|
||||||
|
|
||||||
context->vertexCapacity = 1024;
|
context->vertexCapacity = 1024;
|
||||||
context->vertexBuffer = Silkworm_malloc(sizeof(Silkworm_Vertex) * context->vertexCapacity);
|
context->vertexBuffer = Silkworm_malloc(sizeof(Silkworm_Vertex) * context->vertexCapacity);
|
||||||
|
@ -440,40 +430,39 @@ static inline Silkworm_Cloth* LookupCloth(uint64_t clothId)
|
||||||
|
|
||||||
/* we defer actual destruction to Update to avoid issues with NULL */
|
/* we defer actual destruction to Update to avoid issues with NULL */
|
||||||
|
|
||||||
void Silkworm_DestroyNode(void* nodePtr)
|
static void Silkworm_Internal_DestroyNode(void* nodePtr, uint8_t incrementDestroyCount)
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
Silkworm_Node* node = (Silkworm_Node*) nodePtr;
|
Silkworm_Node* node = (Silkworm_Node*) nodePtr;
|
||||||
|
|
||||||
if (node != NULL)
|
if (node != NULL)
|
||||||
{
|
{
|
||||||
node->markedForDestroy = true;
|
node->markedForDestroy = 1;
|
||||||
|
|
||||||
|
if (incrementDestroyCount)
|
||||||
|
{
|
||||||
|
context->destroyedNodeCount += 1;
|
||||||
|
}
|
||||||
|
|
||||||
for (i = 0; i < node->linkCount; i += 1)
|
for (i = 0; i < node->linkCount; i += 1)
|
||||||
{
|
{
|
||||||
if (node->links[i] != NULL)
|
if (node->links[i] != NULL)
|
||||||
{
|
{
|
||||||
node->links[i]->markedForDestroy = true;
|
node->links[i]->markedForDestroy = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Silkworm_DestroyNode(void* nodePtr)
|
||||||
|
{
|
||||||
|
Silkworm_Internal_DestroyNode(nodePtr, 0);
|
||||||
|
}
|
||||||
|
|
||||||
void Silkworm_DestroyLink(Silkworm_Link* link)
|
void Silkworm_DestroyLink(Silkworm_Link* link)
|
||||||
{
|
{
|
||||||
link->markedForDestroy = true;
|
link->markedForDestroy = 1;
|
||||||
|
context->destroyedLinkCount += 1;
|
||||||
if (context->linkDestructionDataCount >= context->linkDestructionDataCapacity)
|
|
||||||
{
|
|
||||||
context->linkDestructionDataCapacity *= 2;
|
|
||||||
context->linkDestructionData = Silkworm_realloc(context->linkDestructionData, sizeof(Silkworm_Vector2) * context->linkDestructionDataCapacity);
|
|
||||||
}
|
|
||||||
|
|
||||||
Silkworm_Vector2 position;
|
|
||||||
position.x = (link->a->position.x + link->b->position.x) / 2;
|
|
||||||
position.y = (link->a->position.y + link->b->position.y) / 2;
|
|
||||||
context->linkDestructionData[context->linkDestructionDataCount] = position;
|
|
||||||
context->linkDestructionDataCount += 1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Silkworm_ClothDestroy(void* clothPtr)
|
void Silkworm_ClothDestroy(void* clothPtr)
|
||||||
|
@ -518,7 +507,7 @@ void Silkworm_ClothDestroy(void* clothPtr)
|
||||||
|
|
||||||
if (node != NULL)
|
if (node != NULL)
|
||||||
{
|
{
|
||||||
Silkworm_DestroyNode(node);
|
Silkworm_Internal_DestroyNode(node, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Silkworm_free(cloth->nodes[i]);
|
Silkworm_free(cloth->nodes[i]);
|
||||||
|
@ -659,8 +648,8 @@ void Silkworm_Update(float delta, float windSpeedX, float windSpeedY)
|
||||||
Silkworm_Link *link;
|
Silkworm_Link *link;
|
||||||
Silkworm_Node *node;
|
Silkworm_Node *node;
|
||||||
|
|
||||||
context->nodeDestructionDataCount = 0;
|
context->destroyedNodeCount = 0;
|
||||||
context->linkDestructionDataCount = 0;
|
context->destroyedLinkCount = 0;
|
||||||
|
|
||||||
// apply wind
|
// apply wind
|
||||||
for (i = 0; i < context->nodeCount; i += 1)
|
for (i = 0; i < context->nodeCount; i += 1)
|
||||||
|
@ -747,7 +736,7 @@ void Silkworm_Update(float delta, float windSpeedX, float windSpeedY)
|
||||||
|
|
||||||
if (Silkworm_fabs(node->position.x) > context->xBound || Silkworm_fabs(node->position.x) > context->yBound)
|
if (Silkworm_fabs(node->position.x) > context->xBound || Silkworm_fabs(node->position.x) > context->yBound)
|
||||||
{
|
{
|
||||||
Silkworm_DestroyNode(node);
|
Silkworm_Internal_DestroyNode(node, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -792,9 +781,9 @@ void* Silkworm_CreateNode(Silkworm_NodeCreateInfo* nodeCreateInfo)
|
||||||
node->radius = (float) nodeCreateInfo->radius;
|
node->radius = (float) nodeCreateInfo->radius;
|
||||||
node->pushFactor = (float) nodeCreateInfo->pushFactor;
|
node->pushFactor = (float) nodeCreateInfo->pushFactor;
|
||||||
node->windFactor = (float) nodeCreateInfo->windFactor;
|
node->windFactor = (float) nodeCreateInfo->windFactor;
|
||||||
node->pinned = false;
|
node->pinned = 0;
|
||||||
node->destroyable = false;
|
node->destroyable = 0;
|
||||||
node->markedForDestroy = false;
|
node->markedForDestroy = 0;
|
||||||
node->links = NULL;
|
node->links = NULL;
|
||||||
node->linkCount = 0;
|
node->linkCount = 0;
|
||||||
|
|
||||||
|
@ -807,7 +796,7 @@ void Silkworm_ClothNodePin(void* clothPtr, uint32_t i, uint32_t j)
|
||||||
Silkworm_Node* node = cloth->nodes[i][j];
|
Silkworm_Node* node = cloth->nodes[i][j];
|
||||||
if (node != NULL)
|
if (node != NULL)
|
||||||
{
|
{
|
||||||
node->pinned = true;
|
node->pinned = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -817,7 +806,7 @@ void Silkworm_ClothNodeUnpin(void* clothPtr, uint32_t i, uint32_t j)
|
||||||
Silkworm_Node* node = cloth->nodes[i][j];
|
Silkworm_Node* node = cloth->nodes[i][j];
|
||||||
if (node != NULL)
|
if (node != NULL)
|
||||||
{
|
{
|
||||||
node->pinned = false;
|
node->pinned = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -827,7 +816,7 @@ void Silkworm_ClothNodeDestroy(void* clothPtr, uint32_t i, uint32_t j)
|
||||||
Silkworm_Node* node = cloth->nodes[i][j];
|
Silkworm_Node* node = cloth->nodes[i][j];
|
||||||
if (node != NULL)
|
if (node != NULL)
|
||||||
{
|
{
|
||||||
Silkworm_DestroyNode(node);
|
Silkworm_Internal_DestroyNode(node, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -860,7 +849,7 @@ void* Silkworm_CreateLink(void* nodeAPtr, void* nodeBPtr, float distance, float
|
||||||
link->b = nodeB;
|
link->b = nodeB;
|
||||||
link->distance = (float)distance;
|
link->distance = (float)distance;
|
||||||
link->tearThreshold = (float)tearThreshold;
|
link->tearThreshold = (float)tearThreshold;
|
||||||
link->markedForDestroy = false;
|
link->markedForDestroy = 0;
|
||||||
|
|
||||||
link->a->links = Silkworm_realloc(link->a->links, sizeof(Silkworm_Link*) * (link->a->linkCount + 1));
|
link->a->links = Silkworm_realloc(link->a->links, sizeof(Silkworm_Link*) * (link->a->linkCount + 1));
|
||||||
link->a->links[link->a->linkCount] = link;
|
link->a->links[link->a->linkCount] = link;
|
||||||
|
@ -925,10 +914,10 @@ void* Silkworm_ClothCreate(Silkworm_ClothCreateInfo* clothCreateInfo)
|
||||||
{
|
{
|
||||||
nodeCreateInfo.x = clothCreateInfo->x + i * context->clothDensity;
|
nodeCreateInfo.x = clothCreateInfo->x + i * context->clothDensity;
|
||||||
nodeCreateInfo.y = clothCreateInfo->y + j * context->clothDensity;
|
nodeCreateInfo.y = clothCreateInfo->y + j * context->clothDensity;
|
||||||
nodeCreateInfo.destroyable = true;
|
nodeCreateInfo.destroyable = 1;
|
||||||
nodeCreateInfo.friction = clothCreateInfo->friction;
|
nodeCreateInfo.friction = clothCreateInfo->friction;
|
||||||
nodeCreateInfo.mass = clothCreateInfo->mass;
|
nodeCreateInfo.mass = clothCreateInfo->mass;
|
||||||
nodeCreateInfo.pinned = false;
|
nodeCreateInfo.pinned = 0;
|
||||||
nodeCreateInfo.pushFactor = 1;
|
nodeCreateInfo.pushFactor = 1;
|
||||||
nodeCreateInfo.radius = 1;
|
nodeCreateInfo.radius = 1;
|
||||||
nodeCreateInfo.windFactor = clothCreateInfo->windFactor;
|
nodeCreateInfo.windFactor = clothCreateInfo->windFactor;
|
||||||
|
@ -937,7 +926,7 @@ void* Silkworm_ClothCreate(Silkworm_ClothCreateInfo* clothCreateInfo)
|
||||||
|
|
||||||
cloth->nodes[i][j] = node;
|
cloth->nodes[i][j] = node;
|
||||||
|
|
||||||
node->destroyable = true;
|
node->destroyable = 1;
|
||||||
|
|
||||||
node->clothReference.clothId = cloth->id;
|
node->clothReference.clothId = cloth->id;
|
||||||
node->clothReference.horizontalIndex = i;
|
node->clothReference.horizontalIndex = i;
|
||||||
|
@ -1202,7 +1191,7 @@ void Silkworm_PinNodesInRadius(float x, float y, float radius)
|
||||||
|
|
||||||
if (squareDistance <= radius * radius)
|
if (squareDistance <= radius * radius)
|
||||||
{
|
{
|
||||||
node->pinned = true;
|
node->pinned = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1227,7 +1216,7 @@ void Silkworm_UnpinNodesInRadius(float x, float y, float radius)
|
||||||
|
|
||||||
if (squareDistance <= radius * radius)
|
if (squareDistance <= radius * radius)
|
||||||
{
|
{
|
||||||
node->pinned = false;
|
node->pinned = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1252,17 +1241,7 @@ void Silkworm_DestroyNodesInRadius(float x, float y, float radius)
|
||||||
|
|
||||||
if (squareDistance <= radius * radius)
|
if (squareDistance <= radius * radius)
|
||||||
{
|
{
|
||||||
Silkworm_DestroyNode(node);
|
Silkworm_Internal_DestroyNode(node, 1);
|
||||||
|
|
||||||
if (context->nodeDestructionDataCount >= context->nodeDestructionDataCapacity)
|
|
||||||
{
|
|
||||||
context->nodeDestructionDataCapacity *= 2;
|
|
||||||
context->nodeDestructionData = Silkworm_realloc(context->nodeDestructionData, sizeof(Silkworm_Vector2) * context->nodeDestructionDataCapacity);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
context->nodeDestructionData[context->nodeDestructionDataCount] = node->position;
|
|
||||||
context->nodeDestructionDataCount += 1;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1288,20 +1267,20 @@ void Silkworm_DestroyNodesInRectangle(Silkworm_Rectangle* rectangle)
|
||||||
node->position.y >= rectangle->y &&
|
node->position.y >= rectangle->y &&
|
||||||
node->position.y <= rectangle->y + rectangle->h
|
node->position.y <= rectangle->y + rectangle->h
|
||||||
) {
|
) {
|
||||||
Silkworm_DestroyNode(node);
|
Silkworm_Internal_DestroyNode(node, 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (context->nodeDestructionDataCount >= context->nodeDestructionDataCapacity)
|
uint32_t Silkworm_DestroyedNodeCount()
|
||||||
{
|
{
|
||||||
context->nodeDestructionDataCapacity *= 2;
|
return context->destroyedNodeCount;
|
||||||
context->nodeDestructionData = Silkworm_realloc(context->nodeDestructionData, sizeof(Silkworm_Vector2) * context->nodeDestructionDataCapacity);
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
context->nodeDestructionData[context->nodeDestructionDataCount] = node->position;
|
uint32_t Silkworm_DestroyedLinkCount()
|
||||||
context->nodeDestructionDataCount += 1;
|
{
|
||||||
}
|
return context->destroyedLinkCount;
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void* Silkworm_FindClothInRadius(float x, float y, float radius)
|
void* Silkworm_FindClothInRadius(float x, float y, float radius)
|
||||||
|
@ -1365,9 +1344,6 @@ void Silkworm_Finish()
|
||||||
Silkworm_free(context->linkIndexStack);
|
Silkworm_free(context->linkIndexStack);
|
||||||
Silkworm_free(context->clothIndexStack);
|
Silkworm_free(context->clothIndexStack);
|
||||||
|
|
||||||
Silkworm_free(context->nodeDestructionData);
|
|
||||||
Silkworm_free(context->linkDestructionData);
|
|
||||||
|
|
||||||
Silkworm_free(context->vertexBuffer);
|
Silkworm_free(context->vertexBuffer);
|
||||||
|
|
||||||
Silkworm_free(context);
|
Silkworm_free(context);
|
||||||
|
|
|
@ -27,8 +27,6 @@
|
||||||
#ifndef SILKWORM_H
|
#ifndef SILKWORM_H
|
||||||
#define SILKWORM_H
|
#define SILKWORM_H
|
||||||
|
|
||||||
#include <math.h>
|
|
||||||
#include <stdbool.h>
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
|
@ -63,10 +61,10 @@ typedef struct Silkworm_NodeCreateInfo
|
||||||
float mass;
|
float mass;
|
||||||
float friction;
|
float friction;
|
||||||
float radius;
|
float radius;
|
||||||
bool pinned;
|
uint8_t pinned;
|
||||||
float pushFactor;
|
float pushFactor;
|
||||||
float windFactor;
|
float windFactor;
|
||||||
bool destroyable;
|
uint8_t destroyable;
|
||||||
} Silkworm_NodeCreateInfo;
|
} Silkworm_NodeCreateInfo;
|
||||||
|
|
||||||
typedef struct Silkworm_ClothCreateInfo
|
typedef struct Silkworm_ClothCreateInfo
|
||||||
|
@ -126,6 +124,9 @@ SILKWORMAPI void* Silkworm_FindClothInRadius(float x, float y, float radius);
|
||||||
SILKWORMAPI void Silkworm_DestroyNodesInRadius(float x, float y, float radius);
|
SILKWORMAPI void Silkworm_DestroyNodesInRadius(float x, float y, float radius);
|
||||||
SILKWORMAPI void Silkworm_DestroyNodesInRectangle(Silkworm_Rectangle* rectangle);
|
SILKWORMAPI void Silkworm_DestroyNodesInRectangle(Silkworm_Rectangle* rectangle);
|
||||||
|
|
||||||
|
SILKWORMAPI uint32_t Silkworm_DestroyedNodeCount();
|
||||||
|
SILKWORMAPI uint32_t Silkworm_DestroyedLinkCount();
|
||||||
|
|
||||||
SILKWORMAPI void Silkworm_PerformDestroys();
|
SILKWORMAPI void Silkworm_PerformDestroys();
|
||||||
SILKWORMAPI void Silkworm_ClearAll();
|
SILKWORMAPI void Silkworm_ClearAll();
|
||||||
SILKWORMAPI void Silkworm_Finish();
|
SILKWORMAPI void Silkworm_Finish();
|
||||||
|
|
Loading…
Reference in New Issue