Silverlight5通过P/Invoke调用系统win32的三个示例

调用Win32函数

public partial class MainPage : UserControl
{
    [DllImportAttribute("user32.dll", EntryPoint = "MessageBoxW")]
    public static extern int MessageBoxW(
        [In]System.IntPtr hWnd,
        [In][MarshalAs(UnmanagedType.LPWStr)] string lpText,
        [In][MarshalAs(UnmanagedType.LPWStr)] string lpCaption,
        uint uType);
 
    [DllImport("user32.dll", EntryPoint = "MessageBoxA")]
    static extern int MsgBox(int hWnd, string msg, string caption, int type);
 
    [DllImport("kernel32.dll")]
    public static extern bool Beep(int frequency, int duration);
 
    [DllImport("learnDll.dll")]//, EntryPoint = "fnlearnDll"
    public static extern int fnlearnDll();
 
    public void PlaySound()
    {
        Random random = new Random();
        for (int i = 0; i < 50; i++)
        {
            Beep(random.Next(10000), 100);
        }
    }
 
    public MainPage()
    {
        InitializeComponent();
    }
 
    private void button1_Click(object sender, RoutedEventArgs e)
    {
        PlaySound();
        MsgBox(0, "Hello", "Interop", 0);
        //MessageBoxW(IntPtr.Zero, "Hello", "Interop", 0);
        fnlearnDll();
    }
}

-------------------------------------------------------------------------------------------------------------------------------------------------------------

USB设备插取识别

public partial class SilverlightControl1 : UserControl
{
    // Importing a set of necessary native methods from Win32 API.
    [DllImport("User32", EntryPoint = "CreateWindowEx", CharSet = CharSet.Auto, SetLastError = true)]
    static extern IntPtr CreateWindowEx(int dwExStyle, string lpszClassName, string lpszWindowName, int style, int x, int y, int width, int height,
        IntPtr hWndParent, IntPtr hMenu, IntPtr hInst,
        [MarshalAs(UnmanagedType.AsAny)] object pvParam);
 
    [DllImport("user32.dll")]
    static extern IntPtr DefWindowProc(IntPtr hWnd, int uMsg,
        IntPtr wParam, IntPtr lParam);
 
    [DllImport("user32", CharSet = CharSet.Auto, SetLastError = true)]
    public static extern short RegisterClass(WNDCLASS wc);
 
