Пример #1
0
        /// <summary>
        /// Function to load a single dependency for a file.
        /// </summary>
        /// <param name="dependency">Dependency to load.</param>
        /// <param name="childDependencies">The dependencies for this dependency.</param>
        /// <returns>The loaded dependency object.</returns>
        private object LoadDependency(GorgonEditorDependency dependency, IReadOnlyDictionary <GorgonEditorDependency, object> childDependencies)
        {
            GorgonFileSystemFileEntry dependencyFile = FileSystem.GetFile(dependency.Path);

            if (dependencyFile == null)
            {
                throw new IOException(string.Format(Resources.GORFS_ERR_DEPENDENCY_NOT_FOUND, dependency.Path));
            }

            // Find a handler for this file.
            KeyValuePair <Type, Func <Stream, IReadOnlyDictionary <GorgonEditorDependency, object>, object> > handler =
                _fileHandlers.FirstOrDefault(item =>
                                             string.Equals(item.Key.FullName,
                                                           dependency.Type,
                                                           StringComparison.OrdinalIgnoreCase));

            if (handler.Key == null)
            {
                throw new IOException(string.Format(Resources.GORFS_ERR_FILE_NO_HANDLER, dependency.Path));
            }

            using (Stream dependencyStream = dependencyFile.OpenStream(false))
            {
                return(handler.Value(dependencyStream, childDependencies));
            }
        }
Пример #2
0
        /// <summary>
        /// Function to determine if the directory contains the specified file.
        /// </summary>
        /// <param name="file">File to look for.</param>
        /// <param name="searchChildren">[Optional] TRUE to search through child directories, FALSE to only search this directory.</param>
        /// <returns>TRUE if found, FALSE if not.</returns>
        /// <exception cref="System.ArgumentNullException">Thrown when the <paramref name="file"/> parameter is NULL (Nothing in VB.Net).</exception>
        public bool Contains(GorgonFileSystemFileEntry file, bool searchChildren = true)
        {
            if (file == null)
            {
                throw new ArgumentNullException("file");
            }

            return(Files.Any(item => item == file) ||
                   ((searchChildren) && (Directories.Any(directory => directory.Contains(file)))));
        }
Пример #3
0
        /// <summary>
        /// Function to load a file from the editor file.
        /// </summary>
        /// <typeparam name="T">The type of object to load.  Must be a reference type.</typeparam>
        /// <param name="path">Path to the file to load.</param>
        /// <remarks>
        /// Use this method to load a file from the file system generated by the editor. The type parameter T is used to determine how to load an object through a registered type loader.
        /// <para>The type loader is registered by supplying a type and a function to read in the file. This allows the developer to load in their own file formats if required. New loader types
        /// can be added through the <see cref="RegisteredEditorTypes"/> parameter.</para>
        /// <para>Without adding any new loader types Gorgon will support loading of its supported image codecs, sprites (for the 2D renderer), animations and fonts.  The loader will attempt to load
        /// any dependencies required by the requested file as well.</para>
        /// </remarks>
        public T ReadFile <T>(string path)
            where T : class
        {
            if (path == null)
            {
                throw new ArgumentNullException("path");
            }

            if (string.IsNullOrWhiteSpace(path))
            {
                throw new ArgumentException(Resources.GORFS_ERR_PARAMETER_MUST_NOT_BE_EMPTY, "path");
            }

            Type type = typeof(T);
            Func <Stream, IReadOnlyDictionary <GorgonEditorDependency, object>, object> loader;

            if (!_fileHandlers.TryGetValue(type, out loader))
            {
                throw new IOException(string.Format(Resources.GORFS_ERR_FILE_NO_HANDLER, path));
            }

            GorgonFileSystemFileEntry file = FileSystem.GetFile(path);

            if (file == null)
            {
                throw new IOException(string.Format(Resources.GORFS_ERR_FILE_NOT_FOUND, path));
            }

            // Load the meta data if it's not been loaded yet.
            if (_hasMetaData == null)
            {
                GetDependencies();
            }

            GorgonEditorDependencyCollection dependencies;
            IReadOnlyDictionary <GorgonEditorDependency, object> dependencyObjects = new Dictionary <GorgonEditorDependency, object>();

            // Check to see if the file has dependencies.
            if (Dependencies.TryGetValue(file.FullPath, out dependencies))
            {
                dependencyObjects = LoadDependencies(dependencies);
            }

            using (Stream fileStream = file.OpenStream(false))
            {
                return((T)loader(fileStream, dependencyObjects));
            }
        }
