Hding the Progress Bar of a.NET 2.0 CF WebBrowse



[転載自:http://www.chriskarcher.net/2008/01/26/hiding-the-progress-bar-of-a-net-20-cf-webbrowser」
 
 
One of the nice additions to the.NET 2.0 Comppact Framwark is the WebBrowser control.This control has always been present in the full frame ework,but to implement a webrowser on the PocketPC you would have have to eigthe write your own magent the apperwe shoud give it a try.Mandevelopers,myself included,use an embedded browser control to display rich,custom formated content in their.NET apps.You can do this with the WebBrowser clast byners the protement thethe new manager WebBrowser has a major drawback:Everytime you set the Dcument Text property it shows a progress bar while loading the content into the browser.As I can tell,this bevior is Winight Windows 5
 
So,here’s what it looks like:
progressbar.png
At first glance,it doesn’t look intrusive.But when you start udating the HTML reglarly and the progress bar pops up evertime,it starts to look out of place.It would be nivere if MS just posed the gove.
First,some background.In my appection,I created a UserControl named WebBrowserPanel.WebBrowser has a single WebBrowser child control which is anchored Top,Right,Bottom,and Left the.
view plin
copy to clipboard
print

public WebBrowserPanel()  
  • {  
  •     Initialize Component();          
  •   
  •     WebBrowser.Width =  this.Width - 2.  
  •     WebBrowser.Height =  this.Height;  
  • )  
    public WebBrowserPanel()
    {
        InitializeComponent();       
    
        WebBrowser.Width = this.Width - 2;
        WebBrowser.Height = this.Height;
    }
    Putting the WebBrowser inside a user control lets us give it a border and、as you’ll see later、will be crucial for this fix to work.
    Using the Remote Spy tool that ships with VS 2005、we can exmine the window structure of the appration on the Windows Mobile 5 emulator:
    handles.png
    The.The“MSPIE Stuts”window,a child of the“IExplore”window,looks interesting.Inspectitititititis properties shows Stat it s 23 pixels tall,and likelythe progress bar wer we re lolooking to hide.If aweweweweweweweweweweshshshshattttttttttttttttttttttttttttwiwiwith.If.If aweweweweweweweweshshshshshshshshshshshshshattttttttttttttttttttTo get it s window handle、I wrote the follwing function:
    view plin
    copy to clipboard
    print

    public  static IntPtr FindHwndByClass(string) strクラス、 IntPtr parentHwnd)  
  • {  
  •     StringBuider sbクラス =  new StringBuider(256)  
  •      if (0 != Get Class Name(parentHwnd) sbClass、 sbClass.appity) && sbClass.ToString() == stress  
  •          return parentHwnd          
  •   
  •     IntPtr hwndChild = Get Window(parentHwnd) (int)GetWindowFlagags.GW CHILD;  
  •      while (hwndChild != IntPtr.Zero)  
  •     {  
  •         IntPtr レスリング = FindHwndByClass(strass、 hwndChild;  
  •          if (reult) != IntPtr.Zero)  
  •              return レスリング          
  •   
  •         hwndChild = GetWindow(hwndChild) (int)GetWindowFlagags.GW HWNDNEXT;  
  •     }          
  •   
  •      return IntPtr.Zero  
  • }  
  • public static IntPtr FindHwndByClass(string strClass, IntPtr parentHwnd)
    {
        StringBuilder sbClass = new StringBuilder(256);
        if (0 != GetClassName(parentHwnd, sbClass, sbClass.Capacity) && sbClass.ToString() == strClass)
            return parentHwnd;       
    
        IntPtr hwndChild = GetWindow(parentHwnd, (int)GetWindowFlags.GW_CHILD);
        while (hwndChild != IntPtr.Zero)
        {
            IntPtr result = FindHwndByClass(strClass, hwndChild);
            if (result != IntPtr.Zero)
                return result;       
    
            hwndChild = GetWindow(hwndChild, (int)GetWindowFlags.GW_HWNDNEXT);
        }       
    
        return IntPtr.Zero;
    }
    We can pass in「MSPIE Sttus」as the class name and look for it as a child of the WebBrowser.
    Now that we have the handle、we can try to hide it.My initial atemptsto hide the progress bar includeusing SetwindowPos to move the screen、reizi it t to one pixel hihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihihind andandandandandandandandandandandandandandanda nnnumbebebebeber thethethethethethethethethethethethethethethe the thethethethethethethethethethethethethethethethethe hehehehehehererererererererererer in WebBrowserPanel's constructor,I would find the status bar window and destroy it.This seemid to work,kind of.As You can see below,there re abot 20 pixels of whitpace at the bottom of the breowr,noticeable able able able hanments
    DestroyWindow
    Not good,but easuryenough to work around.After we get the progress bar handle we can get its window height.After we destroy the window,we can resize the WebBrowser to be this muctaller than its parent panel,thus clipping off this whitepace.  WebBrowserPanel's constructor now look s like:
    whitespace.png
    view plin
    copy to clipboard
    print
    public WebBrowserPanel()  
  • {  
  •     Initialize Component();  
  •   
  •     WebBrowser.Width =  this.Width - 2.  
  •     WebBrowser.Height =  this.Height;  
  •   
  •     IntPtr hwndStatus = FindHwndByClass(「MSPIE」) Sttus「 WebBrowser.Handle  
  •      if (hwndStatus != IntPtr.Zero)  
  •     {  
  •         RECT rectSttus =  new RECT()  
  •         Get CientRect(hwndSttus)  out rectStatus)  
  •   
  •         DestroyWindow(hwndStatus);  
  •   
  •         WebBrowser.Height += rectStuts.Height;  
  •     }   
  • }  
  • public WebBrowserPanel()
    {
        InitializeComponent();
    
        WebBrowser.Width = this.Width - 2;
        WebBrowser.Height = this.Height;
    
        IntPtr hwndStatus = FindHwndByClass("MSPIE Status", WebBrowser.Handle);
        if (hwndStatus != IntPtr.Zero)
        {
            RECT rectStatus = new RECT();
            GetClientRect(hwndStatus, out rectStatus);
    
            DestroyWindow(hwndStatus);
    
            WebBrowser.Height += rectStatus.Height;
        }
    }
    And we end up with:

    Success!You can now set the Dcument Text any number of times without the progress bar showgup.
    The code presented above makes use of the follwing PInvokes and enums:
    final.png
    view plin
    copy to clipboard
    print
    [DllImport(「corelle.dll」)  
  • pblic  static  extern  要点 Get Class Name(IntPtr) hWnd StringBuider lpClass Name、  要点 nMaxCount)  
  •   
  • [DllImport]]  
  • public  static  extern IntPtr GetWindow(IntPtr) hwnd、  要点 cmd);  
  •   
  • public  エンム GetWindowFlags :  要点  
  • {  
  •     GW WNDFIRST = 0,  
  •     GW WNDLAST = 1,  
  •     GW WNDNEXT = 2,  
  •     GWガンダムPREV = 3,  
  •     GW = 4,  
  •     GWリキッド = 5,  
  •     GW MAX = 5  
  • }  
  •   
  • [DllImport]]  
  • public  static  extern  ブック DestroyWindow(IntPtr) hwnd);  
  •   
  • [StructLayout(LayoutKind.Sequential)]  
  • pblic  struct RECT  
  • {  
  •      public  要点 X;  
  •      public  要点 Y;  
  •      public  要点 Width  
  •      public  要点 ヘight  
  • }  
  •   
  • [DllImport]]  
  • static  extern  ブック Get ClientRect(IntPtr) hWnd  out RECT lpRect);  
    [DllImport("coredll.dll")]
    public static extern int GetClassName(IntPtr hWnd, StringBuilder lpClassName, int nMaxCount);
    
    [DllImport("coredll.dll")]
    public static extern IntPtr GetWindow(IntPtr hwnd, int cmd);
    
    public enum GetWindowFlags : int
    {
        GW_HWNDFIRST = 0,
        GW_HWNDLAST = 1,
        GW_HWNDNEXT = 2,
        GW_HWNDPREV = 3,
        GW_OWNER = 4,
        GW_CHILD = 5,
        GW_MAX = 5
    }
    
    [DllImport("coredll.dll")]
    public static extern bool DestroyWindow(IntPtr hwnd);
    
    [StructLayout(LayoutKind.Sequential)]
    public struct RECT
    {
        public int X;
        public int Y;
        public int Width;
        public int Height;
    }
    
    [DllImport("coredll.dll")]
    static extern bool GetClientRect(IntPtr hWnd, out RECT lpRect);


    >