📄 qwizard.cpp
字号:
QWizard inherits QDialog and represents a wizard. Each page is a QWizardPage (a QWidget subclass). To create your own wizards, you can use these classes directly, or you can subclass them for more control. Topics: \tableofcontents \section1 A Trivial Example The following example illustrates how to create wizard pages and add them to a wizard. For more advanced examples, see \l{dialogs/classwizard}{Class Wizard} and \l{dialogs/licensewizard}{License Wizard}. \quotefromfile dialogs/trivialwizard/trivialwizard.cpp \skipto createIntroPage() \printuntil createRegistrationPage() \printline { \dots \skipto /^\}/ \printline } \printuntil createConclusionPage() \printline { \dots \skipto /^\}/ \printline /^\}/ \printline main( \printuntil /^\}/ \section1 Wizard Look and Feel QWizard supports four wizard looks: \list \o ClassicStyle \o ModernStyle \o MacStyle \o AeroStyle \endlist You can explicitly set the look to use using setWizardStyle() (e.g., if you want the same look on all platforms). \table \header \o ClassicStyle \o ModernStyle \o MacStyle \o AeroStyle \row \o \inlineimage qtwizard-classic1.png \o \inlineimage qtwizard-modern1.png \o \inlineimage qtwizard-mac1.png \o \inlineimage qtwizard-aero1.png \row \o \inlineimage qtwizard-classic2.png \o \inlineimage qtwizard-modern2.png \o \inlineimage qtwizard-mac2.png \o \inlineimage qtwizard-aero2.png \endtable Note: AeroStyle has effect only on a Windows Vista system with alpha compositing enabled. ModernStyle is used as a fallback when this condition is not met. In addition to the wizard style, there are several options that control the look and feel of the wizard. These can be set using setOption() or setOptions(). For example, HaveHelpButton makes QWizard show a \gui Help button along with the other wizard buttons. You can even change the order of the wizard buttons to any arbitrary order using setButtonLayout(), and you can add up to three custom buttons (e.g., a \gui Print button) to the button row. This is achieved by calling setButton() or setButtonText() with CustomButton1, CustomButton2, or CustomButton3 to set up the button, and by enabling the HaveCustomButton1, HaveCustomButton2, or HaveCustomButton3 options. Whenever the user clicks a custom button, customButtonClicked() is emitted. For example: \quotefromfile dialogs/licensewizard/licensewizard.cpp \skipto setButtonText \printuntil printButtonClicked \section1 Elements of a Wizard Page Wizards consist of a sequence of \l{QWizardPage}s. At any time, only one page is shown. A page has the following attributes: \list \o A \l{QWizardPage::}{title}. \o A \l{QWizardPage::}{subTitle}. \o A set of pixmaps, which may or may not be honored, depending on the wizard's style: \list \o WatermarkPixmap (used by ClassicStyle and ModernStyle) \o BannerPixmap (used by ModernStyle) \o LogoPixmap (used by ClassicStyle and ModernStyle) \o BackgroundPixmap (used by MacStyle) \endlist \endlist The diagram belows showns how QWizard renders these attributes, assuming they are all present and ModernStyle is used: \image qtwizard-nonmacpage.png When a \l{QWizardPage::}{subTitle} is set, QWizard displays it in a header, in which case it also uses the BannerPixmap and the LogoPixmap to decorate the header. The WatermarkPixmap is displayed on the left side, below the header. At the bottom, there is a row of buttons allowing the user to navigate through the pages. The page itself (the \l{QWizardPage} widget) occupies the area between the header, the watermark, and the button row. Typically, the page is a QWizardPage on which a QGridLayout is installed, with standard child widgets (\l{QLabel}s, \l{QLineEdit}s, etc.). If the wizard's style is MacStyle, the page looks radically different: \image qtwizard-macpage.png The watermark, banner, and logo pixmaps are ignored by the MacStyle. If the BackgroundPixmap is set, it is used as the background for the wizard; otherwise, a default "assistant" image is used. The title and subtitle are set by calling QWizardPage::setTitle() and QWizardPage::setSubTitle() on the individual pages. They may be plain text or HTML (see titleFormat and subTitleFormat). The pixmaps can be set globally for the entire wizard using setPixmap(), or on a per-page basis using QWizardPage::setPixmap(). \target field mechanism \section1 Registering and Using Fields In many wizards, the contents of a page may affect the default values of the fields of a later page. To make it easy to communicate between pages, QWizard supports a "field" mechanism that allows you to register a field (e.g., a QLineEdit) on a page and to access its value from any page. It is also possible to specify mandatory fields (i.e., fields that must be filled before the user can advance to the next page). To register a field, call QWizardPage::registerField() field. For example: \quotefromfile dialogs/classwizard/classwizard.cpp \skipto ::ClassInfoPage \printuntil { \dots \skipto classNameLabel \printto groupBox = \skipto className \printuntil qobjectMacro \dots \skipto /^\}/ \printline } The above code registers three fields, \c className, \c baseClass, and \c qobjectMacro, which are associated with three child widgets. The asterisk (\c *) next to \c className denotes a mandatory field. \target initialize page The fields of any page are accessible from any other page. For example: \skipto OutputFilesPage::initializePage \printuntil /^\}/ Here, we call QWizardPage::field() to access the contents of the \c className field (which was defined in the \c ClassInfoPage) and use it to initialize the \c OuputFilePage. The field's contents is returned as a QVariant. When we create a field using QWizardPage::registerField(), we pass a unique field name and a widget. We can also provide a Qt property name and a "changed" signal (a signal that is emitted when the property changes) as third and fourth arguments; however, this is not necessary for the most common Qt widgets, such as QLineEdit, QCheckBox, and QComboBox, because QWizard knows which properties to look for. \target mandatory fields If an asterisk (\c *) is appended to the name when the property is registered, the field is a \e{mandatory field}. When a page has mandatory fields, the \gui Next and/or \gui Finish buttons are enabled only when all mandatory fields are filled. To consider a field "filled", QWizard simply checks that the field's current value doesn't equal the original value (the value it had when initializePage() was called). For QLineEdit, QWizard also checks that \l{QLineEdit::hasAcceptableInput()}{hasAcceptableInput()} returns true, to honor any validator or mask. QWizard's mandatory field mechanism is provided for convenience. A more powerful (but also more cumbersome) alternative is to reimplement QWizardPage::isComplete() and to emit the QWizardPage::completeChanged() signal whenever the page becomes complete or incomplete. The enabled/disabled state of the \gui Next and/or \gui Finish buttons is one way to perform validation on the user input. Another way is to reimplement validateCurrentPage() (or QWizardPage::validatePage()) to perform some last-minute validation (and show an error message if the user has entered incomplete or invalid information). If the function returns true, the next page is shown (or the wizard finishes); otherwise, the current page stays up. \section1 Creating Linear Wizards Most wizards have a linear structure, with page 1 followed by page 2 and so on until the last page. The \l{dialogs/classwizard}{Class Wizard} example is such a wizard. With QWizard, linear wizards are created by instantiating the \l{QWizardPage}s and inserting them using addPage(). By default, the pages are shown in the order in which they were added. For example: \quotefromfile dialogs/classwizard/classwizard.cpp \skipto ::ClassWizard \printuntil addPage(new Conclu \dots \skipto /^\}/ \printline } When a page is about to be shown, QWizard calls initializePage() (which in turn calls QWizardPage::initializePage()) to fill the page with default values. By default, this function does nothing, but it can be reimplemented to initialize the page's contents based on other pages' fields (see the \l{initialize page}{example above}). If the user presses \gui Back, cleanupPage() is called (which in turn calls QWizardPage::cleanupPage()). The default implementation resets the page's fields to their original values (the values they had before initializePage() was called). If you want the \gui Back button to be non-destructive and keep the values entered by the user, simply enable the IndependentPages option. \section1 Creating Non-Linear Wizards Some wizards are more complex in that they allow different traversal paths based on the information provided by the user. The \l{dialogs/licensewizard}{License Wizard} example illustrates this. It provides five wizard pages; depending on which options are selected, the user can reach different pages. \image licensewizard-flow.png In complex wizards, pages are identified by IDs. These IDs are typically defined using an enum. For example: \quotefromfile dialogs/licensewizard/licensewizard.h \skipto : public QWizard \printuntil { \dots \skipto enum { \printuntil }; \dots \skipto /^\};/ \printline } The pages are inserted using setPage(), which takes an ID and an instance of QWizardPage (or of a subclass): \quotefromfile dialogs/licensewizard/licensewizard.cpp \skipto ::LicenseWizard \printuntil setPage(Page_Conclusion \dots \skipto /^\}/ \printline } By default, the pages are shown in increasing ID order. To provide a dynamic order that depends on the options chosen by the user, we must reimplement QWizardPage::nextId(). For example: \skipto IntroPage::nextId \printuntil /^\}/ \skipto EvaluatePage::nextId \printuntil /^\}/ \skipto RegisterPage::nextId \printuntil /^\}/ \skipto DetailsPage::nextId \printuntil /^\}/ \skipto ConclusionPage::nextId \printuntil /^\}/ It would also be possible to put all the logic in one place, in a QWizard::nextId() reimplementation. For example: \code int LicenseWizard::nextId() const { switch (currentId()) { case Page_Intro: if (field("intro.evaluate").toBool()) { return Page_Evaluate; } else { return Page_Register; } case Page_Evaluate: return Page_Conclusion; case Page_Register: if (field("register.upgradeKey").toString().isEmpty()) { return Page_Details; } else { return Page_Conclusion; } case Page_Details: return Page_Conclusion; case Page_Conclusion: default: return -1; } } \endcode To start at another page than the page with the lowest ID, call setStartId(). To test whether a page has been visited or not, call hasVisitedPage(). For example: \skipto ConclusionPage::initializePage \printuntil /^\}/ \sa QWizardPage, {Class Wizard Example}, {License Wizard Example}*//*! \enum QWizard::WizardButton This enum specifies the buttons in a wizard. \value BackButton The \gui Back button (\gui {Go Back} on Mac OS X) \value NextButton The \gui Next button (\gui Continue on Mac OS X) \value CommitButton The \gui Commit button \value FinishButton The \gui Finish button (\gui Done on Mac OS X) \value CancelButton The \gui Cancel button (see also NoCancelButton) \value HelpButton The \gui Help button (see also HaveHelpButton) \value CustomButton1 The first user-defined button (see also HaveCustomButton1) \value CustomButton2 The second user-defined button (see also HaveCustomButton2) \value CustomButton3 The third user-defined button (see also HaveCustomButton3) The following value is only useful when calling setButtonLayout(): \value Stretch A horizontal stretch in the button layout \omitvalue NoButton \omitvalue NStandardButtons \omitvalue NButtons \sa setButton(), setButtonText(), setButtonLayout(), customButtonClicked()*//*! \enum QWizard::WizardPixmap This enum specifies the pixmaps that can be associated with a page. \value WatermarkPixmap The tall pixmap on the left side of a ClassicStyle or ModernStyle page \value LogoPixmap The small pixmap on the right side of a ClassicStyle or ModernStyle page header \value BannerPixmap The pixmap that occupies the background of a ModernStyle pa
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -