public EngineResult Execute() { try { _logger.Info("Initializing virtual filesystem"); var mapStream = File.Open(Settings.InputFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); VirtualFile vmapFile; var mixMap = new MixFile(mapStream, Settings.InputFile, 0, mapStream.Length, false, false); if (mixMap.IsValid()) // input max is a mix { var mapArchive = new MixFile(mapStream, Path.GetFileName(Settings.InputFile), true); // grab the largest file in the archive var mixEntry = mapArchive.Index.OrderByDescending(me => me.Value.Length).First(); vmapFile = mapArchive.OpenFile(mixEntry.Key); } else { vmapFile = new VirtualFile(mapStream, Path.GetFileName(Settings.InputFile), true); } var mapFile = new MapFile(vmapFile, Path.GetFileName(Settings.InputFile)); if (!string.IsNullOrEmpty(Settings.ModConfig)) { if (File.Exists(Settings.ModConfig)) { ModConfig cfg; try { using (FileStream f = File.OpenRead(Settings.ModConfig)) cfg = ModConfig.Deserialize(f); ModConfig.ActiveConfig = cfg; if (Settings.Engine != EngineType.AutoDetect) { if (Settings.Engine != cfg.Engine) { _logger.Warn("Provided engine override does not match mod config."); } } else { Settings.Engine = ModConfig.ActiveConfig.Engine; } } catch (IOException) { _logger.Fatal("IOException while loading mod config"); } catch (XmlException) { _logger.Fatal("XmlException while loading mod config"); } catch (SerializationException) { _logger.Fatal("Serialization exception while loading mod config"); } } else { _logger.Fatal("Invalid mod config file specified"); } } if (Settings.Engine == EngineType.AutoDetect) { Settings.Engine = EngineDetector.DetectEngineType(mapFile); _logger.Info("Engine autodetect result: {0}", Settings.Engine); } // --------------------------------------------------------------- // Code to organize moving of maps in a directory for themselves /* * string mapName = DetermineMapName(mapFile, Settings.Engine); * string ndir = Path.Combine(Path.GetDirectoryName(Settings.InputFile), mapName); * if (!Directory.Exists(ndir)) Directory.CreateDirectory(ndir); * mapFile.Close(); * mapFile.Dispose(); * File.Move(Settings.InputFile, Path.Combine(ndir, Path.GetFileName(mapFile.FileName))); * return 0;*/ // --------------------------------------------------------------- // enginetype is now definitive, load mod config if (ModConfig.ActiveConfig == null) { ModConfig.LoadDefaultConfig(Settings.Engine); } // first add the dirs, then load the extra mixes, then scan the dirs foreach (string modDir in ModConfig.ActiveConfig.Directories) { VFS.Add(modDir); } // add mixdir to VFS (if it's not included in the mod config) if (!ModConfig.ActiveConfig.Directories.Any()) { string mixDir = VFS.DetermineMixDir(Settings.MixFilesDirectory, Settings.Engine); VFS.Add(mixDir); } foreach (string mixFile in ModConfig.ActiveConfig.ExtraMixes) { VFS.Add(mixFile); } VFS.Instance.LoadMixes(Settings.Engine); var map = new Map.Map { IgnoreLighting = Settings.IgnoreLighting, StartPosMarking = Settings.StartPositionMarking, MarkOreFields = Settings.MarkOreFields }; if (!map.Initialize(mapFile, Settings.Engine, ModConfig.ActiveConfig.CustomRulesIniFiles, ModConfig.ActiveConfig.CustomArtIniFiles)) { _logger.Error("Could not successfully load this map. Try specifying the engine type manually."); return(EngineResult.LoadRulesFailed); } if (!map.LoadTheater()) { _logger.Error("Could not successfully load all required components for this map. Aborting."); return(EngineResult.LoadTheaterFailed); } if (Settings.StartPositionMarking == StartPositionMarking.Tiled) { map.MarkTiledStartPositions(); } if (Settings.MarkOreFields) { map.MarkOreAndGems(); } if (Settings.FixupTiles) { map.FixupTileLayer(); } map.Draw(); if (Settings.StartPositionMarking == StartPositionMarking.Squared) { map.DrawSquaredStartPositions(); } #if DEBUG // ==================================================================================== using (var form = new DebugDrawingSurfaceWindow(map.GetDrawingSurface(), map.GetTiles(), map.GetTheater(), map)) { form.RequestTileEvaluate += map.DebugDrawTile; form.ShowDialog(); } // ==================================================================================== #endif if (Settings.OutputFile == "") { Settings.OutputFile = DetermineMapName(mapFile, Settings.Engine); } if (Settings.OutputDir == "") { Settings.OutputDir = Path.GetDirectoryName(Settings.InputFile); } // free up as much memory as possible before saving the large images Rectangle saveRect = map.GetSizePixels(Settings.SizeMode); DrawingSurface ds = map.GetDrawingSurface(); saveRect.Intersect(new Rectangle(0, 0, ds.Width, ds.Height)); // if we don't need this data anymore, we can try to save some memory if (!Settings.GeneratePreviewPack) { ds.FreeNonBitmap(); map.FreeUseless(); GC.Collect(); } if (Settings.SaveJPEG) { ds.SaveJPEG(Path.Combine(Settings.OutputDir, Settings.OutputFile + ".jpg"), Settings.JPEGCompression, saveRect); } if (Settings.SavePNG) { ds.SavePNG(Path.Combine(Settings.OutputDir, Settings.OutputFile + ".png"), Settings.PNGQuality, saveRect); } Regex reThumb = new Regex(@"(\+|)?\((\d+),(\d+)\)"); var match = reThumb.Match(Settings.ThumbnailConfig); if (match.Success) { Size dimensions = new Size( int.Parse(match.Groups[2].Captures[0].Value), int.Parse(match.Groups[3].Captures[0].Value)); var cutRect = map.GetSizePixels(Settings.SizeMode); if (match.Groups[1].Captures[0].Value == "+") { // + means maintain aspect ratio double aspectRatio = cutRect.Width / (double)cutRect.Height; if (dimensions.Width / (double)dimensions.Height > aspectRatio) { dimensions.Height = (int)(dimensions.Width / aspectRatio); } else { dimensions.Width = (int)(dimensions.Height / aspectRatio); } } _logger.Info("Saving thumbnail with dimensions {0}x{1}", dimensions.Width, dimensions.Height); ds.SaveThumb(dimensions, cutRect, Path.Combine(Settings.OutputDir, "thumb_" + Settings.OutputFile + ".jpg")); } if (Settings.GeneratePreviewPack || Settings.FixupTiles) { if (mapFile.BaseStream is MixFile) { _logger.Error("Cannot fix tile layer or inject thumbnail into an archive (.mmx/.yro/.mix)!"); } else { if (Settings.GeneratePreviewPack) { map.GeneratePreviewPack(Settings.PreviewMarkers, Settings.SizeMode, mapFile, Settings.FixPreviewDimensions); } _logger.Info("Saving map to " + Settings.InputFile); mapFile.Save(Settings.InputFile); } } } catch (Exception exc) { _logger.Error(string.Format("An unknown fatal exception occured: {0}", exc), exc); #if DEBUG throw; #endif return(EngineResult.Exception); } return(EngineResult.RenderedOk); }