2020年11月17日 星期二

在特製 Widget 的使用右鍵選單

 在特製 Widget 的使用右鍵選單

前言

  在先前的 在 TreeView 使用右鍵選單 使用過右鍵選單,但 TreeView 是由外部控制,而特製 Widget 時是採用"繼承"的方法來控制,這次把學習的過程做個紀錄。


內容

  先到 [ GitLab ] HelloQt 下載範例,這次應用的專案路徑
(HelloQt' directory)/Widget/CustomMenu,執行結果如下

範例的執行結果

在特製的 Widget 上按下右鍵會跳出右鍵選單。


  看到程式碼的部分,看到特製 Widget 的宣告,程式碼如下

#include <QWidget>

#include <QPainter>
#include <QMenu>
#include <QAction>
class MyWidget : public QWidget
{
  Q_OBJECT
public:
  explicit MyWidget(QWidget *parent = nullptr);

protected:
  void paintEvent(QPaintEvent *event) override;
  void onTreeViewCustomMenu(const QPoint &pos);
  void onTreeViewAction1Trigger();
  void onTreeViewAction2Trigger();
  void onTreeViewAction3Trigger();
signals:
  //
private:
  QMenu* m_pTreeViewCustomMenu;
};


右鍵選單在宣告的部分和之前的 TreeView 用馬差不多,只是這次是把事件直接宣告在 Widget ,而非 MainWindow 。接著看到實現的部分,程式碼如下

#include "mywidget.h"

MyWidget::MyWidget(QWidget *parent) : QWidget(parent)
{
  this->setContextMenuPolicy(Qt::CustomContextMenu);
  connect( this , &QWidget::customContextMenuRequested , this , &MyWidget::onTreeViewCustomMenu );
  //Set up custom menu
  m_pTreeViewCustomMenu = new QMenu( this );
  QAction* pAct1 = new QAction( "Action 1" , this );
  connect( pAct1 , &QAction::triggered , this , &MyWidget::onTreeViewAction1Trigger );
  m_pTreeViewCustomMenu->addAction( pAct1 );
  QAction* pAct2 = new QAction( "Action 2" , this );
  connect( pAct2 , &QAction::triggered , this , &MyWidget::onTreeViewAction2Trigger );
  m_pTreeViewCustomMenu->addAction( pAct2 );
  QAction* pAct3 = new QAction( "Action 3" , this );
  connect( pAct3 , &QAction::triggered , this , &MyWidget::onTreeViewAction3Trigger );
  m_pTreeViewCustomMenu->addAction( pAct3 );
}

void MyWidget::paintEvent(QPaintEvent *event)
{
  QPainter painter( this );
  QPen pen( Qt::black );
  pen.setWidth( 4 );
  painter.setPen( pen );
  QRect rc( 4 , 4 , this->width() - 8, this->height() - 8 );
  painter.drawRect( rc );

}

void MyWidget::onTreeViewCustomMenu(const QPoint &pos)
{
  //
  m_pTreeViewCustomMenu->popup( this->mapToGlobal( pos ) );
}

void MyWidget::onTreeViewAction1Trigger()
{
  qDebug( "Action1 triggered" );
}
void MyWidget::onTreeViewAction2Trigger()
{
  qDebug( "Action2 triggered" );
}
void MyWidget::onTreeViewAction3Trigger()
{
  qDebug( "Action3 triggered" );
}


看到 MyWidget::MyWidget() ,開頭需要執行 setContextMenuPolicy() ,這很重要,接著綁定 customContextMenuRequested() 事件,最後是 Menu 的初始化的部分,這部分和之前的 TiewView 範例一樣。觸發事件的部分就和之前 TiewView 的範例一樣,就只是剪貼過來。 右鍵選單的用法不管是外部控制或繼承幾乎是走同一個流程,本來還擔心繼承的用法會有所不同,看來是我多慮了。


參考資料

[ doc.qt.io ] QWidget Class


相關文章與資料

[ GitLab ] HelloQt

在 TreeView 使用右鍵選單

沒有留言:

張貼留言