QT學(xué)習(xí)筆記
1.對(duì)象樹(shù):在Qt中,每個(gè) QObject 內(nèi)部都有一個(gè)list,用來(lái)保存所有的 children,還有一個(gè)指針,保存自己的parent。當(dāng)它自己析構(gòu)時(shí),它會(huì)將自己從parent的列表中刪除,并且析構(gòu)掉所有的children。
我們需要顯試刪除(就是用DELETE刪除)的對(duì)象是那些使用NEW創(chuàng)建的并且沒(méi)有父對(duì)象的對(duì)象(切記是new的才要delete,通過(guò)成員函數(shù)獲得的對(duì)象,沒(méi)有特殊說(shuō)明的,千萬(wàn)不要隨便delete.)。如果我們?cè)趧h除一個(gè)對(duì)象的父對(duì)象之前刪除它,QT會(huì)自動(dòng)地從它的父對(duì)象的子對(duì)象列表中移除它的
2.什么是回調(diào)函數(shù)?
回調(diào)函數(shù)就是把函數(shù)的地址作為參數(shù)傳入另一個(gè)函數(shù)
回調(diào)函數(shù)就是一個(gè)通過(guò)函數(shù)指針調(diào)用的函數(shù)。
① 函數(shù)指針的作用:首先,函數(shù)指針可以在不同時(shí)間傳遞不同函數(shù)的地址,即在不同的時(shí)間使用不同的函數(shù),如果不用函數(shù)指針只能順序執(zhí)行函數(shù)。
注:信號(hào)與槽的槽函數(shù)中使用匿名函數(shù)或函數(shù)指針時(shí)時(shí)可以考慮使用蘭姆達(dá)表達(dá)式。
QT資源文件使用格式:
“:+前綴+文件名”
QtMainWindow

MenuBar是菜單欄,toolbars是工具欄,Dock Widgets是小窗口,Central Widget是中央窗口,Status Bar是狀態(tài)欄

