簡體   English   中英

C++ 中的 GUI 工具包有問題。 將 lambdas 傳遞給 std::function 的向量

[英]Trouble with a GUI toolkit in C++. Passing lambdas into a vector of std::function

我遇到的問題有點難以描述,但我會盡力使其易於理解。

我正在創建一個類似於 C# 中的 Windows 窗體系統的 C++ GUI 工具包。 整個系統是基於事件的。 我的Event類由std::function的向量組成,它充當訂閱者函數的列表和一些實用程序方法。

template<class T>
class Event
{
public:

  Event() {}
  ~Event() {}

  void Raise(T context)
  {
    for(std::function<void(T&)> subscriber : Subscribers)
    {
      subscriber(context);
    }
  }

  void Subscribe(std::function<void(T&)> subscriber)
  {
    try { Subscribers.push_back(subscriber); } catch (std::exception) { /*...*/ }
  }

private:

  std::vector<std::function<void(T&)>>> Subscribers;

}

我的項目包含一個EventProvider類,它為所有派生類提供一堆事件。

class EventProvider
{
public:

  Event<LoadEventContext> LoadEvent;
  // ...
  // ...

}

也像在 Windows 窗體中一樣,我有一個Window類和一個Control類。 它們都繼承了EventProvider 與 C# 中一樣,定義所有功能的實際 Window 類必須繼承Window類。

class Control : public EventProvider { /*...*/ }

class Window : public EventProvider { /*...*/ }

class MyWindow : public Window { /*...*/ }

在我的MyWindow類中,我通過 lambda 將方法綁定到 Window 的事件。 綁定的方法MyWindow類的事件MyWindow類的工作就好了。 將控件的成員函數綁定到MyWindow的事件也沒有問題。 在 Windows 窗體中,控件的所有事件方法也包含在 Window 類中。 我想在我的項目中做同樣的事情。 所以MyWindow類包含我的控件的實例、它自己的事件方法和我的控件的事件方法。 但是,當我嘗試將控件事件函數綁定到控件事件時,出現運行時錯誤。

// ===  MyWindow.hpp  ===

#ifndef __MY_WINDOW_HPP__
#define __MY_WINDOW_HPP__

#include <Control.hpp>
#include <Window.hpp>

class MyWindow : public Window
{
public:

  MyWindow();
  ~MyWindow();

private:

  Control* button = nullptr;

  void OnLoadEvent(LoadEventContext& context);
  void button_OnLoadEvent(LoadEventContext& context);

}

#endif



// ===  MyWindow.cpp ===

#include <MyWindow.hpp>

MyWindow::MyWindow()
{
  button = new Control();

  LoadEvent.Subscribe([&](LoadEventContext& context) { OnLoadEvent(context); }); // WORKS
  LoadEvent.Subscribe([&](LoadEventContext& context) { button->OnLoadEvent(context); }); // WORKS

  button->OnLoadEvent.Subscribe([&](LoadEventContext& context) { OnLoadEvent(context); }); // Runtime Error
}

MyWindow::~MyWindow() { /*...*/ }

MyWindow::OnLoadEvent(LoadEventContext& context) { /*...*/ }

MyWindow::button_OnLoadEvent(LoadEventContext& context) { /*...*/ }

//

MyWindow調用控件的加載事件以將 lambda 函數添​​加到訂閱者函數的事件向量時,會在 stl 的vector類中引發讀取訪問沖突。

在此處輸入圖片說明

這行代碼調用了添加 lambda 函數的事件:

button->OnLoadEvent.Subscribe([&](LoadEventContext& context) { OnLoadEvent(context); }); // Runtime Error

Event類中的這個導致了錯誤:

try { Subscribers.push_back(subscriber); } catch (std::exception) { /*...*/ }

我在使用函數指針、函子、functionoids 和所有這些東西進行編程方面仍然不是很先進。 盡管如此,我希望我已經足夠清楚地為你指出了我的問題,我希望任何人都可以幫助我解決這個問題。

我懂了。 問題是我在完全創建此控件之前將我的事件方法綁定到我的控件的事件。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM