Вставить главное окно приложения qt / C ++ в приложение wpf / mvvm - PullRequest
0 голосов
/ 13 февраля 2020

Мне нужно встроить приложение qt / c ++ в приложение wpf mvvm. Окно этого qt / C ++ должно быть интегрировано в wpf-страницу, отображаемую на вкладке.

Элемент управления страницы имеет следующий вид:

<page x:Class="Wpf_HostExe.Page1"
    xmlns:="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Page1"
    Loaded="OnLoaded">
    <Grid>
        <Border x:Name="HostUi" Background="White"
            HorizontalAlignment="Stretch"
            VerticalAlignment="Stretch"  />
    </Grid>
</Page>

Я запускаю приложение, которое будет размещено с инструкциями ниже:

public static Process StartProcess()
{
    System.Diagnostics.ProcessStartInfo processStartInfo = new System.Diagnostics.ProcessStartInfo();
    processStartInfo.WorkingDirectory = "C:\\ChildApp\\";
    processStartInfo.fileName = "ChildApp.exe";
    processStartInfo.Arguments = "";

    System.Diagnostics.Process proc = System.Diagnostics.Process.Start(processStartInfo);
    proc.WaitForInputIdle();

    return proc;
}

Внешнее окно перерисовывается следующими инструкциями:

public class ApplicationHost : HwndHost
{
    private const uint LBS_NOTIFY = 0x00000001;
    private const uint WS_BORDER = 0x00800000;
    private const int SWP_NO_ACTIVATE = 0x0010;
    private const int GWL_STYLE = -16;
    private const int WS_CAPTION = 0x00C00000;
    private const int WS_THICKFRAME = 0x00040000;
    private const uint WS_VISIBLE = 0x10000000;


    [DllImport("user32.dll")]
    private static extern int SetWindowLong(IntPtr hWnd, int nIndex, int dwNewLong);

    [DllImport("user32.dll"), SetLastError = true]
    private static extern int GetWindowLong(IntPtr hwnd, int nIndex);

    [DllImport("user32.dll")]
    private static extern IntPtr SetParent(IntPtr hWnd, IntPtr hWndParent);

    [DllImport("user32.dll")]
    private static extern bool SetWindowPos(IntPtr hWnd, IntPtr hWndInsertAfter, int X, int Y, int cx, int cy, int uFlags);

    public IntPtr ApplicationHandle { get; set; }
    ...
    protected override HandleRef BuildWindowCore (HandleRef hwndParent)
    {
        var result = new HandleRef(this, ApplicationHandle);
        if (ApplicationHandle.ToInt32() == 0)
        {
            return result;
        }

        var oldParent = SetParent(ApplicationHandle, hwndParent.Handle);

        var styles = GetWindowLong(ApplicationHandle, GWL_STYLE);
        styles |= WS_CHILD | WS_VISIBLE | WS_BORDER | LBS_NOTIFY;
        styles &= ~WS_CAPTION;
        SetWindowLong32(ApplicationHandle, GWL_STYLE, styles);

        return result;
    }
    ...
}

Я также пробовал следующую версию:

    ...
    protected override HandleRef BuildWindowCore (HandleRef hwndParent)
    {
        SetParent(ApplicationHandle, hwndParent.Handle);

        int style = GetWindowLong(ApplicationHandle, GWL_STYLE);
        style = style & ~WS_CAPTION & ~WS_THICKFRAME;
        SetWindowLong(ApplicationHandle, GWL_STYLE, style);
    }
    ...

Процесс размещения приложения запускается без проблем, но SetParent, похоже, не работает, и я получаю следующее сообщение, в то время как метод BuildWindowCore был передан независимо от способа установки setParent:

"An unhandled exception of type 'System.InvalidOperationException' occured in PresentationFramework.dll"
Additional Information : Hosted HWND must be a child window of the specified parent. "

I перепробовал много вещей, найденных в stackoverflow, но у меня все еще есть то же самое InvalidOperationException, и я понятия не имею, как это исправить.

Не могли бы вы мне помочь?

С уважением,

1 Ответ

0 голосов
/ 14 февраля 2020

Я предполагаю, что у вас есть источник для приложения Qt. В этом коде вы должны создать функцию, которая будет render() виджет на QImage. Вызовите эту функцию из WPF и скопируйте изображение из data() QImage в WriteableBitmap, и покажите это с помощью элемента управления. Вы также можете перенаправлять щелчки мыши и клавиатуры в противоположном направлении, а также иметь функцию, которая затем синтезирует QEvent s для взаимодействия с виджетом.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...