QWidget? QMainWindow? QDialog類的區(qū)別:
QWidget類是所有用戶界面對(duì)象的基類。 窗口部件是用戶界面的一個(gè)原子:它從窗口系統(tǒng)接收鼠標(biāo)、鍵盤(pán)和其它事件,并且在屏幕上繪制自己的表現(xiàn)。每一個(gè)窗口部件都是矩形,并且它們按Z軸順序排列的。一個(gè)窗口部件可以被它的父窗口部件或者它前面的窗口部件蓋住一部分。
QMainWindow 類提供一個(gè)有菜單條、錨接窗口(例如工具條)和一個(gè)狀態(tài)條的主應(yīng)用程序窗口。主窗口通常用在提供一個(gè)大的中央窗口部件(例如文本編輯或者繪制畫(huà)布)以及周圍菜單、工具條和一個(gè)狀態(tài)條。QMainWindow常常被繼承,因?yàn)檫@使得封裝中央部件、菜單和工具條以及窗口狀態(tài)變得更容易。繼承使創(chuàng)建當(dāng)用戶點(diǎn)擊菜單項(xiàng)或者工具條按鈕時(shí)被調(diào)用的槽成為可能。你也可以使用Qt設(shè)計(jì)器來(lái)創(chuàng)建主窗口。
QDialog類是對(duì)話框窗口的基類。對(duì)話框窗口是主要用于短期任務(wù)以及和用戶進(jìn)行簡(jiǎn)要通訊的頂級(jí)窗口。QDialog可以是模式的也可以是非模式的。QDialog支持?jǐn)U展性并且可以提供返回值。它們可以有默認(rèn)按鈕。QDialog也可以有一個(gè)QSizeGrip在它的右下角,使用setSizeGripEnabled()。
QDialog 是最普通的頂級(jí)窗口。不被嵌入到一個(gè)父窗口部件的窗口部件被叫做頂級(jí)窗口部件。通常情況下,頂級(jí)窗口部件是有框架和標(biāo)題欄的窗口(盡管如果使用了一定的窗口部件標(biāo)記,創(chuàng)建頂級(jí)窗口部件時(shí)也可能沒(méi)有這些裝飾。)在Qt中,QMainWindow和和不同的QDialog的子類是最普通的頂級(jí)窗口。摘自CSDNQWidget,QMainWindow和QDialog的區(qū)別ikahn的博客-CSDN博客qmainwindow和qdialog
模態(tài)和非模態(tài)對(duì)話框
非模態(tài)對(duì)話框是對(duì)話框后面的其他對(duì)話框或窗口依然可用
模態(tài)對(duì)話框是對(duì)話框后面的其他對(duì)話框或窗口不能操作? 只能先操作當(dāng)前的對(duì)話框
如果從線程角度來(lái)講,模態(tài)對(duì)話框?qū)嶋H上是線程阻塞的,也就是子對(duì)話框是一個(gè)線程,但是在創(chuàng)建這個(gè)子線程之后,父窗口就阻塞了;而非模態(tài)對(duì)話框則不是阻塞型的線程模型,父子線程可以并行運(yùn)行。
過(guò)程:
1 新建一個(gè)dialog
2 利用dialog 成員函數(shù) 指定窗體大小? 顯示窗體(非模態(tài))
3 模態(tài):
方式1 :exec()函數(shù) 阻塞函數(shù) 如果沒(méi)有關(guān)閉窗口 程序會(huì)停在這里不會(huì)向下運(yùn)行
方式2 :dialog成員函數(shù) setModal(true)? 再顯示窗體
需要繼續(xù)加一個(gè)函數(shù)delete相應(yīng)的New(因?yàn)橹挥兄鞔绑w關(guān)閉時(shí)才自動(dòng)釋放? 子窗口創(chuàng)建的對(duì)話框需要手動(dòng)釋放)
dialog->setAttribute(Qt::WA_DeleteOnClose)
8種標(biāo)準(zhǔn)對(duì)話框:
功能 按下按鍵彈出對(duì)應(yīng)的對(duì)話框(顏色對(duì)話框、文件對(duì)話框、字體對(duì)話 框、輸入對(duì)話框)
1 利用信號(hào)與槽的操作,右鍵UI中的按鍵創(chuàng)建出槽函數(shù),填充即可
2 顏色對(duì)話框需要包含頭文件QColorDialog
在槽函數(shù)中實(shí)現(xiàn)顏色對(duì)話框? 用類創(chuàng)建一個(gè)對(duì)象
靜態(tài)函數(shù)方式實(shí)現(xiàn):QColor color = QColorDialog::getColor(Qt::red,this);
qDebug顯示一下color
3 在槽函數(shù)中實(shí)現(xiàn)文件對(duì)話框 文件對(duì)話框需要包括QFileDialog
搜索手冊(cè)發(fā)現(xiàn)他也是有靜態(tài)成員函數(shù),省去了用類創(chuàng)建對(duì)象再調(diào)用函數(shù)的過(guò)程
與上面類似,QString filename = QFileDialog::getOpenFileName(this,"OpenFile(顯示內(nèi)容)",“C:\”,"圖片文件(*.png *.jpg)");
qDebug顯示一下
4 字體對(duì)話框 include<QFontDialog>
與上面一樣,函數(shù)為getFont(bool類型的指針,this); 返回QFont類型的變量
if(ok)
ui->pushButton_3->setFont(返回的變量);
5 輸入對(duì)話框<QInputDialog>
仿照上面的寫(xiě)法 靜態(tài)成員函數(shù)有好幾個(gè) 手冊(cè)上可以看?
例如getText(this,“輸入的title”,"提示",QLineEdit::Normal,"什么都不敲顯示的默認(rèn)字符",bool類型的是否敲入);返回值QString類型變量
測(cè)試輸入整數(shù)getInt(...)
6 消息對(duì)話框<QMessageBox>
question函數(shù)? 問(wèn)題對(duì)話框
information函數(shù): 提示對(duì)話框
warning函數(shù):警告對(duì)話框
critical函數(shù):錯(cuò)誤對(duì)話框
about函數(shù):關(guān)于對(duì)話框
7 進(jìn)度對(duì)話框<QProgressDialog>
定義指針的話,需要開(kāi)辟空間,只有mainWindow關(guān)閉的時(shí)候才會(huì)回收空間
創(chuàng)建對(duì)象的話,函數(shù)結(jié)束對(duì)象就結(jié)束了。對(duì)象的構(gòu)造函數(shù)里要加一些東西
成員函數(shù):setWindowTitle("string") 窗口名設(shè)置
show() 顯示? ? setWindowModality(Qt::WindowModal)變?yōu)槟B(tài)
prodlg.setValue(i)
if(prodlg.wasCanceld())? break;
prodlg.setValue(50000) 輸出結(jié)束
多線程:大文件復(fù)制拷貝時(shí),可以繼續(xù)做其他的事情。增加函數(shù)調(diào)用,QCoreApplicaion::processEvents();
8 錯(cuò)誤信息對(duì)話框<QErrorMessage>
創(chuàng)建對(duì)象 不對(duì)? ? (why?? 因?yàn)閯?chuàng)建對(duì)象的話函數(shù)結(jié)束就釋放了,再點(diǎn)擊一次相當(dāng)于重新創(chuàng)建對(duì)象,無(wú)法保存上次的設(shè)置)
用指針開(kāi)辟空間? 把其放在mainWindow里
9 向?qū)?duì)話框<QWizard>
16 按鈕控件組 button
控件和布局學(xué)習(xí)
Buttons是一個(gè)按鍵組,
push Button 過(guò)。
(1)tool button 工具按鈕,多以圖形或圖標(biāo)方式出現(xiàn),如QQ頭像。

