2 Copyright (C) 1999-2007 id Software, Inc. and contributors.
3 For a list of contributors, see the accompanying CONTRIBUTORS file.
5 This file is part of GtkRadiant.
7 GtkRadiant is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 GtkRadiant is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GtkRadiant; if not, write to the Free Software
19 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
31 qboolean g_stripify = qtrue;
32 qboolean g_release; // don't grab, copy output data to new tree
33 char g_releasedir[1024]; // c:\quake2\baseq2, etc
34 qboolean g_archive; // don't grab, copy source data to new tree
35 char g_only[256]; // if set, only grab this cd
36 qboolean g_skipmodel; // set true when a cd is not g_only
38 // bogus externs for some TA hacks (common/ using them against q3map)
40 // some old defined that was in cmdlib lost during merge
43 #if defined ( __linux__ ) || defined ( __APPLE__ )
44 #define strlwr strlower
48 =======================================================
52 =======================================================
55 unsigned Com_BlockChecksum( void *buffer, int length );
70 packfile_t pfiles[16384];
73 packheader_t pakheader;
79 Filename should be gamedir reletive.
80 Either copies the file to the release dir, or adds it to
84 void ReleaseFile( char *filename ){
92 sprintf( source, "%s%s", gamedir, filename );
93 sprintf( dest, "%s/%s", g_releasedir, filename );
94 printf( "copying to %s\n", dest );
95 QCopyFile( source, dest );
110 ShaderFiles_t s_shaderFiles;
112 void FindShaderFiles( char *filename ){
115 char linebuffer[1024];
118 char *diffuseExtensions[] =
125 char *otherExtensions[] =
133 s_shaderFiles.num = 0;
135 strcpy( stripped, filename );
136 if ( strrchr( stripped, '.' ) ) {
137 *strrchr( stripped, '.' ) = 0;
139 strcat( stripped, ".shader" );
141 if ( FileExists( stripped ) ) {
143 char mapa[512], mapb[512];
145 strcpy( s_shaderFiles.names[s_shaderFiles.num], stripped );
149 len = LoadFile( stripped, (void **)&buf );
153 while ( p - buf < len )
158 while ( *p == ' ' || *p == '\n' || *p == '\t' )
161 // grab rest of the line
162 while ( *p != 0 && *p != '\n' )
173 strlwr( linebuffer );
175 // see if the line specifies an opaque map or blendmap
176 if ( strstr( linebuffer, "opaquemap" ) == linebuffer ||
177 strstr( linebuffer, "blendmap" ) == linebuffer ) {
182 mapa[0] = mapb[0] = 0;
184 // skip past the keyword
185 while ( linebuffer[i] != ' ' && linebuffer[i] != '\t' && linebuffer[i] )
188 while ( ( linebuffer[i] == ' ' || linebuffer[i] == '\t' ) && linebuffer[i] )
191 // grab first map name
193 while ( linebuffer[i] != ' ' && linebuffer[i] != '\t' && linebuffer[i] )
195 mapa[j] = linebuffer[i];
202 while ( ( linebuffer[i] == ' ' || linebuffer[i] == '\t' ) && linebuffer[i] )
205 // grab second map name
207 while ( linebuffer[i] != ' ' && linebuffer[i] != '\t' && linebuffer[i] )
209 mapb[j] = linebuffer[i];
216 if ( mapa[0] != 0 && mapa[0] != '-' ) {
217 sprintf( s_shaderFiles.names[s_shaderFiles.num], "%s%s", gamedir, mapa );
220 if ( mapb[0] != 0 && mapb[0] != '-' && mapb[0] != '^' && mapb[0] != '*' ) {
221 sprintf( s_shaderFiles.names[s_shaderFiles.num], "%s%s", gamedir, mapb );
229 if ( strrchr( stripped, '.' ) ) {
230 *strrchr( stripped, '.' ) = 0;
233 // look for diffuse maps
234 for ( i = 0; i < 3; i++ )
236 strcpy( buffer, stripped );
237 strcat( buffer, diffuseExtensions[i] );
238 if ( FileExists( buffer ) ) {
239 strcpy( s_shaderFiles.names[s_shaderFiles.num], buffer );
244 for ( i = 0; i < 3; i++ )
246 strcpy( buffer, stripped );
247 strcat( buffer, otherExtensions[i] );
248 if ( FileExists( buffer ) ) {
249 strcpy( s_shaderFiles.names[s_shaderFiles.num], buffer );
260 Copies all needed files for a shader to the release directory
263 void ReleaseShader( char *filename ){
269 sprintf( fullpath, "%s%s", gamedir, filename );
271 FindShaderFiles( fullpath );
273 for ( i = 0; i < s_shaderFiles.num; i++ )
275 strcpy( stripped, s_shaderFiles.names[i] );
276 if ( strstr( stripped, gamedir ) ) {
277 memmove( stripped, stripped + strlen( gamedir ), strlen( stripped ) );
279 sprintf( dest, "%s/%s", g_releasedir, stripped );
280 printf( "copying to %s\n", dest );
281 QCopyFile( s_shaderFiles.names[i], dest );
289 This is only used to cause a file to be copied during a release
290 build (default.cfg, maps, etc)
293 void Cmd_File( void ){
295 ReleaseFile( token );
306 void PackDirectory_r( char *dir ){
307 struct _finddata_t fileinfo;
309 char dirstring[1024];
312 sprintf( dirstring, "%s%s/*.*", gamedir, dir );
314 handle = _findfirst( dirstring, &fileinfo );
315 if ( handle == -1 ) {
321 sprintf( filename, "%s/%s", dir, fileinfo.name );
322 if ( fileinfo.attrib & _A_SUBDIR ) { // directory
323 if ( fileinfo.name[0] != '.' ) { // don't pak . and ..
324 PackDirectory_r( filename );
328 // copy or pack the file
329 ReleaseFile( filename );
330 } while ( _findnext( handle, &fileinfo ) != -1 );
332 _findclose( handle );
336 #include <sys/types.h>
340 #include <sys/dirent.h>
343 void PackDirectory_r( char *dir ){
345 struct direct **namelist, *ent;
347 struct dirent **namelist, *ent;
354 char dirstring[1024];
357 sprintf( dirstring, "%s%s", gamedir, dir );
358 count = scandir( dirstring, &namelist, NULL, NULL );
360 for ( i = 0 ; i < count ; i++ )
365 if ( name[0] == '.' ) {
369 sprintf( fullname, "%s/%s", dir, name );
370 sprintf( dirstring, "%s%s/%s", gamedir, dir, name );
372 if ( stat( dirstring, &st ) == -1 ) {
373 Error( "fstating %s", pf->name );
375 if ( st.st_mode & S_IFDIR ) { // directory
376 PackDirectory_r( fullname );
380 // copy or pack the file
381 ReleaseFile( fullname );
391 This is only used to cause a directory to be copied during a
392 release build (sounds, etc)
395 void Cmd_Dir( void ){
397 PackDirectory_r( token );
400 //========================================================================
402 #define MAX_RTEX 16384
404 char rtex[MAX_RTEX][64];
406 void ReleaseTexture( char *name ){
410 for ( i = 0 ; i < numrtex ; i++ )
411 if ( !Q_stricmp( name, rtex[i] ) ) {
415 if ( numrtex == MAX_RTEX ) {
416 Error( "numrtex == MAX_RTEX" );
419 strcpy( rtex[i], name );
422 sprintf( path, "textures/%s.wal", name );
430 Only relevent for release and pak files.
431 Releases the .bsp files for the maps, and scans all of the files to
432 build a list of all textures used, which are then released.
435 void Cmd_Maps( void ){
438 while ( TokenAvailable() )
441 sprintf( map, "maps/%s.bsp", token );
448 // get all the texture references
449 sprintf( map, "%smaps/%s.bsp", gamedir, token );
455 //==============================================================
462 void ParseScript( void ){
466 { // look for a line starting with a $ command
471 if ( token[0] == '$' ) {
474 while ( TokenAvailable() )
481 if ( !strcmp( token, "$modelname" ) ) {
484 else if ( !strcmp( token, "$base" ) ) {
487 else if ( !strcmp( token, "$exit" ) ) {
490 else if ( !strcmp( token, "$3dsconvert" ) ) {
493 else if ( !strcmp( token, "$spritebase" ) ) {
496 else if ( !strcmp( token, "$cd" ) ) {
499 else if ( !strcmp( token, "$origin" ) ) {
502 else if ( !strcmp( token, "$scale" ) ) {
505 else if ( !strcmp( token, "$frame" ) ) {
508 else if ( !strcmp( token, "$skin" ) ) {
511 else if ( !strcmp( token, "$spriteshader" ) ) {
514 else if ( !strcmp( token, "$aseconvert" ) ) {
515 Cmd_ASEConvert( qfalse );
517 else if ( !strcmp( token, "$aseanimconvert" ) ) {
518 Cmd_ASEConvert( qtrue );
524 else if ( !strcmp( token, "$grab" ) ) {
527 else if ( !strcmp( token, "$raw" ) ) {
530 else if ( !strcmp( token, "$colormap" ) ) {
533 else if ( !strcmp( token, "$environment" ) ) {
540 else if ( !strcmp( token, "$video" ) ) {
546 else if ( !strcmp( token, "$file" ) ) {
549 else if ( !strcmp( token, "$dir" ) ) {
552 else if ( !strcmp( token, "$maps" ) ) {
556 Error( "bad command %s\n", token );
561 //=======================================================
570 int main( int argc, char **argv ){
571 static int i; // VC4.2 compiler bug if auto...
574 // using GtkRadiant's versioning next to Id's versioning
575 printf( "Q3Data - (c) 1999 Id Software Inc.\n" );
576 printf( "GtkRadiant - v" RADIANT_VERSION " " __DATE__ "\n" );
578 ExpandWildcards( &argc, &argv );
580 for ( i = 1 ; i < argc ; i++ )
582 if ( !strcmp( argv[i], "-archive" ) ) {
584 strcpy( archivedir, argv[i + 1] );
585 printf( "Archiving source to: %s\n", archivedir );
588 else if ( !strcmp( argv[i], "-release" ) ) {
590 strcpy( g_releasedir, argv[i + 1] );
591 printf( "Copy output to: %s\n", g_releasedir );
594 else if ( !strcmp( argv[i], "-nostrips" ) ) {
596 printf( "Not optimizing for strips\n" );
598 else if ( !strcmp( argv[i], "-writedir" ) ) {
599 strcpy( writedir, argv[i + 1] );
600 printf( "Write output to: %s\n", writedir );
603 else if ( !strcmp( argv[i], "-verbose" ) ) {
606 else if ( !strcmp( argv[i], "-dump" ) ) {
607 printf( "Dumping contents of: '%s'\n", argv[i + 1] );
608 if ( strstr( argv[i + 1], ".md3" ) ) {
609 MD3_Dump( argv[i + 1] );
613 Error( "Do not know how to dump the contents of '%s'\n", argv[i + 1] );
617 else if ( !strcmp( argv[i], "-3dsconvert" ) ) {
618 // NOTE TTimo this is broken, tried on a sample .3ds
619 // what happens .. it calls the Convert3DStoMD3,
620 // which calls the scriptlib function in non initialized state .. and crashes
621 printf( "Converting %s.3DS to %s.MD3\n", argv[i + 1], argv[i + 1] );
622 SetQdirFromPath( argv[i + 1] );
623 vfsInitDirectory( gamedir );
624 Convert3DStoMD3( argv[i + 1] );
627 else if ( !strcmp( argv[i], "-only" ) ) {
628 strcpy( g_only, argv[i + 1] );
629 printf( "Only grabbing %s\n", g_only );
632 else if ( !strcmp( argv[i], "-gamedir" ) ) {
633 strcpy( gamedir, argv[i + 1] );
636 else if ( argv[i][0] == '-' ) {
637 Error( "Unknown option \"%s\"", argv[i] );
645 Error( "usage: q3data [-archive <directory>] [-dump <file.md3>] [-release <directory>] [-only <model>] [-3dsconvert <file.3ds>] [-verbose] [file.qdt]" );
648 for ( ; i < argc ; i++ )
650 printf( "--------------- %s ---------------\n", argv[i] );
652 strcpy( path, argv[i] );
653 DefaultExtension( path, ".qdt" );
655 SetQdirFromPath( path );
658 // q3data went through a partial conversion to use the vfs
659 // it was never actually tested before 1.1.1
660 // the code is still mostly using direct file access calls
661 vfsInitDirectory( gamedir );
662 LoadScriptFile( ExpandArg( path ), -1 );
669 // write out the last model
670 FinishModel( TYPE_UNKNOWN );