0

The excel sheet's hyperlink I have will direct to a folder in the user's pc. What I want to do is import from excel the hyperlink to the DataGridView and from there, be able to open the file the hyperlink directs to. However, I keep seeing people setting the hyperlink website inside their c# code which is not what I'm trying to find since it's hard coding it. Is there a way for it to be achieved?

Reza Aghaei
  • 120,393
  • 18
  • 203
  • 398
  • 1
    I don't think so. You will have to code the CellClicked and the CellPainting events. Or you could host a LinkLabel. Also: What are you targetting: Winforms, WPF, ASP..? YOU should __always__ TAG your questions correctly so one can see it on the questions page! – TaW Feb 03 '20 at 07:07
  • 1
    Use a `DataGridViewLinkColumn`, handle `CellContentClick` and then pass the url to `System.Diagnostics.Process.Start(url)`. – Reza Aghaei Feb 03 '20 at 08:15
  • 1
    Does this answer your question? [How to open in default browser in C#](https://stackoverflow.com/questions/4580263/how-to-open-in-default-browser-in-c-sharp) – oleksa Feb 03 '20 at 09:02
  • 1
    @oleksa There are a few other points as well, like showing the url as a hyperlink, and handling the click event on the hyperlink part of the cell, getting the value from cell. So IMO, the linked post helps to some extent but doesn't answer the question. – Reza Aghaei Feb 03 '20 at 09:13

1 Answers1

2

It's not something automatic and you need to code it manually. You need to use a DataGridViewLinkColumn, and handle its CellContentClick and then pass the value of the cell as url to System.Diagnostics.Process.Start method.

If you have a lot of locations in your application which you have such a requirement, you can make a function to reuse the logic or create custom DataGridViewLinkColumn to have this behavior inside.

Example

private void Form1_Load(object sender, EventArgs e)
{
    //Get data
    var data = new[] {
        new { Title="Stackoverflow", Location = @"https://www.Stackoverflow.com"},
        new { Title="Windows Folder", Location = @"C:\Windows"},
        new { Title="Windows Folder", Location = @"C:\Windows\system.ini"},
        new { Title="Network Share", Location = @"\\127.0.0.1"},
    };

    // Add columns
    dataGridView1.Columns.Add(new DataGridViewTextBoxColumn()
    {
        Name = "TitleColumn", DataPropertyName = "Title", HeaderText = "Title"
    });
    dataGridView1.Columns.Add(new DataGridViewLinkColumn()
    {
        Name = "LocationColumn", DataPropertyName = "Location", HeaderText = "Location"
    });

    //Handle click on link
    dataGridView1.CellContentClick += (obj, args) =>
    {
        if (args.RowIndex < 0 || args.ColumnIndex < 0)
            return;
        if (dataGridView1.Columns[args.ColumnIndex].Name != "LocationColumn")
            return;
        var value = $"{dataGridView1[args.ColumnIndex, args.RowIndex].Value}";
        if (Uri.TryCreate(value, UriKind.Absolute, out Uri uri))
            System.Diagnostics.Process.Start(value);
    };

    //Show data
    dataGridView1.DataSource = data.ToList();
}
Reza Aghaei
  • 120,393
  • 18
  • 203
  • 398
  • Yeap this does help but unfortunately I realised that it won't solve my task because the link is declared inside the excel folder so importing it takes away the link and just makes it a normal string. only way I can think of is to get the link in a separate column and try to read it there through c# I guess. Thanks! – timetoquitcoding Feb 04 '20 at 09:04
  • 1
    A URL is a string, what makes it a URL is the way that you work with it. I don't quiet get it. What's the example data of the link? If it's a URL, then above code should work fine for you. – Reza Aghaei Feb 04 '20 at 09:10
  • J:\pictures\{EMP No} {(EMP Name)}\{Course Name} {(d-ddMMMyyyy)}.pdf. The ones in {} are all changed for every data row. So it can be, for example, 0123 (Tim J)\ Higher Maths (4Feb2020).pdf – timetoquitcoding Feb 04 '20 at 09:14
  • 1
    So it will be something like `J:\0123 (Tim J)\ Higher Maths (4Feb2020).pdf` right? Then there is no problem using that as URL, I updated the code and you can see ` @"C:\Windows\system.ini"` will work well, the same for any other files. – Reza Aghaei Feb 04 '20 at 09:20
  • 1
    You just need to load data into the grid. For the column which contains the URL, add `DataGridViewLinkColumn` and use the code which I shared above to handle click on the link. The reason that I insist on the solution is because I guess you are missing something which may incur additional implementation effort to you. – Reza Aghaei Feb 04 '20 at 09:24
  • Yeap it works as you said but can I also ask how to set an existing column as a datagridviewlinkcolumn? Because the columns already exist in the dataset – timetoquitcoding Feb 05 '20 at 08:07
  • 1
    Columns of DataSet are different from Columns of DataGridView – Reza Aghaei Feb 05 '20 at 08:11
  • 1
    Here we are talking about Columns of DataGridView, the answer shows how you can set up columns of DataGridView and add a new link column using `dataGridView1.Columns.Add(new DataGridViewLinkColumn() ....`. – Reza Aghaei Feb 05 '20 at 08:16
  • 1
    My advice is start by using my code example, and play with it until you understand it. Then try to replace pieces of the code. For example, instead of a data array, use a `DataTable` that you have filled with values from excel, then add desired columns and ... – Reza Aghaei Feb 05 '20 at 08:19
  • Understood. I'll try looking more into it especially since you went through all the trouble. Thank you very much. – timetoquitcoding Feb 05 '20 at 08:26