int ChtblLookup(const CHTbl *htbl, void **data) { ListElmt *element = NULL; int nBucket = 0; nBucket = htbl->hash(*data) % htbl->nBuckets; for (element = ListHead(&htbl->table[nBucket]); element != NULL; element = ListNext(element)) { if (htbl->match(*data, ListData(element))) { *data = ListData(element); return 0; } } return -1; }
// build AE lists void v4pBuildOpenableAELists(PolygonP polygonChain) { PolygonP p ; List l ; ActiveEdgeP b; for (p = polygonChain ; p ; p = p->next) { int isRelative = p->props & relative; v4pPolygonBuildActiveEdgeList(p) ; l = p->ActiveEdge1; while (l) { b = (ActiveEdgeP)ListData(l) ; if (isRelative) { QuickTableAdd(v4p->openableAETable, (b->y0 > 0 ? b->y0 : 0) & YHASH_MASK, l); } else { v4pAbsoluteToView(b->x0, b->y0, &(b->x0v), &(b->y0v)); v4pAbsoluteToView(b->x1, b->y1, &(b->x1v), &(b->y1v)); if (b->y0 < v4p->yvu0) { QuickTableAdd(v4p->openableAETable, 0, l); } else { QuickTableAdd(v4p->openableAETable, b->y0v & YHASH_MASK, l); } } l = ListNext(l); } if (p->sub1) v4pBuildOpenableAELists(p->sub1) ; } }
int ChtblRemove(CHTbl *htbl, void **data) { ListElmt *element = NULL; ListElmt *prev = NULL; int nBucket = 0; nBucket = htbl->hash(*data) % htbl->nBuckets; prev = NULL; for (element = ListHead(&htbl->table[nBucket]); element != NULL; element = ListNext(element)) { if (htbl->match(*data, ListData(element))) { if (ListRemove_Next(&htbl->table[nBucket], prev, data) == 0) { htbl->nSize--; return 0; } else { return -1; } } prev = element; } return -1; }
// delete all ActiveEdges of a poly PolygonP v4pPolygonDelActiveEdges(PolygonP p) { List l ; ActiveEdgeP b; l = p->ActiveEdge1 ; while (l) { b = (ActiveEdgeP)ListData(l) ; QuickHeapFree(v4p->activeEdgeHeap, b); l = ListFree(l) ; } p->ActiveEdge1 = NULL; return p; }
int BFS(Graph *graph, BFSVertex *start, List *hops) { Queue queue; AdjList *adjlist = NULL; AdjList *adjlist_Clear = NULL; BFSVertex *vertex_Clear = NULL; BFSVertex *vertex_Adj = NULL; ListElmt *element = NULL; ListElmt *member = NULL; for (element = ListHead(&GraphAdjLists(graph)); element != NULL; element = ListNext(element)) { vertex_Clear = ((AdjList*)ListData(element))->vertex; if (graph->match(vertex_Clear, start)) { vertex_Clear->color = gray; vertex_Clear->nHops = 0; } else { vertex_Clear->color = white; vertex_Clear->nHops = -1; } } QueueInit(&queue, NULL); if (GraphAdjList(graph, start, &adjlist_Clear) != 0) { QueueDestroy(&queue); return -1; } if (QueueEnqueue(&queue, adjlist_Clear) != 0) { QueueDestroy(&queue); return -1; } while (QueueSize(&queue) > 0) { adjlist = QueuePeek(&queue); for (member = ListHead(&adjlist->Adjacent); member != NULL; member = ListNext(member)) { vertex_Adj = ListData(member); if (GraphAdjList(graph, vertex_Adj, &adjlist_Clear)) { QueueDestroy(&queue); return -1; } vertex_Clear = adjlist_Clear->vertex; if (vertex_Clear->color == white) { vertex_Clear->color = gray; vertex_Clear->nHops = ((BFSVertex*)adjlist->vertex)->nHops + 1; if (QueueEnqueue(&queue, adjlist_Clear) != 0) { QueueDestroy(&queue); return -1; } } } if (QueueDequeue(&queue, (void**)&adjlist) == 0) { ((BFSVertex*)adjlist->vertex)->color = black; } else { QueueDestroy(&queue); return -1; } } QueueDestroy(&queue); ListInit(hops, NULL); for (element = ListHead(&GraphAdjLists(graph)); element != NULL; element = ListNext(element)) { vertex_Clear = ((AdjList*)ListData(element))->vertex; if (vertex_Clear->nHops != -1) { if (ListInsert_Next(hops, ListTail(hops), vertex_Clear) != 0) { ListDestory(hops); return -1; } } } return 0; }
// Render a scene Boolean v4pRender() { List l, pl ; PolygonP p, polyVisible ; ActiveEdgeP b ; Coord y, px, px_collide ; Coord yu; int su, ou1, ou2, ru1, ru2; ILayer z ; PolygonP layers[16] ; int zMax ; UInt16 bz, bi ; // bit-word of layers & collides UInt16 mi ; // masques ICollide i, colli1, colli2 ; int nColli ; PolygonP pColli[16] ; Boolean sortNeeded ; v4pDisplaySetContext(v4p->display); v4pDisplayStart() ; // update AE lists and build an y-index hash table QuickTableReset(v4p->openableAETable); v4pBuildOpenableAELists(v4p->scene->polygons); // list of opened ActiveEdges v4p->openedAEList = NULL ; // yu (scanline y in absolute coordinates) progression during scanline loop ou1 = v4p->divyvub ; ou2 = v4p->divyvub + 1 ; yu = v4p->yvu0 - ou2; ru1 = v4p->modyvub ; ru2 = v4p->modyvub - v4pDisplayHeight ; su = v4p->modyvub; // scan-line loop for (y = 0 ; y < v4pDisplayHeight ; y++) { sortNeeded = false ; if (su >= 0) { su+= ru2 ; yu+= ou2 ; } else { su+= ru1 ; yu+= ou1 ; } // loop among opened ActiveEdge l = v4p->openedAEList ; pl = NULL ; px = -(0x7FFF) ; // not sure its really the min, but we dont care while (l) { b = (ActiveEdgeP)ListData(l); if (b->h <= 0) { // close ActiveEdge if (pl) ListSetNext(pl, l = ListFree(l)) ; else v4p->openedAEList = l = ListFree(l) ; } else { // shift ActiveEdge int x ; b->h--; if (b->o2) { if (b->s > 0) { x = b->x+= b->o2 ; b->s+= b->r2 ; } else { x = b->x+= b->o1 ; b->s+= b->r1 ; } } else x = b->x ; if (x < px) sortNeeded = true ; px = x ; pl = l ; l = ListNext(l) ; } } // opened ActiveEdge loop // sort ActiveEdge if (sortNeeded) v4p->openedAEList = v4pSortActiveEdge(v4p->openedAEList) ; // open newly intersected ActiveEdge List newlyOpenedAEList = v4pOpenActiveEdge(y, yu) ; if (newlyOpenedAEList) { ListSetDataPrior(compareActiveEdgeX) ; v4p->openedAEList = ( v4p->openedAEList ? ListMerge(v4p->openedAEList, newlyOpenedAEList) : newlyOpenedAEList ) ; } // reset layers bz = 0 ; polyVisible = &(v4p->dummyBgPoly) ; zMax = -1 ; // reset collides bi = 0 ; nColli = 0 ; // loop among scanline slices px = px_collide = 0 ; for (l = v4p->openedAEList ; l ; l = ListNext(l)) { // loop ActiveEdge ouvert / x // pb = b ; b = (ActiveEdgeP)ListData(l) ; p = b->p ; z = p->z & 15 ; bz ^= ((UInt16)1 << z) ; //if (b->x > 1000) v4pDisplayDebug("problem %d %d %d", (int)b->x, (int)px, (pb ? pb->x : -1)); //if (px > b->x) v4pDisplayError("pb slice %d %d %d", (int)y, (int)px, (int)b->x); if ((int)z >= zMax) { if (px < v4pDisplayWidth && b->x > 0) v4pDisplaySlice(y, imax(px, 0), imin(b->x, v4pDisplayWidth), polyVisible->color); px = b->x ; if ((int)z > zMax) { polyVisible = layers[z] = p ; zMax = z ; } else { // z == zMax zMax = floorLog2(bz); polyVisible = (zMax >= 0 ? layers[zMax] : &(v4p->dummyBgPoly)) ; } } else { // z < zMax layers[z] = p ; } if (nColli > 1) v4pDisplayCollide(colli1, colli2, y, px_collide, b->x, pColli[colli1], pColli[colli2]); px_collide = b->x; i = p->i ; mi = (i == (ICollide)-1 ? (UInt16)0 : (UInt16)1 << (i & 15)) ; if (layers[z]) { if (mi) { pColli[i] = p ; if (!(bi & mi)) { bi |= mi ; nColli++ ; if (nColli == 1) colli1 = i ; else if (nColli == 2) colli2 = i ; } } } else { if (bi & mi) { bi ^= mi ; nColli-- ; if (nColli == 1 && i == colli1) colli1 = colli2 ; else if (nColli == 2) { if (i == colli1) { colli1 = floorLog2(bi ^ (1 << colli2)); } else if (i == colli2) { colli2 = floorLog2(bi ^ (1 << colli1)); } } } } } // x opened ActiveEdge loop // last slice if (px < v4pDisplayWidth) v4pDisplaySlice(y, imax(0, px), v4pDisplayWidth, polyVisible->color) ; } // y loop ; l = v4p->openedAEList ; while (l) l = ListFree(l) ; v4p->openedAEList = NULL ; if (yu != v4p->yvu1 - v4p->divyvub) v4pDisplayError("problem %d != %d", (int)yu, (int)v4p->yvu1 - v4p->divyvub); v4p->changes = 0 ; v4pDisplayEnd() ; return success ; }
// open all new scan-line intersected ActiveEdge, returns them as a list List v4pOpenActiveEdge(Coord yl, Coord yu) { List newlyOpenedAEList = NULL ; List l; ActiveEdgeP b ; Coord xr0, yr0, xr1, yr1, dx, dy, q, r ; l = QuickTableGet(v4p->openableAETable, yl & YHASH_MASK); for (; l; l = l->quick) { b = (ActiveEdgeP)ListData(l) ; if (!(b->p->props & relative)) { xr0 = b->x0v; yr0 = b->y0v; //if (!yl && b->y0 < v4p->yvu0) { // v4pAbsoluteToView(b->x0, b->y0, &xr0, &yr0) ; //} else { // v4pAbsoluteToView(b->x0, b->y0, &xr0, &yr0) ; // if (yr0 != yl) continue; //} if (yl == 0) { if (yr0 > 0) continue; } else if (yr0 != yl) continue; //v4pAbsoluteToView(b->x1, b->y1, &xr1, &yr1) ; xr1 = b->x1v; yr1 = b->y1v; if (yr1 <= yl) continue ; dx = xr1 - xr0; dy = yr1 - yr0; q = dx / dy ; r = dx > 0 ? dx % dy : (-dx) % dy ; b->o1 = q ; b->o2 = b->o1 + (dx > 0 ? 1 : -1) ; b->r1 = r ; b->r2 = r - dy ; b->s = -dy; if (yr0 < yl) { // top crop needed int dy2 = yl - yr0 ; if (yr0 > 0 && dy2 > v4p->divyvu) v4pDisplayError("issue crop = %d > ratio = %d; yl=%d yu=%d y0=%d", (int)dy2, (int)v4p->divyvub, (int)yl, (int)yu, (int)b->y0); xr0 += dy2 * q + dy2 * (dx > 0 ? r : -r) / dy ; b->s += (dy2 * r) % dy ; } b->h = yr1 - yl - 1; b->x = xr0 ; } else { // relative if (yl == 0) { if (b->y0 > 0) continue; } else if (b->y0 != yl) continue; if (b->y1 <= yl) continue ; b->s = b->r2 - b->r1 ; b->x = b->x0 ; b->h = b->y1 - yl - 1; if (b->y0 < yl) { // top crop needed int dy2 = yl - b->y0 ; dy = b->y1 - b->y0; b->x += dy2 * b->o1 + dy2 * (b->o2 >= 0 ? b->r1 : -b->r1) / dy ; b->s += (dy2 * b->r1) % dy ; } } ListAddData(newlyOpenedAEList, b) ; } if (newlyOpenedAEList) newlyOpenedAEList = v4pSortActiveEdge(newlyOpenedAEList); return newlyOpenedAEList ; }
std::string IDSEXT::InvokeMethod(const std::string& command) { int index = command.find_first_of(" "); string strCommand = command.substr(0, index); string strParam = command.substr(index + 1, command.length()); Json::Reader reader; Json::Value obj; if (strCommand == "getVersion") { return GetVersion(); } else if (strCommand == "registerProvider") { return RegisterProvider(strParam); } else if (strCommand == "setOption") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s\n", "error parsing\n"); return "unable to parse options"; } int option = obj["option"].asInt(); const std::string value = obj["value"].asString(); return( SetOption(option, value) ); } else if (strCommand == "getToken") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); std::string tokenType = obj["tokenType"].asString(); const std::string appliesTo = obj["appliesTo"].asString(); GetToken(provider, tokenType, appliesTo); } else if (strCommand == "clearToken") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); std::string tokenType = obj["tokenType"].asString(); const std::string appliesTo = obj["appliesTo"].asString(); ClearToken(provider, tokenType, appliesTo); } else if (strCommand == "getProperties") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); int propertyType = obj["propertyType"].asInt(); int numProps = obj["numProps"].asInt(); const std::string userProps = obj["userProperties"].asString(); GetProperties(provider, propertyType, numProps, userProps); } else if (strCommand == "getData") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); int dataType = obj["dataType"].asInt(); int dataFlags = obj["dataFlags"].asInt(); const std::string dataName = obj["dataName"].asString(); GetData(provider, dataType, dataFlags, dataName); } else if (strCommand == "createData") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); int dataType = obj["dataType"].asInt(); int dataFlags = obj["dataFlags"].asInt(); const std::string dataName = obj["dataName"].asString(); const std::string dataValue = obj["dataValue"].asString(); CreateData(provider, dataType, dataFlags, dataName, dataValue); } else if (strCommand == "deleteData") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); int dataType = obj["dataType"].asInt(); int dataFlags = obj["dataFlags"].asInt(); const std::string dataName = obj["dataName"].asString(); DeleteData(provider, dataType, dataFlags, dataName); } else if (strCommand == "setData") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); int dataType = obj["dataType"].asInt(); int dataFlags = obj["dataFlags"].asInt(); const std::string dataName = obj["dataName"].asString(); const std::string dataValue = obj["dataValue"].asString(); SetData(provider, dataType, dataFlags, dataName, dataValue); } else if (strCommand == "listData") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); int dataType = obj["dataType"].asInt(); int dataFlags = obj["dataFlags"].asInt(); ListData(provider, dataType, dataFlags); } else if (strCommand == "challenge") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); int challengeType = obj["challengeType"].asInt(); int challengeFlags = obj["challengeFlags"].asInt(); Challenge(provider, challengeType, challengeFlags); } else if (strCommand == "registerNotifier") { // parse the JSON bool parse = reader.parse(strParam, obj); if (!parse) { //fprintf(stderr, "%s", "error parsing\n"); return "unable to parse options"; } event_id = obj["_eventId"].asString(); std::string provider = obj["provider"].asString(); int notifierType = obj["notifierType"].asInt(); int notifierFlags = obj["notifierFlags"].asInt(); std::string notifierName = obj["notifierName"].asString(); RegisterNotifier(provider, notifierType, notifierFlags, notifierName); } return ""; }