铸造mshtml.IHTMLImgElement到mshtml.IHTMLElementRender失败,E_NOINTERFACE [英] Casting mshtml.IHTMLImgElement to mshtml.IHTMLElementRender fails with E_NOINTERFACE

查看:1240
本文介绍了铸造mshtml.IHTMLImgElement到mshtml.IHTMLElementRender失败,E_NOINTERFACE的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有C#.NET 4的WinForms应用程序(使用MSHTML七)推出新的连接到现有的IE浏览器10个实例。它遍历所有的图像和下载他们操纵。这种方法是费时和多余的,因为在图像已经被下载被IE

I have C# .NET 4 WinForms app (using MSHTML 7) that launches new and connects to existing IE 10 instances. It iterates through all images and downloads them to manipulate. This approach is time-consuming and redundant since the image has already been downloaded by IE.

我已经搜索无处不在,只有极少数的论坛讨论的主题,但所有人都能够施展mshtml.IHTMLImgElement反对mshtml.IHTMLElementRender(虽然在C ++ code)。

I have searched everywhere and only a handful of forums discuss the subject but all are able to cast mshtml.IHTMLImgElement objects to mshtml.IHTMLElementRender (although in C++ code).

Unable to cast COM object of type 'mshtml.HTMLImgClass' to interface type 'mshtml.IHTMLElementRender'.
This operation failed because the QueryInterface call on the COM component for the interface with IID '{3050F669-98B5-11CF-BB82-00AA00BDCE0B}' failed due to the following error:
No such interface supported (Exception from HRESULT: 0x80004002 (E_NOINTERFACE)).

课程的目的是为了获得完整的图像,从而替代方法,欢迎为好。这里是code导致上述异常。

The objective of course is to gain access to the full image so alternative approaches are welcome as well. Here is the code causing the exception above.

public static void Main (string [] args)
{
    mshtml.HTMLDocument document = null;
    SHDocVw.InternetExplorer explorer = null;
    System.IntPtr hdc = System.IntPtr.Zero;
    mshtml.IHTMLElementRender render = null;
    mshtml._RemotableHandle handle = default(mshtml._RemotableHandle);

    try
    {
        explorer = new SHDocVw.InternetExplorer();
        explorer.Visible = true;

        try
        {
            explorer.Navigate("http://www.google.com/ncr");

            while (explorer.Busy)
            {
                // Striped events for SO example.
                System.Threading.Thread.Sleep(100);
            }

            document = (mshtml.HTMLDocument) explorer.Document;

            foreach (mshtml.IHTMLImgElement image in document.images)
            {
                Console.WriteLine();

                if ((image.width > 0) && (image.height > 0))
                {
                    // The following [if] will return false if uncommented.
                    //if (image.GetType().GetInterfaces().ToList().Contains(typeof(mshtml.IHTMLElementRender)))
                    {
                        using (Bitmap bitmap = new Bitmap(image.width, image.height))
                        {
                            using (Graphics graphics = Graphics.FromImage(bitmap))
                            {
                                hdc = graphics.GetHdc();
                                handle.fContext = hdc.ToInt32();
                                render = (mshtml.IHTMLElementRender) image; // Causes the exception.
                                //handle = (mshtml._RemotableHandle) Marshal.PtrToStructure(hdc, typeof(mshtml._RemotableHandle));
                                render.DrawToDC(ref handle);
                                graphics.ReleaseHdc(hdc);

                                // Process image here.

                                Console.Write("Press any key to continue...");
                                Console.ReadKey();
                            }
                        }
                    }
                }
            }
        }
        catch (System.Exception e)
        {
            Console.WriteLine(e.Message);
            Console.WriteLine("Stack Trace: " + e.StackTrace);
        }

        explorer.Quit();
    }
    catch (System.Exception e)
    {
        Console.WriteLine(e.Message);
        Console.WriteLine("Stack Trace: " + e.StackTrace);
    }
    finally
    {
    }

#if (DEBUG)
        Console.WriteLine();
        Console.Write("Press any key to continue...");
        Console.ReadKey();
#endif
}

有些收效不大我已经走过的链接:

Some of the links I have gone through without avail:

  • Capture an HTML document as an image
  • Unable to cast COM object of type '…' to interface type '…' while using an ExeCOMServer

推荐答案

您可以很容易地看到REGEDIT.EXE问题的根源。为了弥补大峡谷进程边界之间的接口,需要code表示实现一个代理和一个存根的接口。 code,它知道如何接口方法参数序列化为可以从一个进程发送到另一个RPC数据包。

You can easily see the root of the problem with Regedit.exe. In order for an interface to bridge the Grand Canyon between process boundaries, it needs code that implements a proxy and a stub for an interface. Code that knows how to serialize the interface method arguments into an RPC packet that can be transmitted from one process to another.

COM通过查看注册表中发现,code。你也有REGEDIT.EXE可以,浏览到HKCR \接口,向下滚动相匹配的GUID。你会看到的很多的的{}的GUID那里,看起来像{305xxxx-98B5-11CF-BB82-00AA00BDCE0B}。是的,微软欺骗他们的GUID,更容易调试,IE浏览器,而他们中的很多。他们指出,标准的封送处理,包括类型库GUID,它描述的接口。

COM discovers that code by looking through the registry. You can too with Regedit.exe, navigate to HKCR\Interfaces and scroll down to match the guid. You will see a lot of {guids} there that look like {305xxxx-98B5-11CF-BB82-00AA00BDCE0B}. Yes, Microsoft cheats on their guids, easier for debugging, IE has rather a lot of them. They point to the standard marshaller and include the type library guid that describes the interface.

但你的不可以找到{3050F669-98B5-11CF-BB82-00AA00BDCE0B}。这基本上是异常消息告诉你,它不能找到一种方法来封送接口指针。神秘E_NOINTERFACE错误code是回退的做法不工作或者,未能查询的IMarshal的结果。

But you will not find {3050F669-98B5-11CF-BB82-00AA00BDCE0B}. Which is basically what the exception message is telling you, it can't find a way to marshal the interface pointer. The mysterious E_NOINTERFACE error code is the result of the fallback approach not working either, failing to query for IMarshal.

这是一个有点他们忘了和他们不能让它正常工作之间的胜负难料。这一次严重倾斜向太硬,使其工作。序列化渲染界面上的视频硬件当然,从来没有一台机器和其他​​的比赛太艰难,太多的依赖。甚至在一台机器,需要有图形管线之前可以由任何方法调用正确初始化是过于复杂。

This is a bit of a toss-up between "they forgot" and "they couldn't make it work". This one heavily leans towards "too hard to make it work". Serializing a render interface is way too difficult, too many dependencies on the video hardware which of course never matches between one machine and another. Or even on one machine, the need to have the graphics pipeline initialized properly before any method calls can be made is far too tricky.

这就是责无旁贷,不能使这项工作。你需要自己渲染图像,不容易做到的。对不起,请不要拍的使者。

That's where the buck stops, you cannot make this work. You'll need to render that image yourself, not easy to do. Sorry, please don't shoot the messenger.

这篇关于铸造mshtml.IHTMLImgElement到mshtml.IHTMLElementRender失败,E_NOINTERFACE的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