    // Marshaling the Window structure.
    [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
    public class WNDCLASS
    {
        public int style;
        public WndProc lpfnWndProc;
        public int cbClsExtra;
        public int cbWndExtra;
        public IntPtr hInstance;
        public IntPtr hIcon;
        public IntPtr hCursor;
        public IntPtr hbrBackground;
        public string lpszMenuName;
        public string lpszClassName;
    }
 
    //system detects USB insertion/removal
    const int WM_DEVICECHANGE = 0x0219;
    // system detects a new device
    const int DBT_DEVICEARRIVAL = 0x8000;
    // device removed
    const int DBT_DEVICEREMOVECOMPLETE = 0x8004;
 
    // Callbacks must have AllowReversePInvokeCalls attribute.
    [AllowReversePInvokeCalls]
    private IntPtr Callback(IntPtr hWnd, int msg, IntPtr wparam, IntPtr lparam)
    {
        if (msg == WM_DEVICECHANGE)
        {
            if (wparam.ToInt32() == DBT_DEVICEARRIVAL)
                textBlock1.Text = "USB inserted";
            if (wparam.ToInt32() == DBT_DEVICEREMOVECOMPLETE)
                textBlock1.Text = "USB removed";
        }
        return DefWindowProc(hWnd, msg, wparam, lparam);
    }
 
    public delegate IntPtr WndProc(
        IntPtr hWnd, int msg, IntPtr wParam, IntPtr lParam);
 
    // Preventing garbage collection of the delegate
    private static WndProc dontGCthis;
 
    public SilverlightControl1()
    {
        InitializeComponent();
 
        WNDCLASS wc = new WNDCLASS();
 
        // Preventing garbage collection of the delegate
        dontGCthis = new WndProc(Callback);
        wc.lpfnWndProc = dontGCthis;
 
        // Note that you need to ensure unique names     // for each registered class.
        // For example, if you open the same plugin
        // in two different tabs of the browser,
        // you still should not end up with
        // two registered classes with identical names.
        wc.lpszClassName = "foobar" + (new Random()).Next();
 
        RegisterClass(wc);
 
        IntPtr createResult = CreateWindowEx(0, wc.lpszClassName, "Window title", 0, 100, 100, 500, 500, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero, 0);
    }
}

-----------------------------------------------------------------------------------------------------------------

进程实时管理

<UserControl
  x:Class="SilverlightApplication10.MainPage"
  xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
  xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
  xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
  mc:Ignorable="d"
  d:DesignHeight="300"
  d:DesignWidth="400"
  xmlns:sdk="http://schemas.microsoft.com/winfx/2006/xaml/presentation/sdk"
  xmlns:local="clr-namespace:SilverlightApplication10">
  <UserControl.DataContext>
    <local:ProcessViewModel />
  </UserControl.DataContext>
  <Grid
    x:Name="LayoutRoot"
    Margin="6"
    Background="White">
    <Grid.RowDefinitions>
      <RowDefinition
        Height="Auto" />
      <RowDefinition />
    </Grid.RowDefinitions>
    <TextBlock
      Text="Process Information"
      FontSize="16" />
    <sdk:DataGrid
      Grid.Row="1"
      Margin="2"
      AutoGenerateColumns="true"
      ItemsSource="{Binding Processes}"/>
  </Grid>
</UserControl>

 

public class PropertyChangeNotification : INotifyPropertyChanged
{
  protected void RaisePropertyChanged(string property)
  {
    if (this.PropertyChanged != null)
    {
      this.PropertyChanged(this,
        new PropertyChangedEventArgs(property));
    }
  }
  public event PropertyChangedEventHandler PropertyChanged;
}

 

using System.ComponentModel;
using System.Collections.Generic;
using System.Windows;
using System.Collections.ObjectModel;
using System.Linq;
using System.Windows.Threading;
using System;
using System.Threading.Tasks;
 
public class ProcessViewModel : PropertyChangeNotification
{
  public ProcessViewModel()
  {
    if (Application.Current.HasElevatedPermissions)
    {
      BuildInitialProcessList();
    }
  }
  void BuildInitialProcessList()
  {
    this.Processes = new ObservableCollection<Process>();
    BuildProcessList();
 
    DispatcherTimer timer = new DispatcherTimer();
    timer.Interval = TimeSpan.FromMilliseconds(500);
    timer.Tick += (s, e) => BuildProcessList();
    timer.Start();
  }
  void BuildProcessList()
  {
    IEnumerable<Process> newProcesses = Process.EnumerateCurrentList();
 
    var newProcsOuterJoinedExisting =
      from np in newProcesses
      join op in this.Processes
      on np.Id equals op.Id into joinGroup
      from gp in joinGroup.DefaultIfEmpty()
      select new { NewProcess = np, OldProcess = gp };
 
    foreach (var item in newProcsOuterJoinedExisting.ToList())
    {
      if (item.OldProcess == null)
      {
        this.Processes.Add(item.NewProcess);
      }
      else
      {
        item.OldProcess.Refresh();
      }
    }
 
    var remainingListOuterJoinedNewProcs =
      from cp in this.Processes
      join np in newProcesses
      on cp.Id equals np.Id into joinGroup
      from gp in joinGroup.DefaultIfEmpty()
      select new { CurrentProcess = cp, NewProcess = gp };
 
    foreach (var item in remainingListOuterJoinedNewProcs.ToList())
    {
      if (item.NewProcess == null)
      {
        this.Processes.Remove(item.CurrentProcess);
      }
    }
  }
  public ObservableCollection<Process> Processes
  {
    get
    {
      return (_Processes);
    }
    set
    {
      _Processes = value;
      RaisePropertyChanged("Processes");
    }
  }
  ObservableCollection<Process> _Processes;
}

 

using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
using System.IO;
 
internal class Win32Exception : Exception
{
  public Win32Exception(string message, int errorCode)
    : base(message)
  {
    this.ErrorCode = errorCode;
  }
  public int ErrorCode { get; private set; }
}
public class Process : PropertyChangeNotification
{
  [StructLayout(LayoutKind.Sequential)]
  struct PROCESS_MEMORY_COUNTERS
  {
    public UInt32 cb;
    public UInt32 PageFaultCount;
    public UIntPtr PeakWorkingSetSize;
    public UIntPtr WorkingSetSize;
    public UIntPtr QuotaPeakPagedPoolUsage;
    public UIntPtr QuotaPagedPoolUsage;
    public UIntPtr QuotaPeakNonPagedPoolUsage;
    public UIntPtr QuotaNonPagedPoolUsage;
    public UIntPtr PagefileUsage;
    public UIntPtr PeakPagefileUsage;
  };
 
  public Process(UInt32 processId)
  {
    this.Id = processId;
  }
  public UInt32 Id { get; private set; }
 
