国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

關(guān)于Qt適配不同分辨率和縮放率時(shí)可能遇到的問題和解決方案

這篇具有很好參考價(jià)值的文章主要介紹了關(guān)于Qt適配不同分辨率和縮放率時(shí)可能遇到的問題和解決方案。希望對(duì)大家有所幫助。如果存在錯(cuò)誤或未考慮完全的地方,請(qǐng)大家不吝賜教,您也可以點(diǎn)擊"舉報(bào)違法"按鈕提交疑問。

如果沒有特殊的處理,Qt的UI窗口在不同的分辨率和縮放率下,其顯示效果可能會(huì)出現(xiàn)問題,常見的有:

  • 子控件堆疊,無法顯示完整

  • 窗口尺寸變大,超出屏幕的顯示范圍

  • 控件變形,長(zhǎng)寬比不合理

  • 界面模糊

  • 字體變大,控件尺寸卻沒有變化

    有兩種方式可以對(duì)UI界面進(jìn)行良好的縮放:

  • Qt不做任何事情,由windows系統(tǒng)負(fù)責(zé)縮放

  • windows系統(tǒng)不做任何事情,由Qt負(fù)責(zé)進(jìn)行縮放

1.解決方案:Windows適配

使用qt.conf,在資源qrc里添加,`:/qt/etc/qt.conf`, qt.conf文件內(nèi)容為:
[Platforms][Platforms]
WindowsArguments = dpiawareness=0

這樣的效果就是直接讓windows來接管和控制縮放。它通過類似縮放圖片這樣的方式來實(shí)現(xiàn)界面縮放,好處是各種情況下界面都可以使用,而且子界面不至于變形,壞處是放大后界面會(huì)變得模糊。

2.解決方案:Qt適配(Qt5.6版本及以后)

如果只是想單純地解決問題,而不想深入了解高DPI的相關(guān)原理,那么只需知道對(duì)應(yīng)的操作即可。

想要Qt適配不同分辨率和縮放率,即可以在高DPI下正常顯示,我們需要做如下的工作:

2.1 開啟支持高DPI的屬性

在Qt5.6以及后續(xù)的版本中,添加了對(duì)高DPI顯示的支持,這個(gè)特性默認(rèn)是關(guān)閉的,需要我們手動(dòng)打開這個(gè)特性,注意以下代碼必須在main函數(shù)中,實(shí)例化QApplication對(duì)象之前調(diào)用,否則是不會(huì)起效果的

	QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling, true);
    QCoreApplication::setAttribute(Qt::AA_UseHighDpiPixmaps, true);
    QApplication::setHighDpiScaleFactorRoundingPolicy(
        Qt::HighDpiScaleFactorRoundingPolicy::PassThrough);

以上代碼做了三件事情,分別是:

  • 開啟Qt對(duì)高DPI顯示的支持

  • 開啟Qt對(duì)高分辨率版本pixmap(High resolution versions of pixmaps)的支持

  • 設(shè)置對(duì)高DPI(也就是大于1的DPI值)值的四舍五入規(guī)則

    第一個(gè)沒什么好說的,打開這個(gè)開關(guān),Qt才會(huì)啟動(dòng)對(duì)高DPI特性適配的功能

    第二個(gè)在后續(xù)會(huì)解釋相關(guān)概念和原理,本節(jié)會(huì)介紹如何使用這個(gè)特性。

    第三個(gè)需要解釋一下,當(dāng)設(shè)置高DPI的時(shí)候,我們假設(shè)它的值為 originDPI,它是一個(gè)大于等于1的浮點(diǎn)數(shù),常見取值有:1.0,1.25,1.5,1.75,2.0 等等,具體取決于操作系統(tǒng)中的設(shè)置。而Qt提供了一個(gè)機(jī)制,讓我們決定是否采用這個(gè)原始值,也就是可以對(duì)原始值進(jìn)行舍入的操作,實(shí)際使用的是舍入后的值,即實(shí)際應(yīng)用的DPI值。

    在網(wǎng)絡(luò)上很多關(guān)于講解Qt適配不同分辨率和縮放比的文章中,都會(huì)提到Qt僅支持整數(shù)倍的DPI值,這是錯(cuò)誤的,因?yàn)樗鼈儧]有修改對(duì)DPI的射入政策,使用的默認(rèn)值為:Qt::HighDpiScaleFactorRoundingPolicy::Round,它會(huì)將小數(shù)點(diǎn)后大于等于 0.5 的部分取整,因此結(jié)果如下:

