Browse Source

integrate HashFilename with Filename via Filename::set_pattern()

David Rose 20 years ago
parent
commit
60d2c8e349

+ 96 - 9
dtool/src/dtoolutil/filename.I

@@ -23,8 +23,8 @@
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 INLINE Filename::
 INLINE Filename::
 Filename(const string &filename) {
 Filename(const string &filename) {
-  (*this) = filename;
   _flags = 0;
   _flags = 0;
+  (*this) = filename;
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
@@ -34,8 +34,8 @@ Filename(const string &filename) {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 INLINE Filename::
 INLINE Filename::
 Filename(const char *filename) {
 Filename(const char *filename) {
-  (*this) = filename;
   _flags = 0;
   _flags = 0;
+  (*this) = filename;
 }
 }
 
 
 
 
@@ -45,13 +45,15 @@ Filename(const char *filename) {
 //  Description:
 //  Description:
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 INLINE Filename::
 INLINE Filename::
-Filename(const Filename &copy)
-  : _filename(copy._filename),
-    _dirname_end(copy._dirname_end),
-    _basename_start(copy._basename_start),
-    _basename_end(copy._basename_end),
-    _extension_start(copy._extension_start),
-    _flags(copy._flags)
+Filename(const Filename &copy) :
+  _filename(copy._filename),
+  _dirname_end(copy._dirname_end),
+  _basename_start(copy._basename_start),
+  _basename_end(copy._basename_end),
+  _extension_start(copy._extension_start),
+  _hash_start(copy._hash_start),
+  _hash_end(copy._hash_end),
+  _flags(copy._flags)
 {
 {
 }
 }
 
 
@@ -103,6 +105,19 @@ executable_filename(const string &filename) {
   return result;
   return result;
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: Filename::pattern_filename named constructor
+//       Access: Published
+//  Description: Constructs a filename that represents a sequence of
+//               numbered files.  See set_pattern().
+////////////////////////////////////////////////////////////////////
+INLINE Filename Filename::
+pattern_filename(const string &filename) {
+  Filename result(filename);
+  result.set_pattern(true);
+  return result;
+}
+
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: Filename::Destructor
 //     Function: Filename::Destructor
 //       Access: Published
 //       Access: Published
@@ -124,6 +139,7 @@ operator = (const string &filename) {
 
 
   locate_basename();
   locate_basename();
   locate_extension();
   locate_extension();
+  locate_hash();
   return *this;
   return *this;
 }
 }
 
 
@@ -150,6 +166,8 @@ operator = (const Filename &copy) {
   _basename_start = copy._basename_start;
   _basename_start = copy._basename_start;
   _basename_end = copy._basename_end;
   _basename_end = copy._basename_end;
   _extension_start = copy._extension_start;
   _extension_start = copy._extension_start;
+  _hash_start = copy._hash_start;
+  _hash_end = copy._hash_end;
   _flags = copy._flags;
   _flags = copy._flags;
   return *this;
   return *this;
 }
 }
@@ -388,6 +406,75 @@ get_type() const {
   return (Type)(_flags & (int)F_type);
   return (Type)(_flags & (int)F_type);
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: Filename::set_pattern
+//       Access: Published
+//  Description: Sets the flag indicating whether this is a filename
+//               pattern.  When this is true, the filename is
+//               understood to be a placeholder for a numbered
+//               sequence of filename, such as an image sequence.  In
+//               this case, a sequence of one or more hash characters
+//               ("#") should appear in the filename string; these
+//               characters will be filled in with the corresponding
+//               number (or more) of digits representing the sequence
+//               number.  Sequence numbers always begin counting at 0.
+//
+//               When this is true, methods like has_hash() and
+//               get_hash_to_end() and get_filename_index() may be
+//               called.  Methods like is_exists() will implicitly
+//               test for existance of filename sequence 0.
+////////////////////////////////////////////////////////////////////
+INLINE void Filename::
+set_pattern(bool pattern) {
+  if (pattern != get_pattern()) {
+    if (pattern) {
+      _flags |= F_pattern;
+    } else {
+      _flags &= ~F_pattern;
+    }
+    locate_hash();
+  }
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: Filename::get_pattern
+//       Access: Published
+//  Description: Returns the flag indicating whether this is a
+//               filename pattern.  See set_pattern().
+////////////////////////////////////////////////////////////////////
+INLINE bool Filename::
+get_pattern() const {
+  return (_flags & F_pattern) != 0;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: Filename::has_hash
+//       Access: Published
+//  Description: Returns true if the filename is indicated to be a
+//               filename pattern (that is, set_pattern(true) was
+//               called), and the filename pattern did include a
+//               sequence of hash marks, or false if it was not a
+//               filename pattern or did not include hash marks.  If
+//               this is true, then get_filename_index() will return a
+//               different filename each time.
+////////////////////////////////////////////////////////////////////
+INLINE bool Filename::
+has_hash() const {
+  return (_hash_start != _hash_end);
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: Filename::get_hash_to_end
+//       Access: Published
+//  Description: Returns the part of the filename beginning at the
+//               hash sequence (if any), and continuing to the end of
+//               the filename.
+////////////////////////////////////////////////////////////////////
+INLINE string Filename::
+get_hash_to_end() const {
+  return _filename.substr(_hash_start);
+}
+
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: Filename::is_local
 //     Function: Filename::is_local
 //       Access: Published
 //       Access: Published

+ 110 - 11
dtool/src/dtoolutil/filename.cxx

@@ -284,6 +284,7 @@ Filename(const Filename &dirname, const Filename &basename) {
   if (dirname.empty()) {
   if (dirname.empty()) {
     (*this) = basename;
     (*this) = basename;
   } else {
   } else {
+    _flags = basename._flags;
     string dirpath = dirname.get_fullpath();
     string dirpath = dirname.get_fullpath();
     if (dirpath[dirpath.length() - 1] == '/') {
     if (dirpath[dirpath.length() - 1] == '/') {
       (*this) = dirpath + basename.get_fullpath();
       (*this) = dirpath + basename.get_fullpath();
@@ -291,7 +292,6 @@ Filename(const Filename &dirname, const Filename &basename) {
       (*this) = dirpath + "/" + basename.get_fullpath();
       (*this) = dirpath + "/" + basename.get_fullpath();
     }
     }
   }
   }
-  _flags = 0;
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
@@ -494,6 +494,7 @@ set_dirname(const string &s) {
       _extension_start += length_change;
       _extension_start += length_change;
     }
     }
   }
   }
+  locate_hash();
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
@@ -507,6 +508,7 @@ void Filename::
 set_basename(const string &s) {
 set_basename(const string &s) {
   _filename.replace(_basename_start, string::npos, s);
   _filename.replace(_basename_start, string::npos, s);
   locate_extension();
   locate_extension();
+  locate_hash();
 }
 }
 
 
 
 
@@ -526,6 +528,7 @@ set_fullpath_wo_extension(const string &s) {
     _basename_end += length_change;
     _basename_end += length_change;
     _extension_start += length_change;
     _extension_start += length_change;
   }
   }
+  locate_hash();
 }
 }
 
 
 
 
@@ -548,6 +551,7 @@ set_basename_wo_extension(const string &s) {
     _basename_end += length_change;
     _basename_end += length_change;
     _extension_start += length_change;
     _extension_start += length_change;
   }
   }
+  locate_hash();
 }
 }
 
 
 
 
@@ -578,6 +582,51 @@ set_extension(const string &s) {
     // Replace an existing extension.
     // Replace an existing extension.
     _filename.replace(_extension_start, string::npos, s);
     _filename.replace(_extension_start, string::npos, s);
   }
   }
