컨트롤이있는 Windows Forms 응용 프로그램이 있습니다. 컨트롤은 캔버스가있는 차트 패널로 구성되어 있습니다. 내가 뭘하고 싶은 건 프로그래밍 방식으로 마우스를 드래그하여 캔버스의 오른쪽 가장자리와 캔버스에 그려진 마지막 항목 사이에 특정 거리를 두는 것입니다. 나는 두 가지 접근법을 시도했다. 두 가지 모두 패널이 원하는만큼 드래그된다는 의미에서 작동하지만 원하는 동작의 정밀도를 얻을 수없는 것처럼 보입니다. 필자는 마우스 시뮬레이터를 코딩하여 두 가지 접근 방식을 시도했습니다.프로그래밍 방식으로 마우스 끌기 시뮬레이션
접근 1 :
if(this.ChartControl.ChartPanel.CanFocus)
{
// ... Focus the chart panel to be adjusted.
this.ChartControl.ChartPanel.Focus();
// ... Move cursor to lastBarScreenCoordinates on the chart panel to be adjusted.
Cursor.Position = new Point(lastBarScreenCoordinates.X, lastBarScreenCoordinates.Y);
MouseSimulator.SetMouseDragThresholds();
// ... Move chart panel to required position.
MouseSimulator.LeftMouseButtonDown(lastBarScreenCoordinates.X, lastBarScreenCoordinates.Y);
MouseSimulator.MouseMove(lastBarScreenCoordinates.X-positionShift,
lastBarScreenCoordinates.Y);
MouseSimulator.LeftMouseButtonUp(lastBarScreenCoordinates.X-positionShift,
lastBarScreenCoordinates.Y);
MouseSimulator.ResetMouseDragThresholds(_cx_default, _cy_default);
// ... Redraw the chart panel.
this.ChartControl.ChartPanel.Refresh();
// ... Reset cursor to its starting position.
Cursor.Position = new Point(startingCursorX, startingCursorY);
}
접근법 2 : 나는 마우스 클릭을 시뮬레이션하기위한 SendInput을 사용하고
if(this.ChartControl.ChartPanel.CanFocus)
{
// ... Focus the chart panel to be adjusted.
this.ChartControl.ChartPanel.Focus();
// ... Move cursor to lastBarScreenCoordinates on the chart panel to be adjusted.
Cursor.Position = new Point(lastBarScreenCoordinates.X, lastBarScreenCoordinates.Y);
MouseSimulator.SetMouseDragThresholds();
// ... Move chart panel to required position.
MouseSimulator.LeftMouseButtonDown(lastBarScreenCoordinates.X, lastBarScreenCoordinates.Y);
Cursor.Position = new Point(lastBarScreenCoordinates.X-positionShift,
lastBarScreenCoordinates.Y);
WindowsCommunication.SendMessage(this.ChartControl.Handle, 0x200, IntPtr.Zero,IntPtr.Zero);
MouseSimulator.LeftMouseButtonUp(lastBarScreenCoordinates.X-positionShift,
lastBarScreenCoordinates.Y);
MouseSimulator.ResetMouseDragThresholds(_cx_default, _cy_default);
// ... Redraw the chart panel.
this.ChartControl.ChartPanel.Refresh();
// ... Reset cursor to its starting position.
Cursor.Position = new Point(startingCursorX, startingCursorY);
}
. 여기
private static int CalculateAbsoluteCoordinateX(int x)
{
return ((x * 65536) + GetSystemMetrics(SystemMetric.SM_CXSCREEN) - 1)/
GetSystemMetrics(SystemMetric.SM_CXSCREEN);
}
그래서 여기
는 정밀도 문제입니다 ...public static void LeftMouseButtonDown(int x, int y)
{
INPUT mouseInput = new INPUT();
mouseInput.type = SendInputEventType.InputMouse;
mouseInput.mkhi.mi.dx = CalculateAbsoluteCoordinateX(x);
mouseInput.mkhi.mi.dy = CalculateAbsoluteCoordinateY(y);
mouseInput.mkhi.mi.mouseData = 0;
mouseInput.mkhi.mi.time = 0;
mouseInput.mkhi.mi.dwFlags = MouseEventFlags.MOUSEEVENTF_LEFTDOWN;
SendInput(1, ref mouseInput, Marshal.SizeOf(new INPUT()));
}
... 샘플 마우스 왼쪽 버튼을 아래 코드는 다음과 같이 나는 마우스에 대한 표준화 된 절대 좌표를 계산합니다. 접근법 1 (마우스 이동)을 사용하면 마지막으로 칠한 항목과 캔바스의 오른쪽 가장자리 사이의 측정 거리가 positionShift에서 설정 한 것과 다르며 커서 위치 차이가 positionShift와 동일하지 않습니다. 처음에는 그것이 포인터 탄도 문제로 인해 접근법 2를 시도했기 때문에 생각했습니다. 접근법 2는 포인터 위치 지정에서 정밀함을 제공하지만 패널이 이동한다는 점에서 여전히 어려움을 겪고 있지만 마지막 막대 그리기와 오른쪽 가장자리 사이의 거리는 canvas는 positionShift 양과 같지 않습니다. 항상 꺼져있는 것 같습니다. 나는 오랫동안이 일을 해왔으며 나의 지혜 끝에있다. 나는 여기서 무슨 일이 일어나고 있는지 확신하지 못한다. 시뮬레이션 된 마우스 끌기로 캔버스 드래그의 정밀도를 향상시키는 방법은 무엇입니까?
이 점이 무엇입니까? 캔버스를 직접 그릴 수 있습니다. –
이것은 기존 응용 프로그램에 추가되므로 마지막 요소가 그려지는 위치를 제어 할 수 없습니다. 패널을 끌기 위해 정확하게 그려야합니다. – PBrenek