window下設(shè)置的縮放比 Qt實(shí)際應(yīng)用的縮放比
100% 1x
125% 1x
150% 2x
175% 2x
200% 2x
225% 2x
250% 3x

而Qt::HighDpiScaleFactorRoundingPolicy::PassThrough這個(gè)策略,則不會(huì)對(duì)原始值做任何修改,他會(huì)直接使用,所以實(shí)際的縮放比和設(shè)置的縮放比是完全一樣的。

2.2 圖片對(duì)高DPI的支持

當(dāng)UI被放大的時(shí)候,原本的圖片會(huì)顯得比較模糊,這是因?yàn)橥粡埖膱D片被顯示到了更大的物理矩形框中導(dǎo)致的。

為了解決這個(gè)問題,我們需要開啟Qt對(duì)高分辨率版本pixmap(High resolution versions of pixmaps)的支持,然后按照如下策略提供圖片資源。

2.2.1 外部圖片

QImageReader類負(fù)責(zé)讀取圖片資源,它提供了自動(dòng)識(shí)別并讀入高分辨率版本pixmap的功能。例如,我們?cè)贒PI為1.0時(shí),需要一個(gè)20x20的圖片,它的路徑為 :/icons/basename.png 。當(dāng)DPI為2時(shí),這個(gè)圖片實(shí)際顯示的尺寸就會(huì)被拉伸為原來的兩倍,顯示就會(huì)變得模糊。為了解決這個(gè)問題,我們應(yīng)該提供這個(gè)圖片的高分辨率版本pixmap

:/icons/basename.png
:/icons/basename@2x.png
:/icons/basename@3x.png
:/icons/basename@4x.png

其尺寸分別為:20x20,40x40,60x60,80x80。
QImageReader會(huì)根據(jù)當(dāng)前的DPI設(shè)置,自動(dòng)讀取對(duì)應(yīng)版本的pixmap,然后設(shè)置其devicePixelRatio屬性為DPI值。例如,上面的代碼,在DPI為1時(shí),讀取:/icons/basename.png圖片,devicePixelRatio為1.0;當(dāng)DPI為2時(shí),讀取:/icons/basename@2x.png,devicePixelRatio為2.0;依次類推。
這樣,通過在不同DPI時(shí)應(yīng)用不同的圖片(事實(shí)上,在qt底層,會(huì)使用這些整數(shù)倍的圖片進(jìn)行縮放,獲取當(dāng)前dpi縮放率對(duì)應(yīng)的高分辨率版本pixmap),就不會(huì)有圖片模糊的情況發(fā)生。
qss中設(shè)置的圖片支持這樣的機(jī)制。

但要注意的是,如果使用的是QPixmap,則并非如此,它不會(huì)自動(dòng)讀取對(duì)應(yīng)dpi的圖片。
例如:

	QPixmap pix(":/icons/basename.png");

那么,在任何情況下,無論dpi的值是多少,它讀取的都是:/icons/basename.png,而不是其他圖片。
QIcon類型,查看文檔,它是一個(gè)提供了可縮放圖標(biāo)的類型,也就是說QIcon沒有size這個(gè)說法,要使用它時(shí),先給定一個(gè)size將其轉(zhuǎn)化為QPixmap,然后才能使用。
QIcon在構(gòu)造時(shí),會(huì)根據(jù)dpi自動(dòng)讀取對(duì)應(yīng)的圖片。假如我們提供了上面的四張圖片,那么當(dāng)dpi為1的時(shí)候,它僅讀取1倍圖;當(dāng)dpi為1.25,1.5,1.75,2.0 時(shí),它會(huì)讀取1倍圖,2倍圖;當(dāng)dpi大于2小于3時(shí),會(huì)讀取1倍圖,2倍圖,3倍圖。也就是說,QIcon只讀取它當(dāng)前可能會(huì)用到的圖,用不到的圖不會(huì)讀取。另外要注意:QIcon是根據(jù)圖片名稱來讀取的,例如basename.png實(shí)際是3倍圖,那么它仍然讀取的是這個(gè)圖。是根據(jù)名稱而不是其他來讀取圖片的。
此時(shí),可以使用 QIcon::availableSizes()來返回它讀取的圖片列表的尺寸,尺寸的順序?qū)?yīng)1倍圖,2倍圖,3倍圖這樣的順序。
QIcon::pixmap() 函數(shù),傳入指定的size,返回一個(gè)pixmap。pixmap的尺寸和傳入的size可能不同,可能相同。大概規(guī)則如下:

  • 未開啟Qt::AA_UseHighDpiPixmaps,當(dāng)size小于QIcon::availableSizes()中的最大尺寸時(shí),pixmap的大小為size;否則,pixmap的大小為QIcon::availableSizes()中的最大尺寸
  • 開啟了Qt::AA_UseHighDpiPixmaps,,此時(shí)這個(gè)函數(shù)會(huì)獲取dpi的scale縮放系數(shù),然后嘗試獲取 sizescale 尺寸的pixmap,是否允許的規(guī)則和上述類似,如果 sizescale 小于QIcon::availableSizes()中的最大尺寸時(shí),pixmap的大小為 size*scale ,devicePixelRatio為scale;否則,pixmap的大小為QIcon::availableSizes()中的最大尺寸,devicePixelRatio則是一個(gè)未知的值。

