Main Page   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members  

panda/src/express/virtualFile.cxx

Go to the documentation of this file.
00001 // Filename: virtualFile.cxx
00002 // Created by:  drose (03Aug02)
00003 //
00004 ////////////////////////////////////////////////////////////////////
00005 //
00006 // PANDA 3D SOFTWARE
00007 // Copyright (c) 2001, Disney Enterprises, Inc.  All rights reserved
00008 //
00009 // All use of this software is subject to the terms of the Panda 3d
00010 // Software license.  You should have received a copy of this license
00011 // along with this source code; you will also find a current copy of
00012 // the license at http://www.panda3d.org/license.txt .
00013 //
00014 // To contact the maintainers of this program write to
00015 // panda3d@yahoogroups.com .
00016 //
00017 ////////////////////////////////////////////////////////////////////
00018 
00019 #include "virtualFile.h"
00020 #include "virtualFileSystem.h"
00021 #include "virtualFileList.h"
00022 #include "config_express.h"
00023 
00024 TypeHandle VirtualFile::_type_handle;
00025 
00026 ////////////////////////////////////////////////////////////////////
00027 //     Function: VirtualFile::is_directory
00028 //       Access: Published, Virtual
00029 //  Description: Returns true if this file represents a directory (and
00030 //               scan_directory() may be called), false otherwise.
00031 ////////////////////////////////////////////////////////////////////
00032 bool VirtualFile::
00033 is_directory() const {
00034   return false;
00035 }
00036 
00037 ////////////////////////////////////////////////////////////////////
00038 //     Function: VirtualFile::is_regular_file
00039 //       Access: Published, Virtual
00040 //  Description: Returns true if this file represents a regular file
00041 //               (and read_file() may be called), false otherwise.
00042 ////////////////////////////////////////////////////////////////////
00043 bool VirtualFile::
00044 is_regular_file() const {
00045   return false;
00046 }
00047 
00048 ////////////////////////////////////////////////////////////////////
00049 //     Function: VirtualFile::scan_directory
00050 //       Access: Published
00051 //  Description: If the file represents a directory (that is,
00052 //               is_directory() returns true), this returns the list
00053 //               of files within the directory at the current time.
00054 //               Returns NULL if the file is not a directory or if the
00055 //               directory cannot be read.
00056 ////////////////////////////////////////////////////////////////////
00057 PT(VirtualFileList) VirtualFile::
00058 scan_directory() const {
00059   // First, we have to make sure there aren't any mount points attached
00060   // under this directory.  These will override any local filenames.
00061   VirtualFileSystem *file_system = get_file_system();
00062   Filename this_filename = get_filename();
00063   vector_string mount_points_flat;
00064   file_system->scan_mount_points(mount_points_flat, this_filename);
00065 
00066   // Copy the set of nested mount points to a sorted list so we can
00067   // search it quickly.
00068   ov_set<string> mount_points;
00069   copy(mount_points_flat.begin(), mount_points_flat.end(),
00070        back_inserter(mount_points));
00071   mount_points.sort();
00072 
00073   
00074   PT(VirtualFileList) file_list = new VirtualFileList;
00075 
00076   // Each of those mount points maps to a directory root or something
00077   // from the file system.
00078   ov_set<string>::const_iterator mi;
00079   for (mi = mount_points.begin(); mi != mount_points.end(); ++mi) {
00080     const string &basename = (*mi);
00081     Filename filename(this_filename, basename);
00082     PT(VirtualFile) file = file_system->get_file(filename);
00083     file_list->add_file(file);
00084   }
00085 
00086   // Now, get the actual local files in this directory.
00087   vector_string names;
00088   if (!scan_local_directory(file_list, mount_points)) {
00089     // Not a directory, or unable to read directory.
00090     if (file_list->get_num_files() == 0) {
00091       return NULL;
00092     }
00093 
00094     // We couldn't read the physical directory, but we do have some
00095     // mounted files to return.
00096     return file_list;
00097   }
00098 
00099   return file_list;
00100 }
00101 
00102 ////////////////////////////////////////////////////////////////////
00103 //     Function: VirtualFile::output
00104 //       Access: Published
00105 //  Description: 
00106 ////////////////////////////////////////////////////////////////////
00107 void VirtualFile::
00108 output(ostream &out) const {
00109   out << get_filename();
00110 }
00111 
00112 ////////////////////////////////////////////////////////////////////
00113 //     Function: VirtualFile::ls
00114 //       Access: Published
00115 //  Description: If the file represents a directory, lists its
00116 //               contents.
00117 ////////////////////////////////////////////////////////////////////
00118 void VirtualFile::
00119 ls(ostream &out) const {
00120   CPT(VirtualFileList) contents = scan_directory();
00121   if (contents == (VirtualFileList *)NULL) {
00122     if (!is_directory()) {
00123       out << get_filename() << "\n";
00124     } else {
00125       out << get_filename() << " cannot be read.\n";
00126     }
00127     return;
00128   }
00129 
00130   int num_files = contents->get_num_files();
00131   for (int i = 0; i < num_files; i++) {
00132     VirtualFile *file = contents->get_file(i);
00133     out << file->get_filename().get_basename() << "\n";
00134   }
00135 }
00136 
00137 ////////////////////////////////////////////////////////////////////
00138 //     Function: VirtualFile::ls_all
00139 //       Access: Published
00140 //  Description: If the file represents a directory, recursively lists
00141 //               its contents and those of all subdirectories.
00142 ////////////////////////////////////////////////////////////////////
00143 void VirtualFile::
00144 ls_all(ostream &out) const {
00145   if (!is_directory()) {
00146     out << get_filename() << " is not a directory.\n";
00147   } else {
00148     r_ls_all(out, get_filename());
00149   }
00150 }
00151 
00152 ////////////////////////////////////////////////////////////////////
00153 //     Function: VirtualFile::open_read_file
00154 //       Access: Published, Virtual
00155 //  Description: Opens the file for reading.  Returns a newly
00156 //               allocated istream on success (which you should
00157 //               eventually delete when you are done reading).
00158 //               Returns NULL on failure.
00159 ////////////////////////////////////////////////////////////////////
00160 istream *VirtualFile::
00161 open_read_file() const {
00162   return NULL;
00163 }
00164 
00165 ////////////////////////////////////////////////////////////////////
00166 //     Function: VirtualFile::read_file
00167 //       Access: Public
00168 //  Description: Fills up the indicated string with the contents of
00169 //               the file, if it is a regular file.  Returns true on
00170 //               success, false otherwise.
00171 ////////////////////////////////////////////////////////////////////
00172 bool VirtualFile::
00173 read_file(string &result) const {
00174   result = string();
00175 
00176   istream *in = open_read_file();
00177   if (in == (istream *)NULL) {
00178     express_cat.info()
00179       << "Unable to read " << get_filename() << "\n";
00180     return false;
00181   }
00182   int byte = in->get();
00183   while (!in->eof() && !in->fail()) {
00184     result += (char)byte;
00185     byte = in->get();
00186   }
00187   bool failed = in->fail() && !in->eof();
00188   delete in;
00189 
00190   if (failed) {
00191     express_cat.info()
00192       << "Error while reading " << get_filename() << "\n";
00193   }
00194   return !failed;
00195 }
00196 
00197 ////////////////////////////////////////////////////////////////////
00198 //     Function: VirtualFile::scan_local_directory
00199 //       Access: Protected, Virtual
00200 //  Description: Fills file_list up with the list of files that are
00201 //               within this directory, excluding those whose
00202 //               basenames are listed in mount_points.  Returns true
00203 //               if successful, false if the file is not a directory
00204 //               or the directory cannot be read.
00205 ////////////////////////////////////////////////////////////////////
00206 bool VirtualFile::
00207 scan_local_directory(VirtualFileList *, const ov_set<string> &) const {
00208   return false;
00209 }
00210 
00211 ////////////////////////////////////////////////////////////////////
00212 //     Function: VirtualFile::r_ls_all
00213 //       Access: Private
00214 //  Description: The recursive implementation of ls_all().
00215 ////////////////////////////////////////////////////////////////////
00216 void VirtualFile::
00217 r_ls_all(ostream &out, const Filename &root) const {
00218   CPT(VirtualFileList) contents = scan_directory();
00219   if (contents == (VirtualFileList *)NULL) {
00220     return;
00221   }
00222 
00223   int num_files = contents->get_num_files();
00224   for (int i = 0; i < num_files; i++) {
00225     VirtualFile *file = contents->get_file(i);
00226     Filename filename = file->get_filename();
00227     filename.make_relative_to(root);
00228     out << filename << "\n";
00229     if (file->is_directory()) {
00230       file->r_ls_all(out, root);
00231     }
00232   }
00233 }

Generated on Fri May 2 00:38:46 2003 for Panda by doxygen1.3