流程:1 添加資源文件 加一張圖片? 把圖片加到tool button按鈕上
2.代碼方式添加:ui->toolButton->setIcon(QIcon(":+前綴+文件名"))?
3.添加文本并更改顯示方式(toolButtonStyle)
4.autoRise
(2) Radio Button,選擇相關(guān)按鈕 幾選一,有點(diǎn)像投票的選項(xiàng)(單選)
運(yùn)行時(shí)有默認(rèn)選項(xiàng)功能(代碼實(shí)現(xiàn))
ui->radioButton(也可以改成別的)->setCheck(true);
流程:一年級(jí) 二年級(jí) 三年級(jí)? 分?jǐn)?shù)分檔次, 選中<60分時(shí)用信號(hào)和槽的功能實(shí)現(xiàn)打印信息 不及格
(3) Group Box
用來(lái)分組
(4) check Box 多選
List Widget? 列表選擇
Item views(model-based)適用于大量數(shù)據(jù)的操作
Item Widgets(item-based)比較簡(jiǎn)單
代碼:
listWidget 添加內(nèi)容,用addItem或addItems函數(shù)
addItem(指針or字符串)
用QListWigetItem指針?lè)绞降臉?gòu)造函數(shù)
(List是一個(gè)容器)
文字對(duì)齊:指針->setTextAlignment()? 助手中查看該函數(shù)的使用方法
用addItems()函數(shù) 一次添加多行
Tree Widget
1 創(chuàng)建列:

代碼實(shí)現(xiàn):ui->treeWigdet->setHeaderLabel()
用到QStringList? 可以試試創(chuàng)建匿名對(duì)象
2 創(chuàng)建樹(shù)
代碼:ui->treeWidget->addTopLevelItem();
用到QTreeWidgetItem 指針
3 添加圖標(biāo)? setIcon
4 添加分支 指針->addChild();
Table widget控件
建立控件 √
設(shè)置行列(setColumnCount/setRowCount) √
設(shè)置頭標(biāo)簽(setHorizontalHeaderLabels) √
填充內(nèi)容(setItem)? 用循環(huán) 先填第一列 再填后邊的列 通過(guò)QString類里的number函數(shù)將int類轉(zhuǎn)換為字符串
Containers控件
Group Box 分組
Scroll Area 滾動(dòng)區(qū)域
Tool Box 類似QQ分組
Tab Widget 類似選項(xiàng)卡
Stacked Widget 棧 可以把其他控件放在里邊? QStackedWidget提供了一個(gè)控件棧,在這個(gè)棧中,一次只能顯示一個(gè)控件。
用按鍵切換的方式換頁(yè)復(fù)習(xí)一下蘭姆達(dá)表達(dá)式的相關(guān)知識(shí) 實(shí)現(xiàn)按鈕信號(hào)與槽的功能? 輸出一些字。再實(shí)現(xiàn)按下按鈕切換到相應(yīng)頁(yè)面的功能 (setCurrentIndex函數(shù))
InputWidgets控件
combo box 下拉列表? 通過(guò)addItem函數(shù)添加選項(xiàng)
Font Combo Box 選擇字體? 信號(hào)與槽實(shí)現(xiàn)字體的選擇
LineEdit? 一行 用于輸入姓名或者密碼之類
Text Edit 和Plain Text Edit的區(qū)別:TE可以編輯字體 設(shè)計(jì)格式 PTE是單純的文字沒(méi)有別的
SpinBox、DoubleSpinBox: 數(shù)字增減