所以,如果想要獲取一個(gè)圖片對(duì)應(yīng)當(dāng)前dpi的高分辨率版本pixmap,代碼如下:


  	QCoreApplication::setAttribute(Qt::AA_UseHighDpiPixmaps, true); 

		const QString path = "C:\\Users\\mech-mind_xpp\\Desktop\\icon.png";
    QSize size(22, 22);
#if 1
    QIcon icon(path);  // 實(shí)際應(yīng)存在1倍圖,2倍圖,3倍圖
  	// size最好是一倍圖的尺寸,或等比例縮小的尺寸,例如11x11;其他情況后果自負(fù)
    auto pxm = icon.pixmap(size); 
    ui->svg->setPixmap(pxm);
#else
    QPixmap pxm(path); //icon.png實(shí)際為三倍圖或者其他N倍圖
    qreal pixelRatio = qApp->devicePixelRatio();
    pxm = pxm.scaled(size * pixelRatio, Qt::IgnoreAspectRatio, Qt::SmoothTransformation);
    pxm.setDevicePixelRatio(pixelRatio);
    ui->svg->setPixmap(pxm);
#endif
2.2.2 自繪制圖片

在UI中使用的圖片,有些是自己通過代碼繪制得來的,和從外部讀取的圖片一樣,也會(huì)有模糊的問題。此時(shí)就必須通過一定的策略來讓自己繪制的圖片成為高分辨率版本pixmap。

其關(guān)鍵點(diǎn)如下:

  • 圖片的尺寸和DPI相關(guān)

  • QPixmap(或者其他圖片類)設(shè)置 devicePixelRatio屬性,值為DPI的值

  • 由于圖片的尺寸會(huì)隨著DPI變化,因此實(shí)際繪制的細(xì)節(jié)中所使用的尺寸也都需要跟著DPI變化。由于DPI是一個(gè)浮點(diǎn)數(shù),所以QPainter應(yīng)該盡量使用那些參數(shù)為qreal的重載函數(shù)。

    代碼梗概如下:

QSize size(64,64);
qreal dpi = window()->devicePixelRatioF();

QPixmap pix(size * dpi);
pix.setDevicePixelRatio(dpi);

QPainter painter(&pix);
... ...

事實(shí)上,自繪制的圖片和從外部讀取的圖片,其要點(diǎn)是完全一樣的。

2.2.3 另一種選擇

以上是Qt提供的非常正規(guī)的辦法,但缺點(diǎn)是每個(gè)圖標(biāo)都需要提供多張圖片,會(huì)導(dǎo)致app的尺寸變得更大。一種比較偏門的辦法是直接提供一張N倍圖,例如3倍圖或者4倍圖。比如,當(dāng)顯示效果為20x20,那么我們可以提供一個(gè)尺寸為60x60的圖片(3倍圖),或者80x80的圖片(4倍圖)。這樣,即使是在高DPI下,圖片顯示仍然是清晰的,這是因?yàn)閷⒋蟪叽绲膱D片縮小后設(shè)置給了控件,因此避免了模糊的問題,同時(shí)資源文件的大小也不會(huì)變得太大,算是一種折中的辦法。

接下來說明這種做法的具體操作細(xì)節(jié):

2.2.3.1 qss使用border-image而不是image

假設(shè)現(xiàn)在有一個(gè)圖標(biāo),我們的本意是想將它作為20x20的圖標(biāo)使用。但為了解決模糊的問題,現(xiàn)在給了一個(gè)3倍圖,是60x60。此時(shí)如果使用qss設(shè)置圖片,那么我們應(yīng)該使用border-image而不是image,這是因?yàn)閕mage默認(rèn)并不會(huì)縮放圖片,而是使用圖片的原始尺寸,所以實(shí)際并不能表現(xiàn)為20x20的效果,而是60x60;而border-image則是會(huì)進(jìn)行縮放填滿控件范圍,因此不需要擔(dān)心尺寸問題,反而因?yàn)槭谴蟪叽鐖D片渲染到小尺寸,可以解決圖片模糊的問題。

