2009-03-17 9 views

Respuesta

3

Sugiero utilizar un enfoque de terceros para esto, no hacerlo usted mismo. Sin embargo, si insistes, la forma más torpe es usar System.Diagnostics.Process para iniciar un navegador, luego GetDesktopImage para obtener una captura de pantalla.

estoy seguro de que hay una manera más fácil, pero que se ve así:

using System; 
using System.Drawing; 
using System.Drawing.Imaging; 
using System.Runtime.InteropServices; 

public class PlatformInvokeGDI32 
{ 
    public const int SRCCOPY = 13369376; 

    [DllImport("gdi32.dll",EntryPoint="DeleteDC")] 
    public static extern IntPtr DeleteDC(IntPtr hDc); 

    [DllImport("gdi32.dll",EntryPoint="DeleteObject")] 
    public static extern IntPtr DeleteObject(IntPtr hDc); 

    [DllImport("gdi32.dll",EntryPoint="BitBlt")] 
    public static extern bool BitBlt(IntPtr hdcDest, int xDest, int yDest, int wDest, int hDest, IntPtr hdcSource, int xSrc, int ySrc, int RasterOp); 

    [DllImport ("gdi32.dll",EntryPoint="CreateCompatibleBitmap")] 
    public static extern IntPtr CreateCompatibleBitmap(IntPtr hdc,int nWidth, int nHeight); 

    [DllImport ("gdi32.dll",EntryPoint="CreateCompatibleDC")] 
    public static extern IntPtr CreateCompatibleDC(IntPtr hdc); 

    [DllImport ("gdi32.dll",EntryPoint="SelectObject")] 
    public static extern IntPtr SelectObject(IntPtr hdc,IntPtr bmp); 
} 

public class PlatformInvokeUSER32 
{ 
    public const int SM_CXSCREEN = 0; 
    public const int SM_CYSCREEN = 1; 

    [DllImport("user32.dll", EntryPoint="GetDesktopWindow")] 
    public static extern IntPtr GetDesktopWindow(); 

    [DllImport("user32.dll",EntryPoint="GetDC")] 
    public static extern IntPtr GetDC(IntPtr ptr); 

    [DllImport("user32.dll",EntryPoint="GetSystemMetrics")] 
    public static extern int GetSystemMetrics(int abc); 

    [DllImport("user32.dll",EntryPoint="GetWindowDC")] 
    public static extern IntPtr GetWindowDC(Int32 ptr); 

    [DllImport("user32.dll",EntryPoint="ReleaseDC")] 
    public static extern IntPtr ReleaseDC(IntPtr hWnd,IntPtr hDc); 
} 

public class CaptureScreen 
{ 
    public static Bitmap GetDesktopImage() 
    { 
     //In size variable we shall keep the size of the screen. 
     SIZE size; 

     //Variable to keep the handle to bitmap. 
     IntPtr hBitmap; 

     //Here we get the handle to the desktop device context. 
     IntPtr hDC = PlatformInvokeUSER32.GetDC(PlatformInvokeUSER32.GetDesktopWindow()); 

     //Here we make a compatible device context in memory for screen device context. 
     IntPtr hMemDC = PlatformInvokeGDI32.CreateCompatibleDC(hDC); 

     //We pass SM_CXSCREEN constant to GetSystemMetrics to get the 
     //X coordinates of the screen. 
     size.cx = PlatformInvokeUSER32.GetSystemMetrics(PlatformInvokeUSER32.SM_CXSCREEN); 

     //We pass SM_CYSCREEN constant to GetSystemMetrics to get the Y coordinates of the screen. 
     size.cy = PlatformInvokeUSER32.GetSystemMetrics (PlatformInvokeUSER32.SM_CYSCREEN); 

     //We create a compatible bitmap of the screen size and using the screen device context. 
     hBitmap = PlatformInvokeGDI32.CreateCompatibleBitmap(hDC, size.cx, size.cy); 

     //As hBitmap is IntPtr, we cannot check it against null. 
     //For this purpose, IntPtr.Zero is used. 
     if(hBitmap != IntPtr.Zero) 
     { 
      //Here we select the compatible bitmap in the memeory device 
      //context and keep the refrence to the old bitmap. 
      IntPtr hOld = (IntPtr) PlatformInvokeGDI32.SelectObject(hMemDC, hBitmap); 

      //We copy the Bitmap to the memory device context. 
      PlatformInvokeGDI32.BitBlt(hMemDC, 0, 0, size.cx, size.cy, hDC, 0, 0, PlatformInvokeGDI32.SRCCOPY); 

      //We select the old bitmap back to the memory device context. 
      PlatformInvokeGDI32.SelectObject(hMemDC, hOld); 

      //We delete the memory device context. 
      PlatformInvokeGDI32.DeleteDC(hMemDC); 

      //We release the screen device context. 
      PlatformInvokeUSER32.ReleaseDC(PlatformInvokeUSER32.GetDesktopWindow(), hDC); 

      //Image is created by Image bitmap handle and stored in local variable. 
      Bitmap bmp = System.Drawing.Image.FromHbitmap(hBitmap); 

      //Release the memory to avoid memory leaks. 
      PlatformInvokeGDI32.DeleteObject(hBitmap); 

      //This statement runs the garbage collector manually. 
      GC.Collect(); 

      //Return the bitmap 
      return bmp; 
     } 

     //If hBitmap is null, retun null. 
     return null; 
    } 
} 

