OneNote Continues to Grab My Plugin Button
source link: https://www.codesd.com/item/onenote-continues-to-grab-my-plugin-button.html
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
OneNote Continues to Grab My Plugin Button
I've created a toolbar button in OneNote like Daniel Escapa showed. Usually, it works, but sometimes OneNote decides to grey out the toolbar button, making it impossible to click. I can't figure out what state is causing this. How can I prevent this?
I'm careful to return true from the OnEvent and OnClick handlers, but maybe there's a special case that is causing it to return false? Here is my code:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using OneNoteAddin;
using System.Runtime.InteropServices;
using Microsoft.Win32;
using System.IO;
using OneNote = Microsoft.Office.Interop.OneNote;
namespace NoteTakerPlugin
{
[Guid("792d0410-d53c-402d-92c9-5db9ea29f644")]
public class NoteTakerButton : IOneNoteAddIn
{
// for sending messages to window handles
private struct COPYDATASTRUCT
{
public IntPtr dwData;
public int cbData;
[MarshalAs(UnmanagedType.LPStr)]
public string lpData;
}
// this should be hardcoded in the note taker application
private const string NoteTakerAppClassName = "CubicNoteTaker-792d0410-d53c-402d-92c9-5db9ea29f644::EventReceiver";
private const int WM_COPYDATA = 0x4A;
[DllImport("user32.dll", EntryPoint = "FindWindow", SetLastError = true)]
static extern IntPtr FindWindowByCaption(IntPtr ZeroOnly, string lpWindowName);
[DllImport("User32.dll", EntryPoint = "SendMessage")]
private static extern int SendMessage(IntPtr hWnd, int Msg, int wParam, ref COPYDATASTRUCT lParam);
IntPtr app;
public NoteTakerButton()
{
tellAppSomething("{ \"appStart\": true }", false);
}
public bool OnClick([In] String strActivePageID)
{
// send the click event to the note taker app
tellAppSomething("{ \"click\": { \"pageId\": \"" + strActivePageID + "\" }}", true);
return true;
}
public bool OnEvent([In] OneNote.OneNoteAddIn_Event evt, [In] String strParameter)
{
// send the event to the note taker app
tellAppSomething("{ \"event\": { \"id\": " + (int)evt + ", \"param\": \"" + strParameter + "\" }}", false);
return true;
}
private void tellAppSomething(String message, bool startProgram)
{
// if the process is running
refreshAppStatus();
if( app != IntPtr.Zero )
{
// send a window message to the process telling it the message
sendMessageTo(app, message);
}
else if( startProgram )
{
// start the process with a command line telling it the message
startApp(message);
}
}
private void refreshAppStatus()
{
app = FindWindowByCaption(IntPtr.Zero, NoteTakerAppClassName);
}
private void sendMessageTo(IntPtr hWnd, String msg)
{
int wParam = 0;
int result = 0;
if (hWnd != IntPtr.Zero )
{
byte[] sarr = System.Text.Encoding.Default.GetBytes(msg);
int len = sarr.Length;
COPYDATASTRUCT cds;
cds.dwData = IntPtr.Zero;
cds.lpData = msg;
cds.cbData = len + 1;
result = SendMessage(hWnd, WM_COPYDATA, wParam, ref cds);
}
}
private void startApp(String args)
{
string exe = getAppExe();
if (File.Exists(exe))
{
System.Diagnostics.Process.Start(exe, args);
}
else
{
System.Windows.Forms.MessageBox.Show("You need to reinstall the Note Taker application. The installation is corrupted.");
}
}
private string getAppExe()
{
// use the registry to find where the application is installed
RegistryKey noteTakerKey = Registry.LocalMachine.OpenSubKey("SOFTWARE\\NoteTaker");
String path = noteTakerKey.GetValue("Path","").ToString();
String exe = noteTakerKey.GetValue("Exe", "").ToString();
if (!Directory.Exists(path))
return "";
String combo = Path.Combine(path, exe);
if( File.Exists(combo) )
return combo;
else // not installed
return "";
}
}
}
EDIT: I remember this issue, now! When you close OneNote, check if an instance of it is still running in taskman, I think this sort of locks the addon in future instances and grays them out, make sure you dont have any code left running that would be causing the instance to stay alive.
Recommend
About Joyk
Aggregate valuable and interesting links.
Joyk means Joy of geeK