2.2.3.2 QLabel設(shè)置圖片

還是上面的問題,QLabel默認(rèn)的屬性scaleContents是false,此時(shí)如果設(shè)置一個(gè)pixmap,QLabel會(huì)縮放自身的size來使用pixmap的尺寸。而為了解決模糊的問題,應(yīng)該反過來:給QLabel設(shè)置尺寸,設(shè)置屬性scaleContents為true,然后設(shè)置pixmap。

	label->setFixedSize(20,20);
	label->setScaledContents(true);
	label->setPixmap(QPixmap(":/icons/back.png")); // back.png的尺寸為60x60

但需要注意的是,此時(shí)不能將pixmap進(jìn)行縮放操作,然后再設(shè)置給label,這樣由于從大尺寸圖片縮小為了小尺寸,就丟失了圖片的細(xì)節(jié),仍然不能解決圖片模糊的問題:

	label->setFixedSize(20,20);
	label->setScaledContents(true);
  QPixmap pix = QPixmap(":/icons/back.png"); // back.png的尺寸為60x60
  pix = pix.scaled(QSize(20,20));	//錯(cuò)誤,這樣和直接給一個(gè)20x20的圖片是一樣的,仍然會(huì)模糊
	label->setPixmap(pix); 
2.2.3.3 QPainter繪制圖片

在代碼中,有時(shí)候會(huì)使用QPainter繪制圖片,這種操作也會(huì)導(dǎo)致圖片模糊。還是上面的情況,由于QPainter的drawPixmap不會(huì)縮放圖片,它使用的是pixmap的原始尺寸,所以繪制出來是60x60的大??;而如果提前將pixmap進(jìn)行scale操作,和2.2.3.2中一樣,圖片仍然會(huì)模糊,此時(shí)我們應(yīng)該按照**高分辨率版本pixmap **的邏輯來解決這個(gè)問題:
注意:pixmap的dpr最好和當(dāng)前dpi的設(shè)置一致。否則,可能會(huì)出現(xiàn)圖片變形的問題。

QPixmap pix(":/icons/back.png"); // back.png的尺寸為60x60
QSize size(20,20);
qreal pixelRatio = qApp->devicePixelRatio();
pix = pix.scaled(size * pixelRatio, Qt::IgnoreAspectRatio, Qt::SmoothTransformation);
pix.setDevicePixelRatio(pixelRatio);

QPainter painter;
painter.drawPixmap(...);

2.3 其他注意事項(xiàng)

  • QPainter中應(yīng)該盡量使用qreal類型的重載函數(shù)。
    這是因?yàn)?,?dāng)dpi為1.25,1.5這樣的值時(shí),對(duì)應(yīng)的尺寸也必須跟著scale倍數(shù)放大,如果參數(shù)是整數(shù)類型,那么可能會(huì)因?yàn)閬G失小數(shù)部分而不能體現(xiàn)scale效果
  • 如有必要,可以根據(jù)屏幕的尺寸,也就是分辨率,以及dpi的倍數(shù),來調(diào)整window和dialog的大小
  • 盡量不要給控件設(shè)置固定尺寸,而是通過QSizePolicy給定一個(gè)彈性的尺寸范圍,然后使用layout自適應(yīng)窗口尺寸的變化
2.3.1 高DPI下窗口尺寸超出屏幕范圍

在100%的縮放率下,窗口的寬度為 width x height,那么在大于100的縮放率下,就會(huì)有 width * scale 大于 屏幕分辨率寬度 或者 height * scale 大于 屏幕分辨率高度的情況。這種情況下,建議將 width 和 height 的值修改為當(dāng)前屏幕支持的最大值,或者直接showMax或者ShowFullScreen 。
注意:上面說的屏幕支持的最大值為:screenSize.width() / dpi 。例如當(dāng)前縮放率為200%,屏幕分辨率為1920x1080,那么此時(shí)如果窗口不想超出屏幕,那么支持的最大寬高為:960x540.
示例代碼:

