ShapeConv.cpp

Go to the documentation of this file.
00001 /*
00002  *  Copyright (C) 2002, 2003 The Pentagram Team
00003  *
00004  *  This program is free software; you can redistribute it and/or modify
00005  *  it under the terms of the GNU General Public License as published by
00006  *  the Free Software Foundation; either version 2 of the License, or
00007  *  (at your option) any later version.
00008  *
00009  *  This program is distributed in the hope that it will be useful,
00010  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00011  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012  *  GNU General Public License for more details.
00013  *
00014  *  You should have received a copy of the GNU General Public License
00015  *  along with this program; if not, write to the Free Software
00016  *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
00017  */
00018 
00019 #include "pent_include.h"
00020 
00021 #include "util.h"
00022 
00023 #include "FileSystem.h"
00024 
00025 #include "Args.h"
00026 
00027 #include "ConvertShape.h"
00028 
00029 #include "crusader/ConvertShapeCrusader.h"
00030 #include "u8/ConvertShapeU8.h"
00031 
00032 const ConvertShapeFormat                AutoShapeFormat =
00033 {
00034         "Auto Detected",
00035         
00036         0,              // len_header
00037         0,              // ident
00038 
00039         0,              // bytes_ident
00040         0,              // bytes_header_unk
00041         0,              // bytes_num_frames
00042 
00043         0,              // len_frameheader
00044         0,              // bytes_frame_offset
00045         0,              // bytes_frameheader_unk
00046         0,              // bytes_frame_length
00047         0,              // bytes_frame_length_kludge
00048 
00049         0,              // len_frameheader2
00050         0,              // bytes_frame_unknown
00051         0,              // bytes_frame_compression
00052         0,              // bytes_frame_width
00053         0,              // bytes_frame_height
00054         0,              // bytes_frame_xoff
00055         0,              // bytes_frame_yoff
00056 
00057         0,              // bytes_line_offset
00058         0               // line_offset_absolute
00059 };
00060 
00061 // Convert formats we are using
00062 const ConvertShapeFormat *read_format = &AutoShapeFormat;
00063 const ConvertShapeFormat *write_format = &U8ShapeFormat;
00064 
00065 //#define EXPORT_SHAPENUM
00066 #ifdef EXPORT_SHAPENUM
00067 int shapenum;
00068 #endif
00069 
00070 // Nasty yucky stuff
00071 void ConvertFlexes(IDataSource *readfile, ODataSource *writefile)
00072 {
00073         ConvertShape    shape;
00074         uint32                  i;
00075 
00076         // Number of flex entries
00077         readfile->seek(0x54);
00078         uint32 num_entries = readfile->read4();
00079 
00080         // Write blank stuff for output 
00081         for (i = 0; i < 0x52; i++) writefile->write1(0x1A);
00082         writefile->write2(0);
00083 
00084         // Write num entries
00085         writefile->write4(num_entries);
00086 
00087         // Offset to begin writing a shape at
00088         uint32  write_offset = 0x80 + 8 * num_entries;
00089 
00090         // Write blank index table
00091         for (i = 0x58; i < write_offset; i++)  writefile->write1(0);
00092 
00093         // Convert shapes
00094         con.Printf ("Convering %i shapes...\n", num_entries);
00095         for (uint32 s = 0; s < num_entries; s++)
00096         {
00097 #ifdef EXPORT_SHAPENUM
00098                 shapenum = s;
00099 #endif
00100 
00101                 // Get the read offset and size
00102                 readfile->seek(0x80 + 8*s);
00103                 uint32 read_offset = readfile->read4();
00104                 uint32 read_size = readfile->read4();
00105 
00106                 if (!read_size) continue;
00107 
00108                 // Seek to shape
00109                 readfile->seek(read_offset);
00110 
00111                 // Detect ShapeFormat
00112                 if (read_format == &AutoShapeFormat)
00113                 {
00114                         pout << "Auto detecting format..." << std::endl;
00115 
00116                         if (ConvertShape::Check(readfile, &U8ShapeFormat, read_size))
00117                                 read_format = &U8ShapeFormat;
00118                         else if (ConvertShape::Check(readfile, &U82DShapeFormat, read_size))
00119                                 read_format = &U82DShapeFormat;
00120                         else if (ConvertShape::Check(readfile, &U8SKFShapeFormat, read_size))
00121                                 read_format = &U8SKFShapeFormat;
00122                         else if (ConvertShape::Check(readfile, &CrusaderShapeFormat, read_size))
00123                                 read_format = &CrusaderShapeFormat;
00124                         else if (ConvertShape::Check(readfile, &Crusader2DShapeFormat, read_size))
00125                                 read_format = &Crusader2DShapeFormat;
00126                         else if (ConvertShape::Check(readfile, &PentagramShapeFormat, read_size))
00127                                 read_format = &PentagramShapeFormat;
00128                         else if (ConvertShape::Check(readfile, &U8CMPShapeFormat, read_size))
00129                                 read_format = &U8CMPShapeFormat;
00130                         else
00131                         {
00132                                 perr << "Error: Unable to detect shape format!" << std::endl;
00133                                 return;
00134                         }
00135                         pout << "Detected input format as: " << read_format->name << std::endl;
00136                 }
00137                 
00138                 // Read shape
00139                 con.Printf ("Reading shape %i...\n", s);
00140                 shape.Read(readfile, read_format, read_size);
00141 
00142                 // Write shape
00143                 con.Printf ("Writing shape %i...\n", s);
00144                 writefile->seek(write_offset);
00145                 uint32 write_size;
00146                 shape.Write(writefile, write_format, write_size);
00147 
00148                 // Update the table
00149                 writefile->seek(0x80 + 8*s);
00150                 writefile->write4(write_offset);
00151                 writefile->write4(write_size);
00152 
00153                 // Update the write_offset
00154                 write_offset += write_size;
00155 
00156                 // Free it
00157                 shape.Free();
00158         }
00159         pout << "Done!" << std::endl;
00160 }
00161 
00162 void ConvertShp(IDataSource *readfile, ODataSource *writefile)
00163 {
00164 #ifdef EXPORT_SHAPENUM
00165         shapenum = 1;
00166 #endif
00167         ConvertShape shape;
00168         uint32 read_size = readfile->getSize();
00169 
00170         // Detect ShapeFormat
00171         if (read_format == &AutoShapeFormat)
00172         {
00173                 pout << "Auto detecting format..." << std::endl;
00174                 if (ConvertShape::Check(readfile, &U8ShapeFormat, read_size))
00175                         read_format = &U8ShapeFormat;
00176                 else if (ConvertShape::Check(readfile, &U82DShapeFormat, read_size))
00177                         read_format = &U82DShapeFormat;
00178                 else if (ConvertShape::Check(readfile, &U8SKFShapeFormat, read_size))
00179                         read_format = &U8SKFShapeFormat;
00180                 else if (ConvertShape::Check(readfile, &CrusaderShapeFormat, read_size))
00181                         read_format = &CrusaderShapeFormat;
00182                 else if (ConvertShape::Check(readfile, &Crusader2DShapeFormat, read_size))
00183                         read_format = &Crusader2DShapeFormat;
00184                 else if (ConvertShape::Check(readfile, &PentagramShapeFormat, read_size))
00185                         read_format = &PentagramShapeFormat;
00186                 else if (ConvertShape::Check(readfile, &U8CMPShapeFormat, read_size))
00187                         read_format = &U8CMPShapeFormat;
00188                 else
00189                 {
00190                         perr << "Error: Unable to detect shape format!" << std::endl;
00191                         return;
00192                 }
00193                 pout << "Detected input format as: " << read_format->name << std::endl;
00194         }
00195 
00196         con.Printf ("Reading shape...\n");
00197         shape.Read(readfile, read_format, read_size);
00198         uint32 write_size;
00199         con.Printf ("Writing shape...\n");
00200         shape.Write(writefile, write_format, write_size);
00201         shape.Free();
00202         pout << "Done!" << std::endl;
00203 }
00204 
00205 const ConvertShapeFormat *GetShapeFormat(const char *game)
00206 {
00207         if (!Pentagram::strcasecmp(game, "u8")) return &U8ShapeFormat;
00208         else if (!Pentagram::strcasecmp(game, "u82D")) return &U82DShapeFormat;
00209         else if (!Pentagram::strcasecmp(game, "u8skf")) return &U8SKFShapeFormat;
00210         else if (!Pentagram::strcasecmp(game, "cru")) return &CrusaderShapeFormat;
00211         else if (!Pentagram::strcasecmp(game, "cru2D")) return &Crusader2DShapeFormat;
00212         else if (!Pentagram::strcasecmp(game, "pent")) return &PentagramShapeFormat;
00213 
00214         return 0;
00215 }
00216 
00217 int main(int argc, char **argv)
00218 {
00219         if (argc < 3) {
00220                 perr << "Usage: ShapeConv <inflx> <outflx> [--ifmt u8|u82D|u8skf|u8cmp|cru|cru2D|pent|auto] [--ofmt u8|u82D|u8skf|cru|cru2D|pent] [--singlefile]" << std::endl;
00221                 perr << std::endl;
00222                 perr << "Default input format: Auto Detect" << std::endl;
00223                 perr << "Default output format: Ultima 8" << std::endl;
00224                 return 1;
00225         }
00226 
00227         Args            parameters;
00228         std::string     ifmt, ofmt;
00229         bool            singlefile=false;
00230         //bool          auto_detect=false; // Darke: UNUSED?
00231 
00232         parameters.declare("--ifmt",            &ifmt,      "auto");
00233         parameters.declare("--ofmt",            &ofmt,      "u8");
00234         parameters.declare("--singlefile",      &singlefile, true);
00235 
00236         parameters.process(argc, argv);
00237 
00238         if (!Pentagram::strcasecmp(ifmt.c_str(), "auto")) read_format = &AutoShapeFormat;
00239         else if (!Pentagram::strcasecmp(ifmt.c_str(), "u8cmp")) read_format = &U8CMPShapeFormat;
00240         else read_format = GetShapeFormat(ifmt.c_str());
00241 
00242         write_format = GetShapeFormat(ofmt.c_str());
00243 
00244         if (!read_format) 
00245         {
00246                 perr << "Unknown input format: " << ifmt << std::endl;
00247                 return -1;
00248         }
00249 
00250         if (!write_format) 
00251         {
00252                 perr << "Unknown output format: " << ifmt << std::endl;
00253                 return -1;
00254         }
00255 
00256         // Check to see if the file ends in .shp. If it does, assume single shape file
00257         if (std::strlen(argv[1]) > 4 && !Pentagram::strcasecmp(argv[1]+std::strlen(argv[1])-4, ".shp"))
00258                 singlefile = true;
00259 
00260         if (singlefile) pout << "Single shape mode" << std::endl;
00261 
00262         if (singlefile)
00263                 pout << "Converting " << read_format->name << " format shape in '"<< argv[1] << "' to " << write_format->name << " format in '"<< argv[2] << "'" << std::endl;
00264         else
00265                 pout << "Converting " << read_format->name << " format shapes in flex '"<< argv[1] << "' to " << write_format->name << " format in '"<< argv[2] << "'" << std::endl;
00266 
00267         // Create filesystem object
00268         FileSystem filesys(true);
00269 
00270         // Load read flex/shape file
00271         IDataSource *readfile = filesys.ReadFile(argv[1]);
00272 
00273         // Uh oh, couldn't load it
00274         if(readfile==0)
00275         {
00276                 perr << "Error reading file '" << argv[1] << "'" << std::endl;
00277                 return 1;
00278         }
00279 
00280         // Load write flex/shape file
00281         ODataSource *writefile = filesys.WriteFile(argv[2]);
00282 
00283         // Uh oh, couldn't load it
00284         if(writefile==0)
00285         {
00286                 perr << "Error writing file '" << argv[2] << "'" << std::endl;
00287                 return 1;
00288         }
00289 
00290         if (!singlefile)
00291                 ConvertFlexes(readfile, writefile);
00292         else
00293                 ConvertShp(readfile, writefile);
00294 
00295         // Clean up
00296         delete readfile;
00297         delete writefile;
00298 
00299         return 0;
00300 }

Generated on Fri Jul 27 22:27:36 2007 for pentagram by  doxygen 1.4.7