TimeEdit、DateEdit、Date/Time Edit? 設(shè)置時(shí)間、年月日。例如:顯示系統(tǒng)時(shí)間,利用setTime函數(shù)? 需要?jiǎng)?chuàng)建一個(gè)QDateTime類型的對(duì)象,這個(gè)對(duì)象用該類里的函數(shù)currentDateTime()

Dial :旋鈕 改變數(shù)值

H/V scroll Bar? 水平條和縱向條

H/V Silder 調(diào)整值

自定義控件
1 添加Qt設(shè)計(jì)師界面類 widget
2 ui中添加widget容器 右鍵提升為 添加上面創(chuàng)建的類的名稱
3 關(guān)聯(lián)兩個(gè)控件:

4.添加按鍵? 獲取當(dāng)前值
添加函數(shù)? 返回ui->spinBox中的value值 用信號(hào)與槽關(guān)聯(lián)按鈕與自定義的控件
Label控件
功能:1 顯示字符串
2 顯示圖片信息setPixmap 改變圖片大?。簊etScaledContents
3 添加動(dòng)圖 setMovie 顯示動(dòng)圖 對(duì)象->start
事件 --鼠標(biāo)事件
1 捕獲事件是否產(chǎn)生:通過(guò)調(diào)用QApplication里對(duì)象a的函數(shù)a.exec()
2 事件過(guò)濾
3 事件分發(fā)
4 事件處理
先聲明 再定義鼠標(biāo)點(diǎn)擊事件

常用鼠標(biāo)處理事件:
mousePressEvent
mouseReleaseEvent
mouseDoubleClickEvent
例如:雙擊時(shí)設(shè)置為全屏? 用到函數(shù)windowState
全屏:Qt::WindowFullScreen
設(shè)置窗體狀態(tài):setWindowState()

mouseMoveEvent

wheelEvent

定時(shí)器
兩種使用方法:
方法一:
1 包含頭文件QTimer? 然后創(chuàng)建一個(gè)該類型的指針 開(kāi)辟空間?
2 函數(shù)使用start設(shè)置定時(shí)時(shí)間
3 connect設(shè)置聯(lián)系? 用到QTime::timeout,和蘭姆達(dá)表達(dá)式 設(shè)置label里的內(nèi)容 +1

方法二:(事件)
用定時(shí)器的事件,事件到來(lái)時(shí)用定時(shí)器處理函數(shù)
1 調(diào)用函數(shù)startTimer(定時(shí)時(shí)間) 該函數(shù)返回一個(gè)timer的編號(hào) 可以利用返回值用到不同的timer
2 重新編寫(xiě)timerEvent函數(shù)? 同上
3? 在類中設(shè)置不同的timer id? 然后考慮兩種不同時(shí)長(zhǎng)情況下的變化
事件分發(fā)

個(gè)性化處理
串口調(diào)試助手
功能:1.軟件打開(kāi)時(shí)識(shí)別出可用串口? 放在下拉列表中
第一步:在pro文件中加入 QT +=serialport
第二步:添加頭文件
第三步:設(shè)計(jì)UI? 顯示串口號(hào)
第四步:代碼初始化。設(shè)置窗口大小、設(shè)置標(biāo)題
第五步:由于軟件運(yùn)行時(shí)要周期性掃描,因此定義一個(gè)定時(shí)器,創(chuàng)建定時(shí)器指針,定時(shí),再利用信號(hào)和槽實(shí)現(xiàn)。需要定義一個(gè)函數(shù),做為槽函數(shù)。
第六步:槽函數(shù)設(shè)計(jì):foreach關(guān)鍵字? 按順序遍歷容器中的所有成員
foreach(容器里邊的類型,容器名字)
發(fā)現(xiàn)當(dāng)前可用串口信息:QSerialPortInfo::availablePorts()
類型:QSerialPortInfo 容器:上邊的列表
此時(shí)完成了遍歷串口信息,然后通過(guò)portName得到串口名字 該函數(shù)返回Qstring類型
創(chuàng)建一個(gè)QStringList類型的容器,把名字放進(jìn)這個(gè)容器里 初始時(shí)清空
然后把該容器添加到comboBox里
定義一個(gè)QStringList的對(duì)象 賦初值0? 然后判斷一下當(dāng)前串口數(shù)量和上次的是否相等 不相等再執(zhí)行添加的功能

