How to open a file by clicking on it in TreeView - winforms

How do I open a file (ex. PDF) when I click the lowest child node in my tree.
I have created a TreeView program which is automatically filled by a database file.

Associate a path to that node, then use something like this:
private void LinkClicked(object sender, LinkClickedEventArgs e)
{
Process.Start(#".\" + "YOUR FILE NAME AND EXTENSION");
}
Read about: Process.Start
Starts a process resource by specifying the name of a document or application
file and associates the resource with a new System.Diagnostics.Process component.

You need to look at TreeNode Class
Example :
private void Form1_Load(object sender, EventArgs e)
{
//
// This is the first node in the view.
//
TreeNode treeNode = new TreeNode("Windows");
treeView1.Nodes.Add(treeNode);
//
// Another node following the first node.
//
treeNode = new TreeNode("Linux");
treeView1.Nodes.Add(treeNode);
//
// Create two child nodes and put them in an array.
// ... Add the third node, and specify these as its children.
//
TreeNode node2 = new TreeNode("C#");
TreeNode node3 = new TreeNode("VB.NET");
TreeNode[] array = new TreeNode[] { node2, node3 };
//
// Final node.
//
treeNode = new TreeNode("Dot Net Perls", array);
treeView1.Nodes.Add(treeNode);
}
Though example is not reading nodes from DB. You can do that writing a query to fetch nodes.Follow steps on following path , it will lead you from scratch
Create a TreeView from a Database in Windows Forms and C#
Example Source : Tree View
For opening file on Node click look at
public event TreeNodeMouseClickEventHandler NodeMouseClick
// If a node is double-clicked, open the file indicated by the TreeNode.
void treeView1_NodeMouseClick(object sender,
TreeNodeMouseClickEventArgs e)
{
try
{
System.Diagnostics.Process.Start(#"c:\" + e.Node.Text);//e.Node.Text contains fileName
}
// If the file is not found, handle the exception and inform the user.
catch (System.ComponentModel.Win32Exception)
{
MessageBox.Show("File not found.");
}

Related

Creating a "Chain Reaction" of colliders or triggers in Unity 2D

I'm trying to create a 'Chain Reaction" of sorts. What I mean is that I have a bool on all of my game objects. When Object A's bool is set to true during gameplay, I would like object B to be set to true and then C and so on for every game object that is in the chain. It should also work the other way around, so that if A is set to false again, all of the objects in the 'chain' are set to false.
I currently have a system where I add each currently colliding object to a list of gameObjects. But I have no idea how to create this 'knock on' effect where one object affects all of the objects in the chain.
Is there a simpler way of achieving this?
What you show above can be described as a node, where each node has a child node (or nodes) and a parent node.
public class Node
{
public Node parentNode;
public Node childNode;
public bool someBool;
}
Then you can use a recursive function to traverse the nodes. Below is an example of traversal utilizing the child nodes.
public void SetBoolOnChildNodes(Node rootNode, bool value)
{
if (rootNode != null)
{
rootNode.someBool = value;
SetBoolOnChildNodes(rootNode.childNode, value);
}
}
If order is not important, it would make sense to have the root object hold a list of all nodes and have each node hold reference to the root object. Then you just set the boolean value using a loop constructed from the root objects node list.
public class Node2
{
public Node2 rootNode; // Null for root node, populated for all others
public List<Node2> nodes; // Populated only on root node (or all.. doesnt really matter other than memory)
public bool someBool;
}
public void SetValueOnChildNodes(Node2 rootNode, bool value)
{
if (rootNode == null) return;
rootNode.someBool = value;
foreach (var node in rootNode.nodes)
{
node.someBool = value;
}
}

how to get tag from node in c# window form

enter image description hereHow I can get the full path that exist in the tag of the node (in TreeView hierarchy)?
private void treeView_root_NodeMouseClick(object sender, TreeNodeMouseClickEventArgs e) {
if (e.Node.Parent == null) { }
if (e.Node.Parent != null && *e.Node.Parent.Text == "test"*){ }
}
In the condition, I want to use the current directory, instead of test. The current directory's full path is already in Tag. The question is, how can I get the path from Tag so as to move forward into the directory?enter image description here
Node.Tag is type of object so you must do cast to type, in which you saved it to it.
Example:
Node.Tag = "This is node tag"
string nodeTag = Node.Tag as String;
Or:
Node.Tag = 123
string nodeTag = (int) Node.Tag;

why is this C++/CLI code not adding the files to a listbox

I have this c++ code that is supposed to detect when a file has been modified in a directory and add the file name to a list box.
This is the file watcher part which is inside a button that starts the monitoring process
private: System::Void button1_Click(System::Object^ sender, System::EventArgs^ e) {
array<String^>^ args = Environment::GetCommandLineArgs();
FileSystemWatcher^ fsWatcher = gcnew FileSystemWatcher( );
fsWatcher->Path = "C:\\users\\patchvista2";
fsWatcher->IncludeSubdirectories = true;
fsWatcher->NotifyFilter = static_cast<NotifyFilters>
(NotifyFilters::FileName |
NotifyFilters::Attributes |
NotifyFilters::LastAccess |
NotifyFilters::LastWrite |
NotifyFilters::Security |
NotifyFilters::Size );
Form1^ handler = gcnew Form1();
fsWatcher->Changed += gcnew FileSystemEventHandler(handler, &Form1::OnChanged);
fsWatcher->Created += gcnew FileSystemEventHandler(handler, &Form1::OnChanged);
fsWatcher->EnableRaisingEvents = true;
}
then for the onchange part I have this code
void OnChanged (Object^ source, FileSystemEventArgs^ e)
{
// Here is the problem
MessageBox::Show(e->FullPath);
listBox1->Items->Add(e->FullPath);
// End problem
System::Security::Cryptography::MD5 ^ md5offile = MD5CryptoServiceProvider::Create();
array<Byte>^ hashValue;
FileStream^ fs = File::Open(e->FullPath, IO::FileMode::Open, IO::FileAccess::Read, IO::FileShare::ReadWrite);
fs->Position = 0;
hashValue = md5offile->ComputeHash(fs);
PrintByteArray(hashValue);
fs->Close();
Application::DoEvents();
}
It will message box me the file name but it will not add it to the list box. I tried having it display the file name to a label but that did not work either. it seems like the screen is not refreshing once this code loop is started. I have this code in vb.net and it does add the file name to the list box. can someone show me why the file name is not getting added tot the list box.
Two things:
You need to keep the FileSystemWatcher alive. It's liable to be garbage collected where you've got it now. (Create a class field and stick it there.)
You need to Invoke onto the UI thread whenever you do anything with a UI component.
Here's the approximate syntax for #2 (I'm away from a compiler at the moment, this may not be exact.)
void Form1::AddToListBox(String^ filename)
{
listBox1->Items->Add(filename);
}
void Form1::OnChanged(Object^ source, FileSystemEventArgs^ e)
{
Action<String^>^ addDelegate = gcnew Action<String^>(this, &Form1::AddToListBox);
this->Invoke(addDelegate, e->FullPath);
...
}

Click on treeview node open a new MDI form, focus left on first form

I'm trying to open a new form after clicking a node in a treeview.
In the first MDI form I have a treeview, when I click on a node in the tree view a 2nd MDI form is opened, but the first form keeps the focus. I want the new form to have the focus.
I have noticed the first form's _Enter event is firing as if something is setting focus back to the first form.
There is also a button on the first form that does the same function and it works great. I have a feeling the treeview has some special attribute set to cause the focus to come back to the first form.
Here is the code opening the form
private void tvClientsAccounts_NodeMouseClick(object sender, TreeNodeMouseClickEventArgs e)
{
OpenClientOrAccount(e.Node);
}
private void OpenClientOrAccount(TreeNode Node)
{
if (Node.Tag is Client)
{
frmClients frmC = new frmClients();
Client Client = (Client)Node.Tag;
frmC.Id = Client.Id;
frmC.HouseholdId = Client.Household.Id;
frmC.MdiParent = Program.frmMain;
frmC.Show();
}
else if (Node.Tag is Account)
{
frmAccounts frmA = new frmAccounts();
Account Account = (Account)Node.Tag;
frmA.Id = Account.Id;
frmA.ClientId = Account.Client.Id;
frmA.MdiParent = Program.frmMain;
frmA.Show();
}
}
Here is the designer code defining the treeview
//
// tvClientsAccounts
//
this.tvClientsAccounts.BackColor = System.Drawing.SystemColors.Control;
this.tvClientsAccounts.Indent = 15;
this.tvClientsAccounts.LineColor = System.Drawing.Color.DarkGray;
this.tvClientsAccounts.Location = new System.Drawing.Point(228, 193);
this.tvClientsAccounts.Name = "tvClientsAccounts";
this.tvClientsAccounts.Nodes.AddRange(new System.Windows.Forms.TreeNode[] {
treeNode9});
this.tvClientsAccounts.PathSeparator = "";
this.tvClientsAccounts.ShowNodeToolTips = true;
this.tvClientsAccounts.Size = new System.Drawing.Size(411, 213);
this.tvClientsAccounts.TabIndex = 23;
this.tvClientsAccounts.BeforeExpand += new System.Windows.Forms.TreeViewCancelEventHandler(this.tvClientsAccounts_BeforeExpand);
this.tvClientsAccounts.AfterExpand += new System.Windows.Forms.TreeViewEventHandler(this.tvClientsAccounts_AfterExpand);
this.tvClientsAccounts.BeforeSelect += new System.Windows.Forms.TreeViewCancelEventHandler(this.tvClientsAccounts_BeforeSelect);
this.tvClientsAccounts.AfterSelect += new System.Windows.Forms.TreeViewEventHandler(this.tvClientsAccounts_AfterSelect);
this.tvClientsAccounts.NodeMouseClick += new System.Windows.Forms.TreeNodeMouseClickEventHandler(this.tvClientsAccounts_NodeMouseClick);
Thanks for your help
Russ
Yes, TreeView is a bit of a pain that way, it restores the focus to itself. That's why it has the AfterXxx events, but there's no AfterNodeMouseClick event. The way to solve it is to delay executing the method, until after all event side-effects are completed. That's elegantly done by using the Control.BeginInvoke() method, its delegate target runs when the UI thread goes idle again. Like this:
private void treeView1_NodeMouseClick(object sender, TreeNodeMouseClickEventArgs e) {
this.BeginInvoke(new Action(() => OpenClientOrAccount(e.Node)));
}

How to determine which node was clicked. Silverlight treeview

How to determine on over which node click was performed?
Treeview from silverlight toolkit.
In MouseRightButtonUp i need to get node:
private void treeView_MouseRightButtonUp(object sender, MouseButtonEventArgs e)
The MouseButtonEventArgs has an OriginalSource property which indicates the actual UIElement that generated the event.
In order to discover which Node that element belongs to you will need to traverse the visual tree to discover it. I use this extension method to assist with that:-
public static IEnumerable<DependencyObject> Ancestors(this DependencyObject root)
{
DependencyObject current = VisualTreeHelper.GetParent(root);
while (current != null)
{
yield return current;
current = VisualTreeHelper.GetParent(current);
}
}
Then in the MouseRightButtonUp event you can use this code to find the item:-
TreeViewItem node = ((DependencyObject)e.OriginalSource)
.Ancestors()
.OfType<TreeViewItem>()
.FirstOrDefault();

Resources