簡體   English   中英

線程和位圖方法C#

[英]threading & bitmap method c#

我正在嘗試從c#中的瀏覽器控件獲取屏幕截圖。 當我嘗試初始化瀏覽器控件時,出現錯誤:

由於當前線程不在單線程單元中,因此無法實例化ActiveX控件'8856f961-340a-11d0-a96b-00c04fd705a2'。

現在,我正在嘗試創建一個線程,並在其中進行所有初始化,但是在嘗試聲明Response.ContentType = "image/jpeg";時出現錯誤Response.ContentType = "image/jpeg"; 錯誤消息是:

在這種情況下,響應不可用。

這是我完整的代碼:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.IO;
using System.Net;
using System.Text.RegularExpressions;
using System.Drawing;
using System.Threading;
using System.Drawing.Imaging;
using System.Text;
using System.Windows.Forms;

public partial class _Default : System.Web.UI.Page
{

    string currentPageUrl = "";
    Bitmap bmp = new Bitmap(1024, 768);

    protected void Page_Load(object sender, EventArgs e)
    {       
    }
    protected void btnSubmit_Click(object sender, EventArgs e)
    {

        if (Request.ServerVariables["HTTPS"].ToString() == "")
        {
            currentPageUrl = Request.ServerVariables["SERVER_PROTOCOL"].ToString().ToLower().Substring(0, 4).ToString() + "://" + Request.ServerVariables["SERVER_NAME"].ToString() + ":" + Request.ServerVariables["SERVER_PORT"].ToString() + Request.ServerVariables["SCRIPT_NAME"].ToString();
        }
        else
        {
            currentPageUrl = Request.ServerVariables["SERVER_PROTOCOL"].ToString().ToLower().Substring(0, 5).ToString() + "://" + Request.ServerVariables["SERVER_NAME"].ToString() + ":" + Request.ServerVariables["SERVER_PORT"].ToString() + Request.ServerVariables["SCRIPT_NAME"].ToString();
        }

        Thread thr = new Thread(new ThreadStart(OptimizeWebBrowserAndCreateImage));
        thr.SetApartmentState(ApartmentState.STA);
        thr.Start();   
    }   

    protected void OptimizeWebBrowserAndCreateImage()
    {
        System.Windows.Forms.WebBrowser browser = new System.Windows.Forms.WebBrowser();
        browser.ScrollBarsEnabled = false;
        browser.ScriptErrorsSuppressed = true;
        browser.Navigate(currentPageUrl);
        while (browser.ReadyState != WebBrowserReadyState.Complete)
            System.Windows.Forms.Application.DoEvents();
        System.Threading.Thread.Sleep(1500);
        int width = browser.Document.Body.ScrollRectangle.Width;
        int height = browser.Document.Body.ScrollRectangle.Height;
        browser.Width = width;
        browser.Height = height;
        System.Drawing.Bitmap bmp = new Bitmap(width, height);
        browser.DrawToBitmap(bmp, new System.Drawing.Rectangle(0, 0, width, height));      
        Response.ContentType = "image/jpeg";
        Response.AppendHeader("Content-Disposition", "attachment; filename=screenshot.jpg");
        bmp.Save(Response.OutputStream, ImageFormat.Jpeg);
        bmp.Dispose();
        bmp.Dispose();
        Response.End();
    }
}

正如我在Response.ContentType = "image/jpeg";上所說的那樣,我得到了一個錯誤Response.ContentType = "image/jpeg";

感謝您的幫助,希望有人可以幫助我解決此問題。 在此先感謝Laziale

Updated Version based on Henk's advice:using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.IO;
using System.Net;
using System.Text.RegularExpressions;
using System.Drawing;
using System.Threading;
using System.Drawing.Imaging;
using System.Text;
using System.Windows.Forms;

public partial class _Default : System.Web.UI.Page
{