功能2:

點(diǎn)擊打開(kāi)串口 設(shè)置下面的參數(shù) 再點(diǎn)擊關(guān)閉串口
1 轉(zhuǎn)到槽 編寫(xiě)槽函數(shù)
兩種情況 第一種情況是按鍵內(nèi)容=打開(kāi)串口
在頭文件里聲明一個(gè)私有變量? 類型是SerialPort*? 用其創(chuàng)建一個(gè)串口
設(shè)置串口名字 setPortName(comboBox里的當(dāng)前串口名字currentText)
設(shè)置波特率:setBaudRate? 需要先把字符轉(zhuǎn)換為整型再填進(jìn)去? 用到toInt函數(shù)
設(shè)置數(shù)據(jù)位:setDatabits? 用switch case語(yǔ)句根據(jù)不同情況選擇不同枚舉類型
設(shè)置奇偶校驗(yàn):setParity? 此時(shí)用currentIndex+swich case
停止位設(shè)置:setStopBits 仿照之前的寫(xiě)法

打開(kāi)串口:open(讀寫(xiě))如果打開(kāi)失敗 使用QMessageBox消息對(duì)話框(記得包含頭文件)彈出消息,information(this,"錯(cuò)誤提示",“串口打開(kāi)失敗”,QMessageBox::OK)
最后打開(kāi)后設(shè)置所有參數(shù)不能修改 用setEnable(false)
把當(dāng)前的文本設(shè)置為關(guān)閉窗口
第二種情況 串口已經(jīng)處于打開(kāi)狀態(tài)
直接用close函數(shù)
把setEnable(false)都改為true
設(shè)置文本
優(yōu)化:添加初始參數(shù)默認(rèn)值
用setCurrentIndex
如何添加功能讓串口受到數(shù)據(jù)
1 UI界面創(chuàng)建:
添加label? 接收設(shè)置?
? ? ? ? checkBox 接收方式 ASCII碼(默認(rèn)選中 用setCheckState函數(shù))、十六進(jìn)制、暫停? (只能選中一個(gè))

添加TextEdit? 接收數(shù)據(jù) 發(fā)送數(shù)據(jù)
? ? ? ? Label 接收字節(jié):0? 發(fā)送字節(jié):0
2 創(chuàng)建信號(hào)和槽 connect(串口, readyRead, this, )
槽函數(shù)編寫(xiě):(重點(diǎn))
serialPort_readyRead()
首先判斷當(dāng)前模式(暫停,ASCII,16進(jìn)制)
如果當(dāng)前不是暫停,就讀取全部串口數(shù)據(jù) 函數(shù):readAll? 用字符串類型接收
用字符串里的Length函數(shù)看收到了多少字節(jié)數(shù)據(jù)? 放到一個(gè)long類型的整型數(shù)據(jù)里,在當(dāng)前的label里顯示(注意+=);
如果當(dāng)前模式是16進(jìn)制,

優(yōu)化:

問(wèn)題 怎么收完一組后換行??
如果當(dāng)前模式是ASCII,

最后設(shè)置txetEdit顯示即可
優(yōu)化:讀取前一輪數(shù)據(jù),并追加到當(dāng)前顯示中


發(fā)送功能
1 UI創(chuàng)建按鈕 發(fā)送 轉(zhuǎn)到槽 編寫(xiě)槽函數(shù)
2 提取要發(fā)送的內(nèi)容 toPlainText? 放到一個(gè)字符串中
3 用串口的函數(shù)write? 需要把字符串類型轉(zhuǎn)換為QByteArray類型。用到toLatin1函數(shù)
4 計(jì)算發(fā)送的字節(jié)長(zhǎng)度 用lenth函數(shù) +=一個(gè)值? 然后label中顯示
5 添加清空接收區(qū)和清空發(fā)送區(qū)的功能