I've been having a problem with the following code:
namespace Viewer
{
public partial class Form1 : Form
{
int count = 0;
LinkLabel[] linkLabel = new LinkLabel[200];
string filename;
string extension;
string filepath;
private void btnLoad_Click(object sender, EventArgs e)
{
// Creates a Directory for the Movies Folder
DirectoryInfo myDirectory = new DirectoryInfo(#"C:\Users\User\Movies");
// Creates a list of "File info" objects
List<FileInfo> ls = new List<FileInfo>();
// Adds filetypes to the list
ls.AddRange(myDirectory.GetFiles("*.mp4"));
ls.AddRange(myDirectory.GetFiles("*.avi"));
// Orders the list by Name
List<FileInfo> orderedList = ls.OrderBy(x => x.Name).ToList();
// Loop through file list to act on each item
foreach (FileInfo filFile in orderedList)
{
// Creates a new link label
linkLabel[count] = new LinkLabel();
// Alters name info for display and file calling
filepath = filFile.FullName;
extension = filFile.Extension;
filename = filFile.Name.Remove(filFile.Name.Length - extension.Length);
// Write to the textbox for functional display
textBox1.AppendText(filename + "\r\n");
// Alters link label settings
linkLabel[count].Text = filename;
linkLabel[count].Links.Add(0, linkLabel[count].Text.ToString().Length, filepath);
linkLabel[count].LinkClicked += new LinkLabelLinkClickedEventHandler(LinkedLabelClicked);
// Adds link label to table display
tblDisplay.Controls.Add(linkLabel[count]);
// Indexes count up for arrays
count = count + 1;
}
}
private void LinkedLabelClicked(object sender, LinkLabelLinkClickedEventArgs e)
{
System.Diagnostics.Process.Start(filepath);
}
}
}
My goal is to generate a table of links to all of the media files that I add at launch, and have the links open the files in their respective players.
As of right now, it generates all of the links properly, but whenever I click on any of them, it launches the last item in the list.
For example, if the list contains "300", "Gladiator", and "Top Gun", no matter which link I click, it opens "Top Gun".
I assume that this has to do with it calling the variable "filepath" in the click event, which is left in it's final state. However, I'm not exactly clear on how to create a static link value or action on each individual link, as all of the answers I've researched are in regards to single linklabel situations, not dynamic set-ups.
Any help/advice would be appreciated!
Try as below:
In foreach loop add one line more like:
linkLabel[count].Tag = filepath;
then in click event get this path as blow,
private void LinkedLabelClicked(object sender, LinkLabelLinkClickedEventArgs e)
{
string filepath = ((LinkLabel)sender).Tag.tostring();
System.Diagnostics.Process.Start(filepath);
}
Related
So I want to make some sort of management system or list maker. And I want the data to be stored in a text file. Here's what I have.
So when you click then exit button on the form
private void btnExit_Click(object sender, EventArgs e)
{
if (!File.Exists("paste.txt"))
{
}
else if (File.Exists("paste.txt"))
{
File.Delete("paste.txt");
StreamWriter file = new StreamWriter("paste.txt");
string text = listBox1.Text;
file.Write(text);
file.Close();
}
this.Close();
}
So I want it to save all the text in the textbox to a text file. How could I do this? Right now when I click the exit button the file stays blank.
You can use File.WriteAllText. This will overwrite what's in it at all times, so there's no point in deleting it first if that's what you want.
var path = "paste.txt";
var listBoxText = "";
foreach(var item in listBox1.Items)
{
listBoxText += item.ToString() + "\n";
}
if (File.Exists(path))
{
File.WriteAllText(path, listBoxText, Encoding.UTF8);
}
Not sure what your requirements are OP, but if you also want to create the File if doesn't exist, you could do:
var file = new FileInfo(path);
file.Directory.Create(); // will do nothing if it already exists
File.WriteAllText(path, listBox1.Text, Encoding.UTF8);
https://learn.microsoft.com/en-us/dotnet/api/system.io.file.writealltext?view=netframework-4.8
Here is the pretty way of doing it
Lets say you have an item object
public class ListItem
{
public string Value { get; set; }
public string Description { get; set; }
public string DisplayValue
{
get
{
return $"[{Value}] - {Description}";
}
}
}
You see, I provided an object that could be like that, more complex object, but could be just a string.
When you add objects you create a list and do something like this
var itemList = new List<ListItem>();
// add items
myLst.DisplayMember = "DisplayValue";
myLst.ValueMember = "Value";
myLst.DataSourse = itemList;
In this case you can get the list of "any property" like this (System.Linq)
string[] fileLines =
((List<ListItem>)myLst.DataSourse).Select(itm => itm.Value).ToArray();
Or, if your items are simple strings
string[] fileLines = (from itm in myLst.Items select itm).ToArray();
And then use your file logic to simply in the end call
File.WriteAllLines(path, fileLines);
What I like about this approach is that no explicit loops needs and item can be a more complex item that can have a bunch of properties beyond a simple string description/value in one.
I have created a comboBox inside a Windows Form and inside this comboBox I want to show filenames inside a specific directory.
My code Form 1:
private string path = (#"C:\Users\khaab\Documents\visual studio 2015\Projects\ReadingXML\ReadingXML\bin\Debug\Customers");
private void SelectConfigComboBox_DropDown(object sender, EventArgs e)
{
List<String> Configurations = Directory.EnumerateDirectories(path).ToList();
Path.GetFileName(path);
SelectConfigComboBox.DataSource = Configurations;
}
My problem at this moment is that when I click on the ComboBox it shows me the whole path name I want only the names of the file inside that directory.
after enumerating all files apply Path.GetFileName method to each of them using Select extension method:
private void SelectConfigComboBox_DropDown(object sender, EventArgs e)
{
List<String> Configurations = Directory.EnumerateFiles(path)
.Select(p => Path.GetFileName(p))
.ToList();
SelectConfigComboBox.DataSource = Configurations;
}
Get all fileEntries (full path), and then use Path.GetFileName() to obtain only the filename of each:
List<String> Configurations = new List<string>();
string [] fileEntries = Directory.GetFiles(path);
foreach(string fileName in fileEntries)
{
Configurations.Add(Path.GetFileName(fileName);
}
SelectConfigComboBox.DataSource = Configurations;
Before set DataSource use Path.GetFileName for items in result of Directory.EnumerateDirectories(path).ToList()
FileInfo has a Name property that only contains the filename part.
var files= new DirectoryInfo(path).GetFiles("*");
var firstFilename = files[0].Name;
I initially have a Fileupload tool to upload a textfile, manipulate its content and display into a Listbox or Textbox. The limitation however is Fileupload only supports single uploading, at least to the version of .Net Framework I am using.
What I intend to do is just use a button control and remove the Fileupload. Upon Button click I need to read the textfiles inside a designated folder path and display first the contents inside a multiple lined textbox. (not just the file name) This is my intially written codes, and it is not working.
protected void btnGetFiles_Click(object sender, EventArgs e)
{
string content = string.Empty;
DirectoryInfo dinfo = new DirectoryInfo(#"C:\samplePath");
FileInfo[] Files = dinfo.GetFiles("*.txt");
foreach (FileInfo file in Files)
{
//ListBox1.Items.Add(file.Name);
content += content;
}
txtContent.Text = content;
}
Since your's is web based application you can't access physical paths like c:\\.. you should use Server.MapPath anyway(As per the comment, you don't need to get the file with Server.MapPath). Then for getting the content you can try something like the following:
protected void btnGetFiles_Click(object sender, EventArgs e)
{
try
{
StringBuilder content = new StringBuilder();
if (Directory.Exists(#"C:\samplePath"))
{
// Execute this if the directory exists
foreach (string file in Directory.GetFiles(#"C:\samplePath","*.txt"))
{
// Iterates through the files of type txt in the directories
content.Append(File.ReadAllText(file)); // gives you the conent
}
txtContent.Text = content.ToString();
}
}
catch
{
txtContent.Text = "Something went wrong";
}
}
you wrote content += content;, that is the problem. change it to content += file.Name;, it will work.
I'm attempting to create a dynamic menu strip in my program. Here's an example of what it looks like right now:
Creating the ToolstripMenuItems dynamically itself is easy. What I plan to do is to check if the current month already exists in the folder paths that my program works with, and if it doesn't then it will create an extra menu strip with the date (for example once we hit August, it should create August 2014, with sub-items "NL" & "PL").
However the part that i am stuck at is how to link functionality to these dynamically created sub-items. As I've been unable to find a way to do this, both the "NL" and "PL" tabs open a specific .TXT file of that specific month (which is created elsewhere in the program). However when I make them dynamically, I can't find a way to make them do this and they just don't have any functionality.
At this point I find myself manually creating new menu items & code every month for this. And I would very much prefer the program to run itself.
Any tips on how to make dynamic menuitems functional?
Added code:
private void CreateMenu()
{
ToolStripMenuItem item = new ToolStripMenuItem();
item.Text = "Logs";
DirectoryInfo dir = new DirectoryInfo(#"Y:\Heineken\Tools\Logs\");
foreach (DirectoryInfo directory in dir.GetDirectories())
{
ToolStripMenuItem dateItem = new ToolStripMenuItem(directory.Name);
ToolStripMenuItem NLMenu = new ToolStripMenuItem("NL"); // <--- This needs to open a specific text file on a network share
ToolStripMenuItem PLMenu = new ToolStripMenuItem("PL"); // <--- This needs to open a specific text file on a network share
dateItem.DropDownItems.Add(NLMenu);
dateItem.DropDownItems.Add(PLMenu);
item.DropDownItems.Add(dateItem);
}
menuToolStripMenuItem.DropDownItems.Add(item);
}
It would help if you would post some code snippet of how you are dynamically creating your menu items. In general, you can link functionality to dynamic menu entries by simply passing a delegate into the ToolStripMenuItem constructor, like so:
var entry = new ToolStripMenuItem("NL", null, delegate
{
//TODO: do something
});
owner.DropDownItems.Add(entry);
This assumes the variable "owner" is your parent menu entry.
Edit: Given the code you supplied, you could do it like this
private void OpenTextFile(string id)
{
//TODO: logic for opening the shared file
}
private void CreateMenu()
{
ToolStripMenuItem item = new ToolStripMenuItem();
item.Text = "Logs";
DirectoryInfo dir = new DirectoryInfo(#"Y:\Heineken\Tools\Logs\");
foreach (DirectoryInfo directory in dir.GetDirectories())
{
ToolStripMenuItem dateItem = new ToolStripMenuItem(directory.Name);
ToolStripMenuItem NLMenu = new ToolStripMenuItem("NL", null, (sender, e) => OpenTextFile("NL"));
ToolStripMenuItem PLMenu = new ToolStripMenuItem("PL", null, (sender, e) => OpenTextFile("PL"));
dateItem.DropDownItems.Add(NLMenu);
dateItem.DropDownItems.Add(PLMenu);
item.DropDownItems.Add(dateItem);
}
menuToolStripMenuItem.DropDownItems.Add(item);
}
You need to hook up the click event handler to the dynamically created ToolstripMenuItems. In the click event handler you can then cast the sender to ToolstripMenuItem and access any properties you may need to work out which text file you need to load.
For example this click handler will give a message box with the text of the menu item:
private void toolStripMenuItem_Click(object sender, EventArgs e)
{
MessageBox.Show(((ToolStripMenuItem)sender).Text);
}
To add a new dynamic menu item and link it to the click handler you can do this:
ToolStripMenuItem newItem = new ToolStripMenuItem("Dynamic Option");
newItem.Click += toolStripMenuItem_Click;
existingToolStripMenuItem.DropDownItems.Add(newItem);
Edit after code posted
You can store the file that is supposed to be opened when the menu item is clicked in the Tag property. When the menu item is then clicked you can open the file based on the path in the Tag.
For example, in your CreateMenu method you would need to do something like this:
ToolStripMenuItem NLMenu = new ToolStripMenuItem("NL");
//store the filename here for later
NLMenu.Tag = Path.Combine(dir.FullName, "nl.txt");
//attach the click handler
NLMenu.Click += toolStripMenuItem_Click;
//repeat for PLMenu...
Then in the click handler you can do this:
private void toolStripMenuItem_Click(object sender, EventArgs e)
{
string filename = ((ToolStripMenuItem)sender).Tag;
//do something with the file.
}
Recently I've been quite enjoying C# and I'm just testing with it but there seems to be one part I don't get.
Basically I want it so that when I click the SAVE button must save all the items in the listbox to a text file. At the moment all it comes up with in the file is System.Windows.Forms.ListBox+ObjectCollection.
Here's what I've got so far. With the SaveFile.WriteLine(listBox1.Items); part I've tried putting many different methods in and I can't seem to figure it out. Also take in mind that in the end product of my program I would like it to read back to that to that text file and output what's in the text file to the listbox, if this isn't possible then my bad, I am new to C# after all ;)
private void btn_Save_Click(object sender, EventArgs e)
{
const string sPath = "save.txt";
System.IO.StreamWriter SaveFile = new System.IO.StreamWriter(sPath);
SaveFile.WriteLine(listBox1.Items);
SaveFile.ToString();
SaveFile.Close();
MessageBox.Show("Programs saved!");
}
From your code
SaveFile.WriteLine(listBox1.Items);
your program actually does this:
SaveFile.WriteLine(listBox1.Items.ToString());
The .ToString() method of the Items collection returns the type name of the collection (System.Windows.Forms.ListBox+ObjectCollection) as this is the default .ToString() behavior if the method is not overridden.
In order to save the data in a meaningful way, you need to loop trough each item and write it the way you need. Here is an example code, I am assuming your items have the appropriate .ToString() implementation:
System.IO.StreamWriter SaveFile = new System.IO.StreamWriter(sPath);
foreach(var item in listBox1.Items)
{
SaveFile.WriteLine(item.ToString());
}
Items is a collection, you should iterate through all your items to save them
private void btn_Save_Click(object sender, EventArgs e)
{
const string sPath = "save.txt";
System.IO.StreamWriter SaveFile = new System.IO.StreamWriter(sPath);
foreach (var item in listBox1.Items)
{
SaveFile.WriteLine(item);
}
SaveFile.Close();
MessageBox.Show("Programs saved!");
}
There is one line solution to the problem.
System.IO.File.WriteAllLines(path, Listbox.Items.Cast<string>().ToArray());
put your file path+name and Listbox name in above code.
Example:
in Example below path and name of the file is D:\sku3.txt and list box name is lb
System.IO.File.WriteAllLines(#"D:\sku3.txt", lb.Items.Cast<string>().ToArray());