void showEvent(QShowEvent* event) override
{
  auto dlgSize = this->size();
  const qreal scale = window()->screen()->devicePixelRatio();
  const auto screenSize = window()->screen()->size();

  dlgSize = dlgSize * scale;
  qDebug() << "....scale" << scale;

  if (dlgSize.width() > screenSize.width() || dlgSize.height() >= screenSize.height()) {
    // setFixedWidth(screenSize.width() / scale);
    // setFixedHeight(screenSize.height() / scale);
    // showMaximized();
    showFullScreen();
  }

  QDialog::showEvent(event);
}

然而在很多情況下,窗口的尺寸并不能隨意變化。例如某些窗口要維持一定的長(zhǎng)寬比,否則就不好看;或者將高度或者寬度縮小后,由于其中的子控件設(shè)置了固定尺寸而導(dǎo)致子控件堆疊等等。
所以盡量不要設(shè)置固定尺寸,使用layout管理子控件,讓窗口可以自適應(yīng)size的變化,這是非常重要的。對(duì)于UI設(shè)計(jì)人員來講,也應(yīng)該盡量克制自己對(duì)細(xì)節(jié)的追求,盡量不要使用例如指定固定尺寸,嚴(yán)格指定控件位置等等,這種只適合靜態(tài)布局的方法,而是要考慮到窗口尺寸變化時(shí)子控件跟隨變化的合理性。

3.控件堆疊與Unable to set geometry問題

在實(shí)際中,會(huì)發(fā)生子控件堆疊,不能顯示完全的問題,或者報(bào)警告:Unable to set geometry等。

發(fā)生這兩種情況的根本原因就是:父窗口的尺寸不足以容納全部子窗口,或者即使能容納,子窗口之間也會(huì)非常擁擠,甚至發(fā)生堆疊,顯示不完全。

解決這個(gè)問題的思路,大致分為兩種:

  • 動(dòng)態(tài)設(shè)置window的尺寸,而不是設(shè)置固定尺寸

    • 可以調(diào)用adjustSize()函數(shù),讓window自動(dòng)按照內(nèi)容調(diào)節(jié)大小
    • 根據(jù)當(dāng)前分辨率和縮放率,調(diào)整window的尺寸
  • 使用QScrollArea管理子控件

    為了讓window擁有可以調(diào)節(jié)尺寸的能力,這就要求各個(gè)子控件的尺寸是可調(diào)節(jié)的(或者大多數(shù)子控件的尺寸是可調(diào)節(jié)的),因此控件的尺寸只要不要設(shè)置為固定尺寸,而是通過QSizePolicy設(shè)置為可調(diào)節(jié)的,這樣當(dāng)window窗口需要放大或者縮小時(shí),layout才能適應(yīng)這樣的尺寸變化。

4. DPI基本概念

首先,我們了解兩個(gè)概念:

  • Dots per inch (DPI):每英寸點(diǎn)數(shù)

  • Device-independent pixel (DIPs):獨(dú)立于設(shè)備像素,設(shè)備自由像素

    DPI這個(gè)概念,最早來自于文本印刷行業(yè)。在這個(gè)行業(yè)中,文本的大小使用一種叫做點(diǎn)(points)的概念作為單位來衡量,其中:

    1 pt = 1 / 72 inch

    也就是說,一個(gè)點(diǎn)是七十二分之一英寸大小,一英寸為72個(gè)點(diǎn)。

    我們現(xiàn)在使用的字體中的大小,就叫做point size,就是從印刷行業(yè)繼承下來的。例如一個(gè)12-point大小的字體,它的高度就是 12 / 72 = 1 / 6 英寸。

    但當(dāng)回到屏幕顯示的時(shí)候,就出現(xiàn)了問題。我們知道,屏幕是以像素為單位的,但在不同的屏幕中,一個(gè)像素對(duì)應(yīng)的實(shí)際物理寬度是不一樣的,這取決于屏幕真實(shí)的物理尺寸和屏幕的分辨率。

    所以,定義了一個(gè)新的單位來表示字體的大小,新單位就是:邏輯單元logical units)。一個(gè)72 point大小的字體被定義為一個(gè)邏輯單元高。然后,再將邏輯單元轉(zhuǎn)化為像素。在Windows的發(fā)展歷史中,默認(rèn)定義一個(gè)邏輯單元的大小為96像素。也就是說,此時(shí)一個(gè) 72 point大小的字體將被繪制為96個(gè)像素。一個(gè)12 point 大小的字體會(huì)被繪制成為 16 個(gè)像素。

    此時(shí),DPI的概念就從打印中轉(zhuǎn)移到了屏幕顯示中,雖然名字叫 dots per inch,但已經(jīng)是屏幕顯示中的概念了。默認(rèn)的DPI為96,即每英寸96個(gè)像素。(一個(gè)邏輯單元為72 point,72 point在印刷中為一英寸)。

    而操作系統(tǒng)中設(shè)置縮放率,其本質(zhì)就是在修改DPI的值。如果用戶將DPI修改為了144,那么72 point 大小的字體就會(huì)顯示為144個(gè)像素高。標(biāo)準(zhǔn)DPI被設(shè)置為100%(96 DPI),125%(120 DPI),150(144 DPI),此外還有其他的設(shè)置。

    這樣,我們就明白了,為什么縮放率改變時(shí),文本的大小會(huì)變。這是因?yàn)樽煮w的point size沒有變化,它的邏輯單元也不會(huì)變化,但一個(gè)邏輯單元對(duì)應(yīng)的像素發(fā)生了變化,最后顯示的像素高度就發(fā)生了變化。

