2010-06-27 1 views
1

스크롤 막대 위치를 가져 오는 데 문제가 있습니다. 메모장과 같은 다른 프로세스의 스크롤 막대 위치를 가져올 수 있습니까? 내가 테스트 한 작은 응용 프로그램을 작성하고 항상 스크롤바의 위치로 0 0 얻을.내 양식 내에서 메모장의 ScrollBar 위치를 얻는 방법

[DllImport("user32.dll", CharSet = CharSet.Auto)] 
    public static extern int GetScrollPos(IntPtr hWnd, int nBar); 

    [DllImport("user32.dll")] 
    static extern IntPtr SetParent(IntPtr hWndChild, IntPtr hWndNewParent); 

    [DllImport("user32.dll")] 
    static extern int SetWindowLong(IntPtr hWnd, int nIndex, int dwNewLong); 

    [DllImport("user32.dll", SetLastError = true)] 
    private static extern bool MoveWindow(IntPtr hwnd, int x, int y, int cx, int cy, bool repaint); 

    [DllImport("user32.dll")] 
    static extern IntPtr SetActiveWindow(IntPtr hWnd); 

    [DllImport("user32.dll", SetLastError = true)] 
    static extern void SwitchToThisWindow(IntPtr hWnd, bool fAltTab); 


    private void Form1_Load(object sender, EventArgs e) 
    { 
     this.SuspendLayout(); 

     Process notepad = new Process(); 
     ProcessStartInfo psi = new ProcessStartInfo(@"c:\list1.txt"); 
     psi.WindowStyle = ProcessWindowStyle.Normal; 
     notepad.StartInfo = psi; 

     notepad.Start(); 

     this.ResumeLayout(); 

     notepad.WaitForInputIdle(3000); 

     IntPtr old = SetParent(notepad.MainWindowHandle, this.Handle); 

     SetWindowLong(notepad.MainWindowHandle, GWL_STYLE, WS_VISIBLE + WS_MAXIMIZE); 
     MoveWindow(notepad.MainWindowHandle, 100, 100, 400, 400, true); 

     SetActiveWindow(notepad.MainWindowHandle); 
     SwitchToThisWindow(notepad.MainWindowHandle, true);    
    } 

나는 메모장에 PGDN 이벤트를 전송 버튼이 있고 그것을 잘 작동하지만, 스크롤의 PGDN 이벤트 위치 후도 0 0

private void PGDN_Click(object sender, EventArgs e) 
    { 
     Process[] procs = Process.GetProcessesByName("Notepad"); 
     IntPtr hwnd = procs[0].MainWindowHandle; 

     SetActiveWindow(hwnd); 
     SwitchToThisWindow(hwnd, true); 
     Thread.Sleep(2000); 
     SendKeys.SendWait("{PGDN}"); 
     Thread.Sleep(2000); 
     label1.Text = "OK"; 
     label1.Text = ""; 

     label1.Text = HScrollPos().ToString() + " " + VScrollPos().ToString(); } 
다음

HScrollPos 및 VScrollPos 기능입니다입니다 :

public int VScrollPos() 
    { 
     Process[] procs = Process.GetProcessesByName("Notepad"); 
     IntPtr hwnd = procs[0].MainWindowHandle; 
     if (procs.Length != 0) 
     { 
      return GetScrollPos(hwnd , SB_VERT); 

     } 
     else 
     { 
      MessageBox.Show("Notepad Nor Running"); 
      return 0; 
     }  
    } 

    public int HScrollPos() 
    { 
     Process[] procs = Process.GetProcessesByName("Notepad"); 
     IntPtr hwnd = procs[0].MainWindowHandle; 
     if (procs.Length != 0) 
     { 

      return GetScrollPos(hwnd , SB_HORZ); 
     } 
     else 
     { 
      MessageBox.Show("Notepad Nor Running"); 
      return 0; 
     }    
    } 

다른 방법으로 창에서 다른 프로세스/창의 스크롤 막대 위치를 가져 오는 방법이 있습니까? 도와주세요. Thx는 당연합니다.

다음은 답변을 기반으로 한 작업 코드입니다. 들으

[DllImport("user32.dll", SetLastError = true)] 
    private static extern IntPtr FindWindow(string lpClassName, string lpWindowName); 

    [DllImport("user32.dll", SetLastError = true)] 
    static extern IntPtr FindWindowEx(IntPtr hwndParent, IntPtr hwndChildAfter, string lpszClass, string lpszWindow); 

    private void button4_Click(object sender, EventArgs e) 
    { 
     string lpszParentClass = "Notepad"; 
     string lpszParentWindow = "Untitled - Notepad"; 
     string lpszClass = "Edit"; 

     IntPtr ParenthWnd = new IntPtr(0); 
     IntPtr hWnd = new IntPtr(0); 
     ParenthWnd = FindWindow(lpszParentClass, lpszParentWindow); 
     if (ParenthWnd.Equals(IntPtr.Zero)) 
      MessageBox.Show("Notepad Not Running"); 
     else 
     { 
      hWnd = FindWindowEx(ParenthWnd, hWnd, lpszClass, ""); 
      if (hWnd.Equals(IntPtr.Zero)) 
        MessageBox.Show("Notepad doesn't have an edit component ?"); 
      else 
      { 
       MessageBox.Show("Notepad Window: " + ParenthWnd.ToString()); 
       MessageBox.Show("Edit Control: " + hWnd.ToString()); 
      } 
     } 
     SetActiveWindow(ParenthWnd); 
     label5.Text = GetScrollPos(hWnd, SB_VERT) + " " + GetScrollPos(hWnd, SB_HORZ); 
    } 
+0

왜 지구상에서하고 싶습니까? – SLaks

답변

2

나는 문제가 메인 창 핸들을 사용하고 있는지 의심, 당신은 메인 윈도우의 자식 인 Edit 컨트롤의 핸들을 사용해야합니다.

기본 창 hwnd를 사용하면 enumrate the child windows을 사용하여 편집 컨트롤의 hWnd를 찾은 다음 해당 hWnd를 호출하여 스크롤 막대 위치를 얻을 수 있습니다.

SendKeys는 입력 포커스가있는 창 (이 경우 Edit 컨트롤)에 키 스트로크를 보내기 때문에 작동합니다.

Here은 EnumChildWindows에 대한 interop에 도움이 될 때까지 제공 한 질문에 대한 답변입니다. 필요한 경우 더 많이 있지만 도움이 될 수 있습니다.

+1

+1, 이것이 맞습니다. MainWindowHandle은 메모장의 프레임 창을 반환하지만 스크롤바는 가지고 있지 않습니다. Spy ++로 쉽게 볼 수 있습니다. –

관련 문제