Я работаю с неуправляемой DLL-библиотекой, предоставляемой поставщиком, для взаимодействия с некоторым нестандартным оборудованием.К сожалению, я не могу опубликовать код поставщика, но, надеюсь, приведенный ниже очищенный код предоставит достаточно информации о причине проблемы.
SDK поставщика требует регистрации функции обратного вызова для уведомления о событиях оборудования.У меня есть утилита от поставщика, чтобы подтвердить, что это происходит успешно.Аппаратное обеспечение отправляет в окно пользовательские сообщения WIN32, а SDK присоединяется к циклу сообщений и вызывает функцию обратного вызова при получении одного из этих пользовательских сообщений.
Когда приложение запускается напрямую, все работает.Когда приложение запускается внутри Visual Studio, регистрация завершается успешно, но события не запускаются.Это действительно работает с или без отладки (F5 / Crlt + F5).Я также пытался отключить процесс размещения Visual Studio в свойствах проекта, и это не имело никакого значения.
В библиотеке классов C # я обернул SDK поставщика следующим кодом:
public class Basic {
private delegate void Callback(UInt32 Event, Byte status, UInt16 type, UInt16 devno);
private Callback mInstance;
public delegate void EventHandler(String message);
public event EventHandler HardwareEvent;
[DllImport("VendorSDK.dll")]
private static extern Int32 Register_Callback(Callback shuttleproc, UInt16 type, UInt16 devno);
[DllImport("VendorSDK.dll")]
private static extern Int32 Unregister_Callback(UInt16 type, UInt16 devno);
public Basic() {
mInstance = new Callback(CallbackHandler);
if (Register_Callback(mInstance, 1, 1) != 0)
throw new Exception("Error registereing");
}
~Basic() {
Unregister_Callback(1, 1);
}
public void CallbackHandler(UInt32 Event, Byte status, UInt16 type, UInt16 devno) {
if (HardwareEvent != null)
HardwareEvent(String.Format("Message: {0}, {1}, {2}, {3}", Event, status, type, devno));
}
}
Затем в приложении WPF я использую эту обертку следующим образом:
public partial class MainWindow : Window {
Basic hardware;
public MainWindow() {
InitializeComponent();
}
protected override void OnSourceInitialized(EventArgs e) {
base.OnSourceInitialized(e);
hardware = new Basic();
hardware.HardwareEvent += new Basic.EventHandler(HardwareEvent);
}
void HardwareEvent(string message) {
Messages.Dispatcher.Invoke(new Action(() => { Messages.Items.Insert(0, message); }));
}
}
SDK производителя предоставил неуправляемый пример на C ++, который имеет ту же проблему, что и управляемая оболочка.Приложение отлично работает вне Visual Studio, но запущенные изнутри Visual Studio сообщения не принимаются.
Я полагаю, что это вызвано тем, что Visual Studio либо мешает обратному вызову, либо, скорее всего, когда неуправляемыйпоставщик DLL обращается к текущему дескриптору окна (HWND), возвращается неправильное значение.Однако я не уверен в этом.