5.Qt對(duì)高DPI的支持

本節(jié)內(nèi)容是對(duì)Qt文檔《High DPI Displays》的概述。

有兩種方式可以對(duì)UI界面進(jìn)行縮放:

  • Qt不做任何事情,由windows系統(tǒng)負(fù)責(zé)縮放

  • windows系統(tǒng)不做任何事情,由Qt負(fù)責(zé)進(jìn)行縮放

    第一種方法是通過設(shè)置相關(guān)的環(huán)境變量實(shí)現(xiàn)的,此時(shí)windows會(huì)按照縮放圖片的方式縮放整個(gè)界面,因?yàn)闊o論是文字還是UI,都會(huì)同時(shí)放大縮小。好處是程序是可用的,壞處是界面必然會(huì)模糊。

    第二種方法則由Qt來負(fù)責(zé)縮放,其思路是:為了支持高DPI, Qt會(huì)自動(dòng)縮放字體,并提供一個(gè)DPI值,應(yīng)用程序代碼可以使用它來縮放其余的UI。

    第二種情況下,所需的內(nèi)容,已在第一節(jié)中說明。

6.Pixmap中的devicePixelRatio

dpr的概念,最初是來自于屏幕,引用網(wǎng)上一段話解釋:文章來源地址http://www.zghlxwxcb.cn/news/detail-751309.html

	我們的主人公是喬幫主和比爾蓋茨。此時(shí)喬幫主面前有一臺(tái)mac,屏幕的分辨率是1280*720,這就是物理分辨率。喬幫主對(duì)比爾蓋茨說,給我的mac開發(fā)一個(gè)word軟件吧。蓋茨說OK,于是寫了一個(gè)軟件,這個(gè)軟件顯示的時(shí)候長(zhǎng)度是1280像素,寬度是720像素,正好能夠蓋滿整個(gè)mac屏幕。喬幫主看了之后很滿意。

	有一天,喬幫主看自己的mac屏幕覺得很粗糙,一點(diǎn)都不清晰銳利。于是聰明的喬幫主想到,同樣是15寸的屏幕,我把像素點(diǎn)翻倍,不就可以更清晰了嗎?于是他把mac的物理分辨率改成了2560*1440的分辨率,相當(dāng)于每個(gè)像素點(diǎn)的尺寸減少了4倍(保持原來每個(gè)像素占據(jù)的面積不變,放了4個(gè)像素,這每個(gè)像素占據(jù)的面積是原來像素占據(jù)面積的1/4),這下再也看不出顆粒感了,喬幫主很滿意。但是,當(dāng)喬幫主打開蓋茨給他寫的word的時(shí)候,傻眼了,原本全屏的word現(xiàn)在只占屏幕的四分之一,而且文字非常的小。喬幫主打電話給蓋茨說,你的軟件怎么出問題了?蓋茨回答說,我開發(fā)的時(shí)候你的mac分辨率就是1280*720,你自己改了硬件尺寸怪我咯,我很忙沒空給你改軟件代碼,你就湊合著用吧。喬幫主稍作思考,馬上想出了一個(gè)非常聰明的主意!他在軟件和硬件之間的系統(tǒng)層加了一層邏輯分辨率。雖然屏幕橫向有2560個(gè)像素點(diǎn),但是告訴軟件我只有1280個(gè)像素點(diǎn)!當(dāng)word的寬度要占1280個(gè)像素的時(shí)候,實(shí)際上已經(jīng)占了2560個(gè)像素。于是我們的word又占滿屏幕了!于是喬幫主把這個(gè)機(jī)智的想法命名為邏輯分辨率,不管我顯示器的硬件有多少個(gè)像素點(diǎn),我只會(huì)告訴軟件我的邏輯分辨率,這樣軟件的代碼就不用修改也能在不同的屏幕上顯示效果一致。在多年后,mac的物理分辨率已經(jīng)達(dá)到了5120 x 2880,但是告訴軟件的時(shí)候還是說我的分辨率1280*720,相當(dāng)在蓋茨看來的一個(gè)邏輯像素點(diǎn),背后實(shí)際上已經(jīng)有16個(gè)物理像素點(diǎn)為其工作了!
