Add a little project in F# using XAML + Emgu (OpenCV).
authorGreg Burri <greg.burri@gmail.com>
Sat, 9 May 2015 07:43:42 +0000 (09:43 +0200)
committerGreg Burri <greg.burri@gmail.com>
Sat, 9 May 2015 07:43:42 +0000 (09:43 +0200)
Parasitemia/Parasitemia.sln [new file with mode: 0644]
Parasitemia/Parasitemia/App.config [new file with mode: 0644]
Parasitemia/Parasitemia/AssemblyInfo.fs [new file with mode: 0644]
Parasitemia/Parasitemia/MainWindow.xaml [new file with mode: 0644]
Parasitemia/Parasitemia/MainWindow.xaml.fs [new file with mode: 0644]
Parasitemia/Parasitemia/Parasitemia.fsproj [new file with mode: 0644]
Parasitemia/Parasitemia/Program.fs [new file with mode: 0644]
Parasitemia/Parasitemia/packages.config [new file with mode: 0644]

diff --git a/Parasitemia/Parasitemia.sln b/Parasitemia/Parasitemia.sln
new file mode 100644 (file)
index 0000000..983f997
--- /dev/null
@@ -0,0 +1,22 @@
+
+Microsoft Visual Studio Solution File, Format Version 12.00
+# Visual Studio 14
+VisualStudioVersion = 14.0.22823.1
+MinimumVisualStudioVersion = 10.0.40219.1
+Project("{F2A71F9B-5D33-465A-A702-920D77279786}") = "Parasitemia", "Parasitemia\Parasitemia.fsproj", "{70838E65-F211-44FC-B28F-0ED1CA6E850F}"
+EndProject
+Global
+       GlobalSection(SolutionConfigurationPlatforms) = preSolution
+               Debug|Any CPU = Debug|Any CPU
+               Release|Any CPU = Release|Any CPU
+       EndGlobalSection
+       GlobalSection(ProjectConfigurationPlatforms) = postSolution
+               {70838E65-F211-44FC-B28F-0ED1CA6E850F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+               {70838E65-F211-44FC-B28F-0ED1CA6E850F}.Debug|Any CPU.Build.0 = Debug|Any CPU
+               {70838E65-F211-44FC-B28F-0ED1CA6E850F}.Release|Any CPU.ActiveCfg = Release|Any CPU
+               {70838E65-F211-44FC-B28F-0ED1CA6E850F}.Release|Any CPU.Build.0 = Release|Any CPU
+       EndGlobalSection
+       GlobalSection(SolutionProperties) = preSolution
+               HideSolutionNode = FALSE
+       EndGlobalSection
+EndGlobal
diff --git a/Parasitemia/Parasitemia/App.config b/Parasitemia/Parasitemia/App.config
new file mode 100644 (file)
index 0000000..e6cb850
--- /dev/null
@@ -0,0 +1,14 @@
+<?xml version="1.0" encoding="utf-8"?>
+<configuration>
+  <startup>
+    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.6" />
+  </startup>
+  <runtime>
+    <assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
+      <dependentAssembly>
+        <assemblyIdentity name="FSharp.Core" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
+        <bindingRedirect oldVersion="0.0.0.0-4.4.0.0" newVersion="4.4.0.0" />
+      </dependentAssembly>
+    </assemblyBinding>
+  </runtime>
+</configuration>
\ No newline at end of file
diff --git a/Parasitemia/Parasitemia/AssemblyInfo.fs b/Parasitemia/Parasitemia/AssemblyInfo.fs
new file mode 100644 (file)
index 0000000..269e427
--- /dev/null
@@ -0,0 +1,41 @@
+namespace Parasitemia.AssemblyInfo
+
+open System.Reflection
+open System.Runtime.CompilerServices
+open System.Runtime.InteropServices
+
+// General Information about an assembly is controlled through the following 
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[<assembly: AssemblyTitle("Parasitemia")>]
+[<assembly: AssemblyDescription("")>]
+[<assembly: AssemblyConfiguration("")>]
+[<assembly: AssemblyCompany("")>]
+[<assembly: AssemblyProduct("Parasitemia")>]
+[<assembly: AssemblyCopyright("Copyright ©  2015")>]
+[<assembly: AssemblyTrademark("")>]
+[<assembly: AssemblyCulture("")>]
+
+// Setting ComVisible to false makes the types in this assembly not visible 
+// to COM components.  If you need to access a type in this assembly from 
+// COM, set the ComVisible attribute to true on that type.
+[<assembly: ComVisible(false)>]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[<assembly: Guid("70838e65-f211-44fc-b28f-0ed1ca6e850f")>]
+
+// Version information for an assembly consists of the following four values:
+// 
+//       Major Version
+//       Minor Version 
+//       Build Number
+//       Revision
+// 
+// You can specify all the values or you can default the Build and Revision Numbers 
+// by using the '*' as shown below:
+// [<assembly: AssemblyVersion("1.0.*")>]
+[<assembly: AssemblyVersion("1.0.0.0")>]
+[<assembly: AssemblyFileVersion("1.0.0.0")>]
+
+do
+    ()
\ No newline at end of file
diff --git a/Parasitemia/Parasitemia/MainWindow.xaml b/Parasitemia/Parasitemia/MainWindow.xaml
new file mode 100644 (file)
index 0000000..8578d8c
--- /dev/null
@@ -0,0 +1,11 @@
+<Window xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
+        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d" x:Name="MainWindow" Height="776" Width="920">
+   <Grid Margin="10" RenderTransformOrigin="0.491,0.524">
+      <Grid.RowDefinitions>
+         <RowDefinition/>
+         <RowDefinition Height="100"/>
+      </Grid.RowDefinitions>
+      <Image x:Name="img" HorizontalAlignment="Stretch" Margin="10" VerticalAlignment="Stretch"/>
+      <TextBlock x:Name="txtLog" Margin="10" TextWrapping="Wrap" FontFamily="Monaco" Grid.Row="1" Background="#FF95E633"/>
+   </Grid>
+</Window>
\ No newline at end of file
diff --git a/Parasitemia/Parasitemia/MainWindow.xaml.fs b/Parasitemia/Parasitemia/MainWindow.xaml.fs
new file mode 100644 (file)
index 0000000..26d30c9
--- /dev/null
@@ -0,0 +1,6 @@
+namespace Parasitemia.Views
+
+open FsXaml
+
+type MainWindow = XAML<"MainWindow.xaml">
+
diff --git a/Parasitemia/Parasitemia/Parasitemia.fsproj b/Parasitemia/Parasitemia/Parasitemia.fsproj
new file mode 100644 (file)
index 0000000..c071e66
--- /dev/null
@@ -0,0 +1,122 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <Import Project="..\packages\OpenCV.Net.3.3.0\build\net40\OpenCV.Net.props" Condition="Exists('..\packages\OpenCV.Net.3.3.0\build\net40\OpenCV.Net.props')" />
+  <Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
+  <PropertyGroup>
+    <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
+    <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
+    <SchemaVersion>2.0</SchemaVersion>
+    <ProjectGuid>70838e65-f211-44fc-b28f-0ed1ca6e850f</ProjectGuid>
+    <OutputType>WinExe</OutputType>
+    <RootNamespace>Parasitemia</RootNamespace>
+    <AssemblyName>Parasitemia</AssemblyName>
+    <TargetFrameworkVersion>v4.6</TargetFrameworkVersion>
+    <AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects>
+    <TargetFSharpCoreVersion>4.4.0.0</TargetFSharpCoreVersion>
+    <Name>Parasitemia</Name>
+    <NuGetPackageImportStamp>
+    </NuGetPackageImportStamp>
+    <TargetFrameworkProfile />
+  </PropertyGroup>
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
+    <DebugSymbols>true</DebugSymbols>
+    <DebugType>full</DebugType>
+    <Optimize>false</Optimize>
+    <Tailcalls>false</Tailcalls>
+    <OutputPath>bin\Debug\</OutputPath>
+    <DefineConstants>DEBUG;TRACE</DefineConstants>
+    <WarningLevel>3</WarningLevel>
+    <PlatformTarget>x64</PlatformTarget>
+    <DocumentationFile>bin\Debug\Parasitemia.XML</DocumentationFile>
+    <Prefer32Bit>false</Prefer32Bit>
+  </PropertyGroup>
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
+    <DebugType>pdbonly</DebugType>
+    <Optimize>true</Optimize>
+    <Tailcalls>true</Tailcalls>
+    <OutputPath>bin\Release\</OutputPath>
+    <DefineConstants>TRACE</DefineConstants>
+    <WarningLevel>3</WarningLevel>
+    <PlatformTarget>x64</PlatformTarget>
+    <DocumentationFile>bin\Release\Parasitemia.XML</DocumentationFile>
+    <Prefer32Bit>false</Prefer32Bit>
+  </PropertyGroup>
+  <PropertyGroup>
+    <MinimumVisualStudioVersion Condition="'$(MinimumVisualStudioVersion)' == ''">11</MinimumVisualStudioVersion>
+  </PropertyGroup>
+  <Choose>
+    <When Condition="'$(VisualStudioVersion)' == '11.0'">
+      <PropertyGroup Condition="Exists('$(MSBuildExtensionsPath32)\..\Microsoft SDKs\F#\3.0\Framework\v4.0\Microsoft.FSharp.Targets')">
+        <FSharpTargetsPath>$(MSBuildExtensionsPath32)\..\Microsoft SDKs\F#\3.0\Framework\v4.0\Microsoft.FSharp.Targets</FSharpTargetsPath>
+      </PropertyGroup>
+    </When>
+    <Otherwise>
+      <PropertyGroup Condition="Exists('$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\FSharp\Microsoft.FSharp.Targets')">
+        <FSharpTargetsPath>$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\FSharp\Microsoft.FSharp.Targets</FSharpTargetsPath>
+      </PropertyGroup>
+    </Otherwise>
+  </Choose>
+  <Import Project="$(FSharpTargetsPath)" />
+  <Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
+    <PropertyGroup>
+      <ErrorText>This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them.  For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
+    </PropertyGroup>
+    <Error Condition="!Exists('..\packages\OpenCV.Net.3.3.0\build\net40\OpenCV.Net.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\OpenCV.Net.3.3.0\build\net40\OpenCV.Net.targets'))" />
+    <Error Condition="!Exists('..\packages\OpenCV.Net.3.3.0\build\net40\OpenCV.Net.props')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\OpenCV.Net.3.3.0\build\net40\OpenCV.Net.props'))" />
+  </Target>
+  <Import Project="..\packages\OpenCV.Net.3.3.0\build\net40\OpenCV.Net.targets" Condition="Exists('..\packages\OpenCV.Net.3.3.0\build\net40\OpenCV.Net.targets')" />
+  <ItemGroup>
+    <Compile Include="AssemblyInfo.fs" />
+    <Resource Include="MainWindow.xaml" />
+    <Compile Include="MainWindow.xaml.fs" />
+    <Compile Include="Program.fs" />
+    <None Include="App.config" />
+    <Content Include="packages.config" />
+  </ItemGroup>
+  <ItemGroup>
+    <Reference Include="Emgu.CV">
+      <HintPath>..\..\..\Programs\Emgu\emgucv-windows-universal 3.0.0.2032\bin\Emgu.CV.dll</HintPath>
+    </Reference>
+    <Reference Include="Emgu.CV.WPF">
+      <HintPath>..\..\..\Programs\Emgu\emgucv-windows-universal 3.0.0.2032\bin\Emgu.CV.WPF.exe</HintPath>
+    </Reference>
+    <Reference Include="Emgu.Util">
+      <HintPath>..\..\..\Programs\Emgu\emgucv-windows-universal 3.0.0.2032\bin\Emgu.Util.dll</HintPath>
+    </Reference>
+    <Reference Include="FsXaml.Wpf">
+      <HintPath>..\packages\FsXaml.Wpf.0.9.9\lib\net45\FsXaml.Wpf.dll</HintPath>
+      <Private>True</Private>
+    </Reference>
+    <Reference Include="FsXaml.Wpf.TypeProvider">
+      <HintPath>..\packages\FsXaml.Wpf.0.9.9\lib\net45\FsXaml.Wpf.TypeProvider.dll</HintPath>
+      <Private>True</Private>
+    </Reference>
+    <Reference Include="mscorlib" />
+    <Reference Include="FSharp.Core, Version=$(TargetFSharpCoreVersion), Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
+      <Private>True</Private>
+    </Reference>
+    <Reference Include="PresentationCore" />
+    <Reference Include="PresentationFramework" />
+    <Reference Include="System" />
+    <Reference Include="System.Core" />
+    <Reference Include="System.Drawing" />
+    <Reference Include="System.Numerics" />
+    <Reference Include="System.Windows.Interactivity">
+      <HintPath>..\packages\Expression.Blend.Sdk.1.0.2\lib\net45\System.Windows.Interactivity.dll</HintPath>
+      <Private>True</Private>
+    </Reference>
+    <Reference Include="System.Xaml" />
+    <Reference Include="System.Xml" />
+    <Reference Include="WindowsBase" />
+  </ItemGroup>
+  <PropertyGroup>
+    <PostBuildEvent>xcopy "D:\Programs\Emgu\emgucv-windows-universal 3.0.0.2032\bin\x64\*" $(TargetDir) /Y /D</PostBuildEvent>
+  </PropertyGroup>
+  <!-- To modify your build process, add your task inside one of the targets below and uncomment it. 
+       Other similar extension points exist, see Microsoft.Common.targets.
+  <Target Name="BeforeBuild">
+  </Target>
+  <Target Name="AfterBuild">
+  </Target>
+  -->
+</Project>
\ No newline at end of file
diff --git a/Parasitemia/Parasitemia/Program.fs b/Parasitemia/Parasitemia/Program.fs
new file mode 100644 (file)
index 0000000..e9ae0d4
--- /dev/null
@@ -0,0 +1,68 @@
+module Parasitemia.Main
+
+open System.IO
+open System.Windows
+open System.Windows.Media
+open System.Windows.Markup
+open System.Windows.Shapes
+open System.Windows.Controls
+open System.Drawing
+open System.Diagnostics
+
+open Emgu.CV
+open Emgu.CV.Structure
+open Emgu.CV.WPF
+
+let display (window : Views.MainWindow) (img : IImage) = 
+   let imgControl = window.Root.FindName("img") :?> Controls.Image
+   imgControl.Source <- BitmapSourceConvert.ToBitmapSource(img)
+
+let log (window : Views.MainWindow) (mess : string) =
+   let txtLog = window.Root.FindName("txtLog") :?> Controls.TextBlock
+   txtLog.Text <- txtLog.Text + mess + "\n"
+
+let inline dprintfn fmt =
+    Printf.ksprintf System.Diagnostics.Debug.WriteLine fmt
+
+let measureTime<'a> (print : string -> unit) (f : unit -> 'a) = 
+   let sw = Stopwatch()
+   sw.Start()
+   let res = f ()
+   sw.Stop()
+   print <| sprintf "time: %A ms" sw.ElapsedMilliseconds
+   res
+
+[<System.STAThreadAttribute>]
+do
+   dprintfn "OpenCV test"
+
+   let app = new Application()
+   
+   let mainWindow = Views.MainWindow()
+
+   let timer = measureTime (log mainWindow)
+   
+   use image = new Image<Rgb, byte>("../../../../imgs_corrMK/1412151257/1412151257-Gamma-0.8-0002.png")
+   
+   use scaledImage = image.Resize(0.6, CvEnum.Inter.Area)
+   
+   use imageHSV = scaledImage.Convert<Hsv, uint8>()
+   let H, S = match imageHSV.Split() with // Warning: H is from 0 to 179°.
+                | [| H; S; _|] -> H, S
+                | _ -> failwith "unable to split the HSV channels"                         
+   
+   let hueShiftValue = 175
+    // Modulo operator doesn't exist on matrix thus we have to apply a function to every pixels.
+   let correctedH : Image<Gray, byte> = H.Convert(fun b _ _ ->
+      (255 - int(b) * 255 / 179 + hueShiftValue) % 256 |> byte
+   )
+   
+   let correctedS : Image<Gray, byte> = S.Not()
+
+   let filteredH = correctedH.SmoothMedian(5)
+   let filteredS = correctedS.SmoothMedian(5)
+
+   display mainWindow filteredS
+   mainWindow.Root.Show()
+
+   app.Run() |> ignore
diff --git a/Parasitemia/Parasitemia/packages.config b/Parasitemia/Parasitemia/packages.config
new file mode 100644 (file)
index 0000000..9ac3914
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="utf-8"?>
+<packages>
+  <package id="Expression.Blend.Sdk" version="1.0.2" targetFramework="net46" userInstalled="true" />
+  <package id="FsXaml.Wpf" version="0.9.9" targetFramework="net46" userInstalled="true" />
+  <package id="OpenCV.Net" version="3.3.0" targetFramework="net46" userInstalled="true" />
+</packages>
\ No newline at end of file