Class responsible for rendering map files, in a dedicated thread.
コード例 #1
0
ファイル: MapRenderer.cs プロジェクト: fragmer/fCraft
        static int Main(string[] args) {
            Logger.Logged += OnLogged;
            Logger.DisableFileLogging();

            ReturnCode optionParsingResult = ParseOptions(args);
            if (optionParsingResult != ReturnCode.Success) {
                return (int)optionParsingResult;
            }

            // parse importer name
            if (importerName != null && !importerName.Equals("auto", StringComparison.OrdinalIgnoreCase)) {
                MapFormat importFormat;
                if (!EnumUtil.TryParse(importerName, out importFormat, true)) {
                    Console.Error.WriteLine("Unsupported importer \"{0}\"", importerName);
                    PrintUsage();
                    return (int)ReturnCode.UnrecognizedImporter;
                }
                p.MapImporter = MapUtility.GetImporter(importFormat);
                if (p.MapImporter == null) {
                    Console.Error.WriteLine("Loading from \"{0}\" is not supported", importFormat);
                    PrintUsage();
                    return (int)ReturnCode.UnsupportedLoadFormat;
                }
            }

            // check input paths
            bool hadFile = false,
                 hadDir = false;
            foreach (string inputPath in p.InputPathList) {
                if (hadDir) {
                    Console.Error.WriteLine("MapRenderer: Only one directory may be specified at a time.");
                    return (int)ReturnCode.ArgumentError;
                }
                // check if input path exists, and if it's a file or directory
                try {
                    if (File.Exists(inputPath)) {
                        hadFile = true;
                    } else if (Directory.Exists(inputPath)) {
                        hadDir = true;
                        if (hadFile) {
                            Console.Error.WriteLine("MapRenderer: Cannot mix directories and files in input.");
                            return (int)ReturnCode.ArgumentError;
                        }
                        p.DirectoryMode = true;
                        if (!p.OutputDirGiven) {
                            p.OutputDirName = inputPath;
                        }
                    } else {
                        Console.Error.WriteLine("MapRenderer: Cannot locate \"{0}\"", inputPath);
                        return (int)ReturnCode.InputPathNotFound;
                    }
                } catch (Exception ex) {
                    Console.Error.WriteLine("MapRenderer: {0}: {1}",
                                            ex.GetType().Name,
                                            ex.Message);
                    return (int)ReturnCode.PathError;
                }
            }

            // initialize image encoder
            ImageCodecInfo[] codecs = ImageCodecInfo.GetImageDecoders();
            p.ImageEncoder = codecs.FirstOrDefault(codec => codec.FormatID == p.ExportFormat.Guid);
            if (p.ImageEncoder == null) {
                Console.Error.WriteLine("MapRenderer: Specified image encoder is not supported.");
                return (int)ReturnCode.UnsupportedSaveFormat;
            }

            // check recursive flag
            if (p.Recursive && !p.DirectoryMode) {
                Console.Error.WriteLine("MapRenderer: Recursive flag is given, but input is not a directory.");
                return (int)ReturnCode.ArgumentError;
            }

            // check input filter
            if (p.InputFilter != null && !p.DirectoryMode) {
                Console.Error.WriteLine("MapRenderer: Filter param is given, but input is not a directory.");
                return (int)ReturnCode.ArgumentError;
            }

            // check regex filter
            if (p.UseRegex) {
                try {
                    p.FilterRegex = new Regex(p.InputFilter);
                } catch (ArgumentException ex) {
                    Console.Error.WriteLine("MapRenderer: Cannot parse filter regex: {0}",
                                            ex.Message);
                    return (int)ReturnCode.ArgumentError;
                }
            }

            // check if output dir exists; create it if needed
            if (p.OutputDirName != null) {
                try {
                    if (!Directory.Exists(p.OutputDirName)) {
                        Directory.CreateDirectory(p.OutputDirName);
                    }
                } catch (Exception ex) {
                    Console.Error.WriteLine("MapRenderer: Error checking output directory: {0}: {1}",
                                            ex.GetType().Name,
                                            ex.Message);
                }
            }

            Console.Write("Counting files... ");

            // process inputs, one path at a time
            foreach (string inputPath in p.InputPathList) {
                ProcessInputPath(inputPath);
            }
            int totalFiles = InputPaths.Count;
            Console.WriteLine(totalFiles);

            if (totalFiles > 0) {
                int actualThreadCount = Math.Min(p.ThreadCount, InputPaths.Count);
                RenderWorker[] workers = new RenderWorker[actualThreadCount];
                for (int i = 0; i < workers.Length; i++) {
                    workers[i] = new RenderWorker(WorkQueue, ResultQueue, p);
                    workers[i].Start();
                }

                int inputsProcessed = 0;
                int resultsProcessed = 0;
                while (resultsProcessed < totalFiles) {
                    if (inputsProcessed < totalFiles) {
                        // load and enqueue another map for rendering
                        if (WorkQueue.Count < actualThreadCount) {
                            RenderTask newTask = InputPaths.Dequeue();
                            if (LoadMap(newTask)) {
                                WorkQueue.Add(newTask);
                            } else {
                                resultsProcessed++;
                            }
                            inputsProcessed++;
                        } else {
                            Thread.Sleep(1);
                        }

                        // try dequeue a rendered image for saving
                        RenderTask resultTask;
                        if (ResultQueue.TryTake(out resultTask)) {
                            int percent = (resultsProcessed*100 + 100)/totalFiles;
                            SaveImage(percent, resultTask);
                            resultsProcessed++;
                        }
                    } else {
                        // no more maps to load -- just wait for results
                        int percent = (resultsProcessed*100 + 100)/totalFiles;
                        SaveImage(percent, ResultQueue.Take());
                        resultsProcessed++;
                    }
                }
            }

            Console.WriteLine("MapRenderer: Processed {0} files in {1:0.00} seconds",
                              totalFiles,
                              DateTime.UtcNow.Subtract(StartTime).TotalSeconds);
            return (int)ReturnCode.Success;
        }