而pixmap的dpr概念與之類似,表示的是pixmap的size和想要繪制的設(shè)備無關(guān)像素之間的比例。例如,一個(gè)200x200大小的pixmap,如果它的dpr為2,那么表示它將會(huì)被繪制到100x100的設(shè)備無關(guān)像素矩形內(nèi)。

我們引用QPainter文檔中的《Drawing High Resolution Versions of Pixmaps and Images》一節(jié):
	所謂pixmap的高分辨率版本,指的是device pixel ratio的值大于1的pixmap。當(dāng)pixmap的dpr和底層的QPinterDevice的ptr一致時(shí),pixmap無需轉(zhuǎn)化,就可以直接繪制到相關(guān)設(shè)備上。
	例如,一張64x64大小的圖片,dpr為2,當(dāng)他繪制在一個(gè)高DPI而且dpr也正好為2的屏幕上時(shí),最后實(shí)際繪制出來的時(shí)一個(gè)32x32像素大小的內(nèi)容。當(dāng)Qt中的代碼根據(jù)pixmap的size來計(jì)算布局的尺寸時(shí),會(huì)使用圖片的dpr得到真實(shí)有效的尺寸。這導(dǎo)致pixmap會(huì)按照給分辨率版本的形式顯示(32x32,但由于將圖片提前進(jìn)行了縮放,顯示后的圖片不會(huì)變得模糊),而不是顯示為一個(gè)大的圖片(64x64)。
簡(jiǎn)言之,如果想要最終顯示為32x32像素大小,那么在dpi為1時(shí),需要提供32x32的圖片;dpi為2時(shí),提供32x32的兩倍大小的圖片,圖片的dpr需要設(shè)置為2,這樣圖片會(huì)先縮小2倍在放大2倍顯示,圖片不會(huì)變得模糊;依次類推。

到了這里,關(guān)于關(guān)于Qt適配不同分辨率和縮放率時(shí)可能遇到的問題和解決方案的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點(diǎn)僅代表作者本人,不代表本站立場(chǎng)。本站僅提供信息存儲(chǔ)空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請(qǐng)注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實(shí)不符,請(qǐng)點(diǎn)擊違法舉報(bào)進(jìn)行投訴反饋,一經(jīng)查實(shí),立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費(fèi)用