  public UInt64 WorkingSetBytes
  {
    get
    {
      PROCESS_MEMORY_COUNTERS counters;
      IntPtr handle = GetHandle();
 
      try
      {
        if (!GetProcessMemoryInfo(handle, out counters,
          (UInt32)Marshal.SizeOf(typeof(PROCESS_MEMORY_COUNTERS))))
        {
          throw new Win32Exception("Failed to get memory info",
            Marshal.GetLastWin32Error());
        }
      }
      finally
      {
        CloseHandle(handle);
      }
      return (counters.WorkingSetSize.ToUInt64());
    }
  }
 
  public void Refresh()
  {
    this.RaisePropertyChanged("WorkingSetBytes");
  }
 
  public string ImageName
  {
    get
    {
      if (string.IsNullOrEmpty(this.imageName))
      {
        UInt32 capacity = 128;
        StringBuilder builder = new StringBuilder((int)capacity);
 
        IntPtr handle = GetHandle();
 
        try
        {
          while (GetProcessImageFileName(handle, builder, capacity) == 0)
          {
            int errorCode = Marshal.GetLastWin32Error();
 
            if (errorCode == ERROR_INSUFFICIENT_BUFFER)
            {
              capacity *= 2;
              builder = new StringBuilder((int)capacity);
            }
            else
            {
              throw new Win32Exception("Failed to get image name", errorCode);
            }
          }
          this.imageName = Path.GetFileName(builder.ToString());
        }
        finally
        {
          CloseHandle(handle);
        }
      }
      return (this.imageName);
    }
  }
  string imageName;
 
  IntPtr GetHandle()
  {
    IntPtr handle = OpenProcess(PROCESS_QUERY_INFORMATION, false, this.Id);
 
    if (handle == IntPtr.Zero)
    {
      throw new Win32Exception("Failed to open process",
        Marshal.GetLastWin32Error());
    }
    return (handle);
  }
  static bool TryOpenProcess(UInt32 id)
  {
    IntPtr ptr = OpenProcess(PROCESS_QUERY_INFORMATION, false, id);
 
    if (ptr != IntPtr.Zero)
    {
      CloseHandle(ptr);
    }
    return (ptr != IntPtr.Zero);
  }
  public static IEnumerable<Process> EnumerateCurrentList()
  {
    foreach (var processId in EnumerateProcessIds())
    {
      if (TryOpenProcess(processId))
      {
        yield return new Process(processId);
      }
    }
  }
  static IEnumerable<UInt32> EnumerateProcessIds()
  {
    UInt32[] processIds = new UInt32[32];
    bool retry = true;
 
    while (retry)
    {
      processIds = new UInt32[processIds.Length * 2];
 
      UInt32 arraySize =
        (UInt32)(Marshal.SizeOf(typeof(UInt32)) * processIds.Length);
 
      UInt32 bytesCopied = 0;
 
      retry = EnumProcesses(processIds, arraySize, out bytesCopied);
 
      if (retry)
      {
        retry = (bytesCopied == arraySize);
      }
      else
      {
        throw new Win32Exception("Failed enumerating processes",
          Marshal.GetLastWin32Error());
      }
    }
    return (processIds);
  }
 
  [DllImport("psapi", SetLastError = true)]
  static extern bool EnumProcesses(
    [MarshalAs(UnmanagedType.LPArray)] [In] [Out] UInt32[] processIds,
    UInt32 processIdsSizeBytes,
    out UInt32 bytesCopied);
 
  [DllImport("kernel32", SetLastError = true)]
  static extern IntPtr OpenProcess(UInt32 dwAccess, bool bInheritHandle,
    UInt32 dwProcessId);
 
  [DllImport("kernel32")]
  static extern bool CloseHandle(IntPtr handle);
 
  [DllImport("psapi", SetLastError = true)]
  static extern UInt32 GetProcessImageFileName(
    IntPtr processHandle,
    [In] [Out] StringBuilder lpImageFileName,
    UInt32 bufferSizeCharacters);
 
  [DllImport("psapi", SetLastError = true)]
  static extern bool GetProcessMemoryInfo(
    IntPtr processHandle,
    out PROCESS_MEMORY_COUNTERS counters,
    UInt32 dwSize);
 
  static readonly UInt32 PROCESS_QUERY_INFORMATION = 0x0400;
  const int ERROR_ACCESS_DENIED = 5;
  const int ERROR_INVALID_PARAMETER = 87;
  const int ERROR_INSUFFICIENT_BUFFER = 122;
}

  

 

posted on   chuncn  阅读(1133)  评论(1编辑  收藏  举报

努力加载评论中...

导航

点击右上角即可分享
微信分享提示