积极答复者
HtmlPage.Window.Invoke() 在IE7.0报iexplore.exe异常,在360浏览器正常

问题
-
BLOCKED SCRIPT
<script type="text/javascript">
function CloseBuoyage() {
var control = document.getElementById("silverlightBuoyage");
control.style.display = "none";
}
</script>HTML:
<body>
<object id="SilverlightMain" data="data:application/x-silverlight-2," type="application/x-silverlight-2"
style="width: 0px; height: 0px; position: absolute; top: 250px; left: 500px;">
<param name="source" value="ClientBin/MainAnimation.xap" />.......
</object>
<object id="silverlightBuoyage" data="data:application/x-silverlight-2," type="application/x-silverlight-2"
style="position: absolute; width: 40px; height: 120px">
<param name="source" value="ClientBin/TencentBuoyage.xap" />.......
</object>
</body>C#:
private void Close_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
HtmlPage.Window.Invoke("CloseBuoyage"); 在IE7.0报iexplore.exe异常,在360浏览器正常
}2008年12月9日 5:02
答案
-
堆栈和异常信息,哥们。
没有这些东西,我们只能瞎猜你的问题,然后随便给你一个解决方案。
HtmlPage.Window.Invoke函数的过程是这样的:
-
C#代码通过P/Invoke调用Silverlight Runtime的DLL里面的C函数(虽然是用C++写的,但是声明成C兼容的函数)InvokeBrowseFunc(假设的名字)
-
C函数InvokeBrowseFunc判断浏览器的内核(例如是否是IE,Firefox还是Safari - Mac机),然后通过一些预定义的C++基类调用针对各个内核实现的子类,例如IEBrowserHelp(假设的名字)
-
IEBrowserHelp->Invoke里面调用IE提供的IHTMLXXXXXX接口来操作网页的DOM对象,例如调用脚本程序。
-
IHTMLXXXXXX发现你调用的是脚本函数,调用Javascript解释引擎,告诉Javascript引擎调用脚本函数
-
Javascript引擎将调用结果返回给IHTMLXXXXXX
-
IHTMLXXXXXX将结果返回给IEBrowserHelp->Invoke
-
IEBrowserHelp->Invoke再将结果返回给InvokeBrowseFunc
-
InvokeBrowseFunc再将结果返回给我们的HtmlPage.Window.Invoke
-
HtmlPage.Window.Invoke判断返回的HRESULT值,然后转换成对应的.NET异常。
这9个步骤里面,可能会有Javascript异常,也可能会有C++异常,还有可能会有.NET异常。一般C++异常会将你的IE干掉,而其他两种异常可以被IE消化,然后在左下角出现一个惊叹号!
因此,请给我们你的堆栈和异常信息。
附,你可以用Eval函数试一下,Eval应该可以用。
2008年12月9日 11:35 -
全部回复
-
<object data="data:application/x-silverlight,"
type="application/x-silverlight-2-b2"
width="300" height="100"
<param name="source" value="MySample.xap"/>
<param name="enableHtmlAccess" value="true" />
</object>
同一个域默认为true
enableHtmlAccess设置true,直接调用 HtmlPage..Document 可以吗
有时间我做个例子试试2008年12月9日 6:00 -
堆栈和异常信息,哥们。
没有这些东西,我们只能瞎猜你的问题,然后随便给你一个解决方案。
HtmlPage.Window.Invoke函数的过程是这样的:
-
C#代码通过P/Invoke调用Silverlight Runtime的DLL里面的C函数(虽然是用C++写的,但是声明成C兼容的函数)InvokeBrowseFunc(假设的名字)
-
C函数InvokeBrowseFunc判断浏览器的内核(例如是否是IE,Firefox还是Safari - Mac机),然后通过一些预定义的C++基类调用针对各个内核实现的子类,例如IEBrowserHelp(假设的名字)
-
IEBrowserHelp->Invoke里面调用IE提供的IHTMLXXXXXX接口来操作网页的DOM对象,例如调用脚本程序。
-
IHTMLXXXXXX发现你调用的是脚本函数,调用Javascript解释引擎,告诉Javascript引擎调用脚本函数
-
Javascript引擎将调用结果返回给IHTMLXXXXXX
-
IHTMLXXXXXX将结果返回给IEBrowserHelp->Invoke
-
IEBrowserHelp->Invoke再将结果返回给InvokeBrowseFunc
-
InvokeBrowseFunc再将结果返回给我们的HtmlPage.Window.Invoke
-
HtmlPage.Window.Invoke判断返回的HRESULT值,然后转换成对应的.NET异常。
这9个步骤里面,可能会有Javascript异常,也可能会有C++异常,还有可能会有.NET异常。一般C++异常会将你的IE干掉,而其他两种异常可以被IE消化,然后在左下角出现一个惊叹号!
因此,请给我们你的堆栈和异常信息。
附,你可以用Eval函数试一下,Eval应该可以用。
2008年12月9日 11:35 -
-
JS:
function Close(obj1, obj2) {
document.getElementById(obj1).style.display = "none";
document.getElementById(obj2).style.display = "block"; }
C#
HtmlPage.Window.Invoke("Close", “Main”,"Buoyage”);
HtmlPage.Window.Invoke("Close", “Buoyage”,"Main”);
执行以上其中一句,会异常
现在看下来只要是Close的对象是自己本身的话,也就是display = "none"的对象是自己本身,就会异常。但是在360浏览器中正常
按Killmyday 的分析,那应该算C++异常,因为异常时直接把IE关闭了
Eval函数也是一样的异常。
SIlverlight 2.0 RTM
2008年12月10日 5:54 -
打火机 写: JS:
function Close(obj1, obj2) {
document.getElementById(obj1).style.display = "none";
document.getElementById(obj2).style.display = "block"; }
C#
HtmlPage.Window.Invoke("Close", “Main”,"Buoyage”);
HtmlPage.Window.Invoke("Close", “Buoyage”,"Main”);
执行以上其中一句,会异常
现在看下来只要是Close的对象是自己本身的话,也就是display = "none"的对象是自己本身,就会异常。但是在360浏览器中正常
按Killmyday 的分析,那应该算C++异常,因为异常时直接把IE关闭了
Eval函数也是一样的异常。
SIlverlight 2.0 RTM
嗯,我以前用HtmlPage.Window.Invoke()操作Flash的时候也会异常,浏览器关闭。
最好不要对objectid直接操作,可以操作上层的DIV,楼主试试
2008年12月10日 9:02 -
我重现了一下你的代码,在我的IE 7.0上不会Crash呀,而且一切工作正常,这是我的重现代码:
Js:
function Close(obj1, obj2) {
document.getElementById(obj1).style.display = "none";
document.getElementById(obj2).style.display = "block";
}Html:
<div id="silverlightControlHost">
<object id="Main" data="data:application/x-silverlight," type="application/x-silverlight-2" width="100%" height="100%">
<param name="source" value="TestSilverlight.xap"/>
<param name="onerror" value="onSilverlightError" />
<param name="background" value="white" />
<param name="minRuntimeVersion" value="2.0.31005.0" />
<param name="autoUpgrade" value="true" />
<a href="http://go.microsoft.com/fwlink/?LinkID=124807" style="text-decoration: none;">
<img src="http://go.microsoft.com/fwlink/?LinkId=108181" alt="Get Microsoft Silverlight" style="border-style: none"/>
</a>
</object>
<iframe style='visibility:hidden;height:0;width:0;border:0px'></iframe>
<object id="Buoyage" data="data:application/x-silverlight," type="application/x-silverlight-2" width="100%" height="100%">
<param name="source" value="TestSilverlight.xap"/>
<param name="onerror" value="onSilverlightError" />
<param name="background" value="white" />
<param name="minRuntimeVersion" value="2.0.31005.0" />
<param name="autoUpgrade" value="true" />
<a href="http://go.microsoft.com/fwlink/?LinkID=124807" style="text-decoration: none;">
<img src="http://go.microsoft.com/fwlink/?LinkId=108181" alt="Get Microsoft Silverlight" style="border-style: none"/>
</a>
</object>
</div>C#:
private void Button_Click(object sender, RoutedEventArgs e)
{
HtmlPage.Window.Invoke("Close", "Main","Buoyage");
}XAML:
<Grid x:Name="LayoutRoot" Background="White">
<Button Click="Button_Click" />
</Grid>我建议你用VS附加到IE上,看看到底是什么问题,方法如下:
-
打开IE,并且浏览到你的问题页面
-
打开VS 2008, 点击“Tools” --> "Options" --> "Debugging" --> "Symbols",将Symbol Server的路径设置成微软的公开Symbols Server路径:http://msdl.microsoft.com/download/symbols
-
当然啦,奉劝你同时设置“Cache symbols from symbol severs to this directory”来缓存从网上下载的Symbol
-
最后在VS 2008里面点击“Debug” --> “Attach To Process ...”,你可以手动选择Silverlight,或者Native。由于我怀疑你的问题是IE有其他的插件冲突,因此建议你选择Native来调试IE的C++代码。
-
根据需要勾上在异常发生的时候中断程序执行。你可以参考这篇文章来设置:http://blog.csdn.net/Donjuan/archive/2008/12/05/3454650.aspx
-
执行你的重现步骤,等VS中断了以后,将“堆栈”窗口里面的内容粘贴过来,让我们看看。
注意,你的堆栈如果是这种形式的话,对我们的分析是没有意义的:
user32!68796465
ieexplorer.exe!54045783
你贴出来的堆栈应该是
user32!CreateWindowW(...)
ieexplorer.exe!__main(argc = 1)
如果上面的操作还是不能解决你的问题的话,请参考下面的文章设置验尸调试
http://blog.csdn.net/Donjuan/archive/2008/12/04/3446670.aspx
然后在Windbg里面(Windbg可以从微软的网站上下载到),执行下面这个命令:
.dump /ma c:\badbug.dmp
然后将badbug.dmp发给谁去研究一下吧,当然啦,我很怀疑有人愿意去下载这个dmp文件--太大了(好几百M)。
最后,这篇文章说明了Symbol和内存文件的意义:
http://blog.csdn.net/Donjuan/archive/2008/12/05/3454597.aspx忘记说了,内存文件我没有加--就是把程序在物理内存所占用的内存中的所有数据保存一个文件当中,然后调试器可以通过读取这个内存文件来重现当时进程的环境。这也就是为什么这种调试叫做验尸调试,
2008年12月10日 11:30 -