-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
8517cb9
commit a4d075e
Showing
15 changed files
with
566 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
|
||
Microsoft Visual Studio Solution File, Format Version 12.00 | ||
# Visual Studio 15 | ||
VisualStudioVersion = 15.0.28307.539 | ||
MinimumVisualStudioVersion = 10.0.40219.1 | ||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MandelBrot", "MandelBrot\MandelBrot.csproj", "{64087C44-EACD-4E80-AA68-70E30AF717E5}" | ||
EndProject | ||
Global | ||
GlobalSection(SolutionConfigurationPlatforms) = preSolution | ||
Debug|Any CPU = Debug|Any CPU | ||
Release|Any CPU = Release|Any CPU | ||
EndGlobalSection | ||
GlobalSection(ProjectConfigurationPlatforms) = postSolution | ||
{64087C44-EACD-4E80-AA68-70E30AF717E5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU | ||
{64087C44-EACD-4E80-AA68-70E30AF717E5}.Debug|Any CPU.Build.0 = Debug|Any CPU | ||
{64087C44-EACD-4E80-AA68-70E30AF717E5}.Release|Any CPU.ActiveCfg = Release|Any CPU | ||
{64087C44-EACD-4E80-AA68-70E30AF717E5}.Release|Any CPU.Build.0 = Release|Any CPU | ||
EndGlobalSection | ||
GlobalSection(SolutionProperties) = preSolution | ||
HideSolutionNode = FALSE | ||
EndGlobalSection | ||
GlobalSection(ExtensibilityGlobals) = postSolution | ||
SolutionGuid = {A584772F-1983-40C4-93EE-D7ECFE2CC7F0} | ||
EndGlobalSection | ||
EndGlobal |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
<?xml version="1.0" encoding="utf-8" ?> | ||
<configuration> | ||
<startup> | ||
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.6.1" /> | ||
</startup> | ||
</configuration> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,70 @@ | ||
using System; | ||
using System.Text; | ||
|
||
namespace MandelbrotRenderer | ||
{ | ||
/// <summary> | ||
/// Wrapper around a 2D array with some utility functions I found handy | ||
/// </summary> | ||
/// <typeparam name="T"></typeparam> | ||
class Array2D<T> | ||
{ | ||
private T[][] _Array; | ||
|
||
public int Width { get; } | ||
public int Height { get; } | ||
public int TotalSize => Width * Height; | ||
|
||
public Array2D(int width, int height) | ||
{ | ||
Width = width; | ||
Height = height; | ||
|
||
_Array = new T[width][]; | ||
|
||
for (int i = 0; i < width; i++) | ||
_Array[i] = new T[height]; | ||
} | ||
|
||
public void Each(Func<int, int, T> _Callback) | ||
{ | ||
for (int x = 0; x < Width; x++) | ||
for (int y = 0; y < Height; y++) | ||
_Array[x][y] = _Callback(x, y); | ||
} | ||
|
||
public void Each(Action<int, int> _Callback) | ||
{ | ||
for (int x = 0; x < Width; x++) | ||
for (int y = 0; y < Height; y++) | ||
_Callback(x, y); | ||
} | ||
|
||
public void Each(Action<T> _Callback) | ||
{ | ||
for (int x = 0; x < Width; x++) | ||
for (int y = 0; y < Height; y++) | ||
_Callback(_Array[x][y]); | ||
} | ||
|
||
public T this[int x, int y] | ||
{ | ||
get { return _Array[x][y]; } | ||
set { _Array[x][y] = value; } | ||
} | ||
|
||
public override string ToString() | ||
{ | ||
StringBuilder sb = new StringBuilder(); | ||
for (int x = 0; x < Width; x++) | ||
{ | ||
for (int y = 0; y < Height; y++) | ||
{ | ||
sb.Append(this[x, y].ToString()).Append(", "); | ||
} | ||
sb.Append('\n'); | ||
} | ||
return sb.ToString(); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,65 @@ | ||
using System.Drawing; | ||
using System; | ||
using System.Collections.Generic; | ||
|
||
namespace MandelbrotRenderer | ||
{ | ||
/// <summary> | ||
/// Quick and dirty implementation of a curve in color space | ||
/// </summary> | ||
class ColorCurve | ||
{ | ||
private Curve _R, _G, _B; | ||
|
||
public ColorCurve(Curve r, Curve g, Curve b) | ||
{ | ||
this._R = r; | ||
this._G = g; | ||
this._B = b; | ||
} | ||
|
||
public Color Sample(double value) | ||
{ | ||
int r = (int)Math.Min(_R.Sample(value) * 255, 255); | ||
int g = (int)Math.Min(_G.Sample(value) * 255, 255); | ||
int b = (int)Math.Min(_B.Sample(value) * 255, 255); | ||
return Color.FromArgb(r, g, b); | ||
} | ||
|
||
public static ColorCurve Parse(string args) | ||
{ | ||
string[] values = args.Split(' '); | ||
|
||
List<Keyframe> redCurve = new List<Keyframe>(); | ||
List<Keyframe> greenCurve = new List<Keyframe>(); | ||
List<Keyframe> blueCurve = new List<Keyframe>(); | ||
|
||
for (int j = 0; j < values.Length; j++) | ||
{ | ||
switch (values[j].ToLower()) | ||
{ | ||
case "r": | ||
while (j + 2 < values.Length && double.TryParse(values[++j], out double pos) && double.TryParse(values[++j], out double val)) | ||
redCurve.Add(new Keyframe(pos, val)); | ||
--j; | ||
break; | ||
case "g": | ||
while (j + 2 < values.Length && double.TryParse(values[++j], out double pos) && double.TryParse(values[++j], out double val)) | ||
greenCurve.Add(new Keyframe(pos, val)); | ||
--j; | ||
break; | ||
case "b": | ||
while (j + 2 < values.Length && double.TryParse(values[++j], out double pos) && double.TryParse(values[++j], out double val)) | ||
blueCurve.Add(new Keyframe(pos, val)); | ||
--j; | ||
break; | ||
} | ||
} | ||
|
||
return new ColorCurve( | ||
new Curve(redCurve.ToArray()), | ||
new Curve(greenCurve.ToArray()), | ||
new Curve(blueCurve.ToArray())); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
namespace MandelbrotRenderer | ||
{ | ||
/// <summary> | ||
/// Represents a complex number | ||
/// </summary> | ||
struct ComplexNumber | ||
{ | ||
public double re; // real part of complex number | ||
public double im; // imaginary part of complex number "x*Sqrt(-1))" | ||
|
||
public ComplexNumber(double x, double y) | ||
{ | ||
this.re = x; | ||
this.im = y; | ||
} | ||
|
||
public static ComplexNumber operator +(ComplexNumber a, ComplexNumber b) | ||
=> new ComplexNumber(a.re + b.re, a.im + b.im); | ||
|
||
public static ComplexNumber operator *(ComplexNumber a, ComplexNumber b) | ||
=> new ComplexNumber(a.re * b.re - a.im * b.im, a.re * b.im + a.im * b.re); | ||
|
||
public double Norm | ||
=> re * re + im * im; | ||
|
||
public static ComplexNumber Zero | ||
=> new ComplexNumber(); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
namespace MandelbrotRenderer | ||
{ | ||
/// <summary> | ||
/// Quick and dirty implementation of a keyframed curve where values in between keyframes are interpolated linearly | ||
/// </summary> | ||
class Curve | ||
{ | ||
Keyframe[] _Keyframes; | ||
|
||
public Curve(params Keyframe[] keyframes) | ||
{ | ||
_Keyframes = keyframes; | ||
} | ||
|
||
public double Sample(double value) | ||
{ | ||
for (int i = 1; i < _Keyframes.Length; i++) | ||
if (value < _Keyframes[i].position) | ||
return MathExtension.MapRange(value, | ||
_Keyframes[i - 1].position, | ||
_Keyframes[i].position, | ||
_Keyframes[i - 1].value, | ||
_Keyframes[i].value); | ||
return 1; | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
namespace MandelbrotRenderer | ||
{ | ||
/// <summary> | ||
/// Quick and dirty implementation of a keyframe for in curves | ||
/// </summary> | ||
struct Keyframe | ||
{ | ||
public double position; | ||
public double value; | ||
|
||
public Keyframe(double position, double value) | ||
{ | ||
this.position = position; | ||
this.value = value; | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,52 @@ | ||
| ||
using System.Diagnostics; | ||
|
||
namespace MandelbrotRenderer | ||
{ | ||
/// <summary> | ||
/// Contains the mandelbrot formula and a utility function to fill a 2D array with values from a section of the mandelbrot. | ||
/// </summary> | ||
static class MandelBrot | ||
{ | ||
const double MAX_VALUE_EXTENT = 2.0; | ||
const double MAX_NORM = MAX_VALUE_EXTENT * MAX_VALUE_EXTENT; | ||
|
||
public static double Calculate(ComplexNumber c) | ||
{ | ||
int maxIterations = Settings.Global.Iterations; | ||
|
||
ComplexNumber z = ComplexNumber.Zero; | ||
int i = 0; | ||
|
||
do { z = z * z + c; ++i; } | ||
while (z.Norm < MAX_NORM && i < maxIterations); | ||
|
||
if (i < maxIterations) | ||
return (double)i / maxIterations; | ||
|
||
return 0; | ||
} | ||
|
||
public static Array2D<double> GetValues(Rect rect, int pixelWidth, int pixelHeight) | ||
{ | ||
Array2D<double> array2D = new Array2D<double>(pixelWidth, pixelHeight); | ||
Stopwatch stopwatch = Stopwatch.StartNew(); | ||
Stopwatch timer = Stopwatch.StartNew(); | ||
|
||
array2D.Each((x, y) => | ||
{ | ||
if (stopwatch.ElapsedMilliseconds > 40) | ||
{ | ||
int percentage = (int)(((x *array2D.Height) + y) / (double)array2D.TotalSize * 100); | ||
System.Console.Write($"\rCalculating Mandelbrot: {percentage}% x:{x} y:{y}"); | ||
stopwatch.Restart(); | ||
} | ||
return Calculate(new ComplexNumber(rect.MapWidth(x, 0, pixelWidth), rect.MapHeight(y, 0, pixelHeight))); | ||
}); | ||
|
||
System.Console.WriteLine($"\rCalculating Mandelbrot: 100% x:{array2D.Width} y:{array2D.Height}"); | ||
System.Console.WriteLine($"Calculations done: {timer.Elapsed}"); | ||
return array2D; | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,64 @@ | ||
<?xml version="1.0" encoding="utf-8"?> | ||
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> | ||
<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> | ||
<ProjectGuid>{64087C44-EACD-4E80-AA68-70E30AF717E5}</ProjectGuid> | ||
<OutputType>Exe</OutputType> | ||
<RootNamespace>MandelBrot</RootNamespace> | ||
<AssemblyName>MandelBrot</AssemblyName> | ||
<TargetFrameworkVersion>v4.6.1</TargetFrameworkVersion> | ||
<FileAlignment>512</FileAlignment> | ||
<AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects> | ||
<Deterministic>true</Deterministic> | ||
</PropertyGroup> | ||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' "> | ||
<PlatformTarget>AnyCPU</PlatformTarget> | ||
<DebugSymbols>true</DebugSymbols> | ||
<DebugType>full</DebugType> | ||
<Optimize>false</Optimize> | ||
<OutputPath>bin\Debug\</OutputPath> | ||
<DefineConstants>DEBUG;TRACE</DefineConstants> | ||
<ErrorReport>prompt</ErrorReport> | ||
<WarningLevel>4</WarningLevel> | ||
</PropertyGroup> | ||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' "> | ||
<PlatformTarget>AnyCPU</PlatformTarget> | ||
<DebugType>pdbonly</DebugType> | ||
<Optimize>true</Optimize> | ||
<OutputPath>bin\Release\</OutputPath> | ||
<DefineConstants>TRACE</DefineConstants> | ||
<ErrorReport>prompt</ErrorReport> | ||
<WarningLevel>4</WarningLevel> | ||
</PropertyGroup> | ||
<ItemGroup> | ||
<Reference Include="System" /> | ||
<Reference Include="System.Core" /> | ||
<Reference Include="System.Drawing" /> | ||
<Reference Include="System.Xml.Linq" /> | ||
<Reference Include="System.Data.DataSetExtensions" /> | ||
<Reference Include="Microsoft.CSharp" /> | ||
<Reference Include="System.Data" /> | ||
<Reference Include="System.Net.Http" /> | ||
<Reference Include="System.Xml" /> | ||
</ItemGroup> | ||
<ItemGroup> | ||
<Compile Include="Array2D.cs" /> | ||
<Compile Include="ColorCurve.cs" /> | ||
<Compile Include="ComplexNumber.cs" /> | ||
<Compile Include="Curve.cs" /> | ||
<Compile Include="Keyframe.cs" /> | ||
<Compile Include="MandelBrot.cs" /> | ||
<Compile Include="MathExtension.cs" /> | ||
<Compile Include="Program.cs" /> | ||
<Compile Include="ProgramOptions.cs" /> | ||
<Compile Include="Properties\AssemblyInfo.cs" /> | ||
<Compile Include="Rect.cs" /> | ||
<Compile Include="ValueSpectrumRenderer.cs" /> | ||
</ItemGroup> | ||
<ItemGroup> | ||
<None Include="App.config" /> | ||
</ItemGroup> | ||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" /> | ||
</Project> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
namespace MandelbrotRenderer | ||
{ | ||
/// <summary> | ||
/// Container for globally used math | ||
/// </summary> | ||
class MathExtension | ||
{ | ||
public static double MapRange(double s, double a1, double a2, double b1, double b2) | ||
{ | ||
return b1 + (s - a1) * (b2 - b1) / (a2 - a1); | ||
} | ||
} | ||
} |
Oops, something went wrong.