public void ClearAll() { currentHashMatches.Clear(); unknownHashes.Clear(); currentScanArea = Rectangle.Empty; activeScanner = null; currentState = EState.NoErrors; }
public void DoWork(EMode mode = EMode.Default, int scannerFlags = 0) { Stopwatch timerTotal = new Stopwatch(); Stopwatch timerStep = new Stopwatch(); timerTotal.Start(); bool debugMode = (mode & EMode.Debug) != EMode.None; activeScanner = null; currentMode = mode; // load input bool hasInputImage = LoadInputImage(mode, timerStep, scanClipBounds); if (hasInputImage) { // convert to HSL representation timerStep.Restart(); cachedFastBitmap = ImageUtils.ConvertToFastBitmap(screenReader.cachedScreenshot); timerStep.Stop(); if (debugMode) { Logger.WriteLine("Screenshot convert: " + timerStep.ElapsedMilliseconds + "ms"); } if (Logger.IsSuperVerbose()) { Logger.WriteLine("Screenshot: {0}x{1}", screenReader.cachedScreenshot.Width, screenReader.cachedScreenshot.Height); } // reset scanner's intermediate data bool canResetCache = (mode & EMode.NeverResetCache) == EMode.None; if (canResetCache) { bool forceResetCache = (mode & EMode.AlwaysResetCache) != EMode.None; if (forceResetCache) { unknownHashes.Clear(); currentHashMatches.Clear(); } // invalidate scanner's cache if input image size has changed if (forceResetCache || cachedBitmapSize.Width <= 0 || cachedBitmapSize.Width != cachedFastBitmap.Width || cachedBitmapSize.Height != cachedFastBitmap.Height) { cachedBitmapSize = new Size(cachedFastBitmap.Width, cachedFastBitmap.Height); foreach (var kvp in mapScanners) { kvp.Value.InvalidateCache(); } } } currentState = EState.NoScannerMatch; // pass 1: check if cache is still valid for requested scanner foreach (var kvp in mapScanners) { if ((kvp.Key & mode) != EMode.None && kvp.Value.HasValidCache(cachedFastBitmap, scannerFlags)) { bool scanned = false; try { scanned = kvp.Value.DoWork(cachedFastBitmap, scannerFlags, timerStep, debugMode); } catch (Exception ex) { Logger.WriteLine("Failed to scan [1] image! {0}", ex); scanned = false; } if (scanned) { activeScanner = kvp.Value; currentState = (currentState == EState.NoScannerMatch) ? EState.NoErrors : currentState; if (debugMode) { Logger.WriteLine("Scan [1] successful, type:{0}, state:{1}", kvp.Key, currentState); } } else { currentState = EState.ScannerErrors; } break; } } // pass 2: all requested if (activeScanner == null) { foreach (var kvp in mapScanners) { if ((kvp.Key & mode) != EMode.None) { bool scanned = false; try { scanned = kvp.Value.DoWork(cachedFastBitmap, scannerFlags, timerStep, debugMode); } catch (Exception ex) { Logger.WriteLine("Failed to scan [2] image! {0}", ex); scanned = false; } if (scanned) { activeScanner = kvp.Value; currentState = (currentState == EState.NoScannerMatch) ? EState.NoErrors : currentState; if (debugMode) { Logger.WriteLine("Scan [2] successful, type:{0}, state:{1}", kvp.Key, currentState); } break; } } } } // save debug markup if needed if ((activeScanner != null) && ((mode & EMode.DebugSaveMarkup) != EMode.None)) { List <Rectangle> debugBounds = new List <Rectangle>(); List <ImageUtils.HashPreview> debugHashes = new List <ImageUtils.HashPreview>(); activeScanner.AppendDebugShapes(debugBounds, debugHashes); if (currentScanArea.Width > 0) { debugBounds.Add(currentScanArea); } timerStep.Restart(); string imagePath = GetDefaultScreenshotPath() + "screenshot-markup.png"; if (File.Exists(imagePath)) { File.Delete(imagePath); } using (Bitmap markupBitmap = ImageUtils.ConvertToBitmap(cachedFastBitmap)) { ImageUtils.DrawDebugShapes(markupBitmap, debugBounds); ImageUtils.DrawDebugHashes(markupBitmap, debugHashes); markupBitmap.Save(imagePath, ImageFormat.Png); } timerStep.Stop(); Logger.WriteLine("Screenshot save: " + timerStep.ElapsedMilliseconds + "ms"); } } else { currentState = EState.NoInputImage; } timerTotal.Stop(); if (debugMode) { Logger.WriteLine("Screenshot TOTAL: " + timerTotal.ElapsedMilliseconds + "ms"); } }
public static void RunTests(string path, ScreenAnalyzer.EMode mode) { ScreenAnalyzer screenAnalyzer = new ScreenAnalyzer(); MLDataExporter dataExporter = null; ScannerBase scannerOb = null; foreach (var kvp in screenAnalyzer.mapScanners) { if ((kvp.Key & mode) != ScreenAnalyzer.EMode.None) { scannerOb = kvp.Value; break; } } if (scannerOb == null) { throw new Exception("Test failed! Can't find scanner for requested type:" + mode); } if (exportDetectionPatterns) { dataExporter = new MLDataExporter(); dataExporter.exportPath = AssetManager.Get().CreateFilePath("ml/patternMatch/data"); dataExporter.StartDataExport((mode & ScreenAnalyzer.EMode.ScanAll).ToString()); } string testRoot = AssetManager.Get().CreateFilePath(path); IEnumerable <string> configPaths = Directory.EnumerateFiles(testRoot, "*.json"); foreach (var configPath in configPaths) { string imagePath = configPath.Replace(".json", ".jpg"); if (!File.Exists(imagePath)) { imagePath = imagePath.Replace(".jpg", ".png"); } if (File.Exists(imagePath)) { Logger.WriteLine("==> Testing: " + Path.GetFileNameWithoutExtension(configPath)); bool bNeedsDebugRun = false; screenAnalyzer.debugScreenshotPath = imagePath; screenAnalyzer.debugScannerContext = null; try { screenAnalyzer.DoWork(mode); scannerOb.ValidateScan(configPath, mode, dataExporter); } catch (Exception ex) { Logger.WriteLine("Exception:" + ex); bNeedsDebugRun = true; } // retry, don't catch exceptions if (bNeedsDebugRun && !exportDetectionPatterns) { screenAnalyzer.DoWork(mode | ScreenAnalyzer.EMode.Debug); scannerOb.ValidateScan(configPath, mode | ScreenAnalyzer.EMode.Debug, null); } } } if (exportDetectionPatterns) { dataExporter.FinishDataExport("ml-" + Path.GetFileNameWithoutExtension(path) + ".json"); } }