ShellExecuteEx (shell32)
Last changed: Nige-81.171.173.35

.
Summary

Update:

To me it only works if you change CharSet.Auto to CharSet.Ansi. Since I don't know if it "should" work with the Auto setting, I don't change the code below, but just add the comment up here.

C# Signature::

[DllImport("shell32.dll", CharSet = CharSet.Auto)]
static extern bool ShellExecuteEx(ref SHELLEXECUTEINFO lpExecInfo);

VB.NET Signature:

<DllImport("Shell32", CharSet:=CharSet.Auto, SetLastError:=True)> _
Public Function ShellExecuteEx(ByRef lpExecInfo As SHELLEXECUTEINFO) As Boolean
End Function

User-Defined Types:

(VB.NET)

Public Structure SHELLEXECUTEINFO
    Public cbSize As Integer
    Public fMask As Integer
    Public hwnd As IntPtr
    <MarshalAs(UnmanagedType.LPTStr)> Public lpVerb As String
    <MarshalAs(UnmanagedType.LPTStr)> Public lpFile As String
    <MarshalAs(UnmanagedType.LPTStr)> Public lpParameters As String
    <MarshalAs(UnmanagedType.LPTStr)> Public lpDirectory As String
    Dim nShow As Integer
    Dim hInstApp As IntPtr
    Dim lpIDList As IntPtr
    <MarshalAs(UnmanagedType.LPTStr)> Public lpClass As String
    Public hkeyClass As IntPtr
    Public dwHotKey As Integer
    Public hIcon As IntPtr
    Public hProcess As IntPtr
End Structure

(C#)

[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]

    public struct SHELLEXECUTEINFO
    {
        public int cbSize;
        public uint fMask;
        public IntPtr hwnd;
        public String lpVerb;
        public String lpFile;
        public String lpParameters;
        public String lpDirectory;
        public int nShow;
        public int hInstApp;
        public int lpIDList;
        public String lpClass;
        public int hkeyClass;
        public uint dwHotKey;
        public int hIcon;
        public int hProcess;
    }

Notes:

Check the SW constants at to see what value to pass in the nShow member. Typically you'll pass SW_SHOW.

lpVerb member can be used for a varity of actions like "properties", "find", "openas", "print"..etc depending on the file type you're dealing with.Actions available for a specific file type are stored in registry, setting lpVerb to null results in the default action of that file type to be executed.

Tips & Tricks:

(C#)

using System.Runtime.InteropServices;

(VB.NET)

Imports System.Runtime.InteropServices

Sample Code:

VB.NET

Demonstrates how to open an HTML file in the browser:

Dim info As SHELLEXECUTEINFO
info.cbSize = System.Runtime.InteropServices.Marshal.SizeOf(info)
info.lpVerb = "open"
info.lpFile = "somefile.html"
info.nShow = SW_SHOW
If Not ShellExecuteEx(info) Then
     Dim ex As New System.ComponentModel.Win32Exception(System.Runtime.InteropServices.Marshal.GetLastWin32Error())
     MessageBox.Show(ex.Message, "Error")
End If

Alternative Managed API:

The Process class uses ShellExecuteEx by default:

Dim p As New Process
p.StartInfo.FileName = "somefile.html"
p.StartInfo.ErrorDialog = True ' this opens the "Open With" dialog for unknown file types
p.Start()

C# Example of Property Dialog

private const int SW_SHOW = 5;
private const uint SEE_MASK_INVOKEIDLIST = 12;

[DllImport("shell32.dll")]
static extern bool ShellExecuteEx(ref SHELLEXECUTEINFO lpExecInfo);

public static void ShowFileProperties(string Filename) {
    SHELLEXECUTEINFO info = new SHELLEXECUTEINFO();
    info.cbSize = System.Runtime.InteropServices.Marshal.SizeOf(info);
    info.lpVerb = "properties";
    info.lpFile = Filename;
    info.nShow = SW_SHOW;
    info.fMask = SEE_MASK_INVOKEIDLIST;
    ShellExecuteEx(ref info);
}


Documentation

Verbs for lpVerb:

"open"        - see MSDN
"edit"        - see MSDN
"openas"        - Opens dialog when no program is associated to the extension
"explore"    - see MSDN
"properties"    - see MSDN