Qt设计师的功能虽然强大,但也不是万能的。纵使在其中可以完成有关用户界面设计的绝大部分任务,但仍有少量工作需要靠手工编写C++代码来完成。这种UI设计模式即所谓混合方式UI设计。
通过QtCreator,在C:\Users\Minwei\Projects\Qt路径下,创建名为Editor的项目。
C:\Users\Minwei\Projects\Qt\Editor\Editor.qrc:
xxxxxxxxxx161<RCC>2 <qresource prefix="/">3 <file>images/bld.bmp</file>4 <file>images/clear.bmp</file>5 <file>images/copy.bmp</file>6 <file>images/cut.bmp</file>7 <file>images/exit.bmp</file>8 <file>images/itl.bmp</file>9 <file>images/new.bmp</file>10 <file>images/open.bmp</file>11 <file>images/paste.bmp</file>12 <file>images/under.bmp</file>13 <file>images/AppIcon.ico</file>14 </qresource>15</RCC>16
在Qt设计师中完成界面设计一般遵循如下步骤:
设计动作
设计菜单栏
设计工具栏
设计中心组件
添加预定义信号——槽连接










C:\Users\Minwei\Projects\Qt\Editor\editorwindow.ui:
xxxxxxxxxx3701 2<ui version="4.0">3 <class>EditorWindow</class>4 <widget class="QMainWindow" name="EditorWindow">5 <property name="geometry">6 <rect>7 <x>0</x>8 <y>0</y>9 <width>800</width>10 <height>600</height>11 </rect>12 </property>13 <property name="windowTitle">14 <string>编辑器</string>15 </property>16 <property name="windowIcon">17 <iconset resource="Editor.qrc">18 <normaloff>:/images/AppIcon.ico</normaloff>:/images/AppIcon.ico</iconset>19 </property>20 <widget class="QWidget" name="m_central">21 <layout class="QHBoxLayout" name="m_layout">22 <property name="leftMargin">23 <number>0</number>24 </property>25 <property name="topMargin">26 <number>0</number>27 </property>28 <property name="rightMargin">29 <number>0</number>30 </property>31 <property name="bottomMargin">32 <number>0</number>33 </property>34 <item>35 <widget class="QTextEdit" name="m_edit">36 <property name="font">37 <font>38 <family>微软雅黑</family>39 <pointsize>18</pointsize>40 </font>41 </property>42 <property name="frameShape">43 <enum>QFrame::WinPanel</enum>44 </property>45 <property name="frameShadow">46 <enum>QFrame::Sunken</enum>47 </property>48 </widget>49 </item>50 </layout>51 </widget>52 <widget class="QMenuBar" name="m_menuBar">53 <property name="geometry">54 <rect>55 <x>0</x>56 <y>0</y>57 <width>800</width>58 <height>23</height>59 </rect>60 </property>61 <widget class="QMenu" name="m_menuFile">62 <property name="title">63 <string>文件</string>64 </property>65 <addaction name="m_actNew"/>66 <addaction name="m_actOpen"/>67 <addaction name="separator"/>68 <addaction name="m_actExit"/>69 </widget>70 <widget class="QMenu" name="m_menuEdit">71 <property name="title">72 <string>编辑</string>73 </property>74 <addaction name="m_actCut"/>75 <addaction name="m_actCopy"/>76 <addaction name="m_actPaste"/>77 <addaction name="separator"/>78 <addaction name="m_actClear"/>79 </widget>80 <widget class="QMenu" name="m_menuView">81 <property name="title">82 <string>查看</string>83 </property>84 <addaction name="m_actToolbar"/>85 <addaction name="m_actStatusBar"/>86 </widget>87 <widget class="QMenu" name="m_menuFormat">88 <property name="title">89 <string>格式</string>90 </property>91 <addaction name="m_actBold"/>92 <addaction name="m_actItalic"/>93 <addaction name="m_actUnderline"/>94 </widget>95 <widget class="QMenu" name="m_menuHelp">96 <property name="title">97 <string>帮助</string>98 </property>99 <addaction name="m_actAbout"/>100 </widget>101 <addaction name="m_menuFile"/>102 <addaction name="m_menuEdit"/>103 <addaction name="m_menuFormat"/>104 <addaction name="m_menuView"/>105 <addaction name="m_menuHelp"/>106 </widget>107 <widget class="QStatusBar" name="m_statusBar"/>108 <widget class="QToolBar" name="m_toolBar">109 <property name="windowTitle">110 <string>工具栏</string>111 </property>112 <attribute name="toolBarArea">113 <enum>TopToolBarArea</enum>114 </attribute>115 <attribute name="toolBarBreak">116 <bool>false</bool>117 </attribute>118 <addaction name="m_actNew"/>119 <addaction name="m_actOpen"/>120 <addaction name="m_actExit"/>121 <addaction name="separator"/>122 <addaction name="m_actCut"/>123 <addaction name="m_actCopy"/>124 <addaction name="m_actPaste"/>125 <addaction name="m_actClear"/>126 <addaction name="separator"/>127 <addaction name="m_actBold"/>128 <addaction name="m_actItalic"/>129 <addaction name="m_actUnderline"/>130 </widget>131 <action name="m_actNew">132 <property name="icon">133 <iconset resource="Editor.qrc">134 <normaloff>:/images/new.bmp</normaloff>:/images/new.bmp</iconset>135 </property>136 <property name="text">137 <string>新建</string>138 </property>139 <property name="shortcut">140 <string>Ctrl+N</string>141 </property>142 </action>143 <action name="m_actOpen">144 <property name="icon">145 <iconset resource="Editor.qrc">146 <normaloff>:/images/open.bmp</normaloff>:/images/open.bmp</iconset>147 </property>148 <property name="text">149 <string>打开...</string>150 </property>151 <property name="iconText">152 <string>打开</string>153 </property>154 <property name="shortcut">155 <string>Ctrl+O</string>156 </property>157 </action>158 <action name="m_actExit">159 <property name="icon">160 <iconset resource="Editor.qrc">161 <normaloff>:/images/exit.bmp</normaloff>:/images/exit.bmp</iconset>162 </property>163 <property name="text">164 <string>退出</string>165 </property>166 </action>167 <action name="m_actCut">168 <property name="enabled">169 <bool>false</bool>170 </property>171 <property name="icon">172 <iconset resource="Editor.qrc">173 <normaloff>:/images/cut.bmp</normaloff>:/images/cut.bmp</iconset>174 </property>175 <property name="text">176 <string>剪切</string>177 </property>178 <property name="shortcut">179 <string>Ctrl+X</string>180 </property>181 </action>182 <action name="m_actCopy">183 <property name="enabled">184 <bool>false</bool>185 </property>186 <property name="icon">187 <iconset resource="Editor.qrc">188 <normaloff>:/images/copy.bmp</normaloff>:/images/copy.bmp</iconset>189 </property>190 <property name="text">191 <string>复制</string>192 </property>193 <property name="shortcut">194 <string>Ctrl+C</string>195 </property>196 </action>197 <action name="m_actPaste">198 <property name="icon">199 <iconset resource="Editor.qrc">200 <normaloff>:/images/paste.bmp</normaloff>:/images/paste.bmp</iconset>201 </property>202 <property name="text">203 <string>粘贴</string>204 </property>205 <property name="shortcut">206 <string>Ctrl+V</string>207 </property>208 </action>209 <action name="m_actClear">210 <property name="enabled">211 <bool>false</bool>212 </property>213 <property name="icon">214 <iconset resource="Editor.qrc">215 <normaloff>:/images/clear.bmp</normaloff>:/images/clear.bmp</iconset>216 </property>217 <property name="text">218 <string>清空</string>219 </property>220 </action>221 <action name="m_actBold">222 <property name="checkable">223 <bool>true</bool>224 </property>225 <property name="icon">226 <iconset resource="Editor.qrc">227 <normaloff>:/images/bld.bmp</normaloff>:/images/bld.bmp</iconset>228 </property>229 <property name="text">230 <string>粗体</string>231 </property>232 </action>233 <action name="m_actItalic">234 <property name="checkable">235 <bool>true</bool>236 </property>237 <property name="icon">238 <iconset resource="Editor.qrc">239 <normaloff>:/images/itl.bmp</normaloff>:/images/itl.bmp</iconset>240 </property>241 <property name="text">242 <string>斜体</string>243 </property>244 </action>245 <action name="m_actUnderline">246 <property name="checkable">247 <bool>true</bool>248 </property>249 <property name="icon">250 <iconset resource="Editor.qrc">251 <normaloff>:/images/under.bmp</normaloff>:/images/under.bmp</iconset>252 </property>253 <property name="text">254 <string>下划线</string>255 </property>256 </action>257 <action name="m_actToolbar">258 <property name="checkable">259 <bool>true</bool>260 </property>261 <property name="checked">262 <bool>true</bool>263 </property>264 <property name="text">265 <string>工具栏</string>266 </property>267 </action>268 <action name="m_actStatusBar">269 <property name="checkable">270 <bool>true</bool>271 </property>272 <property name="checked">273 <bool>true</bool>274 </property>275 <property name="text">276 <string>状态栏</string>277 </property>278 </action>279 <action name="m_actAbout">280 <property name="text">281 <string>关于...</string>282 </property>283 </action>284 </widget>285 <resources>286 <include location="Editor.qrc"/>287 </resources>288 <connections>289 <connection>290 <sender>m_actExit</sender>291 <signal>triggered()</signal>292 <receiver>EditorWindow</receiver>293 <slot>close()</slot>294 <hints>295 <hint type="sourcelabel">296 <x>-1</x>297 <y>-1</y>298 </hint>299 <hint type="destinationlabel">300 <x>399</x>301 <y>299</y>302 </hint>303 </hints>304 </connection>305 <connection>306 <sender>m_actCut</sender>307 <signal>triggered()</signal>308 <receiver>m_edit</receiver>309 <slot>cut()</slot>310 <hints>311 <hint type="sourcelabel">312 <x>-1</x>313 <y>-1</y>314 </hint>315 <hint type="destinationlabel">316 <x>399</x>317 <y>317</y>318 </hint>319 </hints>320 </connection>321 <connection>322 <sender>m_actCopy</sender>323 <signal>triggered()</signal>324 <receiver>m_edit</receiver>325 <slot>copy()</slot>326 <hints>327 <hint type="sourcelabel">328 <x>-1</x>329 <y>-1</y>330 </hint>331 <hint type="destinationlabel">332 <x>399</x>333 <y>317</y>334 </hint>335 </hints>336 </connection>337 <connection>338 <sender>m_actPaste</sender>339 <signal>triggered()</signal>340 <receiver>m_edit</receiver>341 <slot>paste()</slot>342 <hints>343 <hint type="sourcelabel">344 <x>-1</x>345 <y>-1</y>346 </hint>347 <hint type="destinationlabel">348 <x>399</x>349 <y>317</y>350 </hint>351 </hints>352 </connection>353 <connection>354 <sender>m_actClear</sender>355 <signal>triggered()</signal>356 <receiver>m_edit</receiver>357 <slot>clear()</slot>358 <hints>359 <hint type="sourcelabel">360 <x>-1</x>361 <y>-1</y>362 </hint>363 <hint type="destinationlabel">364 <x>399</x>365 <y>317</y>366 </hint>367 </hints>368 </connection>369 </connections>370</ui>C:\Users\Minwei\Projects\Qt\Editor\editorwindow.h:
xxxxxxxxxx161...2345...6class EditorWindow : public QMainWindow7{8 ...9private:10 ...11 QFontComboBox* m_combFontName;12 QSpinBox* m_spinFontSize;13 QLabel* m_labCurFile;14 ...15};16...C:\Users\Minwei\Projects\Qt\Editor\editorwindow.cpp:
xxxxxxxxxx241...2EditorWindow::EditorWindow(QWidget *parent)3 : QMainWindow(parent)4 , ui(new Ui::EditorWindow)5{6 ...7 ui->m_toolBar->addSeparator();8
9 ui->m_toolBar->addWidget(new QLabel(" 字体名称:"));10 m_combFontName = new QFontComboBox;11 m_combFontName->setMinimumWidth(80);12 ui->m_toolBar->addWidget(m_combFontName);13
14 ui->m_toolBar->addWidget(new QLabel(" 字体大小:"));15 m_spinFontSize = new QSpinBox;16 m_spinFontSize->setMinimumWidth(60);17 m_spinFontSize->setRange(8, 72);18 ui->m_toolBar->addWidget(m_spinFontSize);19
20 m_labCurFile = new QLabel("当前文件");21 m_labCurFile->setMinimumWidth(400);22 ui->m_statusBar->addWidget(m_labCurFile);23 ...24}通过自定义槽函数,响应用户触发的各种UI事件,实现业务逻辑。
C:\Users\Minwei\Projects\Qt\Editor\editorwindow.h:
xxxxxxxxxx261...2class EditorWindow : public QMainWindow3{4 ...5private slots:6 void on_m_actNew_triggered();7 void on_m_actOpen_triggered();8
9 void on_m_actBold_triggered(bool checked);10 void on_m_actItalic_triggered(bool checked);11 void on_m_actUnderline_triggered(bool checked);12
13 void on_m_actToolbar_triggered(bool checked);14 void on_m_actStatusBar_triggered(bool checked);15
16 void on_m_actAbout_triggered();17
18 void on_m_combFontName_currentIndexChanged(const QString& fontName);19 void on_m_spinFontSize_valueChanged(int fontSize);20
21 void on_m_edit_copyAvailable(bool b);22 void on_m_edit_textChanged();23 void on_m_edit_selectionChanged();24 ...25};26...C:\Users\Minwei\Projects\Qt\Editor\editorwindow.cpp:
xxxxxxxxxx10212...3EditorWindow::EditorWindow(QWidget *parent)4 : QMainWindow(parent)5 , ui(new Ui::EditorWindow)6{7 ...8 on_m_edit_selectionChanged();9
10 connect(m_combFontName, SIGNAL(currentIndexChanged(QString)),11 this, SLOT(on_m_combFontName_currentIndexChanged(QString)));12 connect(m_spinFontSize, SIGNAL(valueChanged(int)),13 this, SLOT(on_m_spinFontSize_valueChanged(int)));14 ...15}16...17void EditorWindow::on_m_actNew_triggered()18{19 QMessageBox::information(this, windowTitle(), "处理“新建”菜单项");20}21
22void EditorWindow::on_m_actOpen_triggered()23{24 QMessageBox::information(this, windowTitle(), "处理“打开...”菜单项");25}26
27void EditorWindow::on_m_actBold_triggered(bool checked)28{29 QTextCharFormat fmt;30 fmt.setFontWeight(checked ? QFont::Bold : QFont::Normal);31 ui->m_edit->mergeCurrentCharFormat(fmt);32}33
34void EditorWindow::on_m_actItalic_triggered(bool checked)35{36 QTextCharFormat fmt;37 fmt.setFontItalic(checked);38 ui->m_edit->mergeCurrentCharFormat(fmt);39}40
41void EditorWindow::on_m_actUnderline_triggered(bool checked)42{43 QTextCharFormat fmt;44 fmt.setFontUnderline(checked);45 ui->m_edit->mergeCurrentCharFormat(fmt);46}47
48void EditorWindow::on_m_actToolbar_triggered(bool checked)49{50 ui->m_toolBar->setHidden(!checked);51}52
53void EditorWindow::on_m_actStatusBar_triggered(bool checked)54{55 ui->m_statusBar->setHidden(!checked);56}57
58void EditorWindow::on_m_actAbout_triggered()59{60 QMessageBox::about(this, windowTitle(), "混合方式UI设计\n版本:1.0");61}62
63void EditorWindow::on_m_combFontName_currentIndexChanged(64 const QString& fontName)65{66 QTextCharFormat fmt;67 fmt = ui->m_edit->currentCharFormat();68 fmt.setFontFamily(fontName);69 ui->m_edit->mergeCurrentCharFormat(fmt);70}71
72void EditorWindow::on_m_spinFontSize_valueChanged(int fontSize)73{74 QTextCharFormat fmt;75 fmt = ui->m_edit->currentCharFormat();76 fmt.setFontPointSize(fontSize);77 ui->m_edit->mergeCurrentCharFormat(fmt);78}79
80void EditorWindow::on_m_edit_copyAvailable(bool b)81{82 ui->m_actCut->setEnabled(b);83 ui->m_actCopy->setEnabled(b);84}85
86void EditorWindow::on_m_edit_textChanged()87{88 ui->m_actClear->setEnabled(ui->m_edit->toPlainText().size());89}90
91void EditorWindow::on_m_edit_selectionChanged()92{93 QFont font = ui->m_edit->currentFont();94
95 ui->m_actBold->setChecked(font.bold());96 ui->m_actItalic->setChecked(font.italic());97 ui->m_actUnderline->setChecked(font.underline());98
99 m_combFontName->setCurrentFont(font);100 m_spinFontSize->setValue(font.pointSize());101}102...运行效果如图所示:
