2016-03-02 92 views
2

我真的被困在一個我想解決的問題上。問題是我有一個用於QMainWindow的類,它爲這個表單保存了Ui變量。現在我想能夠使用該類中的Ui變量在QDialog cpp文件中編輯該窗體。我可能聽起來很蠢,我真的不知道該如何解釋這一點,但我有代碼可能可以幫助。初始化Ui指針從QMainWindow類到QDialog類

MainWindow.h:

#include "ui_mainwindow.h" 
namespace Ui { 
class MainWindow; 
} 
class MainWindow : public QMainWindow 
{ 
Q_OBJECT 

public: 
explicit MainWindow(QWidget *parent = 0); 


~MainWindow(); 
protected: 
    Ui::MainWindow *ui; 
} 

MainWindow.cpp:

#include "mainwindow.h" 
#include "ui_mainwindow.h" 
#include "dialog.h" 
Dialog *dialog; 

MainWindow::MainWindow(QWidget *parent) : 
QMainWindow(parent), 
ui(new Ui::MainWindow) 
{ 
ui->setupUi(this); 
} 

MainWindow::~MainWindow() 
{ 
delete ui; 
} 
void MainWindow::on_pushButton_clicked() 
{ 
dialog = new Dialog(this); 
dialog->show(); 
} 

QDialog.cpp:

#include "ui_mainwindow.h" 
#include "mainwindow.h" 
#include "dialog.h" 
#include "ui_dialog.h" 

Dialog::Dialog(QWidget *parent) : 
QDialog(parent), 
ui(new Ui::Dialog) 
{ 
ui->setupUi(this); 
} 

Dialog::~Dialog() 
{ 
delete ui; 
} 

Ui::MainWindow *mainui; 
void Dialog::on_pushbutton_clicked(){ 
mainui->label->setText("test"); 
} 

所以你可以從上面的代碼中看到,這表明我有一個指向Ui變量的指針,但它的未初始化,因此它會導致一個SIGSEGV錯誤,所以如何執行初始化這個p ointer?這裏的任何幫助都非常感謝,儘管這可能很簡單,但我不知道該怎麼做。 (我已經看過其他問題,但是我不太明白要做什麼,所以請在將我鏈接到類似問題之前解釋我要做的事情。另外,我忽略了Dialog.h文件,因爲我沒有認爲這是需要的,請告訴我是否需要展示它,謝謝!)。

+0

歡迎來到SO。在這裏,爲了標記一個答案,你只需要在正確答案上使用小綠色標記(就像你所做的那樣)。沒有必要編輯問題和/或標題。 –

+0

哦,好吧,不知道(你已經知道我是新的SO:p)謝謝。 –

回答

1

通常在C++中,您應該練習所謂的封裝 - 將類中的數據隱藏於不需要知道的類中。有多個指向UI對象的指針是不好的,因爲現在所有其他對象都必須知道主窗口UI是如何實現的。

在這種情況下,我建議使用Qt的信號和插槽機制來讓對話框告訴主窗口你需要做什麼。這樣做的好處是,如果添加更多對話框或更改主窗口中的實現方式,則不需要更改信號插槽機制,並且細節隱藏得很乾淨。

所以 - 你的對話框中,在頭文件

class Dialog : QDialog 
{ 
    Q_OBJECT 
    signals: 
     void setTextSignal(QString text); 
} 

並在主窗口標題添加一個信號是這樣,添加一個插槽。

class MainWindow : public QMainWindow 
{ 
    Q_OBJECT 
public slots: 
    void setTextSlot(const QString &text); 
} 
在你的方法現在

其中按下按鈕,

void Dialog::on_pushbutton_clicked() 
{ 
    emit setTextSignal("test"); 
} 

,並在主窗口

void MainWindow::setTextSlot(const QString &text) 
{ 
    mainUi->label->setText(text); 
} 

的最後一部分是信號和插槽連接在一起,你將在您創建對話框的主窗口功能中執行:

void MainWindow::on_pushButton_clicked() 
{ 
    dialog = new Dialog(this); 
    connect(dialog, SIGNAL(setTextSignal(QString)), this, SLOT(setTextSlot(QString))); 
    dialog->show(); 
} 

你可以看到有很多優點,對話框不再需要一個指向主窗口UI的指針,並且它使你的代碼更加靈活(你也可以將其他對象連接到信號和插槽)。

+0

完美,這正是我想要的,非常感謝你! –

0

Short answere - your can not!如果你想創建UI的新實例,你就必須做:

MainWindow::Ui *ui = new MainWindow::UI(); 
ui->setupUi(this); 

然而,終場this爲一個QMainWindow基於類的創建必須繼承QMainWindow一個UI - 因此,你可以不。

一般而言,如果您基於QWidget而不是QMainWindow創建您的Ui,因爲它們都會繼承QWidget

Alternativly,你可以嘗試以下方法:

QMainWindow *subWindow = new QMainWindow(this); 
subWindow->setWindowFlags(Qt::Widget); 
MainWindow::Ui *ui = new MainWindow::UI(); 
ui->setupUi(subWindow); 
//... add the mainwindow as a widget to some layout 

但我猜結果會顯得奇怪,甚至有可能不會在第一個工作的地方。

+0

感謝您的回覆,但有人提出了信號和插槽的想法,這正是我需要的。 –

+0

啊,似乎我誤解了你的問題;)我以爲你想創建第二個 – Felix