+  locate_hash();
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: Filename::get_filename_index
+//       Access: Published
+//  Description: If the pattern flag is set for this Filename and the
+//               filename string actually includes a sequence of hash
+//               marks, then this returns a new Filename with the
+//               sequence of hash marks replaced by the indicated
+//               index number.
+//
+//               If the pattern flag is not set for this Filename or
+//               it does not contain a sequence of hash marks, this
+//               quietly returns the original filename.
+////////////////////////////////////////////////////////////////////
+Filename Filename::
+get_filename_index(int index) const {
+  Filename file(*this);
+
+  if (_hash_end != _hash_start) {
+    ostringstream strm;
+    strm << _filename.substr(0, _hash_start) 
+	 << setw(_hash_end - _hash_start) << setfill('0') << index
+	 << _filename.substr(_hash_end);
+    file.set_fullpath(strm.str());
+  }
+  file.set_pattern(false);
+
+  return file;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: Filename::set_hash_to_end
+//       Access: Published
+//  Description: Replaces the part of the filename from the beginning
+//               of the hash sequence to the end of the filename.
+////////////////////////////////////////////////////////////////////
+void Filename::
+set_hash_to_end(const string &s) {
+  _filename.replace(_hash_start, string::npos, s);
+
+  locate_basename();
+  locate_extension();
+  locate_hash();
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
@@ -705,7 +754,9 @@ make_absolute() {
 void Filename::
 void Filename::
 make_absolute(const Filename &start_directory) {
 make_absolute(const Filename &start_directory) {
   if (is_local()) {
   if (is_local()) {
-    (*this) = Filename(start_directory, _filename);
+    Filename new_filename(start_directory, _filename);
+    new_filename._flags = _flags;
+    (*this) = new_filename;
   }
   }
 
 
   standardize();
   standardize();
@@ -748,7 +799,6 @@ make_canonical() {
     return true;
     return true;
   }
   }
 
 
-  // Temporarily save the current working directory.
   Filename cwd = ExecutionEnvironment::get_cwd();
   Filename cwd = ExecutionEnvironment::get_cwd();
   return r_make_canonical(cwd);
   return r_make_canonical(cwd);
 }
 }
@@ -772,6 +822,8 @@ make_canonical() {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 make_true_case() {
 make_true_case() {
+  assert(!get_pattern());
+
   if (empty()) {
   if (empty()) {
     return true;
     return true;
   }
   }
@@ -828,6 +880,8 @@ make_true_case() {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 string Filename::
 string Filename::
 to_os_specific() const {
 to_os_specific() const {
+  assert(!get_pattern());
+
   if (empty()) {
   if (empty()) {
     return string();
     return string();
   }
   }
@@ -865,6 +919,8 @@ to_os_specific() const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 string Filename::
 string Filename::
 to_os_generic() const {
 to_os_generic() const {
+  assert(!get_pattern());
+
 #ifdef WIN32
 #ifdef WIN32
   return back_to_front_slash(to_os_specific());
   return back_to_front_slash(to_os_specific());
 #else // WIN32
 #else // WIN32
@@ -882,7 +938,7 @@ to_os_generic() const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 exists() const {
 exists() const {
-  string os_specific = to_os_specific();
+  string os_specific = get_filename_index(0).to_os_specific();
 
 
 #ifdef WIN32_VC
 #ifdef WIN32_VC
   bool exists = false;
   bool exists = false;
@@ -913,7 +969,7 @@ exists() const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 is_regular_file() const {
 is_regular_file() const {
-  string os_specific = to_os_specific();
+  string os_specific = get_filename_index(0).to_os_specific();
 
 
 #ifdef WIN32_VC
 #ifdef WIN32_VC
   bool isreg = false;
   bool isreg = false;
@@ -943,7 +999,7 @@ is_regular_file() const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 is_directory() const {
 is_directory() const {
-  string os_specific = to_os_specific();
+  string os_specific = get_filename_index(0).to_os_specific();
 
 
 #ifdef WIN32_VC
 #ifdef WIN32_VC
   bool isdir = false;
   bool isdir = false;
@@ -981,7 +1037,7 @@ is_executable() const {
   }
   }
 
 
 #else /* WIN32_VC */
 #else /* WIN32_VC */
-  string os_specific = to_os_specific();
+  string os_specific = get_filename_index(0).to_os_specific();
   if (access(os_specific.c_str(), X_OK) == 0) {
   if (access(os_specific.c_str(), X_OK) == 0) {
     return true;
     return true;
   }
   }
@@ -1008,8 +1064,8 @@ int Filename::
 compare_timestamps(const Filename &other,
 compare_timestamps(const Filename &other,
                    bool this_missing_is_old,
                    bool this_missing_is_old,
                    bool other_missing_is_old) const {
                    bool other_missing_is_old) const {
-  string os_specific = to_os_specific();
-  string other_os_specific = other.to_os_specific();
+  string os_specific = get_filename_index(0).to_os_specific();
+  string other_os_specific = other.get_filename_index(0).to_os_specific();
 
 
 #ifdef WIN32_VC
 #ifdef WIN32_VC
   struct _stat this_buf;
   struct _stat this_buf;
@@ -1085,7 +1141,7 @@ resolve_filename(const DSearchPath &searchpath,
   string found;
   string found;
 
 
   if (is_local()) {
   if (is_local()) {
-    found = searchpath.find_file(get_fullpath());
+    found = searchpath.find_file(*this);
 
 
     if (found.empty()) {
     if (found.empty()) {
       // We didn't find it with the given extension; can we try the
       // We didn't find it with the given extension; can we try the
@@ -1093,7 +1149,7 @@ resolve_filename(const DSearchPath &searchpath,
       if (get_extension().empty() && !default_extension.empty()) {
       if (get_extension().empty() && !default_extension.empty()) {
         Filename try_ext = *this;
         Filename try_ext = *this;
         try_ext.set_extension(default_extension);
         try_ext.set_extension(default_extension);
-        found = searchpath.find_file(try_ext.get_fullpath());
+        found = searchpath.find_file(try_ext);
       }
       }
     }
     }
   } else {
   } else {
@@ -1234,6 +1290,8 @@ find_on_searchpath(const DSearchPath &searchpath) {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 scan_directory(vector_string &contents) const {
 scan_directory(vector_string &contents) const {
+  assert(!get_pattern());
+
 #if defined(WIN32_VC)
 #if defined(WIN32_VC)
   // Use Windows' FindFirstFile() / FindNextFile() to walk through the
   // Use Windows' FindFirstFile() / FindNextFile() to walk through the
   // list of files in a directory.
   // list of files in a directory.
@@ -1374,6 +1432,7 @@ scan_directory(vector_string &contents) const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 open_read(ifstream &stream) const {
 open_read(ifstream &stream) const {
+  assert(!get_pattern());
   assert(is_text() || is_binary());
   assert(is_text() || is_binary());
 
 
   ios_openmode open_mode = ios::in;
   ios_openmode open_mode = ios::in;
@@ -1409,6 +1468,7 @@ open_read(ifstream &stream) const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 open_write(ofstream &stream, bool truncate) const {
 open_write(ofstream &stream, bool truncate) const {
+  assert(!get_pattern());
   assert(is_text() || is_binary());
   assert(is_text() || is_binary());
 
 
   ios_openmode open_mode = ios::out;
   ios_openmode open_mode = ios::out;
@@ -1459,6 +1519,7 @@ open_write(ofstream &stream, bool truncate) const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 open_append(ofstream &stream) const {
 open_append(ofstream &stream) const {
+  assert(!get_pattern());
   assert(is_text() || is_binary());
   assert(is_text() || is_binary());
 
 
   ios_openmode open_mode = ios::app;
   ios_openmode open_mode = ios::app;
@@ -1495,6 +1556,7 @@ open_append(ofstream &stream) const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 open_read_write(fstream &stream) const {
 open_read_write(fstream &stream) const {
+  assert(!get_pattern());
   assert(is_text() || is_binary());
   assert(is_text() || is_binary());
 
 
   ios_openmode open_mode = ios::out | ios::in;
   ios_openmode open_mode = ios::out | ios::in;
@@ -1534,6 +1596,7 @@ open_read_write(fstream &stream) const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 touch() const {
 touch() const {
+  assert(!get_pattern());
 #ifdef WIN32_VC
 #ifdef WIN32_VC
   // In Windows, we have to use the Windows API to do this reliably.
   // In Windows, we have to use the Windows API to do this reliably.
 
 
@@ -1616,6 +1679,7 @@ touch() const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 unlink() const {
 unlink() const {
+  assert(!get_pattern());
   string os_specific = to_os_specific();
   string os_specific = to_os_specific();
   return (::unlink(os_specific.c_str()) == 0);
   return (::unlink(os_specific.c_str()) == 0);
 }
 }
@@ -1631,6 +1695,7 @@ unlink() const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 rename_to(const Filename &other) const {
 rename_to(const Filename &other) const {
+  assert(!get_pattern());
   string os_specific = to_os_specific();
   string os_specific = to_os_specific();
   string other_os_specific = other.to_os_specific();
   string other_os_specific = other.to_os_specific();
   return (rename(os_specific.c_str(),
   return (rename(os_specific.c_str(),
@@ -1652,6 +1717,7 @@ rename_to(const Filename &other) const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Filename::
 bool Filename::
 make_dir() const {
 make_dir() const {
+  assert(!get_pattern());
   if (empty()) {
   if (empty()) {
     return false;
     return false;
   }
   }
@@ -1787,6 +1853,39 @@ locate_extension() {
   // there is no dot.
   // there is no dot.
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: Filename::locate_hash
+//       Access: Protected
+//  Description: Identifies the part of the filename that contains the
+//               sequence of hash marks, if any.
+////////////////////////////////////////////////////////////////////
+void Filename::
+locate_hash() {
+  if (!get_pattern()) {
+    // If it's not a pattern-type filename, these are always set to
+    // the end of the string.
+    _hash_end = string::npos;
+    _hash_start = string::npos;
+
+  } else {
+    // If it is a pattern-type filename, we must search for the hash
+    // marks, which could be anywhere (but are usually toward the
+    // end).
+    _hash_end = _filename.rfind('#');
+    if (_hash_end == string::npos) {
+      _hash_end = string::npos;
+      _hash_start = string::npos;
+      
+    } else {
+      _hash_start = _hash_end;
+      ++_hash_end;
+      while (_hash_start > 0 && _filename[_hash_start - 1] == '#') {
+        --_hash_start;
+      }
+    }
+  }
+}
+
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: Filename::get_common_prefix
 //     Function: Filename::get_common_prefix

+ 15 - 0
dtool/src/dtoolutil/filename.h

@@ -58,6 +58,7 @@ public:
     F_type            = 0x0f,
     F_type            = 0x0f,
     F_binary          = 0x10,
     F_binary          = 0x10,
     F_text            = 0x20,
     F_text            = 0x20,
+    F_pattern         = 0x40,
   };
   };
 
 
 PUBLISHED:
 PUBLISHED:
@@ -75,6 +76,8 @@ PUBLISHED:
   INLINE static Filename dso_filename(const string &filename);
   INLINE static Filename dso_filename(const string &filename);
   INLINE static Filename executable_filename(const string &filename);
   INLINE static Filename executable_filename(const string &filename);
 
 
+  INLINE static Filename pattern_filename(const string &filename);
+
   static Filename from_os_specific(const string &os_specific,
   static Filename from_os_specific(const string &os_specific,
                                    Type type = T_general);
                                    Type type = T_general);
   static Filename expand_from(const string &user_string, 
   static Filename expand_from(const string &user_string, 
@@ -124,6 +127,15 @@ PUBLISHED:
   INLINE void set_type(Type type);
   INLINE void set_type(Type type);
   INLINE Type get_type() const;
   INLINE Type get_type() const;
 
 
+  INLINE void set_pattern(bool pattern);
+  INLINE bool get_pattern() const;
+
+  INLINE bool has_hash() const;
+  Filename get_filename_index(int index) const;
+
+  INLINE string get_hash_to_end() const;
+  void set_hash_to_end(const string &s);
+
   void extract_components(vector_string &components) const;
   void extract_components(vector_string &components) const;
   void standardize();
   void standardize();
 
 
@@ -176,6 +188,7 @@ PUBLISHED:
 protected:
 protected:
   void locate_basename();
   void locate_basename();
   void locate_extension();
   void locate_extension();
+  void locate_hash();
   size_t get_common_prefix(const string &other) const;
   size_t get_common_prefix(const string &other) const;
   static int count_slashes(const string &str);
   static int count_slashes(const string &str);
   bool r_make_canonical(const Filename &cwd);
   bool r_make_canonical(const Filename &cwd);
@@ -187,6 +200,8 @@ protected:
   size_t _basename_start;
   size_t _basename_start;
   size_t _basename_end;
   size_t _basename_end;
   size_t _extension_start;
   size_t _extension_start;
+  size_t _hash_start;
+  size_t _hash_end;
 
 
   int _flags;
   int _flags;
 };
 };

+ 1 - 1
panda/src/egg/eggFilenameNode.h

@@ -54,7 +54,7 @@ public:
     }
     }
   };
   };
 
 
-private:
+protected:
   Filename _filename;
   Filename _filename;
   Filename _fullpath;
   Filename _fullpath;
 
 

+ 8 - 22
panda/src/egg/eggGroupNode.cxx

@@ -33,7 +33,6 @@
 #include "pt_EggMaterial.h"
 #include "pt_EggMaterial.h"
 #include "config_egg.h"
 #include "config_egg.h"
 
 
-#include "hashFilename.h"
 #include "dSearchPath.h"
 #include "dSearchPath.h"
 #include "deg_2_rad.h"
 #include "deg_2_rad.h"
 #include "dcast.h"
 #include "dcast.h"
@@ -429,27 +428,14 @@ resolve_filenames(const DSearchPath &searchpath) {
     EggNode *child = *ci;
     EggNode *child = *ci;
     if (child->is_of_type(EggTexture::get_class_type())) {
     if (child->is_of_type(EggTexture::get_class_type())) {
       EggTexture *tex = DCAST(EggTexture, child);
       EggTexture *tex = DCAST(EggTexture, child);
-      if (tex->has_hash_filename()) {
-	HashFilename tex_filename = tex->get_filename();
-	tex_filename.resolve_filename(searchpath);
-	tex->set_filename(tex_filename);
-	
-	if (tex->has_alpha_filename()) {
-	  HashFilename alpha_filename = tex->get_alpha_filename();
-	  alpha_filename.resolve_filename(searchpath);
-	  tex->set_alpha_filename(alpha_filename);
-	}
-
-      } else {
-	Filename tex_filename = tex->get_filename();
-	tex_filename.resolve_filename(searchpath);
-	tex->set_filename(tex_filename);
-	
-	if (tex->has_alpha_filename()) {
-	  Filename alpha_filename = tex->get_alpha_filename();
-	  alpha_filename.resolve_filename(searchpath);
-	  tex->set_alpha_filename(alpha_filename);
-	}
+      Filename tex_filename = tex->get_filename();
+      tex_filename.resolve_filename(searchpath);
+      tex->set_filename(tex_filename);
+      
+      if (tex->has_alpha_filename()) {
+        Filename alpha_filename = tex->get_alpha_filename();
+        alpha_filename.resolve_filename(searchpath);
+        tex->set_alpha_filename(alpha_filename);
       }
       }
 
 
     } else if (child->is_of_type(EggFilenameNode::get_class_type())) {
     } else if (child->is_of_type(EggFilenameNode::get_class_type())) {

+ 6 - 15
panda/src/egg/eggTexture.I

@@ -17,21 +17,6 @@
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 
 
 
 
-////////////////////////////////////////////////////////////////////
-//     Function: EggTexture::has_hash_filename
-//       Access: Published
-//  Description: Returns true if the texture filename is expected to
-//               contain a hash mark standing in for a sequence
-//               number, or false if the filename is a literal
-//               filename.  This will be true only if TextureType is
-//               TT_3d_texture or TT_cube_map.
-////////////////////////////////////////////////////////////////////
-INLINE bool EggTexture::
-has_hash_filename() const {
-  return (_texture_type == TT_3d_texture ||
-	  _texture_type == TT_cube_map);
-}
-
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: EggTexture::set_texture_type
 //     Function: EggTexture::set_texture_type
 //       Access: Published
 //       Access: Published
@@ -40,6 +25,12 @@ has_hash_filename() const {
 INLINE void EggTexture::
 INLINE void EggTexture::
 set_texture_type(TextureType texture_type) {
 set_texture_type(TextureType texture_type) {
   _texture_type = texture_type;
   _texture_type = texture_type;
+
+  bool pattern_filename = 
+    (_texture_type == TT_3d_texture || _texture_type == TT_cube_map);
+
+  _filename.set_pattern(pattern_filename);
+  _fullpath.set_pattern(pattern_filename);
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////

+ 0 - 2
panda/src/egg/eggTexture.h

@@ -150,8 +150,6 @@ PUBLISHED:
     TG_point_sprite,
     TG_point_sprite,
   };
   };
 
 
-  INLINE bool has_hash_filename() const;
-
   INLINE void set_texture_type(TextureType texture_type);
   INLINE void set_texture_type(TextureType texture_type);
   INLINE TextureType get_texture_type() const;
   INLINE TextureType get_texture_type() const;
 
 

+ 2 - 2
panda/src/egg2pg/eggLoader.cxx

@@ -869,11 +869,11 @@ load_texture(TextureDef &def, const EggTexture *egg_tex) {
     break;
     break;
 
 
   case EggTexture::TT_3d_texture:
   case EggTexture::TT_3d_texture:
-    tex = TexturePool::load_3d_texture(HashFilename(egg_tex->get_fullpath()));
+    tex = TexturePool::load_3d_texture(egg_tex->get_fullpath());
     break;
     break;
 
 
   case EggTexture::TT_cube_map:
   case EggTexture::TT_cube_map:
-    tex = TexturePool::load_cube_map(HashFilename(egg_tex->get_fullpath()));
+    tex = TexturePool::load_cube_map(egg_tex->get_fullpath());
     break;
     break;
   }
   }
 
 

+ 25 - 0
panda/src/express/virtualFile.I

@@ -26,6 +26,18 @@ INLINE VirtualFile::
 VirtualFile() {
 VirtualFile() {
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: VirtualFile::get_original_filename
+//       Access: Published
+//  Description: Returns the original filename as it was used to
+//               locate this VirtualFile.  This is usually, but not
+//               always, the same string returned by get_filename().
+////////////////////////////////////////////////////////////////////
+INLINE const Filename &VirtualFile::
+get_original_filename() const {
+  return _original_filename;
+}
+
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: VirtualFile::read_file
 //     Function: VirtualFile::read_file
 //       Access: Public
 //       Access: Public
@@ -38,6 +50,19 @@ read_file() const {
   return result;
   return result;
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: VirtualFile::set_original_filename
+//       Access: Public
+//  Description: Stores the original filename that was used to locate
+//               this VirtualFile.  This is normally called only by
+//               the VirtualFileSystem, as it creates each
+//               VirtualFile.
+////////////////////////////////////////////////////////////////////
+INLINE void VirtualFile::
+set_original_filename(const Filename &filename) {
+  _original_filename = filename;
+}
+
 
 
 INLINE ostream &
 INLINE ostream &
 operator << (ostream &out, const VirtualFile &file) {
 operator << (ostream &out, const VirtualFile &file) {

+ 4 - 0
panda/src/express/virtualFile.h

@@ -43,6 +43,7 @@ public:
 PUBLISHED:
 PUBLISHED:
   virtual VirtualFileSystem *get_file_system() const=0;
   virtual VirtualFileSystem *get_file_system() const=0;
   virtual Filename get_filename() const=0;
   virtual Filename get_filename() const=0;
+  INLINE const Filename &get_original_filename() const;
 
 
   virtual bool is_directory() const;
   virtual bool is_directory() const;
   virtual bool is_regular_file() const;
   virtual bool is_regular_file() const;
@@ -59,6 +60,7 @@ PUBLISHED:
   virtual streampos get_file_size(istream *stream) const;
   virtual streampos get_file_size(istream *stream) const;
 
 
 public:
 public:
+  INLINE void set_original_filename(const Filename &filename);
   bool read_file(string &result) const;
   bool read_file(string &result) const;
   static bool read_file(istream *stream, string &result);
   static bool read_file(istream *stream, string &result);
   static bool read_file(istream *stream, string &result, size_t max_bytes);
   static bool read_file(istream *stream, string &result, size_t max_bytes);
@@ -71,6 +73,8 @@ protected:
 private:
 private:
   void r_ls_all(ostream &out, const Filename &root) const;
   void r_ls_all(ostream &out, const Filename &root) const;
 
 
+  Filename _original_filename;
+
 
 
 public:
 public:
   virtual TypeHandle get_type() const {
   virtual TypeHandle get_type() const {

+ 12 - 9
panda/src/express/virtualFileSystem.cxx

@@ -290,7 +290,7 @@ get_file(const Filename &filename) const {
     pathname = Filename(_cwd, filename);
     pathname = Filename(_cwd, filename);
   }
   }
   pathname.standardize();
   pathname.standardize();
-  string strpath = pathname.get_fullpath().substr(1);
+  string strpath = pathname.get_filename_index(0).get_fullpath().substr(1);
 
 
   // Now scan all the mount points, from the back (since later mounts
   // Now scan all the mount points, from the back (since later mounts
   // override more recent ones), until a match is found.
   // override more recent ones), until a match is found.
@@ -304,14 +304,14 @@ get_file(const Filename &filename) const {
     if (strpath == mount_point) {
     if (strpath == mount_point) {
       // Here's an exact match on the mount point.  This filename is
       // Here's an exact match on the mount point.  This filename is
       // the root directory of this mount object.
       // the root directory of this mount object.
-      if (found_match(found_file, composite_file, mount, "")) {
+      if (found_match(found_file, composite_file, mount, "", pathname)) {
         return found_file;
         return found_file;
       }
       }
     } else if (mount_point.empty()) {
     } else if (mount_point.empty()) {
       // This is the root mount point; all files are in here.
       // This is the root mount point; all files are in here.
       if (mount->has_file(strpath)) {
       if (mount->has_file(strpath)) {
         // Bingo!
         // Bingo!
-        if (found_match(found_file, composite_file, mount, strpath)) {
+        if (found_match(found_file, composite_file, mount, strpath, pathname)) {
           return found_file;
           return found_file;
         }
         }
       }            
       }            
@@ -322,7 +322,7 @@ get_file(const Filename &filename) const {
       Filename local_filename = strpath.substr(mount_point.length() + 1);
       Filename local_filename = strpath.substr(mount_point.length() + 1);
       if (mount->has_file(local_filename)) {
       if (mount->has_file(local_filename)) {
         // Bingo!
         // Bingo!
-        if (found_match(found_file, composite_file, mount, local_filename)) {
+        if (found_match(found_file, composite_file, mount, local_filename, pathname)) {
           return found_file;
           return found_file;
         }
         }
       }            
       }            
@@ -381,7 +381,7 @@ resolve_filename(Filename &filename,
   PT(VirtualFile) found;
   PT(VirtualFile) found;
 
 
   if (filename.is_local()) {
   if (filename.is_local()) {
-    found = find_file(filename.get_fullpath(), searchpath);
+    found = find_file(filename, searchpath);
 
 
     if (found.is_null()) {
     if (found.is_null()) {
       // We didn't find it with the given extension; can we try the
       // We didn't find it with the given extension; can we try the
@@ -389,7 +389,7 @@ resolve_filename(Filename &filename,
       if (filename.get_extension().empty() && !default_extension.empty()) {
       if (filename.get_extension().empty() && !default_extension.empty()) {
         Filename try_ext = filename;
         Filename try_ext = filename;
         try_ext.set_extension(default_extension);
         try_ext.set_extension(default_extension);
-        found = find_file(try_ext.get_fullpath(), searchpath);
+        found = find_file(try_ext, searchpath);
       }
       }
     }
     }
   } else {
   } else {
@@ -408,7 +408,7 @@ resolve_filename(Filename &filename,
   }
   }
 
 
   if (!found.is_null()) {
   if (!found.is_null()) {
-    filename = found->get_filename();
+    filename = found->get_original_filename();
     return true;
     return true;
   }
   }
 
 
@@ -670,10 +670,12 @@ normalize_mount_point(const string &mount_point) const {
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool VirtualFileSystem::
 bool VirtualFileSystem::
 found_match(PT(VirtualFile) &found_file, VirtualFileComposite *&composite_file,
 found_match(PT(VirtualFile) &found_file, VirtualFileComposite *&composite_file,
-            VirtualFileMount *mount, const string &local_filename) const {
+            VirtualFileMount *mount, const string &local_filename,
+            const Filename &original_filename) const {
   if (found_file == (VirtualFile *)NULL) {
   if (found_file == (VirtualFile *)NULL) {
     // This was our first match.  Save it.
     // This was our first match.  Save it.
     found_file = new VirtualFileSimple(mount, local_filename);
     found_file = new VirtualFileSimple(mount, local_filename);
+    found_file->set_original_filename(original_filename);
     if (!mount->is_directory(local_filename)) {
     if (!mount->is_directory(local_filename)) {
       // If it's not a directory, we're done.
       // If it's not a directory, we're done.
       return true;
       return true;
@@ -690,7 +692,8 @@ found_match(PT(VirtualFile) &found_file, VirtualFileComposite *&composite_file,
     // need a composite directory.
     // need a composite directory.
     if (composite_file == (VirtualFileComposite *)NULL) {
     if (composite_file == (VirtualFileComposite *)NULL) {
       composite_file =
       composite_file =
-        new VirtualFileComposite((VirtualFileSystem *)this, found_file->get_filename());
+        new VirtualFileComposite((VirtualFileSystem *)this, found_file->get_original_filename());
+      composite_file->set_original_filename(original_filename);
       composite_file->add_component(found_file);
       composite_file->add_component(found_file);
       found_file = composite_file;
       found_file = composite_file;
     }
     }

+ 2 - 1
panda/src/express/virtualFileSystem.h

@@ -94,7 +94,8 @@ public:
 private:
 private:
   Filename normalize_mount_point(const string &mount_point) const;
   Filename normalize_mount_point(const string &mount_point) const;
   bool found_match(PT(VirtualFile) &found_file, VirtualFileComposite *&composite_file,
   bool found_match(PT(VirtualFile) &found_file, VirtualFileComposite *&composite_file,
-                   VirtualFileMount *mount, const string &local_filename) const;
+                   VirtualFileMount *mount, const string &local_filename,
+                   const Filename &original_filename) const;
   static void parse_option(const string &option,
   static void parse_option(const string &option,
                            int &flags, string &password);
                            int &flags, string &password);
 
 

+ 12 - 11
panda/src/gobj/texture.cxx

@@ -29,7 +29,6 @@
 #include "preparedGraphicsObjects.h"
 #include "preparedGraphicsObjects.h"
 #include "pnmImage.h"
 #include "pnmImage.h"
 #include "virtualFileSystem.h"
 #include "virtualFileSystem.h"
-#include "hashFilename.h"
 
 
 #include <stddef.h>
 #include <stddef.h>
 
 
@@ -450,10 +449,11 @@ write(const Filename &name, int z) const {
 //               corresponding number of digits.
 //               corresponding number of digits.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Texture::
 bool Texture::
-read_pages(const HashFilename &fullpath_template, int z_size) {
-  if (!fullpath_template.has_hash()) {
+read_pages(Filename fullpath_pattern, int z_size) {
+  fullpath_pattern.set_pattern(true);
+  if (!fullpath_pattern.has_hash()) {
     gobj_cat.error()
     gobj_cat.error()
-      << "Template " << fullpath_template << " contains no hash marks.\n";
+      << "Template " << fullpath_pattern << " contains no hash marks.\n";
     return false;
     return false;
   }
   }
 
 
@@ -478,7 +478,7 @@ read_pages(const HashFilename &fullpath_template, int z_size) {
   if (z_size != 0) {
   if (z_size != 0) {
     set_z_size(z_size);
     set_z_size(z_size);
     for (int z = 0; z < z_size; z++) {
     for (int z = 0; z < z_size; z++) {
-      if (!read(fullpath_template.get_filename_index(z), z)) {
+      if (!read(fullpath_pattern.get_filename_index(z), z)) {
         return false;
         return false;
       }
       }
     }
     }
@@ -487,14 +487,14 @@ read_pages(const HashFilename &fullpath_template, int z_size) {
     int z = 0;
     int z = 0;
     VirtualFileSystem *vfs = VirtualFileSystem::get_global_ptr();
     VirtualFileSystem *vfs = VirtualFileSystem::get_global_ptr();
 
 
-    Filename file = fullpath_template.get_filename_index(z);
+    Filename file = fullpath_pattern.get_filename_index(z);
     while (vfs->exists(file)) {
     while (vfs->exists(file)) {
       if (!read(file, z)) {
       if (!read(file, z)) {
         return false;
         return false;
       }
       }
       ++z;
       ++z;
 
 
-      file = fullpath_template.get_filename_index(z);
+      file = fullpath_pattern.get_filename_index(z);
     }
     }
   }
   }
 
 
@@ -515,15 +515,16 @@ read_pages(const HashFilename &fullpath_template, int z_size) {
 //               corresponding number of digits.
 //               corresponding number of digits.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 bool Texture::
 bool Texture::
-write_pages(const HashFilename &fullpath_template) {
-  if (!fullpath_template.has_hash()) {
+write_pages(Filename fullpath_pattern) {
+  fullpath_pattern.set_pattern(true);
+  if (!fullpath_pattern.has_hash()) {
     gobj_cat.error()
     gobj_cat.error()
-      << "Template " << fullpath_template << " contains no hash marks.\n";
+      << "Template " << fullpath_pattern << " contains no hash marks.\n";
     return false;
     return false;
   }
   }
 
 
   for (int z = 0; z < _z_size; z++) {
   for (int z = 0; z < _z_size; z++) {
-    if (!write(fullpath_template.get_filename_index(z), z)) {
+    if (!write(fullpath_pattern.get_filename_index(z), z)) {
       return false;
       return false;
     }
     }
   }
   }

+ 2 - 3
panda/src/gobj/texture.h

@@ -31,7 +31,6 @@ class PNMImage;
 class TextureContext;
 class TextureContext;
 class FactoryParams;
 class FactoryParams;
 class PreparedGraphicsObjects;
 class PreparedGraphicsObjects;
-class HashFilename;
 class CullTraverser;
 class CullTraverser;
 class CullTraverserData;
 class CullTraverserData;
 
 
@@ -168,8 +167,8 @@ PUBLISHED:
 		    int primary_file_num_channels = 0, int alpha_file_channel = 0);
 		    int primary_file_num_channels = 0, int alpha_file_channel = 0);
   bool write(const Filename &fullpath, int z = 0) const;
   bool write(const Filename &fullpath, int z = 0) const;
 
 
-  bool read_pages(const HashFilename &fullpath_template, int z_size = 0);
-  bool write_pages(const HashFilename &fullpath_template);
+  bool read_pages(Filename fullpath_pattern, int z_size = 0);
+  bool write_pages(Filename fullpath_pattern);
 
 
   virtual bool load(const PNMImage &pnmimage, int z = 0);
   virtual bool load(const PNMImage &pnmimage, int z = 0);
   bool store(PNMImage &pnmimage, int z = 0) const;
   bool store(PNMImage &pnmimage, int z = 0) const;

+ 4 - 4
panda/src/gobj/texturePool.I

@@ -84,8 +84,8 @@ load_texture(const string &filename, const string &alpha_filename,
 //               filled in with the index number of each level.
 //               filled in with the index number of each level.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 INLINE Texture *TexturePool::
 INLINE Texture *TexturePool::
-load_3d_texture(const string &filename_template) {
-  return get_global_ptr()->ns_load_3d_texture(filename_template);
+load_3d_texture(const string &filename_pattern) {
+  return get_global_ptr()->ns_load_3d_texture(filename_pattern);
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
@@ -98,8 +98,8 @@ load_3d_texture(const string &filename_template) {
 //               the index number of each pagee.
 //               the index number of each pagee.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 INLINE Texture *TexturePool::
 INLINE Texture *TexturePool::
-load_cube_map(const string &filename_template) {
-  return get_global_ptr()->ns_load_cube_map(filename_template);
+load_cube_map(const string &filename_pattern) {
+  return get_global_ptr()->ns_load_cube_map(filename_pattern);
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////

+ 16 - 34
panda/src/gobj/texturePool.cxx

@@ -296,42 +296,33 @@ ns_load_texture(const Filename &orig_filename,
 //  Description: The nonstatic implementation of load_3d_texture().
 //  Description: The nonstatic implementation of load_3d_texture().
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 Texture *TexturePool::
 Texture *TexturePool::
-ns_load_3d_texture(const HashFilename &filename_template) {
-  // Look up filename 0 on the model path.
-  Filename filename = filename_template.get_filename_index(0);
-  if (!_fake_texture_image.empty()) {
-    filename = _fake_texture_image;
-  }
+ns_load_3d_texture(const Filename &filename_pattern) {
+  Filename filename(filename_pattern);
 
 
   VirtualFileSystem *vfs = VirtualFileSystem::get_global_ptr();
   VirtualFileSystem *vfs = VirtualFileSystem::get_global_ptr();
   vfs->resolve_filename(filename, get_texture_path()) ||
   vfs->resolve_filename(filename, get_texture_path()) ||
     vfs->resolve_filename(filename, get_model_path());
     vfs->resolve_filename(filename, get_model_path());
 
 
-  // Then, replace everything before the hash code with the directory
-  // we've found.
-  string hash = filename_template.get_hash_to_end();
-  HashFilename hash_filename(filename.substr(0, filename.length() - hash.length()) + hash);
-
   Textures::const_iterator ti;
   Textures::const_iterator ti;
-  ti = _textures.find(hash_filename);
+  ti = _textures.find(filename);
   if (ti != _textures.end()) {
   if (ti != _textures.end()) {
     // This texture was previously loaded.
     // This texture was previously loaded.
     return (*ti).second;
     return (*ti).second;
   }
   }
 
 
   gobj_cat.info()
   gobj_cat.info()
-    << "Loading 3-d texture " << hash_filename << "\n";
-  PT(Texture) tex = make_texture(hash_filename.get_extension());
+    << "Loading 3-d texture " << filename << "\n";
+  PT(Texture) tex = make_texture(filename.get_extension());
   tex->setup_3d_texture();
   tex->setup_3d_texture();
-  if (!tex->read_pages(hash_filename)) {
+  if (!tex->read_pages(filename)) {
     // This texture was not found or could not be read.
     // This texture was not found or could not be read.
     report_texture_unreadable(filename);
     report_texture_unreadable(filename);
   }
   }
 
 
   // Set the original filename, before we searched along the path.
   // Set the original filename, before we searched along the path.
-  tex->set_filename(filename_template);
+  tex->set_filename(filename_pattern);
 
 
-  _textures[hash_filename] = tex;
+  _textures[filename] = tex;
   return tex;
   return tex;
 }
 }
 
 
@@ -341,42 +332,33 @@ ns_load_3d_texture(const HashFilename &filename_template) {
 //  Description: The nonstatic implementation of load_cube_map().
 //  Description: The nonstatic implementation of load_cube_map().
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 Texture *TexturePool::
 Texture *TexturePool::
-ns_load_cube_map(const HashFilename &filename_template) {
-  // Look up filename 0 on the model path.
-  Filename filename = filename_template.get_filename_index(0);
-  if (!_fake_texture_image.empty()) {
-    filename = _fake_texture_image;
-  }
+ns_load_cube_map(const Filename &filename_pattern) {
+  Filename filename(filename_pattern);
 
 
   VirtualFileSystem *vfs = VirtualFileSystem::get_global_ptr();
   VirtualFileSystem *vfs = VirtualFileSystem::get_global_ptr();
   vfs->resolve_filename(filename, get_texture_path()) ||
   vfs->resolve_filename(filename, get_texture_path()) ||
     vfs->resolve_filename(filename, get_model_path());
     vfs->resolve_filename(filename, get_model_path());
 
 
-  // Then, replace everything before the hash code with the directory
-  // we've found.
-  string hash = filename_template.get_hash_to_end();
-  HashFilename hash_filename(filename.substr(0, filename.length() - hash.length()) + hash);
-
   Textures::const_iterator ti;
   Textures::const_iterator ti;
-  ti = _textures.find(hash_filename);
+  ti = _textures.find(filename);
   if (ti != _textures.end()) {
   if (ti != _textures.end()) {
     // This texture was previously loaded.
     // This texture was previously loaded.
     return (*ti).second;
     return (*ti).second;
   }
   }
 
 
   gobj_cat.info()
   gobj_cat.info()
-    << "Loading cube map texture " << hash_filename << "\n";
-  PT(Texture) tex = make_texture(hash_filename.get_extension());
+    << "Loading cube map texture " << filename << "\n";
+  PT(Texture) tex = make_texture(filename.get_extension());
   tex->setup_cube_map();
   tex->setup_cube_map();
-  if (!tex->read_pages(hash_filename)) {
+  if (!tex->read_pages(filename)) {
     // This texture was not found or could not be read.
     // This texture was not found or could not be read.
     report_texture_unreadable(filename);
     report_texture_unreadable(filename);
   }
   }
 
 
   // Set the original filename, before we searched along the path.
   // Set the original filename, before we searched along the path.
-  tex->set_filename(filename_template);
+  tex->set_filename(filename_pattern);
 
 
-  _textures[hash_filename] = tex;
+  _textures[filename] = tex;
   return tex;
   return tex;
 }
 }
 
 

+ 4 - 5
panda/src/gobj/texturePool.h

@@ -23,7 +23,6 @@
 #include "texture.h"
 #include "texture.h"
 #include "filename.h"
 #include "filename.h"
 #include "config_gobj.h"
 #include "config_gobj.h"
-#include "hashFilename.h"
 
 
 #include "pmap.h"
 #include "pmap.h"
 
 
@@ -48,8 +47,8 @@ PUBLISHED:
                                       const string &alpha_filename, 
                                       const string &alpha_filename, 
                                       int primary_file_num_channels = 0,
                                       int primary_file_num_channels = 0,
                                       int alpha_file_channel = 0);
                                       int alpha_file_channel = 0);
-  INLINE static Texture *load_3d_texture(const string &filename_template);
-  INLINE static Texture *load_cube_map(const string &filename_template);
+  INLINE static Texture *load_3d_texture(const string &filename_pattern);
+  INLINE static Texture *load_cube_map(const string &filename_pattern);
 
 
   INLINE static Texture *get_normalization_cube_map(int size);
   INLINE static Texture *get_normalization_cube_map(int size);
 
 
@@ -87,8 +86,8 @@ private:
                            const Filename &orig_alpha_filename, 
                            const Filename &orig_alpha_filename, 
                            int primary_file_num_channels,
                            int primary_file_num_channels,
                            int alpha_file_channel);
                            int alpha_file_channel);
-  Texture *ns_load_3d_texture(const HashFilename &filename_template);
-  Texture *ns_load_cube_map(const HashFilename &filename_template);
+  Texture *ns_load_3d_texture(const Filename &filename_pattern);
+  Texture *ns_load_cube_map(const Filename &filename_pattern);
   Texture *ns_get_normalization_cube_map(int size);
   Texture *ns_get_normalization_cube_map(int size);
 
 
   void ns_add_texture(Texture *texture);
   void ns_add_texture(Texture *texture);

+ 0 - 3
panda/src/putil/Sources.pp

@@ -32,7 +32,6 @@
     firstOfPairCompare.I firstOfPairCompare.h \
     firstOfPairCompare.I firstOfPairCompare.h \
     firstOfPairLess.I firstOfPairLess.h \
     firstOfPairLess.I firstOfPairLess.h \
     globalPointerRegistry.I globalPointerRegistry.h \
     globalPointerRegistry.I globalPointerRegistry.h \
-    hashFilename.I hashFilename.h \
     indirectCompareNames.I indirectCompareNames.h \
     indirectCompareNames.I indirectCompareNames.h \
     indirectCompareSort.I indirectCompareSort.h \
     indirectCompareSort.I indirectCompareSort.h \
     indirectCompareTo.I indirectCompareTo.h \
     indirectCompareTo.I indirectCompareTo.h \
@@ -74,7 +73,6 @@
     factoryBase.cxx \
     factoryBase.cxx \
     factoryParam.cxx factoryParams.cxx \
     factoryParam.cxx factoryParams.cxx \
     globalPointerRegistry.cxx \
     globalPointerRegistry.cxx \
-    hashFilename.cxx \
     ioPtaDatagramFloat.cxx \
     ioPtaDatagramFloat.cxx \
     ioPtaDatagramInt.cxx ioPtaDatagramShort.cxx \
     ioPtaDatagramInt.cxx ioPtaDatagramShort.cxx \
     keyboardButton.cxx lineStream.cxx lineStreamBuf.cxx \
     keyboardButton.cxx lineStream.cxx lineStreamBuf.cxx \
@@ -119,7 +117,6 @@
     firstOfPairCompare.I firstOfPairCompare.h \
     firstOfPairCompare.I firstOfPairCompare.h \
     firstOfPairLess.I firstOfPairLess.h \
     firstOfPairLess.I firstOfPairLess.h \
     globalPointerRegistry.I globalPointerRegistry.h \
     globalPointerRegistry.I globalPointerRegistry.h \
-    hashFilename.I hashFilename.h \
     indirectCompareNames.I indirectCompareNames.h \
     indirectCompareNames.I indirectCompareNames.h \
     indirectCompareSort.I indirectCompareSort.h \
     indirectCompareSort.I indirectCompareSort.h \
     indirectCompareTo.I indirectCompareTo.h \
     indirectCompareTo.I indirectCompareTo.h \

+ 0 - 112
panda/src/putil/hashFilename.I

@@ -1,112 +0,0 @@
-// Filename: hashFilename.I
-// Created by:  drose (02Aug05)
-//
-////////////////////////////////////////////////////////////////////
-//
-// PANDA 3D SOFTWARE
-// Copyright (c) 2001 - 2004, Disney Enterprises, Inc.  All rights reserved
-//
-// All use of this software is subject to the terms of the Panda 3d
-// Software license.  You should have received a copy of this license
-// along with this source code; you will also find a current copy of
-// the license at http://etc.cmu.edu/panda3d/docs/license/ .
-//
-// To contact the maintainers of this program write to
-// [email protected] .
-//
-////////////////////////////////////////////////////////////////////
-
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::Constructor
-//       Access: Published
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE HashFilename::
-HashFilename(const string &filename_pattern) :
-  Filename(filename_pattern)
-{
-  locate_hash();
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::Copy Constructor
-//       Access: Published
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE HashFilename::
-HashFilename(const HashFilename &copy) :
-  Filename(copy),
-  _hash_start(copy._hash_start),
-  _hash_end(copy._hash_end)
-{
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::Copy Constructor
-//       Access: Published
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE HashFilename::
-HashFilename(const Filename &copy) :
-  Filename(copy)
-{
-  locate_hash();
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::Copy Assignment Operator
-//       Access: Published
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE void HashFilename::
-operator = (const HashFilename &copy) {
-  Filename::operator = (copy);
-  _hash_start = copy._hash_start;
-  _hash_end = copy._hash_end;
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::Copy Assignment Operator
-//       Access: Published
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE void HashFilename::
-operator = (const Filename &copy) {
-  Filename::operator = (copy);
-  locate_hash();
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::Destructor
-//       Access: Published
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE HashFilename::
-~HashFilename() {
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::has_hash
-//       Access: Published
-//  Description: Returns true if the filename pattern did include a
-//               sequence of hash marks, false otherwise.  If this is
-//               true, then get_filename_index() will return a
-//               different filename each time.
-////////////////////////////////////////////////////////////////////
-INLINE bool HashFilename::
-has_hash() const {
-  return (_hash_start != _hash_end);
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::get_hash_to_end
-//       Access: Published
-//  Description: Returns the part of the filename beginning at the
-//               hash sequence (if any), and continuing to the end of
-//               the filename.
-////////////////////////////////////////////////////////////////////
-INLINE string HashFilename::
-get_hash_to_end() const {
-  return _filename.substr(_hash_start);
-}

+ 0 - 165
panda/src/putil/hashFilename.cxx

@@ -1,165 +0,0 @@
-// Filename: hashFilename.cxx
-// Created by:  drose (02Aug05)
-//
-////////////////////////////////////////////////////////////////////
-//
-// PANDA 3D SOFTWARE
-// Copyright (c) 2001 - 2004, Disney Enterprises, Inc.  All rights reserved
-//
-// All use of this software is subject to the terms of the Panda 3d
-// Software license.  You should have received a copy of this license
-// along with this source code; you will also find a current copy of
-// the license at http://etc.cmu.edu/panda3d/docs/license/ .
-//
-// To contact the maintainers of this program write to
-// [email protected] .
-//
-////////////////////////////////////////////////////////////////////
-
-#include "hashFilename.h"
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::get_filename_index
-//       Access: Published
-//  Description: Returns a Filename, derived from the HashFilename,
-//               with the sequence of hash marks (if any) replaced by
-//               the indicated index number.  If the HashFilename does
-//               not contain a sequence of hash marks, this quietly
-//               returns the original filename.
-////////////////////////////////////////////////////////////////////
-Filename HashFilename::
-get_filename_index(int index) const {
-  Filename file(*this);
-
-  if (_hash_end != _hash_start) {
-    ostringstream strm;
-    strm << _filename.substr(0, _hash_start) 
-	 << setw(_hash_end - _hash_start) << setfill('0') << index
-	 << _filename.substr(_hash_end);
-    file.set_fullpath(strm.str());
-  }
-
-  return file;
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::set_hash_to_end
-//       Access: Published
-//  Description: Replaces the part of the filename from the beginning
-//               of the hash sequence to the end of the filename.
-////////////////////////////////////////////////////////////////////
-void HashFilename::
-set_hash_to_end(const string &s) {
-  _filename.replace(_hash_start, string::npos, s);
-
-  locate_basename();
-  locate_extension();
-  locate_hash();
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::resolve_filename
-//       Access: Published
-//  Description: Searches the given search path for the filename.  If
-//               it is found, updates the filename to the full
-//               pathname found and returns true; otherwise, returns
-//               false.
-////////////////////////////////////////////////////////////////////
-bool HashFilename::
-resolve_filename(const DSearchPath &searchpath,
-                 const string &default_extension) {
-  if (!has_hash()) {
-    return Filename::resolve_filename(searchpath, default_extension);
-  }
-
-  Filename file0 = get_filename_index(0);
-  if (!file0.resolve_filename(searchpath, default_extension)) {
-    return false;
-  }
-
-  int change = file0.length() - length();
-
-  if (file0.length() < _hash_start || _hash_end + change < 0 ||
-      file0.substr(_hash_end + change) != substr(_hash_end)) {
-    // Hmm, somehow the suffix part of the filename--everything after
-    // the hash sequence--was changed by the above resolve operation.
-    // Abandon ship.
-    return false;
-  }
-
-  // Replace the prefix part of the filename--everything before the
-  // hash sequence.
-  _filename = file0.substr(0, _hash_start + change) + substr(_hash_start);
-  _hash_start += change;
-  _hash_end += change;
-
-  return true;
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::find_on_searchpath
-//       Access: Published
-//  Description: Performs the reverse of the resolve_filename()
-//               operation: assuming that the current filename is
-//               fully-specified pathname (i.e. beginning with '/'),
-//               look on the indicated search path for a directory
-//               under which the file can be found.  When found,
-//               adjust the Filename to be relative to the indicated
-//               directory name.
-//
-//               Returns the index of the directory on the searchpath
-//               at which the file was found, or -1 if it was not
-//               found.
-////////////////////////////////////////////////////////////////////
-int HashFilename::
-find_on_searchpath(const DSearchPath &searchpath) {
-  if (!has_hash()) {
-    return Filename::find_on_searchpath(searchpath);
-  }
-
-  Filename file0 = get_filename_index(0);
-  int index = file0.find_on_searchpath(searchpath);
-  if (index == -1) {
-    return -1;
-  }
-
-  int change = file0.length() - length();
-
-  if (file0.length() < _hash_start || _hash_end + change < 0 ||
-      file0.substr(_hash_end + change) != substr(_hash_end)) {
-    // Hmm, somehow the suffix part of the filename--everything after
-    // the hash sequence--was changed by the above resolve operation.
-    // Abandon ship.
-    return false;
-  }
-
-  // Replace the prefix part of the filename--everything before the
-  // hash sequence.
-  _filename = file0.substr(0, _hash_start + change) + substr(_hash_start);
-  _hash_start += change;
-  _hash_end += change;
-
-  return index;
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: HashFilename::locate_hash
-//       Access: Private
-//  Description: Identifies the part of the filename that contains the
-//               sequence of hash marks, if any.
-////////////////////////////////////////////////////////////////////
-void HashFilename::
-locate_hash() {
-  _hash_end = _filename.rfind('#');
-  if (_hash_end == string::npos) {
-    _hash_end = string::npos;
-    _hash_start = string::npos;
-
-  } else {
-    _hash_start = _hash_end;
-    ++_hash_end;
-    while (_hash_start > 0 && _filename[_hash_start - 1] == '#') {
-      --_hash_start;
-    }
-  }
-}

+ 0 - 65
panda/src/putil/hashFilename.h

@@ -1,65 +0,0 @@
-// Filename: hashFilename.h
-// Created by:  drose (02Aug05)
-//
-////////////////////////////////////////////////////////////////////
-//
-// PANDA 3D SOFTWARE
-// Copyright (c) 2001 - 2004, Disney Enterprises, Inc.  All rights reserved
-//
-// All use of this software is subject to the terms of the Panda 3d
-// Software license.  You should have received a copy of this license
-// along with this source code; you will also find a current copy of
-// the license at http://etc.cmu.edu/panda3d/docs/license/ .
-//
-// To contact the maintainers of this program write to
-// [email protected] .
-//
-////////////////////////////////////////////////////////////////////
-
-#ifndef HASHFILENAME_H
-#define HASHFILENAME_H
-
-#include "pandabase.h"
-#include "filename.h"
-
-////////////////////////////////////////////////////////////////////
-//       Class : HashFilename
-// Description : This is a specialization on Filename that is intended
-//               to be used to record a filename pattern for reading a
-//               numeric sequence of filenames in a directory; for
-//               instance, as used by TexturePool::load_cube_map().
-//
-//               The Filename may include a string of one or more hash
-//               marks ('#') in the basename or extension part.  These
-//               will be filled in with digits when
-//               get_filename_index() is called.
-////////////////////////////////////////////////////////////////////
-class EXPCL_PANDA HashFilename : public Filename {
-PUBLISHED:
-  INLINE HashFilename(const string &filename_pattern = string());
-  INLINE HashFilename(const HashFilename &copy);
-  INLINE HashFilename(const Filename &copy);
-  INLINE void operator = (const HashFilename &copy);
-  INLINE void operator = (const Filename &copy);
-  INLINE ~HashFilename();
-
-  INLINE bool has_hash() const;
-  Filename get_filename_index(int index) const;
-
-  INLINE string get_hash_to_end() const;
-  void set_hash_to_end(const string &s);
-
-  bool resolve_filename(const DSearchPath &searchpath,
-                        const string &default_extension = string());
-  int find_on_searchpath(const DSearchPath &searchpath);
-  
-private:
-  void locate_hash();
-
-  size_t _hash_start;
-  size_t _hash_end;
-};
-
-#include "hashFilename.I"
-
-#endif

+ 0 - 1
panda/src/putil/putil_composite1.cxx

@@ -18,7 +18,6 @@
 #include "factoryParam.cxx"
 #include "factoryParam.cxx"
 #include "factoryParams.cxx"
 #include "factoryParams.cxx"
 #include "globalPointerRegistry.cxx"
 #include "globalPointerRegistry.cxx"
-#include "hashFilename.cxx"
 #include "ioPtaDatagramFloat.cxx"
 #include "ioPtaDatagramFloat.cxx"
 #include "ioPtaDatagramInt.cxx"
 #include "ioPtaDatagramInt.cxx"
 #include "ioPtaDatagramShort.cxx"
 #include "ioPtaDatagramShort.cxx"