コード例 #2
0
        static int Main(string[] args)
        {
            Logger.Logged += OnLogged;
            Logger.DisableFileLogging();

            ReturnCode optionParsingResult = ParseOptions(args);

            if (optionParsingResult != ReturnCode.Success)
            {
                return((int)optionParsingResult);
            }

            // parse importer name
            if (importerName != null && !importerName.Equals("auto", StringComparison.OrdinalIgnoreCase))
            {
                MapFormat importFormat;
                if (!EnumUtil.TryParse(importerName, out importFormat, true))
                {
                    Console.Error.WriteLine("Unsupported importer \"{0}\"", importerName);
                    PrintUsage();
                    return((int)ReturnCode.UnrecognizedImporter);
                }
                p.MapImporter = MapUtility.GetImporter(importFormat);
                if (p.MapImporter == null)
                {
                    Console.Error.WriteLine("Loading from \"{0}\" is not supported", importFormat);
                    PrintUsage();
                    return((int)ReturnCode.UnsupportedLoadFormat);
                }
            }

            // check input paths
            bool hadFile = false,
                 hadDir  = false;

            foreach (string inputPath in p.InputPathList)
            {
                if (hadDir)
                {
                    Console.Error.WriteLine("MapRenderer: Only one directory may be specified at a time.");
                    return((int)ReturnCode.ArgumentError);
                }
                // check if input path exists, and if it's a file or directory
                try {
                    if (File.Exists(inputPath))
                    {
                        hadFile = true;
                    }
                    else if (Directory.Exists(inputPath))
                    {
                        hadDir = true;
                        if (hadFile)
                        {
                            Console.Error.WriteLine("MapRenderer: Cannot mix directories and files in input.");
                            return((int)ReturnCode.ArgumentError);
                        }
                        p.DirectoryMode = true;
                        if (!p.OutputDirGiven)
                        {
                            p.OutputDirName = inputPath;
                        }
                    }
                    else
                    {
                        Console.Error.WriteLine("MapRenderer: Cannot locate \"{0}\"", inputPath);
                        return((int)ReturnCode.InputPathNotFound);
                    }
                } catch (Exception ex) {
                    Console.Error.WriteLine("MapRenderer: {0}: {1}",
                                            ex.GetType().Name,
                                            ex.Message);
                    return((int)ReturnCode.PathError);
                }
            }

            // initialize image encoder
            ImageCodecInfo[] codecs = ImageCodecInfo.GetImageDecoders();
            p.ImageEncoder = codecs.FirstOrDefault(codec => codec.FormatID == p.ExportFormat.Guid);
            if (p.ImageEncoder == null)
            {
                Console.Error.WriteLine("MapRenderer: Specified image encoder is not supported.");
                return((int)ReturnCode.UnsupportedSaveFormat);
            }

            // check recursive flag
            if (p.Recursive && !p.DirectoryMode)
            {
                Console.Error.WriteLine("MapRenderer: Recursive flag is given, but input is not a directory.");
                return((int)ReturnCode.ArgumentError);
            }

            // check input filter
            if (p.InputFilter != null && !p.DirectoryMode)
            {
                Console.Error.WriteLine("MapRenderer: Filter param is given, but input is not a directory.");
                return((int)ReturnCode.ArgumentError);
            }

            // check regex filter
            if (p.UseRegex)
            {
                try {
                    p.FilterRegex = new Regex(p.InputFilter);
                } catch (ArgumentException ex) {
                    Console.Error.WriteLine("MapRenderer: Cannot parse filter regex: {0}",
                                            ex.Message);
                    return((int)ReturnCode.ArgumentError);
                }
            }

            // check if output dir exists; create it if needed
            if (p.OutputDirName != null)
            {
                try {
                    if (!Directory.Exists(p.OutputDirName))
                    {
                        Directory.CreateDirectory(p.OutputDirName);
                    }
                } catch (Exception ex) {
                    Console.Error.WriteLine("MapRenderer: Error checking output directory: {0}: {1}",
                                            ex.GetType().Name, ex.Message);
                }
            }

            Console.Write("Counting files... ");

            // process inputs, one path at a time
            foreach (string inputPath in p.InputPathList)
            {
                ProcessInputPath(inputPath);
            }
            int totalFiles = InputPaths.Count;

            Console.WriteLine(totalFiles);

            if (totalFiles > 0)
            {
                int            actualThreadCount = Math.Min(p.ThreadCount, InputPaths.Count);
                RenderWorker[] workers           = new RenderWorker[actualThreadCount];
                for (int i = 0; i < workers.Length; i++)
                {
                    workers[i] = new RenderWorker(WorkQueue, ResultQueue, p);
                    workers[i].Start();
                }

                int inputsProcessed  = 0;
                int resultsProcessed = 0;
                while (resultsProcessed < totalFiles)
                {
                    if (inputsProcessed < totalFiles)
                    {
                        // load and enqueue another map for rendering
                        if (WorkQueue.Count < actualThreadCount)
                        {
                            RenderTask newTask = InputPaths.Dequeue();
                            if (LoadMap(newTask))
                            {
                                WorkQueue.Enqueue(newTask);
                            }
                            else
                            {
                                resultsProcessed++;
                            }
                            inputsProcessed++;
                        }
                        else
                        {
                            Thread.Sleep(1);
                        }

                        // try dequeue a rendered image for saving
                        RenderTask resultTask;
                        if (ResultQueue.TryDequeue(out resultTask))
                        {
                            int percent = (resultsProcessed * 100 + 100) / totalFiles;
                            SaveImage(percent, resultTask);
                            resultsProcessed++;
                        }
                    }
                    else
                    {
                        // no more maps to load -- just wait for results
                        int percent = (resultsProcessed * 100 + 100) / totalFiles;
                        SaveImage(percent, ResultQueue.WaitDequeue());
                        resultsProcessed++;
                    }
                }
            }

            Console.WriteLine("MapRenderer: Processed {0} files in {1:0.00} seconds",
                              totalFiles,
                              DateTime.UtcNow.Subtract(StartTime).TotalSeconds);
            return((int)ReturnCode.Success);
        }