    string currentPageUrl = "";
    Bitmap bmp = new Bitmap(1024, 768);
    Thread thr = null;

    protected void Page_Load(object sender, EventArgs e)
    {       
    }
    protected void btnSubmit_Click(object sender, EventArgs e)
    {

        if (Request.ServerVariables["HTTPS"].ToString() == "")
        {
            currentPageUrl = Request.ServerVariables["SERVER_PROTOCOL"].ToString().ToLower().Substring(0, 4).ToString() + "://" + Request.ServerVariables["SERVER_NAME"].ToString() + ":" + Request.ServerVariables["SERVER_PORT"].ToString() + Request.ServerVariables["SCRIPT_NAME"].ToString();
        }
        else
        {
            currentPageUrl = Request.ServerVariables["SERVER_PROTOCOL"].ToString().ToLower().Substring(0, 5).ToString() + "://" + Request.ServerVariables["SERVER_NAME"].ToString() + ":" + Request.ServerVariables["SERVER_PORT"].ToString() + Request.ServerVariables["SCRIPT_NAME"].ToString();
        }
        thr = new Thread(new ThreadStart(OptimizeWebBrowserAndCreateImage));
        thr.SetApartmentState(ApartmentState.STA);
        thr.Start();      
    }  

    protected void OptimizeWebBrowserAndCreateImage()
    {
        /*
        Bitmap bitmap = new Bitmap(CaptureWebPage2(currentPageUrl));
        Response.ContentType = "image/jpeg";
        Response.AppendHeader("Content-Disposition", "attachment; filename=screenshot.jpg");
        bitmap.Save(Response.OutputStream, ImageFormat.Jpeg);
        bitmap.Dispose();
        bitmap.Dispose();
        Response.End();
        */

        System.Windows.Forms.WebBrowser browser = new System.Windows.Forms.WebBrowser();
        browser.ScrollBarsEnabled = false;
        browser.ScriptErrorsSuppressed = true;
        browser.Navigate(currentPageUrl);
        while (browser.ReadyState != WebBrowserReadyState.Complete)
            System.Windows.Forms.Application.DoEvents();
        System.Threading.Thread.Sleep(1500);
        int width = browser.Document.Body.ScrollRectangle.Width;
        int height = browser.Document.Body.ScrollRectangle.Height;
        browser.Width = width;
        browser.Height = height;
        System.Drawing.Bitmap bmp = new Bitmap(width, height);
        browser.DrawToBitmap(bmp, new System.Drawing.Rectangle(0, 0, width, height));      
     /*  Response.ContentType = "image/jpeg";
        Response.AppendHeader("Content-Disposition", "attachment; filename=screenshot.jpg");
        bmp.Save(Response.OutputStream, ImageFormat.Jpeg);
        bmp.Dispose();
        bmp.Dispose();
        Response.End();
      */
    }

    protected void Page_PreRender(object sender, EventArgs e)
    {
        if (thr != null)
        {
            thr.Join();

            Response.ContentType = "image/jpeg";
            Response.AppendHeader("Content-Disposition", "attachment; filename=screenshot.jpg");
            bmp.Save(Response.OutputStream, ImageFormat.Jpeg);
            bmp.Dispose();
            //bmp.Dispose();
            Response.End();
        }
    }
}

您在瀏覽器中,因此可以使用WebBrowser的Document屬性獲取網頁的數據。
如何從文檔中獲取數據,則取決於文檔本身。
我也看不到您在哪里啟動響應。 發布代碼中是否缺少此代碼?

您正在運行一個單獨的線程,因此該線程正在HttpContext外部運行。 這就是為什么您沒有得到有用的響應(或請求或會話)的原因。 因此,將Context作為參數傳遞給您的方法,並從那里獲取響應。

或者重寫代碼,以使該方法不依賴於HttpContext(因為這可能不是線程安全的)。 在頁面生命周期的稍后階段拾取位圖結果,您可以在其中使用響應。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM