2009-08-26 3 views
0

나는 비스타 64 시스템에서 WPF 툴킷 데이터 그리드를 스크롤 마우스 휠을 사용할 때 나는 비밀 낮은 수준의 오류 얻을 : 나는 오버 플로우를 피할 수있는 방법을 때 휠 scolling WPF DataGrid에

at System.IntPtr.op_Explicit(IntPtr value) 
    at System.Windows.Interop.HwndMouseInputProvider.FilterMessage(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled) 
    at System.Windows.Interop.HwndSource.InputFilterMessage(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled) 
    at MS.Win32.HwndWrapper.WndProc(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled) 
    at MS.Win32.HwndSubclass.DispatcherCallbackOperation(Object o) 
    at System.Windows.Threading.ExceptionWrapper.InternalRealCall(Delegate callback, Object args, Boolean isSingleParameter) 
    at System.Windows.Threading.ExceptionWrapper.TryCatchWhen(Object source, Delegate callback, Object args, Boolean isSingleParameter, Delegate catchHandler) 

은 내가 issue on CodePlex 기록을 .

하지만 이미이 문제를 해결할 방법을 찾은 사람이 있습니까?

답변

0

이 버그는 Microsoft의 라이브러리에 있으며 아직 거기에 있다는 것을 믿을 수 없습니다. - 빌드 탭을 선택> 속성

이 프로젝트를 마우스 오른쪽 버튼으로 클릭하고 선택

에서는 Visual Studio를 가지고 당신이 개발자 추정을 회피합니다. 플랫폼 대상 : x86

그런 다음 프로젝트를 다시 빌드하십시오.

배경 :

나는 32 비트 OS에서 완벽하게 훌륭한 프로그램을 작성했다. 그런 다음 Windows 7 64 비트 OS가 설치된 새 랩톱을 구입했습니다. Visual Studio와 솔루션을 설치했습니다. Windows 메시지를 처리하여 WndProc로 사용자 입력을 처리하는 한 프로젝트가 실패했습니다. 당신도 마우스 메시지 처리와 비슷합니다.

Microsoft의 Visual Studio 팀에서 패치를 찾지 못한 후 플랫폼 대상을 "Any CPU"에서 "x86"으로 변경하고 64 비트 OS에 다시 배포하고 saw 프로그램이 올바르게 작동합니다. 이것은 유일한 변화였습니다.

0

나는이 문제를 직접 다루기 시작했다.

여전히 유용 할 지 모르겠지만 다른 사람에게도 필요한 수정 사항은 여기에 있습니다.

나는 비스타 64 기계에서 WPF 프로젝트에 대해 가지고있는 문제와 비슷한 냄새가 나는 OpenTK 프로젝트에서 this 스레드를 발견했습니다. 그 스레드에서 설명한 것처럼 문제는 MouseWheel 메시지의 wParam에서 잘못 처리 된 노래 비트로 보입니다. 오버플로 예외는 wParam IntPtr을 int로 형변환하려고 시도 할 때 HwndMouseInputProvider 호출에서 발생합니다.

해결 방법은 기본 창에서 Windows 메시지를 필터링하는 후크를 추가하는 것입니다. 후크 콜백은 WM_MOUSEWHEEL 메시지의 wparam 값을 검사합니다. 값이 오버플로 된 다음 값 시프터 주변 비트 정보를 복구하기 위해 현재 메시지가 처리 된 것으로 표시되고 새 메시지가 새 값으로 게시됩니다.

public partial class Window1 : Window 
{  
    private const int WM_MOUSEWHEEL = 0x020A; 

    public Window1() 
    { 
     InitializeComponent(); 

     SourceInitialized += (o, e) => 
     { 
      HwndSource source = PresentationSource.FromVisual(this) as HwndSource; 
      source.AddHook(WndProc); 
     }; 
    } 

    [DllImport("user32.dll")] 
    private static extern IntPtr PostMessage(IntPtr hwnd, IntPtr msg, IntPtr wParam, IntPtr lParam); 

    private IntPtr WndProc(IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, ref bool handled) 
    { 
     switch (msg) 
     { 
      case WM_MOUSEWHEEL: 
       // Check that wParam won't cause an OverflowException 
       if ((long)wParam >= (long)Int32.MaxValue) 
       { 
        // Filter the evenet 
        handled = true; 

        HwndSource source = PresentationSource.FromVisual(this) as HwndSource; 
        // Repost the event with the proper value 
        PostMessage(source.Handle, new IntPtr(msg), new IntPtr((long)wParam <<32>> 32), lParam); 
       } 

       break; 
     } 

     return IntPtr.Zero; 
    } 

이것은 잘 작동합니다. 누구나 추가하거나 수정할 수 있다면 좋을 것입니다! K