void TileStorage::CompressTile(uint64_t uid)
{
  uint8_t * m0;
  uint8_t * m1;
  uint8_t * m2;
  uint8_t * m3;
  uint8_t * dataptr = m_tiles[uid];
  uint8_t * compressedmipmaps = new uint8_t[680];
  if ( !dataptr )
  {
    delete [] compressedmipmaps;
    throw InvalidTileDataPointerException();
    
  }
  uint32_t s;
  uint32_t s2 = 0;
  ILuint mip1 = ilGenImage();
  ilBindImage(mip1);
  ilTexImage(32,32,1,4,IL_RGBA,IL_UNSIGNED_BYTE,dataptr);
  /*std::stringstream ss;
  ss << "Tile" << uid << ".png";
  ilSaveImage(ss.str().c_str());*/
  m0 = ilCompressDXT(ilGetData(),32,32,1,IL_DXT1,&s);
  memcpy(&compressedmipmaps[s2],m0,s);
  s2 += s;
  iluScale(16,16,1);
  m1 = ilCompressDXT(ilGetData(),16,16,1,IL_DXT1,&s);
  memcpy(&compressedmipmaps[s2],m1,s);
  s2 += s;
  iluScale(8,8,1);
  m2 = ilCompressDXT(ilGetData(),8,8,1,IL_DXT1,&s);
  memcpy(&compressedmipmaps[s2],m2,s);
  s2 += s;
  iluScale(4,4,1);
  m3 = ilCompressDXT(ilGetData(),4,4,1,IL_DXT1,&s);
  memcpy(&compressedmipmaps[s2],m3,s);
  s2 += s;
  ilDeleteImage(mip1);
  
  /*squish::CompressImage(dataptr,32,32,m0,squish::kDxt1);
  squish::CompressImage(dataptr,16,16,m1,squish::kDxt1);
  squish::CompressImage(dataptr,8,8,m2,squish::kDxt1);
  squish::CompressImage(dataptr,4,4,m3,squish::kDxt1);*/
  
  
  
  
  free(m0);
  free(m1);
  free(m2);
  free(m3);
  
  m_tiles_compressed[uid] = compressedmipmaps;
  //std::cout << "Tile " << uid << " compressed!" << std::endl;
  
}
Esempio n. 2
0
void SMFMap::Compile()
{
    SMFHeader hdr;
    strcpy(hdr.magic,"spring map file");
    hdr.version = 1;
    hdr.mapid = rand();
    hdr.mapx = (texture->w / 1024)*128;
    hdr.mapy = (texture->h / 1024)*128;
    hdr.squareSize = 8;
    hdr.texelPerSquare = 8;
    hdr.tilesize = 32;
    hdr.minHeight = m_minh;
    hdr.maxHeight = m_maxh;


    short int * hmap = new short int[(mapy+1)*(mapx+1)];bzero(hmap,((mapy+1)*(mapx+1))*2);
    if ( heightmap )
    {
        //heightmap->GetRect(0,0,heightmap->w,heightmap->h,IL_LUMINANCE,IL_SHORT,hmap); : IL seems to fail to convert from unsigned short to signed
        /*for ( int k = 0; k < (mapy+1)*(mapx+1); k++ )
	{
	  int pix = ((unsigned short*)heightmap->datapointer)[k];
	  hmap[k] = short(int(pix)-int(32767));
	  
	  */
	memcpy(hmap,heightmap->datapointer,((mapy+1)*(mapx+1))*2);
    }
    unsigned char * typedata = new unsigned char[mapy/2 * mapx/2];bzero(typedata,(mapy/2 * mapx/2));
    if ( typemap )
    {
      typemap->GetRect(0,0,typemap->w,typemap->h,IL_LUMINANCE,IL_UNSIGNED_BYTE,typedata);
      
    }
    uint8_t * minimap_data = new uint8_t[699064];
    bzero(minimap_data,699064);
    if ( minimap )
    {
        int p = 0;
        int s = 1024;

        Image * im2 = new Image();
        im2->AllocateRGBA(1024,1024,(char*)minimap->datapointer);
        for ( int i = 0; i < 9; i++ )
        {
	    //std::cout << ">Mipmap " << i << std::endl;
	    im2->Rescale(s,s);
	    //std::cout << "<Mipmap " << i << std::endl;
	    ILuint ss;
            ILubyte * dxtdata = ilCompressDXT(im2->datapointer,s,s,1,IL_DXT1,&ss);
	    //std::cout << ss << " " << s;
	    memcpy(&minimap_data[p],dxtdata,ss);
	    free(dxtdata);
            p += ss;
	    
            s = s >> 1;
	    
        }
        delete im2;

    }
    unsigned char * metalmap_data = new unsigned char[mapx/2 * mapy/2];bzero(metalmap_data,(mapy/2 * mapx/2));
    if ( metalmap )
    {
      metalmap->GetRect(0,0,metalmap->w,metalmap->h,IL_LUMINANCE,IL_UNSIGNED_BYTE,metalmap_data);
      
    }
    /*hdr.heightmapPtr = sizeof(hdr);
    hdr.typeMapPtr = hdr.heightmapPtr + ((mapy+1)*(mapx+1))*2;
    hdr.minimapPtr = hdr.typeMapPtr + (mapy/2 * mapx/2);
    hdr.metalmapPtr = hdr.minimapPtr + 699048;
    hdr.featurePtr = hdr.metalmapPtr + (mapy/2 * mapx/2);*/
    MapFeatureHeader mfhdr;
    
    hdr.tilesPtr = hdr.featurePtr + sizeof(mfhdr);
    hdr.numExtraHeaders = 1;
    ExtraHeader grassHeader;
    grassHeader.size = 4;
    grassHeader.type = 1;
    MapTileHeader mthdr;
    mthdr.numTileFiles = 1;
    unsigned char * grass_data = new unsigned char[mapx/4 * mapy/4];bzero(grass_data,mapx/4 * mapy/4);
    if ( vegetationmap )
    {
      vegetationmap->GetRect(0,0,vegetationmap->w,vegetationmap->h,IL_LUMINANCE,IL_UNSIGNED_BYTE,grass_data);
      
    }
    int * tiles = new int[mapx/4 * mapy/4];
    std::vector<uint64_t> order;
    DoCompress(tiles,order);
   /* for ( int y = 0; y < mapy/4; y++ )
    {
    for ( int x = 0; x < mapx/4; x++ )
      {
	printf("%5d,",tiles[(mapx/4)*y+x]);
      }
      printf("\n");
    }*/
    
    FILE * tilefile = fopen((m_name+std::string(".smt")).c_str(),"wb");
    delete texture; //Temporarily delete texture from memory to reduce mem usage
    m_tiles->WriteToFile(tilefile,order);
    texture = new Image(texpath.c_str());
     
    fclose(tilefile);
    FILE * smffile = fopen((m_name+std::string(".smf")).c_str(),"wb");
    fwrite(&hdr,sizeof(hdr),1,smffile);
    fwrite(&grassHeader,sizeof(grassHeader),1,smffile);
    int _ofs = ftell(smffile)+4;
    fwrite(&_ofs,4,1,smffile);
    fwrite(grass_data,mapx/4 * mapy/4,1,smffile);
    
    hdr.minimapPtr  = ftell(smffile);
    fwrite(minimap_data,699064,1,smffile);
    hdr.heightmapPtr = ftell(smffile);
    fwrite(hmap,((mapy+1)*(mapx+1))*2,1,smffile);
    hdr.typeMapPtr = ftell(smffile);
    fwrite(typedata,mapy/2 * mapx/2,1,smffile);
    
    hdr.metalmapPtr  = ftell(smffile);
    fwrite(metalmap_data,mapy/2 * mapx/2,1,smffile);
    hdr.featurePtr  = ftell(smffile);
    

    mfhdr.numFeatures = 0;
    for ( std::map<std::string,std::list<MapFeatureStruct*> * >::iterator it = features.begin(); it != features.end(); it++ )//Enumerate features
      mfhdr.numFeatures += (*it).second->size();
    mfhdr.numFeatureType = features.size();
    fwrite(&mfhdr,sizeof(mfhdr),1,smffile);
    {
      std::map<std::string,unsigned int> featureTypes;
      unsigned int z = 0;
      for ( std::map<std::string,std::list<MapFeatureStruct*> * >::iterator it = features.begin(); it != features.end(); it++ )//Write feature types
      {
	fwrite((*it).first.c_str(),(*it).first.size()+1,1,smffile);
	featureTypes[(*it).first] = z++;
      }
      for ( std::map<std::string,std::list<MapFeatureStruct*> * >::iterator it = features.begin(); it != features.end(); it++ )//Write feature types
      {
	for ( std::list<MapFeatureStruct*>::iterator it2 = (*it).second->begin(); it2 != (*it).second->end(); it2++ )
	{
	  (*it2)->featureType = featureTypes[(*it).first];
	  if ( (*it2)->ypos < 490000.0f ) // Align on terrain
	  {
	    unsigned int hmapx = ((*it2)->xpos/float((mapx/128)*1024))*heightmap->w;
	    unsigned int hmapy = ((*it2)->zpos/float((mapy/128)*1024))*heightmap->h;
	    (*it2)->ypos = hdr.minHeight+(float(hmap[hmapy*(mapx+1)+hmapx])/32767.0)*(hdr.maxHeight-hdr.minHeight);
	    std::cout << "Feature " << (*it).first << " Instance " << (*it2) << " Terrain height: " << (*it2)->ypos << std::endl;
	  }
	  
	  fwrite((*it2),sizeof(MapFeatureStruct),1,smffile);
	}
	
      }
      
      
      
    }
    
    hdr.tilesPtr = ftell(smffile);
    uint32_t tc = m_tiles->GetTileCount();
    mthdr.numTiles = tc;
    fwrite(&mthdr,sizeof(mthdr),1,smffile);
    fwrite(&tc,4,1,smffile);
    fwrite((m_name+std::string(".smt")).c_str(),(m_name+std::string(".smt")).length()+1,1,smffile);
    fwrite(tiles,(mapx/4 * mapy/4)*4,1,smffile);
    fseek(smffile,0,SEEK_SET);
    fwrite(&hdr,sizeof(hdr),1,smffile);
    fclose(smffile);
    delete [] metalmap_data;
    delete [] hmap;
    delete [] typedata;
    delete [] tiles;
    delete [] minimap_data;
    delete [] grass_data;
}