//This structure shall be used to keep the size of the screen. 
public struct SIZE 
{ 
    public int cx; 
    public int cy; 
} 
2

Hay varios componentes de 3 ª parte que hace esto. Aparentemente no es trivial, ya que cosas como Flash y esas cosas no se capturan tan fácilmente, por ejemplo.

He usado HTMLSnapshot en el pasado y estaba contento con él (no es gratis, pero es bastante barato).

Le recomiendo encarecidamente que no pierda demasiado tiempo implementando esto usted mismo porque es probable que termine rehaciendo muchos casos finales que estas soluciones de terceros ya manejan.

+0

Me pregunto si alguien le aconsejó a Larry Page y Sergey Brin lo mismo: P –

2

Busqué en todas partes para encontrar una solución a este problema y el problema con el uso de WebBrowser y otras sugerencias es que necesita un montón de acceso a la caja.

Hasta la fecha esta es la mejor herramienta de terceros que he podido encontrar:

http://www.websitesscreenshot.com/

Su SEO es terrible, pero creo que he encontrado en un foro o incluso Pila ... I posee una licencia y lo que obtiene es solo una DLL a la que puede hacer referencia. Pasar una licencia al constructor elimina su marca de agua.

Después de echar un rápido vistazo a ILSpy, creo que lo que hace es interpretar el HTML y volcar una imagen para su placer visual.

Uso

Almacenamiento de una dirección URL

WebsitesScreenshot.WebsitesScreenshot _Obj; 
_Obj = new WebsitesScreenshot.WebsitesScreenshot(); 
WebsitesScreenshot.WebsitesScreenshot.Result _Result; 
_Result = _Obj.CaptureWebpage("http://www.google.com"); 
if (_Result == WebsitesScreenshot.WebsitesScreenshot.Result.Captured) 
{ 
    _Obj.ImageFormat = WebsitesScreenshot. 
     WebsitesScreenshot.ImageFormats.PNG; 
    _Obj.SaveImage ("c:\\google.png"); 
}    
_Obj.Dispose(); 

ahorro de HTML puro cadena

WebsitesScreenshot.WebsitesScreenshot _Obj; 
_Obj=new WebsitesScreenshot.WebsitesScreenshot(); 
WebsitesScreenshot.WebsitesScreenshot.Result _Result; 
_Result = _Obj.CaptureHTML(
"<html><body><h1> Hello world </h1></body></html>"); 
if (_Result == WebsitesScreenshot.WebsitesScreenshot.Result.Captured) 
{ 
    _Obj.ImageFormat = WebsitesScreenshot. 
     WebsitesScreenshot.ImageFormats.GIF; 
    _Obj.SaveImage("c:\\test.gif"); 
} 
_Obj.Dispose(); 

Puede encontrar más en su página de uso. Aquí encontrado:

http://www.websitesscreenshot.com/Usage.html

Espero que esto ayude!

¡Salud!

Cuestiones relacionadas