Skip to content

Instantly share code, notes, and snippets.

@davidwhitney
Created January 28, 2015 09:38
Show Gist options
  • Select an option

  • Save davidwhitney/9fa81da34a6c7071246c to your computer and use it in GitHub Desktop.

Select an option

Save davidwhitney/9fa81da34a6c7071246c to your computer and use it in GitHub Desktop.
ASCII Transcoder
using System;
using System.Collections.Generic;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Text;
using NUnit.Framework;
namespace RubberDucky
{
[TestFixture]
public class SomeTests
{
[Test]
public void DuckYou()
{
var duck = (Bitmap)Bitmap.FromFile("skydiving-insurance.jpg");
var ascii = ImageTranscoder.Render(duck);
System.Diagnostics.Debug.Write(ascii);
}
[TestCase]
public void Render_GivenSingleBlackPixel_ReturnsBlock()
{
var pixel = CreateBitmapForMatrix(new[,]
{
{Color.Black}
});
var output = ImageTranscoder.Render(pixel);
Assert.That(output, Is.EqualTo("█"));
}
[Test]
public void Render_GivenSingleWhitePixel_ReturnsSpace()
{
var pixel = CreateBitmapForMatrix(new[,]
{
{Color.White}
});
var output = ImageTranscoder.Render(pixel);
Assert.That(output, Is.EqualTo(" "));
}
[Test]
public void Render_GivenSingleYellowPixel_ReturnsSpace()
{
var pixel = CreateBitmapForMatrix(new[,]
{
{Color.Yellow}
});
var output = ImageTranscoder.Render(pixel);
Assert.That(output, Is.EqualTo("o"));
}
[Test]
public void Render_GivenSingleRedPixel_Returns25pcGreyThing()
{
var pixel = CreateBitmapForMatrix(new[,]
{
{Color.DarkRed}
});
var output = ImageTranscoder.Render(pixel);
Assert.That(output, Is.EqualTo("▒"));
}
[Test]
public void Render_GivenTwoPixelsOneBlackOneWhite_ReturnsBlockAndSpace()
{
var image = CreateBitmapForMatrix(new[,]
{
{Color.Black},
{Color.White}
});
var output = ImageTranscoder.Render(image);
Assert.That(output, Is.EqualTo("█ "));
}
[Test]
public void Render_GivenTwoByTwoImageCheckered_ReturnsWBBW()
{
var image = CreateBitmapForMatrix(new[,]
{
{Color.White, Color.Black},
{Color.Black, Color.White}
});
var output = ImageTranscoder.Render(image);
Assert.That(output, Is.EqualTo(" █\r\n█ "));
}
private static Bitmap CreateBitmapForMatrix(Color[,] matrix)
{
var width = matrix.GetUpperBound(0);
var height = matrix.GetUpperBound(1);
var bitmap = new Bitmap(width + 1, height + 1);
for (int y = 0; y <= height; y++)
{
for (int x = 0; x <= width; x++)
{
bitmap.SetPixel(x, y, matrix[x, y]);
}
}
return bitmap;
}
}
public class ImageTranscoder
{
private static readonly Dictionary<float, string> Map;
static ImageTranscoder()
{
Map = new Dictionary<float, string>
{
{1, " "},
{0.75f, "."},
{0.5f, "o"},
{0.25f, "▒"},
{0, "█"}
};
}
public static string Render(Bitmap image)
{
image = ResizeAllSmallLike(image);
var map = Map.OrderBy(kvp => kvp.Key);
var sb = new StringBuilder();
for (int y = 0; y < image.Height; y++)
{
for (int x = 0; x < image.Width; x++)
{
var pixel = image.GetPixel(x, y);
var currentChar = MapColourToCharacter(map, pixel);
sb.Append(currentChar);
}
sb.Append(Environment.NewLine);
}
return PostProcessOutput(sb);
}
private static Bitmap ResizeAllSmallLike(Bitmap image)
{
if (image.Width <= 100 || image.Height <= 100)
{
return image;
}
Bitmap newImage = new Bitmap(100, 100);
using (Graphics gr = Graphics.FromImage(newImage))
{
gr.DrawImage(image, new Rectangle(0, 0, 100, 100));
}
return newImage;
}
private static string MapColourToCharacter(IEnumerable<KeyValuePair<float, string>> map, Color pixel)
{
var brightness = pixel.GetBrightness();
var currentChar = "";
foreach (var kvp in map)
{
if (kvp.Key <= brightness)
{
currentChar = kvp.Value;
}
}
return currentChar;
}
private static string PostProcessOutput(StringBuilder sb)
{
var output = sb.ToString();
output = output.Substring(0, output.Length - Environment.NewLine.Length);
return output;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment