Add image from local system to listbox - c#

I have a listbox and i want to update my listbox with all the logical drives. I want to show all the images in a parent and child format. I am using this code
string[] path = System.IO.Directory.GetLogicalDrives();
foreach (string directories in path)
{
Bitmap bitimg = null;
DirectoryInfo dinfo = new DirectoryInfo(directories);
FileInfo[] Files = dinfo.GetFiles("*.jpg");
for (int i = 0; i < Files.Count(); i++)
{
string fileName = Files[i].FullName;
Uri uri = new Uri(fileName, UriKind.Relative);
BitmapImage bitmap=new BitmapImage(uri);
Image img = new Image();
img.Source(bitmap);
listBox1.Items.Add(img);
}
}
But i am getting error as
Cannot create an instance of the abstract class or interface 'System.Drawing.Image'

Related

Listview puts the same images in every group

My listview should make a group for every directory on a specified path, and add the pictures from each directory to the group that was created for it; but instead it adds the pictures from the last directory to each group.
Any ideas how can i solve this problem?
Thank you!
private void Form2_Load(object sender, EventArgs e)
{
string path = #"C:\pics\";
string[] tabs_needed = System.IO.Directory.GetDirectories(path);
foreach (string folder in tabs_needed)
{
FileInfo f = new FileInfo(folder);
listBox1.Items.Add(f.Name);
TabPage ghhk = new TabPage(f.Name);
tabControl1.Controls.Add(ghhk);
ListView listView1 = new ListView();
ghhk.Controls.Add(listView1);
listView1.Dock = DockStyle.Fill;
string new_path = path + f.Name;
string[] groups_needed =System.IO.Directory.GetDirectories(new_path);
foreach (string ufolder in groups_needed)
{
FileInfo uf = new FileInfo(ufolder);
string f_path = String.Concat(new_path + #"\" + uf.Name + #"\");
DirectoryInfo dir = new DirectoryInfo(f_path);
ImageList imagelist = new ImageList();
foreach (FileInfo file in dir.GetFiles())
{
try
{
imagelist.Images.Add(Image.FromFile(file.FullName));
}
catch
{
}
}
imagelist.ImageSize = new Size(32, 32);
listView1.View = View.LargeIcon;
ListViewGroup gr1 = new ListViewGroup(uf.Name);
listView1.Groups.Add(gr1);
string tpath = String.Concat(f_path, "gf.txt");
for (int counter = 0; counter < imagelist.Images.Count; counter++)
{
ListViewItem item = new ListViewItem();
item.Text = File.ReadAllLines(tpath).Skip(counter).Take(1).First();
item.ImageIndex = counter;
item.Group = gr1;
listView1.Items.Add(item);
}
listView1.LargeImageList = imagelist;
}
This is happening because you are instantiating the ImageList each time in the foreach loop. When you assign the imagelist finally to listView1.LargeImageList, it is only the final imagelist instance that gets attached.
You will need to move the instantiation out of the foreach loop
ImageList imagelist = new ImageList();
foreach (string ufolder in groups_needed)
{
...
}
You may also need to change the logic for your ImageIndex to get this working, now that the ImageList is out of the loop.
You should replace
listView1.LargeImageList = imagelist;
with
listView1.LargeImageList.Images.AddRange(imagelist.Images.Cast<System.Drawing.Image>().ToArray())
Because you are overwriting image list at each cycle.

How to get icon image

I want to make same Window File explorer.
but I don't know how to get file default Icon image.
If I can get file default image(Icon), I would like to add to the listview.
my code is as below
private void AddFiles(string strPath)
{
lv_local.BeginUpdate();
lv_local.Items.Clear();
iFiles = 0;
try
{
DirectoryInfo di = new DirectoryInfo(strPath + "\\");
FileInfo[] theFiles = di.GetFiles();
foreach (FileInfo theFile in theFiles)
{
iFiles++;
ListViewItem lvItem = new ListViewItem(theFile.Name);
lvItem.SubItems.Add(String.Format("{0:N0}", theFile.Length) + "KB");
lvItem.SubItems.Add(theFile.Extension);
lvItem.SubItems.Add(theFile.LastWriteTime.ToShortDateString());
lvItem.ImageIndex = 4;
// I want to put an image that was read default image
lv_local.Items.Add(lvItem);
}
}
catch (Exception Exc)
{
}
lv_local.EndUpdate();
}
Create ImageList and add icons
var imageList = new ImageList();
imageList.Images.Add("IconKey", icon);
Assign the ImageList to ListView
listView.LargeImageList = imageList;
Assign icon for the list view item
listViewItem.ImageKey = "itemImageKey";
or listViewItem.ImageIndex = 1;

ERROR: The process cannot access the file 'Companion.jpg' because it is being used by another process

I have a problem when trying to delete the files from a directory because it says a file is being used by another process. I cant figure out how to delete all the files in the folder after I run the cmdCombine Method. Here is the code, a little help please:
private void cmdCombine_Click(object sender, EventArgs e)
{
DirectoryInfo directory = new DirectoryInfo(#"C:\Users\Elder Zollinger\Desktop\Images");
if (directory != null)
{
FileInfo[] files = directory.GetFiles();
ResizeImages(files);
}
DirectoryInfo directory2 = new DirectoryInfo(#"C:\Users\Elder Zollinger\Desktop\Upload");
if (directory2 != null)
{
FileInfo[] files = directory2.GetFiles();
CombineImages(files);
System.IO.DirectoryInfo downloadedMessageInfo = new DirectoryInfo(#"C:\Users\Elder Zollinger\Desktop\Images");
foreach (FileInfo file2 in downloadedMessageInfo.GetFiles())
{
file2.Delete();
}
foreach (DirectoryInfo dir in downloadedMessageInfo.GetDirectories())
{
dir.Delete(true);
}
}
}
//Method for resizing the images
private void ResizeImages(FileInfo[] files)
{
//Set Count integers and strings to save files
int fileCount = Directory.GetFiles(#"C:\Users\Elder Zollinger\Desktop\Images").Length;
int count = 1;
string fileNameOnly = Path.GetFileNameWithoutExtension(#"C:\Users\Elder Zollinger\Desktop\Upload\NewImage.jpg");
string extension = Path.GetExtension(#"C:\Users\Elder Zollinger\Desktop\Upload\NewImage.jpg");
string uploadPath = Path.GetDirectoryName(#"C:\Users\Elder Zollinger\Desktop\Upload\NewImage.jpg");
string newFullUploadPath = #"C:\Users\Elder Zollinger\Desktop\Upload\NewImage.jpg";
//Read Files in the folder
foreach (FileInfo file in files)
{
//Create a new file name that doesnt exist
while (File.Exists(newFullUploadPath))
{
string tempFileName = string.Format("{0}({1})", fileNameOnly, count++);
newFullUploadPath = Path.Combine(uploadPath, tempFileName + extension);
}
//Resize and save images when there is more than 2
if (fileCount > 2)
{
Image img = Image.FromFile(file.FullName);
var newImage = resizeImage(img, new Size(66, 200));
newImage.Save(newFullUploadPath, System.Drawing.Imaging.ImageFormat.Jpeg);
}
//Resize and save images for 1 or 2 images
else
{
Image img = Image.FromFile(file.FullName);
var newImage = resizeImage(img, new Size(100, 200));
newImage.Save(newFullUploadPath, System.Drawing.Imaging.ImageFormat.Jpeg);
}
}
}
//Stitch Images
private void CombineImages(FileInfo[] files)
{
//Create strings for saved images
int count = 1;
string fileNameOnly = Path.GetFileNameWithoutExtension(#"C:\Users\Elder Zollinger\Desktop\Dump\Final.jpg");
string extension = Path.GetExtension(#"C:\Users\Elder Zollinger\Desktop\Dump\Final.jpg");
string uploadPath = Path.GetDirectoryName(#"C:\Users\Elder Zollinger\Desktop\Dump\Final.jpg");
string newFullUploadPath = #"C:\Users\Elder Zollinger\Desktop\Dump\Final.jpg";
List<int> imageHeights = new List<int>();
int nIndex = 0;
int width = 0;
foreach (FileInfo file in files)
{
Image img = Image.FromFile(file.FullName);
imageHeights.Add(img.Height);
width += img.Width;
img.Dispose();
}
imageHeights.Sort();
int height = imageHeights[imageHeights.Count - 1];
Bitmap img3 = new Bitmap(width, height);
Graphics g = Graphics.FromImage(img3);
g.Clear(SystemColors.AppWorkspace);
foreach (FileInfo file in files)
{
Image img = Image.FromFile(file.FullName);
if (nIndex == 0)
{
g.DrawImage(img, new Point(0, 0));
nIndex++;
width = img.Width;
}
else
{
g.DrawImage(img, new Point(width, 0));
width += img.Width;
}
img.Dispose();
}
g.Dispose();
while (File.Exists(newFullUploadPath))
{
string tempFileName = string.Format("{0}({1})", fileNameOnly, count++);
newFullUploadPath = Path.Combine(uploadPath, tempFileName + extension);
}
img3.Save(newFullUploadPath, System.Drawing.Imaging.ImageFormat.Jpeg);
img3.Dispose();
imageLocation.Image = Image.FromFile(newFullUploadPath);
foreach (FileInfo file in files)
{
file.Delete();
}
}
//Method to resize the images
private static Image resizeImage(Image imgToResize, Size size)
{
return (Image)(new Bitmap(imgToResize, size));
}
private void SelectImages_Click(object sender, EventArgs e)
{
Stream myStream = null;
OpenFileDialog openFileDialog1 = new OpenFileDialog();
openFileDialog1.InitialDirectory = "c:\\";
openFileDialog1.Filter = "png files (*.png)|*.png|All files (*.*)|*.*";
openFileDialog1.FilterIndex = 2;
openFileDialog1.RestoreDirectory = true;
if (openFileDialog1.ShowDialog() == DialogResult.OK)
{
if ((myStream = openFileDialog1.OpenFile()) != null)
{
int count = 1;
string fileNameOnly = Path.GetFileNameWithoutExtension(#"C:\Users\Elder Zollinger\Desktop\Images\Companion.jpg");
string extension = Path.GetExtension(#"C:\Users\Elder Zollinger\Desktop\Images\Companion.jpg");
string uploadPath = Path.GetDirectoryName(#"C:\Users\Elder Zollinger\Desktop\Images\Companion.jpg");
string newFullUploadPath = #"C:\Users\Elder Zollinger\Desktop\Images\Companion.jpg";
while (File.Exists(newFullUploadPath))
{
string tempFileName = string.Format("{0}({1})", fileNameOnly, count++);
newFullUploadPath = Path.Combine(uploadPath, tempFileName + extension);
}
System.IO.File.Copy(openFileDialog1.FileName, newFullUploadPath);
}
}
}
private void Clear_Click(object sender, EventArgs e)
{
imageLocation.Image = null;
System.IO.DirectoryInfo downloadedMessageInfo = new DirectoryInfo(#"C:\Users\Elder Zollinger\Desktop\Images");
foreach (FileInfo file in downloadedMessageInfo.GetFiles())
{
file.Delete();
}
foreach (DirectoryInfo dir in downloadedMessageInfo.GetDirectories())
{
dir.Delete(true);
}
}
}
}
I suspect this is the problem:
Image img = Image.FromFile(file.FullName);
That opens the file - but you never dispose the same object, so the file will be open until the object is finalized. Image implements IDisposable, so you should use a using statement:
using (Image image = ...)
{
...
}
You should also dispose of the resized image, although at least that isn't holding on to a file handle.
Note that you've got the almost exactly the same block of code for whether there are more than two files or not. It would be cleaner to choose just the size conditionally:
Size size = fileCount > 2 ? new Size(66, 200) : new Size(100, 200);
using (Image original = Image.FromFile(file.FullName))
using (Image resized = ResizeImage(original, size))
{
resized.Save(newFullUploadPath, ImageFormat.Jpeg);
}
Much cleaner, IMO.

how could I show filename under the image shown in the listview

I am writing a code where I need to show several images in a listview, I can get the images shown, but how could I also show the file's name beneath the image?
Below is part of my code
string stu_name_1 = listBox4.SelectedItem.ToString();
string stu_name_2 = listBox6.SelectedItem.ToString();
string add = stu_name_1 +"/"+ stu_name_2;
Directory.CreateDirectory(add);
OpenFileDialog sf = new OpenFileDialog();
Dictionary<string, string> imageDictionary = new Dictionary<string, string>();
sf.Multiselect = true;
if (sf.ShowDialog() == DialogResult.OK)
{
string[] files = sf.FileNames;
foreach (string file in files)
{
// Use static Path methods to extract only the file name from the path.
string fileName = System.IO.Path.GetFileName(file);
string destFile = System.IO.Path.Combine(add, fileName);
Image imgToAdd = Image.FromFile(file);
imgToAdd.Tag = file;
System.IO.File.Copy(file, destFile, true);
imageList1.Images.Add(imgToAdd);
//imageDictionary.Add(Path.GetFileName(file), file);
}
}
listView1.Items.Clear();
for (int i = 0; i < imageList1.Images.Count; i++)
{
ListViewItem lvi = new ListViewItem();
lvi.ImageIndex = i;
listView1.Items.Add(lvi);
string stu_name_1 = listBox4.SelectedItem.ToString();
string stu_name_2 = listBox6.SelectedItem.ToString();
string add = stu_name_1 +"/"+ stu_name_2;
Directory.CreateDirectory(add);
OpenFileDialog sf = new OpenFileDialog();
Dictionary<string, string> imageDictionary = new Dictionary<string, string>();
sf.Multiselect = true;
if (sf.ShowDialog() == DialogResult.OK)
{
listView1.Items.Clear();//Clear first
string[] files = sf.FileNames;
foreach (string file in files)
{
// Use static Path methods to extract only the file name from the path.
string fileName = System.IO.Path.GetFileName(file);
string destFile = System.IO.Path.Combine(add, fileName);
Image imgToAdd = Image.FromFile(file);
imgToAdd.Tag = file;
System.IO.File.Copy(file, destFile, true);
imageList1.Images.Add(imgToAdd);//Suppose the imageList1 is dedicated to your listView1 only.
listView1.Items.Add(fileName, imageList1.Images.Count-1);
//imageDictionary.Add(Path.GetFileName(file), file);
}
}

c# foreach image in folder

Below is some code that
creates a directory
uses MagickNet to covert a PDF into separate BMP images and stores it in a folder (ImagePath)
Then it uses TessNet2 to scan each image in that folder to parse out information
I can't seem to get the foreach loop that scans the ImagePath folder. Any help?
The error right now is on the 'foreach' statement and it says "Cannot convert type 'char' to 'System.Drawing.Image'"
static void Main(string[] args)
{
string ImagePath = exePath + "\\Images";
if (!Directory.Exists(ImagePath))
{
Directory.CreateDirectory(ImagePath);
}
MagickReadSettings settings = new MagickReadSettings();
settings.Density = new MagickGeometry(300, 300);
using (MagickImageCollection images = new MagickImageCollection())
{
images.Read(#"D:\Test\ABStest.pdf",settings);
int page = 1;
foreach (MagickImage image in images)
{
image.Write(ImagePath + "\\ABS" + page + ".bmp");
page++;
}
}
foreach (Image item in ImagePath)
{
using (Bitmap bmp = new Bitmap(item))
{
tessnet2.Tesseract tessocr = new tessnet2.Tesseract();
tessocr.Init(#"C:\Users\Matt Taylor\Documents\Visual Studio 2012\Projects\TessNet2\TessNet2\bin\Debug\tessdata", "eng", false);
tessocr.GetThresholdedImage(bmp, Rectangle.Empty).Save("c:\\temp\\" + Guid.NewGuid().ToString() + ".bmp");
// Tessdata directory must be in the directory than this exe
Console.WriteLine("Multithread version");
ocr.DoOCRMultiThred(bmp, "eng");
//Console.WriteLine("Normal version");
//ocr.DoOCRNormal(bmp, "eng");
}
}
}
You can use Directory.GetFiles to return all the filenames in the directory and create your Bitmaps from there
foreach (string imageFileName in Directory.GetFiles(ImagePath))
{
using (Bitmap bmp = new Bitmap(imageFileName))
{
}
}
But if there are other files in that folder you should add a filter
foreach (string imageFileName in Directory.GetFiles(ImagePath, "*.jpg"))
{
using (Bitmap bmp = new Bitmap(imageFileName))
{
}
}
You don't need to save the file to disk. You could use the .ToBitmap() method of MagickImage.
foreach (MagickImage image in images)
{
using (Bitmap bmp = image.ToBitmap())
{
tessnet2.Tesseract tessocr = new tessnet2.Tesseract();
// etc...
}
}
You are looping through String ImagePath, which gives you a collection of characters. You need to search through the directory with Directory.GetFiles(), and load the images with Image.FromFile():
foreach (String itemPath in Directory.GetFiles(ImagePath))
{
using (Image item = Image.FromFile(itemPath))
{
...
}
}

Categories

Resources