例如,這是IFileOpenDialog接口,Windows Shell界面,從Pinvoke現場拍攝的完整定義:在C#中定義Windows API接口時,是否必須定義所有成員?我只能定義我要使用的方法嗎?
[ComImport, Guid ("d57c7288-d4ad-4768-be02-9d969532d960"), InterfaceType (ComInterfaceType.InterfaceIsIUnknown)]
interface IFileOpenDialog : IFileDialog
{
// Defined on IModalWindow - repeated here due to requirements of COM interop layer
// --------------------------------------------------------------------------------
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime), PreserveSig]
int Show ([In] IntPtr parent);
// Defined on IFileDialog - repeated here due to requirements of COM interop layer
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetFileTypes ([In] uint cFileTypes, [In] COMDLG_FILTERSPEC[] rgFilterSpec);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetFileTypeIndex ([In] uint iFileType);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void GetFileTypeIndex (out uint piFileType);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void Advise ([In, MarshalAs (UnmanagedType.Interface)] IFileDialogEvents pfde, out uint pdwCookie);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void Unadvise ([In] uint dwCookie);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetOptions ([In] FOS fos);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void GetOptions (out FOS pfos);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetDefaultFolder ([In, MarshalAs (UnmanagedType.Interface)] IShellItem psi);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetFolder ([In, MarshalAs (UnmanagedType.Interface)] IShellItem psi);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void GetFolder ([MarshalAs (UnmanagedType.Interface)] out IShellItem ppsi);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void GetCurrentSelection ([MarshalAs (UnmanagedType.Interface)] out IShellItem ppsi);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetFileName ([In, MarshalAs (UnmanagedType.LPWStr)] string pszName);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void GetFileName ([MarshalAs (UnmanagedType.LPWStr)] out string pszName);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetTitle ([In, MarshalAs (UnmanagedType.LPWStr)] string pszTitle);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetOkButtonLabel ([In, MarshalAs (UnmanagedType.LPWStr)] string pszText);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetFileNameLabel ([In, MarshalAs (UnmanagedType.LPWStr)] string pszLabel);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void GetResult ([MarshalAs (UnmanagedType.Interface)] out IShellItem ppsi);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void AddPlace ([In, MarshalAs (UnmanagedType.Interface)] IShellItem psi, NativeMethods.FDAP fdap);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetDefaultExtension ([In, MarshalAs (UnmanagedType.LPWStr)] string pszDefaultExtension);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void Close ([MarshalAs (UnmanagedType.Error)] int hr);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetClientGuid ([In] ref Guid guid);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void ClearClientData ();
// Not supported: IShellItemFilter is not defined, converting to IntPtr
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetFilter ([MarshalAs (UnmanagedType.Interface)] IntPtr pFilter);
// Defined by IFileOpenDialog
// ---------------------------------------------------------------------------------
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void GetResults ([MarshalAs (UnmanagedType.Interface)] out IShellItemArray ppenum);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void GetSelectedItems ([MarshalAs (UnmanagedType.Interface)] out IShellItemArray ppsai);
}
如果我只打算使用兩種方法從這個接口,可我定義它喜歡:
[ComImport, Guid ("d57c7288-d4ad-4768-be02-9d969532d960"), InterfaceType (ComInterfaceType.InterfaceIsIUnknown)]
interface IFileOpenDialog : IFileDialog
{
// Defined on IModalWindow - repeated here due to requirements of COM interop layer
// --------------------------------------------------------------------------------
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime), PreserveSig]
int Show ([In] IntPtr parent);
[MethodImpl (MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
void SetOptions ([In] FOS fos);
}
它是否會工作?還是我必須用所有方法定義完整的界面?
你試過了嗎? – 2010-11-11 13:11:08
是的,如果我只調用Show方法,它會起作用,如果我嘗試調用SetOptions,則會得到一個異常:「嘗試讀取或寫入受保護的內存,這通常表示其他內存已損壞。 – AnAurelian 2010-11-11 14:01:22