Реализация опции перетаскивания через окно - PullRequest
1 голос
/ 16 июля 2009

Примечание:

  • Использование Windows Forms
  • предпочтительно C # .NET

Вопрос:

  • Наилучший метод для реализации a инструмента перетаскивания через окно , аналогичного (или идентичного) таковому в проводнике процессов получить идентификатор процесса , соответствующий выбранному окну

1 Ответ

1 голос
/ 16 июля 2009

Я думаю, что самый простой способ - это установить контроль над вашей формой, который будет служить отправной точкой; Вы нажимаете там кнопку мыши, а затем перемещаете ее по экрану, пока кнопка нажата, и выбираете идентификатор процесса, на который вы указываете. В моем примере я использовал панель (называемую _aim).

Сначала мы настроим события мыши:

private void Panel_MouseDown(object sender, MouseEventArgs e)
{
     // make all mouse events being raised in the _aim panel
     // regardless of whether the mouse is within the control's
     // bounds or not
    _aim.Capture = true;
}

private void Panel_MouseMove(object sender, MouseEventArgs e)
{
    if (_aim.Capture)
    {   
        // get the process id only if we have mouse capture 
        uint processId = GetProcessIdFromPoint(
            _aim.PointToScreen(e.Location)).ToString();
        // do something with processId (store it for remembering the 
        // last processId seen, to be used as MouseUp for instance)
    }
}
private void Panel_MouseUp(object sender, MouseEventArgs e)
{
    if (_aim.Capture)
    {
        // release capture if we have it
        _aim.Capture = false;
        // perhaps do something more (fetch info about last seen
        // process id, if we stored it during MouseMove, for instance)
    }
}

Метод GetProcessIdFromPoint выглядит следующим образом:

private uint GetProcessIdFromPoint(Point point)
{
    uint procId;
    WinApi.GetWindowThreadProcessId(WinApi.WindowFromPoint(point), out procId);
    return procId;
}

И, наконец, Windows API (от pinvoke.net ):

public static class WinApi
{
    [StructLayout(LayoutKind.Sequential)]
    public struct POINT
    {
        public int X;
        public int Y;

        public POINT(int x, int y)
        {
            this.X = x;
            this.Y = y;
        }

        public static implicit operator System.Drawing.Point(POINT p)
        {
            return new System.Drawing.Point(p.X, p.Y);
        }

        public static implicit operator POINT(System.Drawing.Point p)
        {
            return new POINT(p.X, p.Y);
        }
    }

    [DllImport("user32.dll")]
    public static extern IntPtr WindowFromPoint(POINT Point);

    [DllImport("user32.dll", SetLastError = true)]
    public static extern uint GetWindowThreadProcessId(IntPtr hWnd, out uint lpdwProcessId);
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...