Printing text onto an image

This was originally a repsonse to a forum post at CompuTeach where a student was asking a question about a program that was throwing an ambiguous exception, rather than being satisfied with simply fixing the issue I went a bit mad and rewrote the whole thing.

Hello

I’m trying to add a logo to an image and save it to a new file.However , the final line below throws a
System.Runtime.InteropServices.ExternalException –
“A Generic error occured in GDI+”.I can’t spot the problem,
can anyone help? The code for the console application is
below.

Thanks

—————————————-
——————-

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;

namespace Ch6Objective2P3
{
class Program
{

static void Main(string[] args)
{

DirectoryInfo di = new DirectoryInfo
(@”C:\Documents and Settings\All Users\Documents\My Pictures\Sample Pictures”);
//New folder for picture with logo
DirectoryInfo di1 = new DirectoryInfo
(@”C:\Documents and Settings\All Users\Documents\New Sample Pictures”);

//New file for picture with logo
File.Create
(@”C:\Documents and Settings\All Users\Documents\New Sample Pictures\New Picture”);

Image im = Image.FromFile
(@”C:\Documents and Settings\All Users\Documents\My Pictures\Sample Pictures\Sunset.Jpg”);
Graphics g = Graphics.FromImage(im);

//font
FontFamily ff = new FontFamily(“Arial”);
Font f = new Font(ff, 12);

g.DrawString(“Testing”, f, Brushes.Yellow, 10, 10);

im.Save(@”C:\Documents and Settings\All Users\Documents\New Sample Pictures\New Picture”);

}
}
}

So the solution to this is simply that im.Save() thinks the file is opened by another process, which is actually the program. So to solve it you could simply remove the File.Create() call and it would work as intended, but I got thinking then that if a FileStream had been used then this problem wouldnt have showed its head.

Then I thought oh maybe some defensive programming would be good here

So what did I do to the OP’s program?

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;

namespace Ch6Objective2P3
{
public static class Program
{
static void Main(string[] args)
{
ImageManipulate im = new ImageManipulate();
im.Run(args);

}

}

public class ImageManipulate
{
string samplePath;
string newSamplePath;

public void Run(string[] args)
{
if (args == null || args.Length < 1)
{
string allUsersPicsPath = Environment.GetFolderPath(Environment.SpecialFolder.CommonPictures);
samplePath = allUsersPicsPath + “\\Sample Pictures”;
newSamplePath = allUsersPicsPath + “\\New Sample Pictures”;
}
else
{
samplePath = args[1];
if (args.Length < 1 && args[2] != null)
newSamplePath = args[2];
else
newSamplePath = samplePath + “\\New”;
}

DirectoryInfo di = new DirectoryInfo(samplePath);
if (di.Exists == false)
throw new FileNotFoundException(@”The directory ‘Sample Pictures’ does not exist”);

Console.ForegroundColor = ConsoleColor.Green;
foreach (FileInfo file in di.GetFiles())
{
Console.WriteLine(file.Name);
}
Console.ResetColor();

string pictureName = GetFileName();

while(!TestFileName(pictureName))
pictureName = GetFileName();;

//New folder for picture with logo
DirectoryInfo di1 = new DirectoryInfo(newSamplePath);
if (di1.Exists == false)
Directory.CreateDirectory(newSamplePath);

Image im = Image.FromFile(samplePath + “\\” + pictureName);
Graphics g = Graphics.FromImage(im);

//font
FontFamily ff = new FontFamily(“Arial”);
Font f = new Font(ff, 12);

Console.WriteLine(“Type what you would like to graffiti onto the image”);
string grafitti = Console.ReadLine();

g.DrawString(grafitti, f, Brushes.Yellow, 10, 10);

string newImagePath = newSamplePath + “\\New ” + pictureName;
FileStream stream = new FileStream(newImagePath, FileMode.Create);

im.Save(stream, ImageFormat.Jpeg);
}

private bool TestFileName(string pictureName)
{
FileInfo fInfo = new FileInfo(samplePath + “\\” + pictureName);
if (fInfo.Exists == false)
{
Console.ForegroundColor = ConsoleColor.Red;
Console.WriteLine(“Invalid file name, try again”);
Console.ResetColor();
}
return fInfo.Exists;
}

private static string GetFileName()
{
Console.WriteLine(“Type the name of the file you wish to grafitti”);
return Console.ReadLine();
}
}
}

Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s