Пример #4
0
        /// <summary>
        /// Initializes a new instance of the <see cref="GorgonFileSystemStream"/> class.
        /// </summary>
        /// <param name="file">File being read/written.</param>
        /// <param name="baseStream">The underlying stream to use for this stream.</param>
        /// <exception cref="System.ArgumentNullException">Thrown when the <paramref name="baseStream"/> or the <paramref name="file"/> parameter is NULL (Nothing in VB.Net).</exception>
        public GorgonFileSystemStream(GorgonFileSystemFileEntry file, Stream baseStream)
        {
            if (file == null)
            {
                throw new ArgumentNullException("file");
            }
            if (baseStream == null)
            {
                throw new ArgumentNullException("baseStream");
            }

            CloseUnderlyingStream = true;
            _baseStream           = baseStream;
            FileEntry             = file;

            // Reset the position to the beginning.
            if (_baseStream.CanSeek)
            {
                _baseStream.Position = 0;
            }
        }
Пример #5
0
        /// <summary>
        /// Function called when a file is read from the provider.
        /// </summary>
        /// <param name="file">File to read.</param>
        /// <returns>The file data stored in a byte array or NULL if the file could not be read.</returns>
        /// <remarks>Implementors must implement this method to read the file from the physical file system.</remarks>
        protected internal virtual byte[] OnReadFile(GorgonFileSystemFileEntry file)
        {
            byte[] data;

            // Return an empty file if the file does not exist on the physical file system.
            if (!File.Exists(file.PhysicalFileSystemPath))
            {
                return(new byte[0]);
            }

            using (FileStream stream = File.Open(file.PhysicalFileSystemPath, FileMode.Open, FileAccess.Read, FileShare.Read))
            {
                data = new byte[stream.Length];

                if (stream.Length > 0)
                {
                    stream.Read(data, 0, (int)stream.Length);
                }
            }

            return(data);
        }
Пример #6
0
 /// <summary>
 /// Function called when a file is opened as a file stream.
 /// </summary>
 /// <param name="file">File to open.</param>
 /// <returns>The open <see cref="GorgonFileSystemStream"/> file stream object.</returns>
 protected internal virtual GorgonFileSystemStream OnOpenFileStream(GorgonFileSystemFileEntry file)
 {
     return(new GorgonFileSystemStream(file, File.Open(file.PhysicalFileSystemPath, FileMode.Open, FileAccess.Read, FileShare.Read)));
 }
Пример #7
0
        /// <summary>
        /// Function to retrieve the dependencies file and process it.
        /// </summary>
        private void GetDependencies()
        {
            if ((_hasMetaData != null) &&
                (!_hasMetaData.Value))
            {
                return;
            }

            // If we've already loaded the file system meta data for this file system, then leave.
            if (_metaDataFile != null)
            {
                return;
            }

            GorgonFileSystemFileEntry file = FileSystem.GetFile(MetaDataFile);

            if (file == null)
            {
                _hasMetaData = false;
                return;
            }

            // Create and load the object.
            using (Stream metaFile = file.OpenStream(false))
            {
                _metaDataFile = XDocument.Load(metaFile);
            }

            XElement rootNode = _metaDataFile.Element(MetaDataRootName);

            if (rootNode == null)
            {
                _hasMetaData = false;
                return;
            }

            XElement dependencyNode = rootNode.Element(ContentDependencyFiles);

            if (dependencyNode == null)
            {
                _hasMetaData = false;
                return;
            }

            IEnumerable <XElement> fileNodes = dependencyNode.Elements(FileNode);
            var dependencies = new Dictionary <string, GorgonEditorDependencyCollection>();

            // Lock here because we're updating a collection that's not thread safe.
            foreach (XElement fileNode in fileNodes)
            {
                XAttribute path = fileNode.Attribute(NameAttr);

                if ((path == null) ||
                    (string.IsNullOrWhiteSpace(path.Value)))
                {
                    continue;
                }

                dependencies.Add(path.Value,
                                 GorgonEditorDependencyCollection
                                 .Deserialize(fileNode.Elements(GorgonEditorDependency.DependencyNode)));
            }

            Dependencies = dependencies;

            _hasMetaData = Dependencies.Count > 0;
        }