2010-12-30 4 views
3

.NET 창에서는 양식에 컨트롤 모음이 있고 내부적으로 모두 Microsoft Windows에서 제공하는 창 하위 시스템으로 둘러 쌉니다. MFC와 다소 비슷합니다. 이것은 윈도우 API 주위의 얕은 래퍼입니다. 폼/윈도우 내의 제어는 트리 구조를 생성하고 이벤트는 리프 노드에 의해 수신된다. MouseMove 이벤트는 마우스 바로 아래의 창/컨트롤에 의해 수신됩니다.Windows에서 이벤트 라우팅 전략을 변경할 수 있습니까?

그러나 프리젠 테이션 프레임 워크에서 마이크로 소프트는 다음과 같은 전략

  1. 터널 중 하나를 가질 수있는 RoutedEvent 제공은 라우팅 된 이벤트는 터널링 전략을 사용하는 경우 루트에서 소스 요소에 트리를 통해 아래로 이벤트 인스턴스 경로 .
  2. 버블 라우팅 된 이벤트는 버블 링 전략을 사용합니다. 버블 전략은 이벤트 인스턴스가 트리를 통해 이벤트 소스에서 루트로 위쪽으로 라우팅합니다.
  3. 직접 라우팅 된 이벤트는 요소 트리를 통해 라우팅되지 않습니다.

내 생각 엔 그 프리젠 테이션 프레임 워크는 하나의 메인 윈도우를 생성하고 자식 요소가

지금 내 일반 창 형태로이 전략을 변경할 수있는 이벤트 라우팅 전략을 지원하기 위해 자체적으로 드로잉을한다. 내가 원한다면 터널 또는 버블이고 현재 윈도우 시스템은 입니다. 그 위에 컨트롤이 있어도 MouseEnter/MouseLeave 이벤트를 받길 원합니다. 한 가지 방법은 글로벌 마우스/키보드 후크입니다. 그러나 나는 그것을 피하고 싶다고 말하자.

+0

WPF에 대해 이야기하고 있습니까? – Arseny

+0

WPF에서 할 수 있습니다. Windows Forms와 Microsoft Windows에서 CreateWindow() API로 만든 모든 창에 대해 이야기하고 있습니다. – affan

답변

7

Windows에는 거품이 발생하지만 메시지를 기반으로합니다. 예를 들어 MouseWheel은 거품을 일으키지 만 MouseEnter도 Leave도 마찬가지입니다. 버블 링 동작을 추가하는 것은 기술적으로 가능하지만 올바르게 진행하기가 매우 어렵습니다. 부모/자식 트리의 모든 창은 협력하여 명시 적으로 부모에게 거품을 일으킬 필요가 있습니다.

어쨌든이 특별한 경우에는 문제가 해결되지 않습니다. 중요한 문제는 자식 컨트롤에 대한 MouseLeave가 부모에 대한 MouseEnter를 보장한다는 보장이 없다는 것입니다. 마우스 이동 메시지는 정확하지 않을 뿐이지 만 모든 통과 된 픽셀이보고되는 것은 아닙니다. 자식 윈도우가 부모 가장자리 가까이에있을 때 마우스를 충분히 빠르게 움직이면 부모를위한 MouseEnter를 얻지 못하게됩니다.

이것은 마우스 캡처, Control.Capture 속성으로 해결됩니다. 이렇게하면 마우스가 더 이상 윈도우 클라이언트 사각형 내에 있지 않을 때에도 마우스 이동 메시지가 생성됩니다. 그러나 이는 여러 개의 창이 아닌 단일 창에 대해 마우스를 모니터링 할 때 잘 작동합니다. 컨트롤을 클릭하자마자 컨트롤 자체는 일반적으로 마우스를 캡처하여 시작한 마우스를 취소하려고합니다. 예를 들어, 버튼은 MouseUp 이벤트를보고 버튼을 다시 그려서 버튼 업 상태를 표시 할 수 있습니다.

거친 쿠키. 이 특정 문제에 대해 알고있는 유일한 괜찮은 접근 방식은 타이머를 사용하는 것입니다. 일반적으로 200msec 정도면 충분합니다. 마우스가 들어가면 시작하십시오. Tick ​​이벤트 핸들러에서 Mouse.Position 및 Control.PointToClient를 사용하여 마우스가 외부 창 사각형 내부에 여전히 있는지 확인합니다.

관련 문제