/* * groupSize() * Returns the size of a given square's group * Marks all squares of the group "checked" * return int */ int groupSize(square** &map, int height, int width, int i, int j) { int counter=1, stop=0; map[i][j].state=1; //If a square standing next to current square is in a 4square group and is the same type, current square is in a 4sq groupe if (i+1<height && stop == 0) { if(map[i+1][j].type==map[i][j].type && map[i+1][j].state==2) { counter=8; stop=1; } } if (j+1<width && stop == 0) { if(map[i][j+1].type==map[i][j].type && map[i][j+1].state==2) { counter=8; stop=1; } } if (i>0 && stop == 0) { if(map[i-1][j].type==map[i][j].type && map[i-1][j].state==2) { counter=8; stop=1; } } if (j>0 && stop == 0) { if(map[i][j-1].type==map[i][j].type && map[i][j-1].state==2) { counter=8; stop=1; } } if (i+1<height && stop == 0) { if(map[i+1][j].type==map[i][j].type && map[i+1][j].state!=1) counter += groupSize(map, height, width, i+1, j); } if (j+1<width && stop == 0) { if(map[i][j+1].type==map[i][j].type && map[i][j+1].state!=1) counter += groupSize(map, height, width, i, j+1); } if (i>0 && stop == 0) { if(map[i-1][j].type==map[i][j].type && map[i-1][j].state!=1) counter += groupSize(map, height, width, i-1, j); } if (j>0 && stop == 0) { if(map[i][j-1].type==map[i][j].type && map[i][j-1].state!=1) counter += groupSize(map, height, width, i, j-1); } return counter; }
float GroupMgr::groupBonus() { switch (groupSize()) { case 2: return 1.02; case 3: return 1.06; case 4: return 1.10; case 5: return 1.14; case 6: return 1.20; default: return 1.00; } }
void generateMap(square** &map, int height, int width) { do { for(int i = 0; i<height; i++) { for(int j = 0; j<width; j++) { map[i][j].type = rand() %3; map[i][j].state = 0; } } while(!(mapFull(map, height, width))) { for(int i = 0; i<height; i++) { for(int j = 0; j<width; j++) { if(map[i][j].state!=2) { //Can the given square be included in a 4 (or more) square group ? if(groupSize(map, height, width, i, j)>=8) { //Yes. Then all the squares in the same groupe are to be frozen map[i][j].state=2; for(int k = 0; k<height; k++) { for(int l = 0; l<width; l++) { if(map[k][l].state==1)map[k][l].state=2; } } } else { //No. Then all the squares in the same groupe will be randomized and analysed again map[i][j].type = rand()%3; for(int k = 0; k<height; k++) { for(int l = 0; l<width; l++) { if(map[k][l].state==1) { map[k][l].type= rand()%3; map[k][l].state = 0; } } } } } } } } } while(!(threeTypesPresent(map, height, width))); }
// unfortunately we get back all groups double wrapped, seems // apple was preparing for something that never came, if that // day does come this might need to go void flatPackArray(lua_State* L, plist_t node, int depth) { int i; if (nodeType(node) == PLIST_ARRAY) { for (i=0;i<groupSize(node);i++) { flatPackArray(L, arrayElem(node, i), depth); } } else { parseNode(L, node, depth); } }
void convertToSphericalMaps( const GLCubeMapContainer<ChannelCount, HasDepthBuffer>& container, const GLTexture2DArray* sphereMapArrays) { m_ConvertPass.m_Program.use(); Vec3u groupSize(16, 16, 4); for(auto i = 0u; i < ChannelCount; ++i) { sphereMapArrays[i].bindImage(0u, 0, GL_WRITE_ONLY, GL_RGBA32F); m_ConvertPass.uSphereMap.set(0u); m_ConvertPass.uCubeMapContainer.set(i, 0u, container); glDispatchCompute(1 + sphereMapArrays[i].getWidth() / groupSize.x, 1 + sphereMapArrays[i].getHeight() / groupSize.y, 1 + container.size() / groupSize.z); } glMemoryBarrier(GL_ALL_BARRIER_BITS); }
void convertToDualParaboloidMaps( const GLCubeMapContainer<ChannelCount, HasDepthBuffer>& container, const GLBufferStorage<Vec4f>* dualParaboloidMapBuffers, uint32_t paraboloidMapWidth, uint32_t paraboloidMapHeight) { m_DualParaboloidConversionPass.m_Program.use(); Vec3u groupSize(16, 16, 4); for(auto i = 0u; i < ChannelCount; ++i) { dualParaboloidMapBuffers[i].bindBase(GL_SHADER_STORAGE_BUFFER, 0); m_DualParaboloidConversionPass.uCubeMapContainer.set(i, 0u, container); m_DualParaboloidConversionPass.uParaboloidMapWidth.set(paraboloidMapWidth); m_DualParaboloidConversionPass.uParaboloidMapHeight.set(paraboloidMapHeight); m_DualParaboloidConversionPass.uDualParaboloidMapCount.set(container.size()); glDispatchCompute(1 + 2 * paraboloidMapWidth / groupSize.x, 1 + paraboloidMapHeight / groupSize.y, 1 + container.size() / groupSize.z); } glMemoryBarrier(GL_ALL_BARRIER_BITS); }
void convertToSphericalMaps( const GLCubeMapContainer<ChannelCount, HasDepthBuffer>& container, const GLBufferStorage<Vec4f>* sphereMapBuffers, uint32_t sphereMapWidth, uint32_t sphereMapHeight) { m_ConvertPass2.m_Program.use(); Vec3u groupSize(16, 16, 4); for(auto i = 0u; i < ChannelCount; ++i) { sphereMapBuffers[i].bindBase(GL_SHADER_STORAGE_BUFFER, 0); m_ConvertPass2.uCubeMapContainer.set(i, 0u, container); m_ConvertPass2.uSphereMapWidth.set(sphereMapWidth); m_ConvertPass2.uSphereMapHeight.set(sphereMapHeight); m_ConvertPass2.uSphereMapCount.set(container.size()); glDispatchCompute(1 + sphereMapWidth / groupSize.x, 1 + sphereMapHeight / groupSize.y, 1 + container.size() / groupSize.z); } glMemoryBarrier(GL_ALL_BARRIER_BITS); }
bool CDistanceRoutine::_getGroupShapeDistanceIfSmaller(int groupID,int shapeID, float& dist,float ray[7],int buffer[3],bool overrideMeasurableFlagShape,bool pathPlanningRoutineCalling) { // Distance is measured from group to shape // If the distance is smaller than 'dist', 'dist' is replaced and the return value is true // If the distance is bigger, 'dist' doesn't change and the return value is false // ray contains the point on object1 (0-2), the point on object2 (3-5) and the distance (6) // groupID can be -1 in which case all objects are tested against the shape! // buffer[0]=-1; // Artificially disabling caching for tests int propMask=sim_objectspecialproperty_measurable; // We get the single shape and all shapes/dummies in the group: CShape* shape=App::ct->objCont->getShape(shapeID); if (shape==NULL) return(false); if ( ((shape->getMainProperty()&sim_objectspecialproperty_measurable)==0)&&(!overrideMeasurableFlagShape) ) return(false); if (pathPlanningRoutineCalling&&(shape->getMainProperty()&sim_objectspecialproperty_pathplanning_ignored)&&(!overrideMeasurableFlagShape)) return(false); std::vector<C3DObject*> group; if (groupID==-1) { // Special case: std::vector<C3DObject*> exceptionObject; exceptionObject.push_back(shape); App::ct->objCont->getAllShapesAndDummiesFromSceneExcept(exceptionObject,group,propMask,pathPlanningRoutineCalling); } else { // regular case: if (!App::ct->collections->getShapesAndDummiesFromGroup(groupID,&group,propMask,pathPlanningRoutineCalling)) return(false); } // Build the collision nodes only when needed. So do it right here! for (int i=0; i<int(group.size()); i++) { if (group[i]->getObjectType()==sim_object_shape_type) ((CShape*)group[i])->initializeCalculationStructureIfNeeded(); } shape->initializeCalculationStructureIfNeeded(); bool returnValue=false; // This part is for handling the cached distance: C3DObject* buffTree=App::ct->objCont->getObject(buffer[0]); if (buffTree!=NULL) { //We check if buffTree is in the group: for (int i=0; i<int(group.size()); i++) { if (group[i]==buffTree) { group.erase(group.begin()+i); // We remove that element because we measure it here if (buffTree->getObjectType()==sim_object_shape_type) { // We have a shape if (buffTree!=shape) { // We never measure a shape against itself! (shouldn't anyway happen here) returnValue=_getBufferedDistance_IfSmaller((CShape*)buffTree,shape,buffer+1,dist,ray); // Now we check these two shapes: if (((CShape*)buffTree)->getShapeShapeDistance_IfSmaller(shape,dist,ray,buffer+1)) returnValue=true; } else buffer[0]=-1; } if (buffTree->getObjectType()==sim_object_dummy_type) { // Here we have a dummy int auxBuff=buffer[2]; returnValue=_getBufferedDistance_IfSmaller(shape,(CDummy*)buffTree,auxBuff,dist,ray); if (shape->getDistanceToDummy_IfSmaller((CDummy*)buffTree,dist,ray,auxBuff)) returnValue=true; if (returnValue) { buffer[2]=auxBuff; _invertRay(ray); } } break; } } } // Here we process all dummy-shape distances (ordered) std::vector<C3DObject*> exploringOrder; std::vector<float> approxDistances; exploringOrder.reserve(group.size()); exploringOrder.clear(); approxDistances.reserve(group.size()); approxDistances.clear(); C4X4Matrix shapeCM(shape->getCumulativeTransformation().getMatrix()); C3Vector shapeSize(shape->geomData->getBoundingBoxHalfSizes()); int i=0; while (i<int(group.size())) { if (group[i]->getObjectType()==sim_object_dummy_type) { float testDist; C3Vector dummyPos(group[i]->getCumulativeTransformation().X); testDist=CCollDistInterface::getBoxPointDistance(shapeCM,shapeSize,dummyPos); // We have the EXACT (not approx anymore!) distance and put it in the ordered list: int k; for (k=0; k<int(approxDistances.size()); k++) { if (testDist<approxDistances[k]) break; } approxDistances.insert(approxDistances.begin()+k,testDist); exploringOrder.insert(exploringOrder.begin()+k,group[i]); group.erase(group.begin()+i); } else i++; } // Now find the smallest distance (dummy-shape): for (int i=0; i<int(approxDistances.size()); i++) { if (approxDistances[i]>dist) break; int auxBuffer; if (shape->getDistanceToDummy_IfSmaller((CDummy*)exploringOrder[i],dist,ray,auxBuffer)) { buffer[0]=exploringOrder[i]->getID(); buffer[2]=auxBuffer; _invertRay(ray); returnValue=true; } } // group doesn't contain any dummies anymore // group contains only shapes! // Now go through all shapes and in the group and order them according to // their approximate distance to shape (from smallest to biggest): exploringOrder.clear(); approxDistances.clear(); for (int i=0; i<int(group.size()); i++) { if (group[i]->getObjectType()==sim_object_shape_type) { // Just in case... (should anyway contain only shapes!) C4X4Matrix groupCM(group[i]->getCumulativeTransformation().getMatrix()); C3Vector groupSize(((CShape*)group[i])->geomData->getBoundingBoxHalfSizes()); float testDist=CCollDistInterface::getApproximateBoxBoxDistance(groupCM,groupSize,shapeCM,shapeSize); // We have the approx distance and put it in the ordered list: int k; for (k=0; k<int(approxDistances.size()); k++) { if (testDist<approxDistances[k]) break; } approxDistances.insert(approxDistances.begin()+k,testDist); exploringOrder.insert(exploringOrder.begin()+k,group[i]); } } // Now find the smallest distance (shape-shape): for (int i=0; i<int(approxDistances.size()); i++) { if (approxDistances[i]>dist) break; if (exploringOrder[i]!=shape) { // We never measure a shape against itself!! if (((CShape*)exploringOrder[i])->getShapeShapeDistance_IfSmaller(shape,dist,ray,buffer+1)) { buffer[0]=exploringOrder[i]->getID(); returnValue=true; } } } return(returnValue); }
/** * @~English * @brief Write image(s) in a KTX-formatted stdio FILE stream. * * @param [in] dst pointer to the FILE stream to write to. * @param [in] textureInfo pointer to a KTX_image_info structure providing * information about the images to be included in * the KTX file. * @param [in] bytesOfKeyValueData * specifies the number of bytes of key-value data. * @param [in] keyValueData a pointer to the keyValue data. * @param [in] numImages number of images in the following array * @param [in] images array of KTX_image_info providing image size and * data. * * @return KTX_SUCCESS on success, other KTX_* enum values on error. * * @exception KTX_INVALID_VALUE @p dst or @p target are @c NULL * @exception KTX_INVALID_VALUE @c glTypeSize in @p textureInfo is not 1, 2, or 4 or * is different from the size of the type specified * in @c glType. * @exception KTX_INVALID_VALUE @c pixelWidth in @p textureInfo is 0 or pixelDepth != 0 * && pixelHeight == 0. * @exception KTX_INVALID_VALUE @c numberOfFaces != 1 || numberOfFaces != 6 or * numberOfArrayElements or numberOfMipmapLevels are < 0. * @exception KTX_INVALID_OPERATION * numberOfFaces == 6 and images are either not 2D or * are not square. * @exception KTX_INVALID_OPERATION * number of images is insufficient for the specified * number of mipmap levels and faces. * @exception KTX_INVALID_OPERATION * the size of a provided image is different than that * required for the specified width, height or depth * or for the mipmap level being processed. * @exception KTX_FILE_WRITE_ERROR a system error occurred while writing the file. */ KTX_error_code ktxWriteKTXF(FILE* dst, const KTX_texture_info* textureInfo, GLsizei bytesOfKeyValueData, const void* keyValueData, GLuint numImages, KTX_image_info images[]) { KTX_header header = KTX_IDENTIFIER_REF; GLuint i, level, dimension, cubemap = 0; GLuint numMipmapLevels, numArrayElements; GLbyte pad[4] = { 0, 0, 0, 0 }; KTX_error_code errorCode = KTX_SUCCESS; GLboolean compressed = GL_FALSE; if (!dst) { return KTX_INVALID_VALUE; } //endianess int.. if this comes out reversed, all of the other ints will too. header.endianness = KTX_ENDIAN_REF; header.glType = textureInfo->glType; header.glTypeSize = textureInfo->glTypeSize; header.glFormat = textureInfo->glFormat; header.glInternalFormat = textureInfo->glInternalFormat; header.glBaseInternalFormat = textureInfo->glBaseInternalFormat; header.pixelWidth = textureInfo->pixelWidth; header.pixelHeight = textureInfo->pixelHeight; header.pixelDepth = textureInfo->pixelDepth; header.numberOfArrayElements = textureInfo->numberOfArrayElements; header.numberOfFaces = textureInfo->numberOfFaces; header.numberOfMipmapLevels = textureInfo->numberOfMipmapLevels; header.bytesOfKeyValueData = bytesOfKeyValueData; /* Do some sanity checking */ if (header.glTypeSize != 1 && header.glTypeSize != 2 && header.glTypeSize != 4) { /* Only 8, 16, and 32-bit types supported so far */ return KTX_INVALID_VALUE; } if (header.glTypeSize != sizeofGLtype(header.glType)) return KTX_INVALID_VALUE; if (header.glType == 0 || header.glFormat == 0) { if (header.glType + header.glFormat != 0) { /* either both or none of glType & glFormat must be zero */ return KTX_INVALID_VALUE; } else compressed = GL_TRUE; } /* Check texture dimensions. KTX files can store 8 types of textures: * 1D, 2D, 3D, cube, and array variants of these. There is currently * no GL extension that would accept 3D array or cube array textures * but we'll let such files be created. */ if ((header.pixelWidth == 0) || (header.pixelDepth > 0 && header.pixelHeight == 0)) { /* texture must have width */ /* texture must have height if it has depth */ return KTX_INVALID_VALUE; } if (header.pixelHeight > 0 && header.pixelDepth > 0) dimension = 3; else if (header.pixelHeight > 0) dimension = 2; else dimension = 1; if (header.numberOfFaces == 6) { if (dimension != 2) { /* cube map needs 2D faces */ return KTX_INVALID_OPERATION; } if (header.pixelWidth != header.pixelHeight) { /* cube maps require square images */ return KTX_INVALID_OPERATION; } } else if (header.numberOfFaces != 1) { /* numberOfFaces must be either 1 or 6 */ return KTX_INVALID_VALUE; } if (header.numberOfArrayElements < 0 || header.numberOfMipmapLevels < 0) return KTX_INVALID_VALUE; if (header.numberOfArrayElements == 0) { numArrayElements = 1; if (header.numberOfFaces == 6) cubemap = 1; } else numArrayElements = header.numberOfArrayElements; /* Check number of mipmap levels */ if (header.numberOfMipmapLevels == 0) { numMipmapLevels = 1; } else numMipmapLevels = header.numberOfMipmapLevels; if (numMipmapLevels > 1) { GLuint max_dim = MAX(MAX(header.pixelWidth, header.pixelHeight), header.pixelDepth); if (max_dim < ((GLuint)1 << (header.numberOfMipmapLevels - 1))) { /* Can't have more mip levels than 1 + log2(max(width, height, depth)) */ return KTX_INVALID_VALUE; } } if (numImages < numMipmapLevels * header.numberOfFaces) { /* Not enough images */ return KTX_INVALID_OPERATION; } //write header fwrite(&header, sizeof(KTX_header), 1, dst); //write keyValueData if (bytesOfKeyValueData != 0) { if (keyValueData == NULL) return KTX_INVALID_OPERATION; if (fwrite(keyValueData, 1, bytesOfKeyValueData, dst) != bytesOfKeyValueData) return KTX_FILE_WRITE_ERROR; } /* Write the image data */ for (level = 0, i = 0; level < numMipmapLevels; ++level) { GLuint pixelWidth, pixelHeight, pixelDepth; GLuint face, faceLodSize, faceLodRounding; pixelWidth = MAX(1, header.pixelWidth >> level); pixelHeight = MAX(1, header.pixelHeight >> level); pixelDepth = MAX(1, header.pixelDepth >> level); faceLodSize = images[i].size; faceLodRounding = 3 - ((faceLodSize + 3) % 4); if (fwrite(&faceLodSize, sizeof(faceLodSize), 1, dst) != 1) { errorCode = KTX_FILE_WRITE_ERROR; goto cleanup; } for (face = 0; face < header.numberOfFaces; ++face, ++i) { /* Calculate LOD & face sizes based on glType, glFormat, width & height * and compare with size of supplied file. Can do only for uncompressed * textures. */ if (!compressed) { /* Sanity check. */ GLsizei size = groupSize(header.glFormat, header.glType) * pixelWidth * pixelHeight * pixelDepth * numArrayElements; if (images[i].size != size) { errorCode = KTX_INVALID_OPERATION; goto cleanup; } } if (fwrite(images[i].data, faceLodSize, 1, dst) != 1) { errorCode = KTX_FILE_WRITE_ERROR; goto cleanup; } if (faceLodRounding) { if (fwrite(pad, sizeof(GLbyte), faceLodRounding, dst) != 1) errorCode = KTX_FILE_WRITE_ERROR; } } } cleanup: return errorCode; }
void parseNode(lua_State* L, plist_t node, int depth) { char* name, *id, *bundleId; plist_t kids; int numChildren; int i; if (node == NULL) { return; } switch (nodeType(node)) { case PLIST_DICT: lua_newtable(L); addToTable(L, kIconUserDataType); id = getStringVal(node, kAppleDisplayIDKey); name = getStringVal(node, kAppleDisplayNameKey); bundleId = getStringVal(node, kAppleBundleIdKey); kids = dictEntry(node, kAppleIconListKey); if (name == NULL && id == NULL) { lua_pushstring(L, "unexpected value reading icons!"); lua_error(L); } if (name != NULL) { SET_STRING(L, kIconName,name); } if (id != NULL) { SET_STRING(L, kIconId,id); } if (bundleId != NULL) { SET_STRING(L, kAppleBundleIdKey,id); } storeIconInRegistry(L, node, name, id); if (groupSize(kids) > 0) { lua_newtable(L); flatPackArray(L, kids, depth+1); lua_setfield(L, -2, kIconsKey); } break; case PLIST_ARRAY: lua_newtable(L); addToTable(L, depth == 0 ? kIconCollectionTypeKey : kPageTypeKey); numChildren = groupSize(node); for (i=0;i<numChildren;i++) { parseNode(L, arrayElem(node, i), depth+1); } default: break; case PLIST_BOOLEAN:break; case PLIST_UINT:break; case PLIST_REAL:break; case PLIST_STRING:break; case PLIST_DATE:break; case PLIST_DATA:break; case PLIST_KEY:break; case PLIST_UID:break; case PLIST_NONE:break; } // append to the end of our parent container lua_rawseti(L, -2, lua_rawlen(L, -2) + 1); }