相關(guān)文章

  • 【Unity】多分辨率適配

    【Unity】多分辨率適配

    筆者按:使用Unity版本為2021.3LTS,與其他版本或有異同。請(qǐng)僅做參考 一、前言。 本文是筆者在學(xué)習(xí)使用Unity引擎的過程中,產(chǎn)學(xué)研的一個(gè)筆記。由筆者根據(jù)官方文檔Unity User Manual 2021.3 (LTS)/Create user interfaces (UI)/Unity UI/UI 操作方法/設(shè)計(jì)用于多種分辨率的 UI相關(guān)部分結(jié)合自身經(jīng)驗(yàn)

    2024年02月04日
    瀏覽(27)
  • C# 獲取系統(tǒng)DPI縮放比例以及分辨率大小

    虛擬屏幕是指所有物理屏幕組合成的邏輯屏幕,可以用于跨越多個(gè)物理屏幕顯示應(yīng)用程序。 這兩個(gè)方法都可以在 正常情況 下獲取到屏幕的分辨率 - 當(dāng)桌面縮放比例不是 100% 的時(shí)候獲取到的分辨率就是“真實(shí)”的分辨率了,而是按縮放比例調(diào)整以后屏幕顯示的內(nèi)容的寬度和高

    2023年04月26日
    瀏覽(16)
  • 【MATLAB】Linux版本 高分辨率屏 調(diào)整顯示縮放

    【MATLAB】Linux版本 高分辨率屏 調(diào)整顯示縮放

    安裝了linux版本的MATLAB?R2023b之后,發(fā)現(xiàn)工具欄字體很小不方便使用,所以上網(wǎng)找到了MATLAB論壇上某位大佬的教程:參考鏈接,放在這里供各位參考?。 這里注明我的matlab安裝環(huán)境僅供參考,未在其他環(huán)境下測(cè)試過,有效性未知: Ubuntu 20.04 MATLAB R2023b 在MATLAB命令行中輸入下面

    2024年01月16日
    瀏覽(56)
  • 使用 FFmpeg 輕松調(diào)整視頻的大小/縮放/更改分辨率

    使用 FFmpeg 輕松調(diào)整視頻的大小/縮放/更改分辨率

    在此 FFmpeg 教程中,我們學(xué)習(xí)使用 FFmpeg 的命令行工具更改視頻的分辨率(或調(diào)整視頻的大小/縮放)。 更改視頻的分辨率(也稱為調(diào)整大小或縮放)是視頻編輯、處理和壓縮中非常常見的操作。對(duì)于 ABR 視頻流尤其如此,其中將單個(gè)視頻作為源并壓縮為多個(gè)不同的比特率分辨

    2024年01月20日
    瀏覽(20)
  • Unity中UGUI界面的分辨率適配設(shè)置

    Unity中UGUI界面的分辨率適配設(shè)置

    以下是個(gè)人對(duì)Unity中屏幕適配方案的理解: 一、Scale With Screen Size方案(根據(jù)屏幕大小自動(dòng)縮放) 1、如果選用的是下圖所示的分辨率適配方案,也就是把Canvas和Canvas Scaler這兩個(gè)組件中設(shè)置和下圖一樣的話。 還有就是你所制作的UI界面一定是要掛載在和下圖中一樣設(shè)置的Canvas物

    2024年02月16日
    瀏覽(25)
  • Unity Texture2D的裁剪、鏡像、翻轉(zhuǎn)、縮放、合并、分辨率

    本人最近做了一個(gè)拍照并打印的程序,使用到了多種圖片編輯功能,現(xiàn)在羅列一下,希望對(duì)大家有所幫助。 裁剪,將貼圖上的某個(gè)區(qū)域裁剪? ?縮放,縮放和放大原有貼圖 ?水平鏡像 ?垂直鏡像 ?逆時(shí)針旋轉(zhuǎn)90度 順時(shí)針旋轉(zhuǎn)90度? 兩張貼圖合并,可以實(shí)現(xiàn)水印等功能,該代碼

    2024年02月16日
    瀏覽(30)
  • Python 不同分辨率圖像峰值信噪比[PSNR]

    Python 不同分辨率圖像峰值信噪比[PSNR]

    PNNR:全稱為“Peak Signal-to-Noise Ratio”,中文直譯為峰值信噪比 前言 一、定義 二、Python代碼 1.自定義 2.Tensorflow 總結(jié) 峰值信噪比是一種衡量圖像質(zhì)量的指標(biāo),描述的是最大值信號(hào)與背景噪音之間的關(guān)系。 一般來說,PSNR高于40dB說明圖像質(zhì)量極好(即非常接近原始圖像);在

    2024年02月01日
    瀏覽(25)
  • 兩個(gè)鏡頭、視野、分辨率不同的相機(jī)(rgb、紅外)的視野校正

    兩個(gè)鏡頭、視野、分辨率不同的相機(jī)(rgb、紅外)的視野校正

    目前在做的項(xiàng)目用到兩個(gè)攝像頭,一個(gè)是熱成像攝像頭、另一個(gè)是普通的rgb攝像頭。 一開始的目標(biāo)是讓他們像素級(jí)重合,使得點(diǎn)擊rgb圖像時(shí),即可知道其像素對(duì)應(yīng)的溫度。但是在嘗試的過程中,發(fā)現(xiàn)基本不可能。因?yàn)橛捎诳v深、遮擋、透視變形、視差等問題,兩個(gè)攝像頭拍攝

    2024年02月14日
    瀏覽(19)
  • python求不同分辨率圖像的峰值信噪比,一文搞懂

    python求不同分辨率圖像的峰值信噪比,一文搞懂

    可以使用 Python 的 NumPy 和 OpenCV 庫來實(shí)現(xiàn)這個(gè)任務(wù)。提前準(zhǔn)備一張圖片作為素材。 峰值信噪比(Peak Signal to Noise Ratio,PSNR)是衡量圖像質(zhì)量的常用指標(biāo),它表示圖像中信號(hào)和噪聲的比值。通常,較高的 PSNR 值表示圖像質(zhì)量較高。 PSNR 的公式如下: 其中, MAX 是圖像的最大亮度

    2024年02月05日
    瀏覽(31)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請(qǐng)作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包