namespace LibraryTests (* Initial Setup -- Populating the Test Folders. =========================================================================== If you have just cloned this repository or have not run any of the tests before, please head over to script.fs (in Test Centre) and populate the LoadingTestArea and SavingTestArea folders. More information will be provided there about what the scripts do. It is worth pointing out here the .gitignore file ignores any .png files in them. This is why you must populate them before running any tests. *) module TestingHelpers = (* When you are writing tests, please keep all helper functions in this module. If this module grows to a point where it hinders the actual testing modules, consider moving it then. If you do decide to move them out, pay attention to ConsoleTests.fs and its helper functions. *) open System open System.Drawing open System.Reflection open System.IO open DeathSocket.Domain open SkiaSharp let rand = Random () (* These are duplicates from ConsoleTests.fs (both of them). See point about helpers. Tests for checking these locations can be found in ConsoleTests.fs. Also, these folders should not show up in Visual Studios Solution Explorer -- unless you are viewing the solution in its folder format. *) let loadLocation = __SOURCE_DIRECTORY__ + "/LoadingTestArea" let saveLocation = __SOURCE_DIRECTORY__ + "/SavingTestArea" let allColours = let properties = typeof.GetProperties (BindingFlags.Public ||| BindingFlags.Static) seq { for prop in properties -> prop} |> Seq.toArray let randomBrush () = let item = allColours.[rand.Next(allColours.Length)] item.GetValue (null, null) let allSKColours = let properties = typeof.GetFields (BindingFlags.Static ||| BindingFlags.Public) seq {for prop in properties -> prop} |> Seq.toArray let randomSKColour () = let item = allSKColours.[rand.Next(allSKColours.Length)] item.GetValue (null) :?> SKColor (* Max. value is arbitrary (change for performance). Min. value is to stop divide by zero exceptions. Intended for horizontal and vertical line tests. *) let newNum () = rand.Next(1, 1000) let newPenWidth () = rand.Next (1, 10) let newRGBANum () = rand.Next (255) let imagesInLoadingTestArea = Directory.GetFileSystemEntries (loadLocation, "*.png") let generateLoadPath () = let files = imagesInLoadingTestArea files.[rand.Next(files.Length)] let generateSavePath originalFilePath = let fileName = Path.GetFileName originalFilePath saveLocation + "/" + fileName (* To "manually" clear out the SavingTestArea folder, use this function in script.fsx. More information can be found there, also. *) let resetSavingTestArea () = let files = Directory.GetFileSystemEntries(saveLocation, "*.png") match files.Length with | 0 -> () | _ -> files |> Array.iter (fun f -> File.Delete(f)) let makeTestRGBASpec r g b a = { originalPath = "test path" savePath = "test path" alpha = float a red = float r green = float g blue = float b penWidth = float32 10 rows = newNum () columns = newNum () } module PropertyTests = open FsCheck.Xunit open DeathSocket open System.Drawing open DeathSocket.GridPainter open TestingHelpers open System.IO (* With regards to the "saving images" tests, you should end up with one image left over in the SavingTestArea folder. Comment out the "reset" function to see all the images produced by this test. This will mean you will need to manually delete the images yourself if you do. *) [] let ``Can apply grid to image and save it using BrushSpec`` () = resetSavingTestArea () let oPath = generateLoadPath () let sPath = generateSavePath oPath { originalPath = oPath savePath = sPath colour = randomBrush () :?> Brush penWidth = float32 (newPenWidth()) rows = 10 columns = 10 } |> applyBrushSpecGridAsync |> Async.RunSynchronously (File.Exists sPath) = true [] let ``Can apply grid to image and save it using RGBASpec`` () = resetSavingTestArea () let oPath = generateLoadPath () let sPath = generateSavePath oPath { originalPath = oPath savePath = sPath alpha = float (newRGBANum ()) red = float (newRGBANum ()) green = float (newRGBANum ()) blue = float (newRGBANum ()) penWidth = float32 (newPenWidth()) rows = 10 columns = 10 } |> applyRGBAGridAsync |> Async.RunSynchronously (File.Exists sPath) = true [] let ``SolidBrush colour matches the individual RGBA values`` () = let a = newRGBANum () let r = newRGBANum () let g = newRGBANum () let b = newRGBANum () let referenceColour = Color.FromArgb (a, r, g, b) let brush = makeSolidBrushFromRGBA r g b a brush.Color = referenceColour [] let ``SolidBrush colour matches the RGBASpec`` () = let a = newRGBANum () let r = newRGBANum () let g = newRGBANum () let b = newRGBANum () let referenceColour = Color.FromArgb (a, r, g, b) let referenceSpec = makeTestRGBASpec r g b a let brush = makeSolidBrushFromRGBASpec referenceSpec brush.Color = referenceColour [] let ``Can return a collection of points which represent a grids horizontal lines`` () = let result = determineHorizontalLines (newNum()) (newNum()) (newNum()) result.Length > 0 [] let ``Can return a collection of points which represent a grids vertical lines`` () = let result = determineVerticalLines (newNum()) (newNum()) (newNum()) result.Length > 0 [] let ``Can apply grid to image and save it using SkiaSpec`` () = resetSavingTestArea() let oPath = generateLoadPath () let sPath = generateSavePath oPath { originalPath = oPath savePath= sPath skColour = randomSKColour () penWidth = float32 (newPenWidth()) rows = newNum () columns = newNum () } |> applySkiaGridAsync |> Async.RunSynchronously (File.Exists sPath) = true [] let ``Can apply grid to image and save it using SkiaRGBSpec`` () = resetSavingTestArea() let oPath = generateLoadPath () let sPath = generateSavePath oPath { originalPath = oPath savePath= sPath red = float32 (newRGBANum ()) green = float32 (newRGBANum ()) blue = float32 (newRGBANum ()) penWidth = float32 (newPenWidth()) rows = newNum () columns = newNum () } |> applySkiaRGBGridAsync |> Async.RunSynchronously (File.Exists sPath) = true [] let ``Can return a collection of SKPoints which represent a grids horizontal lines`` () = let result = determineSKHorizontalLines (newNum()) (newNum()) (newNum()) result.Length > 0 [] let ``Can return a collection of SKPoints which represent a grids vertical lines`` () = let result = determineSKVerticalLines (newNum()) (newNum()) (newNum()) result.Length > 0 module UnitTests = open TestingHelpers open Xunit open DeathSocket open System open System.IO (* This test is a pre-test test (a test for the tests if you will...). It is here to make sure the property test has what it needs to run. If the property test fails, here is a good place to start. See script.fs (in Test Centre) for information on populating the LoadingTestArea folder. *) [] let ``LoadingTestArea contains at least 100 test images`` () = let length = imagesInLoadingTestArea.Length let imagesAreThere = if length < 100 then false else true Assert.True imagesAreThere (* This test is a pre-test test. If the property tests fails, here is a good place to start. The easiest way to get this test to pass is to create a folder called "SavingTestArea" in this projects folder (at the root). You can, also, see script.fs (in Test Centre) for creating this folder via code. (See "LoadingTestArea contains..." note for extra context. *) [] let ``SavingTestArea folder can be found`` () = Assert.True (Directory.Exists saveLocation) [] let ``Divide By Zero Exception is thrown when 0 rows is used when determining horizontal lines`` () = let result () = GridPainter.determineHorizontalLines 100 100 0 Assert.Throws(fun () -> result () |> ignore) [] let ``Divide By Zero Exception is thrown when 0 columns is used when determining vertical lines`` () = let result () = GridPainter.determineVerticalLines 100 100 0 Assert.Throws(fun () -> result () |> ignore)