use*_*490 2 hook vba add-in dllimport excel-vba
我正在编写Excel 2007 Addin.使用VS2008和.net 3.5,C#.
我抓住了Microsoft.Office.Interop.Excel.Application的WindowActivate和WindowDeActivate事件.
令人惊讶的是,当我在两个Excel Windows之间切换时,WindowActivate和Deactivate仅触发.如果我切换到记事本,我希望触发Deactivate,但它没有发生.如果我切换到excel窗口,记事本的方式相同,我希望触发Activate但它没有发生.看起来行为表明窗口是MDI-Child窗口.
现在我要做的是获取Excel的Mainwindow的HWnd并使用dllimport功能挂钩Window Activate和Deactivates.
谁能指导我这个.
问候
我在编写Excel插件时解决了类似的问题.不需要dll导入.我使用System.Windows.Forms.NativeWindow类解决了这个问题.
首先,我创建了自己的继承自NativeWindow类的类,并在其中声明了两个事件Activated和Deactivate,最后重写了WndProc()方法,以便在将消息WM_ACTIVATE传递给WndProc方法时引发这些事件.根据"消息"参数,WParm是Excel窗口激活或停用.
public class ExcelWindow: NativeWindow
{
public const int WM_ACTIVATED = 0x0006;
public ExcelWindow():base(){}
//events
public event EventHandler Activated;
public event EventHandler Deactivate;
//catching windows messages
protected override void WndProc(ref Message m)
{
if (m.Msg== WM_ACTIVATED)
{
if (m.WParam.ToInt32() == 1)
{
//raise activated event
if (Activated!=null)
{
Activated(this, new EventArgs());
}
}
else if (m.WParam.ToInt32() == 0)
{
//raise deactivated event
if (Deactivate!=null)
{
Deactivate(this, new EventArgs());
}
}
}
base.WndProc(ref m);
}
}
Run Code Online (Sandbox Code Playgroud)
然后我在我的addin类字段"ExcelWindow myExcelWindow"中添加了以下代码并添加到我的插件的OnConnection方法:
ExcelWindow myExcelWindow;
void Extensibility.IDTExtensibility2.OnConnection(object application, Extensibility.ext_ConnectMode ConnectMode, object AddInInst, ref Array custom)
{
excel = application as Excel.Application;
myExcelWindow = new ExcelWindow();
myExcelWindow.AssignHandle(new IntPtr(excel.Hwnd));
myExcelWindow.Activated += new EventHandler(myExcelWindow_Activated);
myExcelWindow.Deactivate += new EventHandler(myExcelWindow_Deactivate);
//addin code here
}
void myExcelWindow_Activated(object sender, EventArgs e)
{
//do some stuff here
}
void myExcelWindow_Deactivate(object sender, EventArgs e)
{
//do some stuff here
}
Run Code Online (Sandbox Code Playgroud)
我希望这能帮到您.