我尝试使用几个代码片段将 ActiveX 对象与 Javascript 事件处理程序挂钩。我无法确定为什么事件处理程序没有被调用。
带有项目的 Github 存储库。 https://github.com/JesseKPhillips/CsharpActiveX
Update
通过在“onLoad”事件中放置对 SayHello() 的 javascript 调用,我能够触发 ActiveX 事件。现在我正在研究 C# 调用,以及如何将其挂接到 Javascript 使用的 ActiveX 对象中。
(这也可能依赖于从 IE 的高级选项启用本地脚本)。
留言继续
事件处理程序是在与此问题所描述的形式相同 https://stackoverflow.com/questions/150814/how-to-handle-an-activex-event-in-javascript.
<script for="MyObject" event="OnUpdateString(stuff)">
document.write("<p>" + stuff);
document.writeln("</p>");
</script>
利用MSDN 文档 https://msdn.microsoft.com/en-us/library/system.windows.forms.webbrowser.objectforscripting.aspx我创建了一个 WinForms 应用程序,其中包含一个充当 ObjectForScripting 的 WebBrowser 控件(与问题无关)。该容器调用 ActiveX 事件,但未被 Javascript 处理。我将 C# 表单代码包含在 ActiveX 交互中以使其完整,并使其成为 ActiveX 和/或 WebBrowser 控件的未来用户的参考。
此文件旨在与新的 Windows 窗体项目一起使用,其中 WebBrowser 控件已添加到主窗口。
C# Form1.cs
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Security.Permissions;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using ActiveXObjectSpace;
namespace TestActiveX
{
[PermissionSet(SecurityAction.Demand, Name = "FullTrust")]
[System.Runtime.InteropServices.ComVisibleAttribute(true)]
public partial class Form1 : Form
{
MyObject myObject = new MyObject();
public Form1()
{
InitializeComponent();
Text = "ActiveX Test";
Load += new EventHandler(Form1_Load);
}
private void Form1_Load(object sender, EventArgs e)
{
webBrowser1.AllowWebBrowserDrop = false;
webBrowser1.ObjectForScripting = this;
webBrowser1.Url = new Uri(@"C:\path\to\TestPage.html");
// Call ActiveX
myObject.SayHello("C# Launch");
}
public string ControlObject()
{
return "<p>Control Object Called.</p>";
}
}
}
结合来自帮助two http://blogs.msdn.com/b/asiatech/archive/2011/12/05/how-to-develop-and-deploy-activex-control-in-c.aspx other 代码片段 https://stackoverflow.com/questions/1455577/how-can-i-make-an-activex-control-written-with-c-sharp-raise-events-in-javascrip我创建了一个ActiveX对象。如前所述,需要在构建后进行注册。
C# ObjectX.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Runtime.InteropServices;
/// http://blogs.msdn.com/b/asiatech/archive/2011/12/05/how-to-develop-and-deploy-activex-control-in-c.aspx
/// https://stackoverflow.com/questions/11175145/create-com-activexobject-in-c-use-from-jscript-with-simple-event
///
/// Register with %NET64%\regasm /codebase <full path of dll file>
/// Unregister with %NET64%\regasm /u <full path of dll file>
namespace ActiveXObjectSpace
{
/// <summary>
/// Provides the ActiveX event listeners for Javascript.
/// </summary>
[Guid("4E250775-61A1-40B1-A57B-C7BBAA25F194"), InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
public interface IActiveXEvents
{
[DispId(1)]
void OnUpdateString(string data);
}
/// <summary>
/// Provides properties accessible from Javascript.
/// </summary>
[Guid("AAD0731A-E84A-48D7-B5F8-56FF1B7A61D3"), InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
public interface IActiveX
{
[DispId(10)]
string CustomProperty { get; set; }
}
[ProgId("MyObject")]
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.AutoDual)]
[Guid("7A5D58C7-1C27-4DFF-8C8F-F5876FF94C64")]
[ComSourceInterfaces(typeof(IActiveXEvents))]
public class MyObject : IActiveX
{
public delegate void OnContextChangeHandler(string data);
new public event OnContextChangeHandler OnUpdateString;
// Dummy Method to use when firing the event
private void MyActiveX_nMouseClick(string index)
{
}
public MyObject()
{
// Bind event
this.OnUpdateString = new OnContextChangeHandler(this.MyActiveX_nMouseClick);
}
[ComVisible(true)]
public string CustomProperty { get; set; }
[ComVisible(true)]
public void SayHello(string who)
{
OnUpdateString("Calling Callback: " + who);
}
}
}
最后是由浏览器或容器加载的 html 页面。它成功加载 ActiveX 对象并包含 OnUpdateString 的事件处理程序。它检查 ActiveX 提供的函数 SayHello 是否可以调用并进行调用。
我希望将 Javascript 和 C# 调用写入文档,但没有写入此类条目。
测试页.html
<!DOCTYPE html>
<html lang="en" xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>DemoCSharpActiveX webpage</title>
</head>
<body>
<script type="text/javascript">
window.objectLoadFailure = false;
</script>
<object id="MyObject" onerror="window.objectLoadFailure = true" classid="clsid:7A5D58C7-1C27-4DFF-8C8F-F5876FF94C64"></object>
<script for="MyObject" event="OnUpdateString(stuff)">
document.write("<p>" + stuff);
document.writeln("</p>");
</script>
<script type="text/javascript">
document.write("<p>Loaded ActiveX Object: " + !window.objectLoadFailure);
document.writeln("</p>");
if (typeof window.external.ControlObject !== "undefined") {
document.write(window.external.ControlObject());
}
var obj = document.MyObject;
if (typeof obj.SayHello !== "undefined") {
document.writeln("<p>Can Call say hello</p>")
}
obj.SayHello("Javascript Load");
</script>
</body>
</html>
包含页面显示此输出
Output
已加载 ActiveX 对象:true
调用的控制对象。
可以打电话打个招呼