Merge remote-tracking branch 'origin/5.8' into dev
Conflicts: src/qml/jsruntime/qv4object_p.h Change-Id: Iff4d3aba7710a999b8befdc493cbe959e1ce02f9
This commit is contained in:
commit
5d4cbf4094
|
@ -42,6 +42,72 @@ import QtQuick 2.0
|
|||
|
||||
ListModel {
|
||||
id: stocks
|
||||
|
||||
// pre-fetch data for all entries
|
||||
Component.onCompleted: {
|
||||
for (var idx = 0; idx < count; ++idx) {
|
||||
getCloseValue(idx)
|
||||
}
|
||||
}
|
||||
|
||||
function requestUrl(stockId) {
|
||||
var endDate = new Date(""); // today
|
||||
var startDate = new Date()
|
||||
startDate.setDate(startDate.getDate() - 5);
|
||||
|
||||
var request = "http://ichart.finance.yahoo.com/table.csv?";
|
||||
request += "s=" + stockId;
|
||||
request += "&g=d";
|
||||
request += "&a=" + startDate.getMonth();
|
||||
request += "&b=" + startDate.getDate();
|
||||
request += "&c=" + startDate.getFullYear();
|
||||
request += "&d=" + endDate.getMonth();
|
||||
request += "&e=" + endDate.getDate();
|
||||
request += "&f=" + endDate.getFullYear();
|
||||
request += "&g=d";
|
||||
request += "&ignore=.csv";
|
||||
return request;
|
||||
}
|
||||
|
||||
function getCloseValue(index) {
|
||||
var req = requestUrl(get(index).stockId);
|
||||
|
||||
if (!req)
|
||||
return;
|
||||
|
||||
var xhr = new XMLHttpRequest;
|
||||
|
||||
xhr.open("GET", req, true);
|
||||
|
||||
xhr.onreadystatechange = function() {
|
||||
if (xhr.readyState === XMLHttpRequest.LOADING || xhr.readyState === XMLHttpRequest.DONE) {
|
||||
var records = xhr.responseText.split('\n');
|
||||
if (records.length > 0 && xhr.status == 200) {
|
||||
var r = records[1].split(',');
|
||||
var today = parseFloat(r[4]);
|
||||
setProperty(index, "value", today.toFixed(2));
|
||||
|
||||
r = records[2].split(',');
|
||||
var yesterday = parseFloat(r[4]);
|
||||
var change = today - yesterday;
|
||||
if (change >= 0.0)
|
||||
setProperty(index, "change", "+" + change.toFixed(2));
|
||||
else
|
||||
setProperty(index, "change", change.toFixed(2));
|
||||
|
||||
var changePercentage = (change / yesterday) * 100.0;
|
||||
if (changePercentage >= 0.0)
|
||||
setProperty(index, "changePercentage", "+" + changePercentage.toFixed(2) + "%");
|
||||
else
|
||||
setProperty(index, "changePercentage", changePercentage.toFixed(2) + "%");
|
||||
} else {
|
||||
var unknown = "n/a";
|
||||
set(index, {"value": unknown, "change": unknown, "changePercentage": unknown});
|
||||
}
|
||||
}
|
||||
}
|
||||
xhr.send()
|
||||
}
|
||||
// Uncomment to test invalid entries
|
||||
// ListElement {name: "The Qt Company"; stockId: "TQTC"; value: "999.0"; change: "0.0"; changePercentage: "0.0"}
|
||||
|
||||
|
|
|
@ -64,65 +64,6 @@ Rectangle {
|
|||
model: StockListModel{}
|
||||
currentIndex: -1 // Don't pre-select any item
|
||||
|
||||
function requestUrl(stockId) {
|
||||
var endDate = new Date(""); //today
|
||||
var startDate = new Date()
|
||||
startDate.setDate(startDate.getDate() - 5);
|
||||
|
||||
var request = "http://ichart.finance.yahoo.com/table.csv?";
|
||||
request += "s=" + stockId;
|
||||
request += "&g=d";
|
||||
request += "&a=" + startDate.getMonth();
|
||||
request += "&b=" + startDate.getDate();
|
||||
request += "&c=" + startDate.getFullYear();
|
||||
request += "&d=" + endDate.getMonth();
|
||||
request += "&e=" + endDate.getDate();
|
||||
request += "&f=" + endDate.getFullYear();
|
||||
request += "&g=d";
|
||||
request += "&ignore=.csv";
|
||||
return request;
|
||||
}
|
||||
|
||||
function getCloseValue(index) {
|
||||
var req = requestUrl(model.get(index).stockId);
|
||||
|
||||
if (!req)
|
||||
return;
|
||||
|
||||
var xhr = new XMLHttpRequest;
|
||||
|
||||
xhr.open("GET", req, true);
|
||||
|
||||
xhr.onreadystatechange = function() {
|
||||
if (xhr.readyState === XMLHttpRequest.LOADING || xhr.readyState === XMLHttpRequest.DONE) {
|
||||
var records = xhr.responseText.split('\n');
|
||||
if (records.length > 0 && xhr.status == 200) {
|
||||
var r = records[1].split(',');
|
||||
var today = parseFloat(r[4]);
|
||||
model.setProperty(index, "value", today.toFixed(2));
|
||||
|
||||
r = records[2].split(',');
|
||||
var yesterday = parseFloat(r[4]);
|
||||
var change = today - yesterday;
|
||||
if (change >= 0.0)
|
||||
model.setProperty(index, "change", "+" + change.toFixed(2));
|
||||
else
|
||||
model.setProperty(index, "change", change.toFixed(2));
|
||||
|
||||
var changePercentage = (change / yesterday) * 100.0;
|
||||
if (changePercentage >= 0.0)
|
||||
model.setProperty(index, "changePercentage", "+" + changePercentage.toFixed(2) + "%");
|
||||
else
|
||||
model.setProperty(index, "changePercentage", changePercentage.toFixed(2) + "%");
|
||||
} else {
|
||||
var unknown = "n/a";
|
||||
model.set(index, {"value": unknown, "change": unknown, "changePercentage": unknown});
|
||||
}
|
||||
}
|
||||
}
|
||||
xhr.send()
|
||||
}
|
||||
|
||||
onCurrentIndexChanged: {
|
||||
if (currentItem) {
|
||||
root.currentStockId = model.get(currentIndex).stockId;
|
||||
|
@ -175,7 +116,6 @@ Rectangle {
|
|||
horizontalAlignment: Text.AlignRight
|
||||
verticalAlignment: Text.AlignVCenter
|
||||
text: value
|
||||
Component.onCompleted: view.getCloseValue(index);
|
||||
}
|
||||
|
||||
Text {
|
||||
|
|
|
@ -66,14 +66,14 @@ Rectangle {
|
|||
anchors.left: parent.left
|
||||
anchors.leftMargin: page.width / 32
|
||||
anchors.topMargin: page.height / 48
|
||||
spacing: elementSpacing
|
||||
spacing: page.elementSpacing
|
||||
|
||||
//! [0]
|
||||
Rectangle {
|
||||
id: green
|
||||
color: "#80c342"
|
||||
width: 100 * ratio
|
||||
height: 100 * ratio
|
||||
width: 100 * page.ratio
|
||||
height: 100 * page.ratio
|
||||
|
||||
Text {
|
||||
anchors.left: parent.right
|
||||
|
@ -95,8 +95,8 @@ Rectangle {
|
|||
Rectangle {
|
||||
id: blue
|
||||
color: "#14aaff"
|
||||
width: 100 * ratio
|
||||
height: 100 * ratio
|
||||
width: 100 * page.ratio
|
||||
height: 100 * page.ratio
|
||||
|
||||
Text {
|
||||
anchors.left: parent.right
|
||||
|
@ -117,8 +117,8 @@ Rectangle {
|
|||
Rectangle {
|
||||
id: purple
|
||||
color: "#6400aa"
|
||||
width: 100 * ratio
|
||||
height: 100 * ratio
|
||||
width: 100 * page.ratio
|
||||
height: 100 * page.ratio
|
||||
|
||||
Text {
|
||||
anchors.left: parent.right
|
||||
|
@ -140,8 +140,8 @@ Rectangle {
|
|||
Rectangle {
|
||||
id: hidingRect
|
||||
color: "#006325"
|
||||
width: 100 * ratio
|
||||
height: 100 * ratio
|
||||
width: 100 * page.ratio
|
||||
height: 100 * page.ratio
|
||||
visible: false
|
||||
|
||||
Text {
|
||||
|
|
|
@ -55,7 +55,7 @@ Item {
|
|||
interval: 2000
|
||||
running: true
|
||||
repeat: true
|
||||
onTriggered: effectiveOpacity = (effectiveOpacity == 1.0 ? 0.0 : 1.0);
|
||||
onTriggered: page.effectiveOpacity = (page.effectiveOpacity == 1.0 ? 0.0 : 1.0);
|
||||
}
|
||||
|
||||
Column {
|
||||
|
@ -65,7 +65,7 @@ Item {
|
|||
top: parent.top
|
||||
topMargin: page.height / 48
|
||||
}
|
||||
spacing: elementSpacing
|
||||
spacing: page.elementSpacing
|
||||
|
||||
populate: Transition {
|
||||
NumberAnimation { properties: "x,y"; from: 200; duration: 100; easing.type: Easing.OutBounce }
|
||||
|
@ -77,32 +77,32 @@ Item {
|
|||
NumberAnimation { properties: "y"; easing.type: Easing.OutBounce }
|
||||
}
|
||||
|
||||
Rectangle { color: "#80c342"; width: bigSize; height: smallSize }
|
||||
Rectangle { color: "#80c342"; width: page.bigSize; height: page.smallSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenV1
|
||||
visible: opacity != 0
|
||||
width: bigSize; height: smallSize
|
||||
width: page.bigSize; height: page.smallSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#14aaff"; width: bigSize; height: smallSize }
|
||||
Rectangle { color: "#14aaff"; width: page.bigSize; height: page.smallSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenV2
|
||||
visible: opacity != 0
|
||||
width: bigSize; height: smallSize
|
||||
width: page.bigSize; height: page.smallSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#6400aa"; width: bigSize; height: smallSize }
|
||||
Rectangle { color: "#80c342"; width: bigSize; height: smallSize }
|
||||
Rectangle { color: "#6400aa"; width: page.bigSize; height: page.smallSize }
|
||||
Rectangle { color: "#80c342"; width: page.bigSize; height: page.smallSize }
|
||||
}
|
||||
|
||||
Row {
|
||||
|
@ -112,7 +112,7 @@ Item {
|
|||
bottom: page.bottom
|
||||
bottomMargin: page.height / 48
|
||||
}
|
||||
spacing: elementSpacing
|
||||
spacing: page.elementSpacing
|
||||
|
||||
populate: Transition {
|
||||
NumberAnimation { properties: "x,y"; from: 200; duration: 100; easing.type: Easing.OutBounce }
|
||||
|
@ -124,40 +124,40 @@ Item {
|
|||
NumberAnimation { properties: "x"; easing.type: Easing.OutBounce }
|
||||
}
|
||||
|
||||
Rectangle { color: "#80c342"; width: smallSize; height: bigSize }
|
||||
Rectangle { color: "#80c342"; width: page.smallSize; height: page.bigSize }
|
||||
|
||||
Rectangle {
|
||||
id: blueH1
|
||||
visible: opacity != 0
|
||||
width: smallSize; height: bigSize
|
||||
width: page.smallSize; height: page.bigSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#14aaff"; width: smallSize; height: bigSize }
|
||||
Rectangle { color: "#14aaff"; width: page.smallSize; height: page.bigSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenH2
|
||||
visible: opacity != 0
|
||||
width: smallSize; height: bigSize
|
||||
width: page.smallSize; height: page.bigSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#6400aa"; width: smallSize; height: bigSize }
|
||||
Rectangle { color: "#80c342"; width: smallSize; height: bigSize }
|
||||
Rectangle { color: "#6400aa"; width: page.smallSize; height: page.bigSize }
|
||||
Rectangle { color: "#80c342"; width: page.smallSize; height: page.bigSize }
|
||||
}
|
||||
|
||||
Grid {
|
||||
anchors.top: parent.top
|
||||
anchors.topMargin: page.height / 48
|
||||
anchors.left: flow.left
|
||||
anchors.left: flowItem.left
|
||||
columns: 3
|
||||
spacing: elementSpacing
|
||||
spacing: page.elementSpacing
|
||||
|
||||
populate: Transition {
|
||||
NumberAnimation { properties: "x,y"; from: 200; duration: 100; easing.type: Easing.OutBounce }
|
||||
|
@ -169,55 +169,55 @@ Item {
|
|||
NumberAnimation { properties: "x,y"; easing.type: Easing.OutBounce }
|
||||
}
|
||||
|
||||
Rectangle { color: "#80c342"; width: smallSize; height: smallSize }
|
||||
Rectangle { color: "#80c342"; width: page.smallSize; height: page.smallSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenG1
|
||||
visible: opacity != 0
|
||||
width: smallSize; height: smallSize
|
||||
width: page.smallSize; height: page.smallSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#14aaff"; width: smallSize; height: smallSize }
|
||||
Rectangle { color: "#14aaff"; width: page.smallSize; height: page.smallSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenG2
|
||||
visible: opacity != 0
|
||||
width: smallSize; height: smallSize
|
||||
width: page.smallSize; height:page. smallSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#6400aa"; width: smallSize; height: smallSize }
|
||||
Rectangle { color: "#6400aa"; width: page.smallSize; height: page.smallSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenG3
|
||||
visible: opacity != 0
|
||||
width: smallSize; height: smallSize
|
||||
width: page.smallSize; height: page.smallSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#80c342"; width: smallSize; height: smallSize }
|
||||
Rectangle { color: "#14aaff"; width: smallSize; height: smallSize }
|
||||
Rectangle { color: "#6400aa"; width: smallSize; height: smallSize }
|
||||
Rectangle { color: "#80c342"; width:page. smallSize; height: page.smallSize }
|
||||
Rectangle { color: "#14aaff"; width: smallSize; height: page.smallSize }
|
||||
Rectangle { color: "#6400aa"; width: page.page.smallSize; height: page.smallSize }
|
||||
}
|
||||
|
||||
Flow {
|
||||
id: flow
|
||||
id: flowItem
|
||||
|
||||
anchors.right: page.right
|
||||
anchors.rightMargin: page.width / 32
|
||||
y: 2 * bigSize
|
||||
width: 1.8 * bigSize
|
||||
spacing: elementSpacing
|
||||
y: 2 * page.bigSize
|
||||
width: 1.8 * page.bigSize
|
||||
spacing: page.elementSpacing
|
||||
|
||||
//! [move]
|
||||
move: Transition {
|
||||
|
@ -237,42 +237,42 @@ Item {
|
|||
}
|
||||
//! [populate]
|
||||
|
||||
Rectangle { color: "#80c342"; width: smallSize; height: smallSize }
|
||||
Rectangle { color: "#80c342"; width: page.smallSize; height: page.smallSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenF1
|
||||
visible: opacity != 0
|
||||
width: 0.6 * bigSize; height: smallSize
|
||||
width: 0.6 * page.bigSize; height: page.smallSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#14aaff"; width: 0.3 * bigSize; height: smallSize }
|
||||
Rectangle { color: "#14aaff"; width: 0.3 * page.bigSize; height: page.smallSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenF2
|
||||
visible: opacity != 0
|
||||
width: 0.6 * bigSize; height: smallSize
|
||||
width: 0.6 * page.bigSize; height: page.smallSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#6400aa"; width: smallSize; height: smallSize }
|
||||
Rectangle { color: "#6400aa"; width: page.smallSize; height: page.smallSize }
|
||||
|
||||
Rectangle {
|
||||
id: greenF3
|
||||
visible: opacity != 0
|
||||
width: 0.4 * bigSize; height: smallSize
|
||||
width: 0.4 * page.bigSize; height: page.smallSize
|
||||
color: "#006325"
|
||||
border.color: "transparent"
|
||||
Behavior on opacity { NumberAnimation {} }
|
||||
opacity: effectiveOpacity
|
||||
opacity: page.effectiveOpacity
|
||||
}
|
||||
|
||||
Rectangle { color: "#80c342"; width: 0.8 * bigSize; height: smallSize }
|
||||
Rectangle { color: "#80c342"; width: 0.8 * page.bigSize; height: page.smallSize }
|
||||
}
|
||||
}
|
||||
|
|
|
@ -42,12 +42,10 @@
|
|||
#include <QQuickItem>
|
||||
#include <QQuickWindow>
|
||||
#include <QSGRendererInterface>
|
||||
#include <QFile>
|
||||
|
||||
#if QT_CONFIG(d3d12)
|
||||
|
||||
#include "vs_shader.hlslh"
|
||||
#include "ps_shader.hlslh"
|
||||
|
||||
D3D12RenderNode::D3D12RenderNode(QQuickItem *item)
|
||||
: m_item(item)
|
||||
{
|
||||
|
@ -78,7 +76,7 @@ void D3D12RenderNode::releaseResources()
|
|||
void D3D12RenderNode::init()
|
||||
{
|
||||
QSGRendererInterface *rif = m_item->window()->rendererInterface();
|
||||
m_device = static_cast<ID3D12Device *>(rif->getResource(m_item->window(), QSGRendererInterface::Device));
|
||||
m_device = static_cast<ID3D12Device *>(rif->getResource(m_item->window(), QSGRendererInterface::DeviceResource));
|
||||
Q_ASSERT(m_device);
|
||||
|
||||
D3D12_ROOT_PARAMETER rootParameter;
|
||||
|
@ -111,12 +109,25 @@ void D3D12RenderNode::init()
|
|||
{ "COLOR", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 8, D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA, 0 }
|
||||
};
|
||||
|
||||
QFile f(QStringLiteral(":/scenegraph/rendernode/shader_vert.cso"));
|
||||
if (!f.open(QIODevice::ReadOnly)) {
|
||||
qWarning("Failed to open file with vertex shader bytecode");
|
||||
return;
|
||||
}
|
||||
QByteArray vshader_cso = f.readAll();
|
||||
f.close();
|
||||
f.setFileName(QStringLiteral(":/scenegraph/rendernode/shader_frag.cso"));
|
||||
if (!f.open(QIODevice::ReadOnly)) {
|
||||
qWarning("Failed to open file with fragment shader bytecode");
|
||||
return;
|
||||
}
|
||||
QByteArray fshader_cso = f.readAll();
|
||||
D3D12_SHADER_BYTECODE vshader;
|
||||
vshader.pShaderBytecode = g_VS_Simple;
|
||||
vshader.BytecodeLength = sizeof(g_VS_Simple);
|
||||
vshader.pShaderBytecode = vshader_cso.constData();
|
||||
vshader.BytecodeLength = vshader_cso.size();
|
||||
D3D12_SHADER_BYTECODE pshader;
|
||||
pshader.pShaderBytecode = g_PS_Simple;
|
||||
pshader.BytecodeLength = sizeof(g_PS_Simple);
|
||||
pshader.pShaderBytecode = fshader_cso.constData();
|
||||
pshader.BytecodeLength = fshader_cso.size();
|
||||
|
||||
D3D12_RASTERIZER_DESC rastDesc = {};
|
||||
rastDesc.FillMode = D3D12_FILL_MODE_SOLID;
|
||||
|
@ -235,7 +246,8 @@ void D3D12RenderNode::render(const RenderState *state)
|
|||
init();
|
||||
|
||||
QSGRendererInterface *rif = m_item->window()->rendererInterface();
|
||||
ID3D12GraphicsCommandList *commandList = static_cast<ID3D12GraphicsCommandList *>(rif->getResource(m_item->window(), QSGRendererInterface::CommandList));
|
||||
ID3D12GraphicsCommandList *commandList = static_cast<ID3D12GraphicsCommandList *>(
|
||||
rif->getResource(m_item->window(), QSGRendererInterface::CommandListResource));
|
||||
Q_ASSERT(commandList);
|
||||
|
||||
const int msize = 16 * sizeof(float);
|
||||
|
|
|
@ -15,24 +15,10 @@ target.path = $$[QT_INSTALL_EXAMPLES]/quick/scenegraph/rendernode
|
|||
INSTALLS += target
|
||||
|
||||
OTHER_FILES += \
|
||||
main.qml \
|
||||
shader.hlsl
|
||||
main.qml
|
||||
|
||||
qtConfig(d3d12) {
|
||||
HEADERS += d3d12renderer.h
|
||||
SOURCES += d3d12renderer.cpp
|
||||
LIBS += -ld3d12
|
||||
|
||||
VSPS = shader.hlsl
|
||||
vshader.input = VSPS
|
||||
vshader.header = vs_shader.hlslh
|
||||
vshader.entry = VS_Simple
|
||||
vshader.type = vs_5_0
|
||||
pshader.input = VSPS
|
||||
pshader.header = ps_shader.hlslh
|
||||
pshader.entry = PS_Simple
|
||||
pshader.type = ps_5_0
|
||||
|
||||
HLSL_SHADERS = vshader pshader
|
||||
load(hlsl_bytecode_header)
|
||||
}
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
<RCC>
|
||||
<qresource prefix="/scenegraph/rendernode">
|
||||
<file>main.qml</file>
|
||||
<file>shader_vert.cso</file>
|
||||
<file>shader_frag.cso</file>
|
||||
</qresource>
|
||||
</RCC>
|
||||
|
|
Binary file not shown.
Binary file not shown.
|
@ -61,7 +61,7 @@ void SoftwareRenderNode::releaseResources()
|
|||
void SoftwareRenderNode::render(const RenderState *renderState)
|
||||
{
|
||||
QSGRendererInterface *rif = m_item->window()->rendererInterface();
|
||||
QPainter *p = static_cast<QPainter *>(rif->getResource(m_item->window(), QSGRendererInterface::Painter));
|
||||
QPainter *p = static_cast<QPainter *>(rif->getResource(m_item->window(), QSGRendererInterface::PainterResource));
|
||||
Q_ASSERT(p);
|
||||
|
||||
p->setTransform(matrix()->toTransform());
|
||||
|
|
|
@ -44,6 +44,7 @@
|
|||
#include <QQuickView> //Not using QQmlApplicationEngine because many examples don't have a Window{}
|
||||
#define DECLARATIVE_EXAMPLE_MAIN(NAME) int main(int argc, char* argv[]) \
|
||||
{\
|
||||
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);\
|
||||
QGuiApplication app(argc,argv);\
|
||||
app.setOrganizationName("QtProject");\
|
||||
app.setOrganizationDomain("qt-project.org");\
|
||||
|
|
|
@ -221,7 +221,7 @@ Item {
|
|||
\qmlproperty string TestCase::name
|
||||
|
||||
This property defines the name of the test case for result reporting.
|
||||
The default is the empty string.
|
||||
The default value is an empty string.
|
||||
|
||||
\code
|
||||
TestCase {
|
||||
|
@ -835,7 +835,7 @@ Item {
|
|||
\c{QEXPECT_FAIL(tag, message, Abort)} in C++.
|
||||
|
||||
If the test is not data-driven, then \a tag must be set to
|
||||
the empty string.
|
||||
an empty string.
|
||||
|
||||
\sa expectFailContinue()
|
||||
*/
|
||||
|
@ -861,7 +861,7 @@ Item {
|
|||
\c{QEXPECT_FAIL(tag, message, Continue)} in C++.
|
||||
|
||||
If the test is not data-driven, then \a tag must be set to
|
||||
the empty string.
|
||||
an empty string.
|
||||
|
||||
\sa expectFail()
|
||||
*/
|
||||
|
|
|
@ -55,8 +55,12 @@ Module {
|
|||
name: "QQuickWindow"
|
||||
defaultProperty: "data"
|
||||
prototype: "QWindow"
|
||||
exports: ["QtQuick.Window/Window 2.0"]
|
||||
exportMetaObjectRevisions: [0]
|
||||
exports: [
|
||||
"QtQuick.Window/Window 2.0",
|
||||
"QtQuick.Window/Window 2.1",
|
||||
"QtQuick.Window/Window 2.2"
|
||||
]
|
||||
exportMetaObjectRevisions: [0, 1, 2]
|
||||
Enum {
|
||||
name: "SceneGraphError"
|
||||
values: {
|
||||
|
|
|
@ -1292,14 +1292,16 @@ void QQuickImageParticle::finishBuildParticleNodes(QSGNode** node)
|
|||
// OS X 10.8.3 introduced a bug in the AMD drivers, for at least the 2011 macbook pros,
|
||||
// causing point sprites who read gl_PointCoord in the frag shader to come out as
|
||||
// green-red blobs.
|
||||
if (perfLevel < Deformable && strstr((char *) glGetString(GL_VENDOR), "ATI")) {
|
||||
const GLubyte *glVendor = QOpenGLContext::currentContext()->functions()->glGetString(GL_VENDOR);
|
||||
if (perfLevel < Deformable && glVendor && strstr((char *) glVendor, "ATI")) {
|
||||
perfLevel = Deformable;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef Q_OS_LINUX
|
||||
// Nouveau drivers can potentially freeze a machine entirely when taking the point-sprite path.
|
||||
if (perfLevel < Deformable && strstr((const char *) glGetString(GL_VENDOR), "nouveau"))
|
||||
const GLubyte *glVendor = QOpenGLContext::currentContext()->functions()->glGetString(GL_VENDOR);
|
||||
if (perfLevel < Deformable && glVendor && strstr((const char *) glVendor, "nouveau"))
|
||||
perfLevel = Deformable;
|
||||
#endif
|
||||
|
||||
|
|
|
@ -3236,11 +3236,11 @@ void QSGD3D12EnginePrivate::DeviceLossTester::killDevice()
|
|||
void *QSGD3D12EnginePrivate::getResource(QSGRendererInterface::Resource resource) const
|
||||
{
|
||||
switch (resource) {
|
||||
case QSGRendererInterface::Device:
|
||||
case QSGRendererInterface::DeviceResource:
|
||||
return device;
|
||||
case QSGRendererInterface::CommandQueue:
|
||||
case QSGRendererInterface::CommandQueueResource:
|
||||
return commandQueue.Get();
|
||||
case QSGRendererInterface::CommandList:
|
||||
case QSGRendererInterface::CommandListResource:
|
||||
return commandList;
|
||||
default:
|
||||
break;
|
||||
|
|
|
@ -39,10 +39,6 @@
|
|||
|
||||
#include "qsgd3d12publicnodes_p.h"
|
||||
|
||||
// for rebuildGeometry
|
||||
#include <private/qsgdefaultninepatchnode_p.h>
|
||||
#include <private/qsgdefaultimagenode_p.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
QSGD3D12RectangleNode::QSGD3D12RectangleNode()
|
||||
|
@ -138,7 +134,7 @@ void QSGD3D12ImageNode::setRect(const QRectF &r)
|
|||
return;
|
||||
|
||||
m_rect = r;
|
||||
QSGDefaultImageNode::rebuildGeometry(&m_geometry, texture(), m_rect, m_sourceRect, m_texCoordMode);
|
||||
QSGImageNode::rebuildGeometry(&m_geometry, texture(), m_rect, m_sourceRect, m_texCoordMode);
|
||||
markDirty(DirtyGeometry);
|
||||
}
|
||||
|
||||
|
@ -153,7 +149,7 @@ void QSGD3D12ImageNode::setSourceRect(const QRectF &r)
|
|||
return;
|
||||
|
||||
m_sourceRect = r;
|
||||
QSGDefaultImageNode::rebuildGeometry(&m_geometry, texture(), m_rect, m_sourceRect, m_texCoordMode);
|
||||
QSGImageNode::rebuildGeometry(&m_geometry, texture(), m_rect, m_sourceRect, m_texCoordMode);
|
||||
markDirty(DirtyGeometry);
|
||||
}
|
||||
|
||||
|
@ -170,7 +166,7 @@ void QSGD3D12ImageNode::setTexture(QSGTexture *texture)
|
|||
delete m_material.texture();
|
||||
|
||||
m_material.setTexture(texture);
|
||||
QSGDefaultImageNode::rebuildGeometry(&m_geometry, texture, m_rect, m_sourceRect, m_texCoordMode);
|
||||
QSGImageNode::rebuildGeometry(&m_geometry, texture, m_rect, m_sourceRect, m_texCoordMode);
|
||||
|
||||
DirtyState dirty = DirtyMaterial;
|
||||
const bool wasAtlas = m_isAtlasTexture;
|
||||
|
@ -192,7 +188,7 @@ void QSGD3D12ImageNode::setTextureCoordinatesTransform(TextureCoordinatesTransfo
|
|||
return;
|
||||
|
||||
m_texCoordMode = mode;
|
||||
QSGDefaultImageNode::rebuildGeometry(&m_geometry, texture(), m_rect, m_sourceRect, m_texCoordMode);
|
||||
QSGImageNode::rebuildGeometry(&m_geometry, texture(), m_rect, m_sourceRect, m_texCoordMode);
|
||||
markDirty(DirtyMaterial);
|
||||
}
|
||||
|
||||
|
@ -247,7 +243,7 @@ void QSGD3D12NinePatchNode::setPadding(qreal left, qreal top, qreal right, qreal
|
|||
|
||||
void QSGD3D12NinePatchNode::update()
|
||||
{
|
||||
QSGDefaultNinePatchNode::rebuildGeometry(m_material.texture(), &m_geometry, m_padding, m_bounds, m_devicePixelRatio);
|
||||
QSGNinePatchNode::rebuildGeometry(m_material.texture(), &m_geometry, m_padding, m_bounds, m_devicePixelRatio);
|
||||
markDirty(QSGNode::DirtyGeometry | QSGNode::DirtyMaterial);
|
||||
}
|
||||
|
||||
|
|
|
@ -2692,6 +2692,7 @@ void convertConst(Const *c, Type targetType)
|
|||
case UndefinedType:
|
||||
c->value = qt_qnan();
|
||||
c->type = targetType;
|
||||
break;
|
||||
default:
|
||||
Q_UNIMPLEMENTED();
|
||||
Q_ASSERT(!"Unimplemented!");
|
||||
|
|
|
@ -131,7 +131,8 @@ public:
|
|||
Value *jsAlloca(int nValues) {
|
||||
Value *ptr = jsStackTop;
|
||||
jsStackTop = ptr + nValues;
|
||||
memset(ptr, 0, nValues*sizeof(Value));
|
||||
for (int i = 0; i < nValues; ++i)
|
||||
ptr[i] = Primitive::undefinedValue();
|
||||
return ptr;
|
||||
}
|
||||
|
||||
|
|
|
@ -107,11 +107,18 @@ inline void qYouForgotTheQ_MANAGED_Macro(T1, T2) {}
|
|||
(classname::func == QV4::Managed::func ? 0 : classname::func)
|
||||
|
||||
// Q_VTABLE_FUNCTION triggers a bogus tautological-compare warning in GCC6+
|
||||
#if defined(Q_CC_GNU) && Q_CC_GNU >= 600
|
||||
#if (defined(Q_CC_GNU) && Q_CC_GNU >= 600)
|
||||
#define QT_WARNING_SUPPRESS_GCC_TAUTOLOGICAL_COMPARE_ON \
|
||||
QT_WARNING_PUSH; \
|
||||
QT_WARNING_DISABLE_GCC("-Wtautological-compare")
|
||||
|
||||
#define QT_WARNING_SUPPRESS_GCC_TAUTOLOGICAL_COMPARE_OFF \
|
||||
;QT_WARNING_POP
|
||||
#elif defined(Q_CC_CLANG) && Q_CC_CLANG >= 306
|
||||
#define QT_WARNING_SUPPRESS_GCC_TAUTOLOGICAL_COMPARE_ON \
|
||||
QT_WARNING_PUSH; \
|
||||
QT_WARNING_DISABLE_CLANG("-Wtautological-compare")
|
||||
|
||||
#define QT_WARNING_SUPPRESS_GCC_TAUTOLOGICAL_COMPARE_OFF \
|
||||
;QT_WARNING_POP
|
||||
#else
|
||||
|
|
|
@ -58,8 +58,6 @@
|
|||
#include "qv4value_p.h"
|
||||
#include "qv4internalclass_p.h"
|
||||
|
||||
#include <type_traits>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
||||
|
@ -147,7 +145,7 @@ struct ObjectVTable
|
|||
#define DEFINE_OBJECT_VTABLE_BASE(classname) \
|
||||
const QV4::ObjectVTable classname::static_vtbl = \
|
||||
{ \
|
||||
DEFINE_MANAGED_VTABLE_INT(classname, (std::is_same<classname::SuperClass, Object>::value) ? Q_NULLPTR : &classname::SuperClass::static_vtbl.vTable), \
|
||||
DEFINE_MANAGED_VTABLE_INT(classname, (std::is_same<classname::SuperClass, Object>::value) ? nullptr : &classname::SuperClass::static_vtbl.vTable), \
|
||||
call, \
|
||||
construct, \
|
||||
get, \
|
||||
|
|
|
@ -46,6 +46,7 @@
|
|||
#include "qv4stringobject_p.h"
|
||||
#endif
|
||||
#include <QtCore/QHash>
|
||||
#include <QtCore/private/qnumeric_p.h>
|
||||
|
||||
using namespace QV4;
|
||||
|
||||
|
|
|
@ -1100,6 +1100,13 @@ QQmlPropertyCache::property(QJSEngine *engine, QObject *obj, const QStringRef &n
|
|||
return qQmlPropertyCacheProperty<const QStringRef &>(engine, obj, name, context, local);
|
||||
}
|
||||
|
||||
QQmlPropertyData *
|
||||
QQmlPropertyCache::property(QJSEngine *engine, QObject *obj, const QLatin1String &name,
|
||||
QQmlContextData *context, QQmlPropertyData &local)
|
||||
{
|
||||
return qQmlPropertyCacheProperty<const QLatin1String &>(engine, obj, name, context, local);
|
||||
}
|
||||
|
||||
// these two functions are copied from qmetaobject.cpp
|
||||
static inline const QMetaObjectPrivate *priv(const uint* data)
|
||||
{ return reinterpret_cast<const QMetaObjectPrivate*>(data); }
|
||||
|
|
|
@ -408,6 +408,8 @@ public:
|
|||
|
||||
static QQmlPropertyData *property(QJSEngine *, QObject *, const QStringRef &,
|
||||
QQmlContextData *, QQmlPropertyData &);
|
||||
static QQmlPropertyData *property(QJSEngine *, QObject *, const QLatin1String &,
|
||||
QQmlContextData *, QQmlPropertyData &);
|
||||
static QQmlPropertyData *property(QJSEngine *, QObject *, const QV4::String *,
|
||||
QQmlContextData *, QQmlPropertyData &);
|
||||
|
||||
|
|
|
@ -165,9 +165,9 @@ private:
|
|||
void QQmlConnections::setTarget(QObject *obj)
|
||||
{
|
||||
Q_D(QQmlConnections);
|
||||
d->targetSet = true; // even if setting to 0, it is *set*
|
||||
if (d->target == obj)
|
||||
if (d->targetSet && d->target == obj)
|
||||
return;
|
||||
d->targetSet = true; // even if setting to 0, it is *set*
|
||||
foreach (QQmlBoundSignal *s, d->boundsignals) {
|
||||
// It is possible that target is being changed due to one of our signal
|
||||
// handlers -> use deleteLater().
|
||||
|
|
|
@ -183,6 +183,7 @@ namespace QtQuickTest
|
|||
case MouseMove:
|
||||
// with move event the button is NoButton, but 'buttons' holds the currently pressed buttons
|
||||
me = QMouseEvent(QEvent::MouseMove, pos, window->mapToGlobal(pos), Qt::NoButton, button, stateKey);
|
||||
me.setTimestamp(++lastMouseTimestamp);
|
||||
break;
|
||||
default:
|
||||
QTEST_ASSERT(false);
|
||||
|
|
|
@ -617,74 +617,75 @@ void QQuickAnchorsPrivate::updateVerticalAnchors()
|
|||
if (fill || centerIn || !isItemComplete())
|
||||
return;
|
||||
|
||||
if (updatingVerticalAnchor < 2) {
|
||||
++updatingVerticalAnchor;
|
||||
if (usedAnchors & QQuickAnchors::TopAnchor) {
|
||||
//Handle stretching
|
||||
bool invalid = true;
|
||||
qreal height = 0.0;
|
||||
if (usedAnchors & QQuickAnchors::BottomAnchor) {
|
||||
invalid = calcStretch(topAnchorItem, topAnchorLine,
|
||||
bottomAnchorItem, bottomAnchorLine,
|
||||
topMargin, -bottomMargin, QQuickAnchors::TopAnchor, height);
|
||||
} else if (usedAnchors & QQuickAnchors::VCenterAnchor) {
|
||||
invalid = calcStretch(topAnchorItem, topAnchorLine,
|
||||
vCenterAnchorItem, vCenterAnchorLine,
|
||||
topMargin, vCenterOffset, QQuickAnchors::TopAnchor, height);
|
||||
height *= 2;
|
||||
}
|
||||
if (!invalid)
|
||||
setItemHeight(height);
|
||||
|
||||
//Handle top
|
||||
if (topAnchorItem == readParentItem(item)) {
|
||||
setItemY(adjustedPosition(topAnchorItem, topAnchorLine) + topMargin);
|
||||
} else if (readParentItem(topAnchorItem) == readParentItem(item)) {
|
||||
setItemY(position(topAnchorItem, topAnchorLine) + topMargin);
|
||||
}
|
||||
} else if (usedAnchors & QQuickAnchors::BottomAnchor) {
|
||||
//Handle stretching (top + bottom case is handled above)
|
||||
if (usedAnchors & QQuickAnchors::VCenterAnchor) {
|
||||
qreal height = 0.0;
|
||||
bool invalid = calcStretch(vCenterAnchorItem, vCenterAnchorLine,
|
||||
bottomAnchorItem, bottomAnchorLine,
|
||||
vCenterOffset, -bottomMargin, QQuickAnchors::TopAnchor,
|
||||
height);
|
||||
if (!invalid)
|
||||
setItemHeight(height*2);
|
||||
}
|
||||
|
||||
//Handle bottom
|
||||
if (bottomAnchorItem == readParentItem(item)) {
|
||||
setItemY(adjustedPosition(bottomAnchorItem, bottomAnchorLine) - readHeight(item) - bottomMargin);
|
||||
} else if (readParentItem(bottomAnchorItem) == readParentItem(item)) {
|
||||
setItemY(position(bottomAnchorItem, bottomAnchorLine) - readHeight(item) - bottomMargin);
|
||||
}
|
||||
} else if (usedAnchors & QQuickAnchors::VCenterAnchor) {
|
||||
//(stetching handled above)
|
||||
|
||||
//Handle vCenter
|
||||
if (vCenterAnchorItem == readParentItem(item)) {
|
||||
setItemY(adjustedPosition(vCenterAnchorItem, vCenterAnchorLine)
|
||||
- vcenter(item) + vCenterOffset);
|
||||
} else if (readParentItem(vCenterAnchorItem) == readParentItem(item)) {
|
||||
setItemY(position(vCenterAnchorItem, vCenterAnchorLine) - vcenter(item) + vCenterOffset);
|
||||
}
|
||||
} else if (usedAnchors & QQuickAnchors::BaselineAnchor) {
|
||||
//Handle baseline
|
||||
if (baselineAnchorItem == readParentItem(item)) {
|
||||
setItemY(adjustedPosition(baselineAnchorItem, baselineAnchorLine)
|
||||
- readBaselineOffset(item) + baselineOffset);
|
||||
} else if (readParentItem(baselineAnchorItem) == readParentItem(item)) {
|
||||
setItemY(position(baselineAnchorItem, baselineAnchorLine)
|
||||
- readBaselineOffset(item) + baselineOffset);
|
||||
}
|
||||
}
|
||||
--updatingVerticalAnchor;
|
||||
} else {
|
||||
if (Q_UNLIKELY(updatingVerticalAnchor > 1)) {
|
||||
// ### Make this certain :)
|
||||
qmlInfo(item) << QQuickAnchors::tr("Possible anchor loop detected on vertical anchor.");
|
||||
return;
|
||||
}
|
||||
|
||||
++updatingVerticalAnchor;
|
||||
if (usedAnchors & QQuickAnchors::TopAnchor) {
|
||||
//Handle stretching
|
||||
bool invalid = true;
|
||||
qreal height = 0.0;
|
||||
if (usedAnchors & QQuickAnchors::BottomAnchor) {
|
||||
invalid = calcStretch(topAnchorItem, topAnchorLine,
|
||||
bottomAnchorItem, bottomAnchorLine,
|
||||
topMargin, -bottomMargin, QQuickAnchors::TopAnchor, height);
|
||||
} else if (usedAnchors & QQuickAnchors::VCenterAnchor) {
|
||||
invalid = calcStretch(topAnchorItem, topAnchorLine,
|
||||
vCenterAnchorItem, vCenterAnchorLine,
|
||||
topMargin, vCenterOffset, QQuickAnchors::TopAnchor, height);
|
||||
height *= 2;
|
||||
}
|
||||
if (!invalid)
|
||||
setItemHeight(height);
|
||||
|
||||
//Handle top
|
||||
if (topAnchorItem == readParentItem(item)) {
|
||||
setItemY(adjustedPosition(topAnchorItem, topAnchorLine) + topMargin);
|
||||
} else if (readParentItem(topAnchorItem) == readParentItem(item)) {
|
||||
setItemY(position(topAnchorItem, topAnchorLine) + topMargin);
|
||||
}
|
||||
} else if (usedAnchors & QQuickAnchors::BottomAnchor) {
|
||||
//Handle stretching (top + bottom case is handled above)
|
||||
if (usedAnchors & QQuickAnchors::VCenterAnchor) {
|
||||
qreal height = 0.0;
|
||||
bool invalid = calcStretch(vCenterAnchorItem, vCenterAnchorLine,
|
||||
bottomAnchorItem, bottomAnchorLine,
|
||||
vCenterOffset, -bottomMargin, QQuickAnchors::TopAnchor,
|
||||
height);
|
||||
if (!invalid)
|
||||
setItemHeight(height*2);
|
||||
}
|
||||
|
||||
//Handle bottom
|
||||
if (bottomAnchorItem == readParentItem(item)) {
|
||||
setItemY(adjustedPosition(bottomAnchorItem, bottomAnchorLine) - readHeight(item) - bottomMargin);
|
||||
} else if (readParentItem(bottomAnchorItem) == readParentItem(item)) {
|
||||
setItemY(position(bottomAnchorItem, bottomAnchorLine) - readHeight(item) - bottomMargin);
|
||||
}
|
||||
} else if (usedAnchors & QQuickAnchors::VCenterAnchor) {
|
||||
//(stetching handled above)
|
||||
|
||||
//Handle vCenter
|
||||
if (vCenterAnchorItem == readParentItem(item)) {
|
||||
setItemY(adjustedPosition(vCenterAnchorItem, vCenterAnchorLine)
|
||||
- vcenter(item) + vCenterOffset);
|
||||
} else if (readParentItem(vCenterAnchorItem) == readParentItem(item)) {
|
||||
setItemY(position(vCenterAnchorItem, vCenterAnchorLine) - vcenter(item) + vCenterOffset);
|
||||
}
|
||||
} else if (usedAnchors & QQuickAnchors::BaselineAnchor) {
|
||||
//Handle baseline
|
||||
if (baselineAnchorItem == readParentItem(item)) {
|
||||
setItemY(adjustedPosition(baselineAnchorItem, baselineAnchorLine)
|
||||
- readBaselineOffset(item) + baselineOffset);
|
||||
} else if (readParentItem(baselineAnchorItem) == readParentItem(item)) {
|
||||
setItemY(position(baselineAnchorItem, baselineAnchorLine)
|
||||
- readBaselineOffset(item) + baselineOffset);
|
||||
}
|
||||
}
|
||||
--updatingVerticalAnchor;
|
||||
}
|
||||
|
||||
static inline QQuickAnchors::Anchor reverseAnchorLine(QQuickAnchors::Anchor anchorLine)
|
||||
|
|
|
@ -113,12 +113,12 @@ public:
|
|||
, inDestructor(false)
|
||||
, baselineAnchorLine(QQuickAnchors::InvalidAnchor)
|
||||
, centerAligned(true)
|
||||
, usedAnchors(QQuickAnchors::InvalidAnchor)
|
||||
, componentComplete(true)
|
||||
, updatingFill(0)
|
||||
, updatingCenterIn(0)
|
||||
, updatingHorizontalAnchor(0)
|
||||
, updatingVerticalAnchor(0)
|
||||
, componentComplete(true)
|
||||
, usedAnchors(QQuickAnchors::InvalidAnchor)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -198,13 +198,16 @@ public:
|
|||
uint inDestructor : 1;
|
||||
QQuickAnchors::Anchor baselineAnchorLine : 7;
|
||||
uint centerAligned : 1;
|
||||
uint updatingFill : 2;
|
||||
uint updatingCenterIn : 2;
|
||||
uint updatingHorizontalAnchor : 2;
|
||||
uint updatingVerticalAnchor : 2;
|
||||
|
||||
uint componentComplete : 1;
|
||||
uint usedAnchors : 7; // QQuickAnchors::Anchors
|
||||
uint componentComplete : 1;
|
||||
|
||||
// Instead of using a mostly empty bit field, we can stretch the following fields up to be full
|
||||
// bytes. The advantage is that incrementing/decrementing does not need any combining ands/ors.
|
||||
qint8 updatingFill;
|
||||
qint8 updatingCenterIn;
|
||||
qint8 updatingHorizontalAnchor;
|
||||
qint8 updatingVerticalAnchor;
|
||||
|
||||
|
||||
static inline QQuickAnchorsPrivate *get(QQuickAnchors *o) {
|
||||
return static_cast<QQuickAnchorsPrivate *>(QObjectPrivate::get(o));
|
||||
|
|
|
@ -2308,29 +2308,31 @@ QQuickItem::~QQuickItem()
|
|||
while (!d->childItems.isEmpty())
|
||||
d->childItems.constFirst()->setParentItem(0);
|
||||
|
||||
const auto listeners = d->changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
QQuickAnchorsPrivate *anchor = change.listener->anchorPrivate();
|
||||
if (anchor)
|
||||
anchor->clearItem(this);
|
||||
}
|
||||
if (!d->changeListeners.isEmpty()) {
|
||||
const auto listeners = d->changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
QQuickAnchorsPrivate *anchor = change.listener->anchorPrivate();
|
||||
if (anchor)
|
||||
anchor->clearItem(this);
|
||||
}
|
||||
|
||||
/*
|
||||
/*
|
||||
update item anchors that depended on us unless they are our child (and will also be destroyed),
|
||||
or our sibling, and our parent is also being destroyed.
|
||||
*/
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
QQuickAnchorsPrivate *anchor = change.listener->anchorPrivate();
|
||||
if (anchor && anchor->item && anchor->item->parentItem() && anchor->item->parentItem() != this)
|
||||
anchor->update();
|
||||
}
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
QQuickAnchorsPrivate *anchor = change.listener->anchorPrivate();
|
||||
if (anchor && anchor->item && anchor->item->parentItem() && anchor->item->parentItem() != this)
|
||||
anchor->update();
|
||||
}
|
||||
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Destroyed)
|
||||
change.listener->itemDestroyed(this);
|
||||
}
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Destroyed)
|
||||
change.listener->itemDestroyed(this);
|
||||
}
|
||||
|
||||
d->changeListeners.clear();
|
||||
d->changeListeners.clear();
|
||||
}
|
||||
|
||||
/*
|
||||
Remove any references our transforms have to us, in case they try to
|
||||
|
@ -2601,7 +2603,7 @@ void QQuickItem::setParentItem(QQuickItem *parentItem)
|
|||
if (parentItem) {
|
||||
QQuickItem *itemAncestor = parentItem;
|
||||
while (itemAncestor != 0) {
|
||||
if (itemAncestor == this) {
|
||||
if (Q_UNLIKELY(itemAncestor == this)) {
|
||||
qWarning() << "QQuickItem::setParentItem: Parent" << parentItem << "is already part of the subtree of" << this;
|
||||
return;
|
||||
}
|
||||
|
@ -3549,10 +3551,12 @@ QQuickAnchors *QQuickItemPrivate::anchors() const
|
|||
void QQuickItemPrivate::siblingOrderChanged()
|
||||
{
|
||||
Q_Q(QQuickItem);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::SiblingOrder) {
|
||||
change.listener->itemSiblingOrderChanged(q);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::SiblingOrder) {
|
||||
change.listener->itemSiblingOrderChanged(q);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -3654,20 +3658,18 @@ void QQuickItem::geometryChanged(const QRectF &newGeometry, const QRectF &oldGeo
|
|||
QQuickAnchorsPrivate::get(d->_anchors)->updateMe();
|
||||
|
||||
QQuickGeometryChange change;
|
||||
QRectF diff(newGeometry.x() - oldGeometry.x(),
|
||||
newGeometry.y() - oldGeometry.y(),
|
||||
newGeometry.width() - oldGeometry.width(),
|
||||
newGeometry.height() - oldGeometry.height());
|
||||
change.setXChange(diff.x() != 0);
|
||||
change.setYChange(diff.y() != 0);
|
||||
change.setWidthChange(diff.width() != 0);
|
||||
change.setHeightChange(diff.height() != 0);
|
||||
change.setXChange(newGeometry.x() != oldGeometry.x());
|
||||
change.setYChange(newGeometry.y() != oldGeometry.y());
|
||||
change.setWidthChange(newGeometry.width() != oldGeometry.width());
|
||||
change.setHeightChange(newGeometry.height() != oldGeometry.height());
|
||||
|
||||
const auto listeners = d->changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &listener : listeners) {
|
||||
if (listener.types & QQuickItemPrivate::Geometry) {
|
||||
if (change.matches(listener.gTypes))
|
||||
listener.listener->itemGeometryChanged(this, change, diff);
|
||||
if (!d->changeListeners.isEmpty()) {
|
||||
const auto listeners = d->changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &listener : listeners) {
|
||||
if (listener.types & QQuickItemPrivate::Geometry) {
|
||||
if (change.matches(listener.gTypes))
|
||||
listener.listener->itemGeometryChanged(this, change, oldGeometry);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4224,12 +4226,14 @@ void QQuickItem::setBaselineOffset(qreal offset)
|
|||
|
||||
d->baselineOffset = offset;
|
||||
|
||||
const auto listeners = d->changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Geometry) {
|
||||
QQuickAnchorsPrivate *anchor = change.listener->anchorPrivate();
|
||||
if (anchor)
|
||||
anchor->updateVerticalAnchors();
|
||||
if (!d->changeListeners.isEmpty()) {
|
||||
const auto listeners = d->changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Geometry) {
|
||||
QQuickAnchorsPrivate *anchor = change.listener->anchorPrivate();
|
||||
if (anchor)
|
||||
anchor->updateVerticalAnchors();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -5977,20 +5981,24 @@ void QQuickItemPrivate::itemChange(QQuickItem::ItemChange change, const QQuickIt
|
|||
switch (change) {
|
||||
case QQuickItem::ItemChildAddedChange: {
|
||||
q->itemChange(change, data);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Children) {
|
||||
change.listener->itemChildAdded(q, data.item);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Children) {
|
||||
change.listener->itemChildAdded(q, data.item);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case QQuickItem::ItemChildRemovedChange: {
|
||||
q->itemChange(change, data);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Children) {
|
||||
change.listener->itemChildRemoved(q, data.item);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Children) {
|
||||
change.listener->itemChildRemoved(q, data.item);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
@ -6000,30 +6008,36 @@ void QQuickItemPrivate::itemChange(QQuickItem::ItemChange change, const QQuickIt
|
|||
break;
|
||||
case QQuickItem::ItemVisibleHasChanged: {
|
||||
q->itemChange(change, data);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Visibility) {
|
||||
change.listener->itemVisibilityChanged(q);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Visibility) {
|
||||
change.listener->itemVisibilityChanged(q);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case QQuickItem::ItemParentHasChanged: {
|
||||
q->itemChange(change, data);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Parent) {
|
||||
change.listener->itemParentChanged(q, data.item);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Parent) {
|
||||
change.listener->itemParentChanged(q, data.item);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case QQuickItem::ItemOpacityHasChanged: {
|
||||
q->itemChange(change, data);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Opacity) {
|
||||
change.listener->itemOpacityChanged(q);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Opacity) {
|
||||
change.listener->itemOpacityChanged(q);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
@ -6033,10 +6047,12 @@ void QQuickItemPrivate::itemChange(QQuickItem::ItemChange change, const QQuickIt
|
|||
break;
|
||||
case QQuickItem::ItemRotationHasChanged: {
|
||||
q->itemChange(change, data);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Rotation) {
|
||||
change.listener->itemRotationChanged(q);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::Rotation) {
|
||||
change.listener->itemRotationChanged(q);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
@ -6395,10 +6411,12 @@ void QQuickItem::resetWidth()
|
|||
void QQuickItemPrivate::implicitWidthChanged()
|
||||
{
|
||||
Q_Q(QQuickItem);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::ImplicitWidth) {
|
||||
change.listener->itemImplicitWidthChanged(q);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::ImplicitWidth) {
|
||||
change.listener->itemImplicitWidthChanged(q);
|
||||
}
|
||||
}
|
||||
}
|
||||
emit q->implicitWidthChanged();
|
||||
|
@ -6559,10 +6577,12 @@ void QQuickItem::resetHeight()
|
|||
void QQuickItemPrivate::implicitHeightChanged()
|
||||
{
|
||||
Q_Q(QQuickItem);
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::ImplicitHeight) {
|
||||
change.listener->itemImplicitHeightChanged(q);
|
||||
if (!changeListeners.isEmpty()) {
|
||||
const auto listeners = changeListeners; // NOTE: intentional copy (QTBUG-54732)
|
||||
for (const QQuickItemPrivate::ChangeListener &change : listeners) {
|
||||
if (change.types & QQuickItemPrivate::ImplicitHeight) {
|
||||
change.listener->itemImplicitHeightChanged(q);
|
||||
}
|
||||
}
|
||||
}
|
||||
emit q->implicitHeightChanged();
|
||||
|
|
|
@ -115,12 +115,14 @@ private:
|
|||
int kind;
|
||||
};
|
||||
|
||||
#define QT_QUICK_NEW_GEOMETRY_CHANGED_HANDLING
|
||||
|
||||
class QQuickItemChangeListener
|
||||
{
|
||||
public:
|
||||
virtual ~QQuickItemChangeListener() {}
|
||||
|
||||
virtual void itemGeometryChanged(QQuickItem *, QQuickGeometryChange, const QRectF & /* diff */) {}
|
||||
virtual void itemGeometryChanged(QQuickItem *, QQuickGeometryChange, const QRectF & /* oldGeometry */) {}
|
||||
virtual void itemSiblingOrderChanged(QQuickItem *) {}
|
||||
virtual void itemVisibilityChanged(QQuickItem *) {}
|
||||
virtual void itemOpacityChanged(QQuickItem *) {}
|
||||
|
|
|
@ -1207,10 +1207,10 @@ void QQuickItemViewPrivate::showVisibleItems() const
|
|||
}
|
||||
|
||||
void QQuickItemViewPrivate::itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change,
|
||||
const QRectF &diff)
|
||||
const QRectF &oldGeometry)
|
||||
{
|
||||
Q_Q(QQuickItemView);
|
||||
QQuickFlickablePrivate::itemGeometryChanged(item, change, diff);
|
||||
QQuickFlickablePrivate::itemGeometryChanged(item, change, oldGeometry);
|
||||
if (!q->isComponentComplete())
|
||||
return;
|
||||
|
||||
|
|
|
@ -131,7 +131,7 @@ public:
|
|||
|
||||
void updateAverage();
|
||||
|
||||
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change, const QRectF &diff) Q_DECL_OVERRIDE;
|
||||
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change, const QRectF &oldGeometry) Q_DECL_OVERRIDE;
|
||||
void fixupPosition() Q_DECL_OVERRIDE;
|
||||
void fixup(AxisData &data, qreal minExtent, qreal maxExtent) Q_DECL_OVERRIDE;
|
||||
bool flick(QQuickItemViewPrivate::AxisData &data, qreal minExtent, qreal maxExtent, qreal vSize,
|
||||
|
@ -1401,11 +1401,11 @@ bool QQuickListViewPrivate::hasStickyFooter() const
|
|||
}
|
||||
|
||||
void QQuickListViewPrivate::itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change,
|
||||
const QRectF &diff)
|
||||
const QRectF &oldGeometry)
|
||||
{
|
||||
Q_Q(QQuickListView);
|
||||
|
||||
QQuickItemViewPrivate::itemGeometryChanged(item, change, diff);
|
||||
QQuickItemViewPrivate::itemGeometryChanged(item, change, oldGeometry);
|
||||
if (!q->isComponentComplete())
|
||||
return;
|
||||
|
||||
|
@ -1426,24 +1426,22 @@ void QQuickListViewPrivate::itemGeometryChanged(QQuickItem *item, QQuickGeometry
|
|||
// position all subsequent items
|
||||
if (visibleItems.count() && item == visibleItems.constFirst()->item) {
|
||||
FxListItemSG *listItem = static_cast<FxListItemSG*>(visibleItems.constFirst());
|
||||
const QRectF oldGeometry(item->x() - diff.x(),
|
||||
item->y() - diff.y(),
|
||||
item->width() - diff.width(),
|
||||
item->height() - diff.height());
|
||||
if (listItem->transitionScheduledOrRunning())
|
||||
return;
|
||||
if (orient == QQuickListView::Vertical) {
|
||||
const qreal oldItemEndPosition = verticalLayoutDirection == QQuickItemView::BottomToTop ? -oldGeometry.y() : oldGeometry.y() + oldGeometry.height();
|
||||
const qreal heightDiff = item->height() - oldGeometry.height();
|
||||
if (verticalLayoutDirection == QQuickListView::TopToBottom && oldItemEndPosition < q->contentY())
|
||||
listItem->setPosition(listItem->position() - diff.height(), true);
|
||||
listItem->setPosition(listItem->position() - heightDiff, true);
|
||||
else if (verticalLayoutDirection == QQuickListView::BottomToTop && oldItemEndPosition > q->contentY())
|
||||
listItem->setPosition(listItem->position() + diff.height(), true);
|
||||
listItem->setPosition(listItem->position() + heightDiff, true);
|
||||
} else {
|
||||
const qreal oldItemEndPosition = q->effectiveLayoutDirection() == Qt::RightToLeft ? -oldGeometry.x() : oldGeometry.x() + oldGeometry.width();
|
||||
const qreal widthDiff = item->width() - oldGeometry.width();
|
||||
if (q->effectiveLayoutDirection() == Qt::LeftToRight && oldItemEndPosition < q->contentX())
|
||||
listItem->setPosition(listItem->position() - diff.width(), true);
|
||||
listItem->setPosition(listItem->position() - widthDiff, true);
|
||||
else if (q->effectiveLayoutDirection() == Qt::RightToLeft && oldItemEndPosition > q->contentX())
|
||||
listItem->setPosition(listItem->position() + diff.width(), true);
|
||||
listItem->setPosition(listItem->position() + widthDiff, true);
|
||||
}
|
||||
}
|
||||
forceLayoutPolish();
|
||||
|
|
|
@ -65,12 +65,12 @@ QQuickLoaderPrivate::~QQuickLoaderPrivate()
|
|||
disposeInitialPropertyValues();
|
||||
}
|
||||
|
||||
void QQuickLoaderPrivate::itemGeometryChanged(QQuickItem *resizeItem, QQuickGeometryChange change
|
||||
, const QRectF &diff)
|
||||
void QQuickLoaderPrivate::itemGeometryChanged(QQuickItem *resizeItem, QQuickGeometryChange change,
|
||||
const QRectF &oldGeometry)
|
||||
{
|
||||
if (resizeItem == item)
|
||||
_q_updateSize(false);
|
||||
QQuickItemChangeListener::itemGeometryChanged(resizeItem, change, diff);
|
||||
QQuickItemChangeListener::itemGeometryChanged(resizeItem, change, oldGeometry);
|
||||
}
|
||||
|
||||
void QQuickLoaderPrivate::itemImplicitWidthChanged(QQuickItem *)
|
||||
|
|
|
@ -84,7 +84,7 @@ public:
|
|||
QQuickLoaderPrivate();
|
||||
~QQuickLoaderPrivate();
|
||||
|
||||
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change, const QRectF &diff) Q_DECL_OVERRIDE;
|
||||
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change, const QRectF &oldGeometry) Q_DECL_OVERRIDE;
|
||||
void itemImplicitWidthChanged(QQuickItem *) Q_DECL_OVERRIDE;
|
||||
void itemImplicitHeightChanged(QQuickItem *) Q_DECL_OVERRIDE;
|
||||
void clear();
|
||||
|
|
|
@ -892,7 +892,7 @@ void QQuickTextEdit::setWrapMode(WrapMode mode)
|
|||
/*!
|
||||
\qmlproperty int QtQuick::TextEdit::lineCount
|
||||
|
||||
Returns the total number of lines in the textEdit item.
|
||||
Returns the total number of lines in the TextEdit item.
|
||||
*/
|
||||
int QQuickTextEdit::lineCount() const
|
||||
{
|
||||
|
@ -2350,6 +2350,7 @@ void QQuickTextEdit::moveCursorDelegate()
|
|||
QRectF cursorRect = cursorRectangle();
|
||||
d->cursorItem->setX(cursorRect.x());
|
||||
d->cursorItem->setY(cursorRect.y());
|
||||
d->cursorItem->setHeight(cursorRect.height());
|
||||
}
|
||||
|
||||
void QQuickTextEdit::updateSelection()
|
||||
|
|
|
@ -160,18 +160,14 @@ void QQuickTextNode::addImage(const QRectF &rect, const QImage &image)
|
|||
QSGRenderContext *sg = QQuickItemPrivate::get(m_ownerElement)->sceneGraphRenderContext();
|
||||
QSGInternalImageNode *node = sg->sceneGraphContext()->createInternalImageNode();
|
||||
QSGTexture *texture = sg->createTexture(image);
|
||||
if (m_ownerElement->smooth()) {
|
||||
if (m_ownerElement->smooth())
|
||||
texture->setFiltering(QSGTexture::Linear);
|
||||
texture->setMipmapFiltering(QSGTexture::Linear);
|
||||
}
|
||||
m_textures.append(texture);
|
||||
node->setTargetRect(rect);
|
||||
node->setInnerTargetRect(rect);
|
||||
node->setTexture(texture);
|
||||
if (m_ownerElement->smooth()) {
|
||||
if (m_ownerElement->smooth())
|
||||
node->setFiltering(QSGTexture::Linear);
|
||||
node->setMipmapFiltering(QSGTexture::Linear);
|
||||
}
|
||||
appendChildNode(node);
|
||||
node->update();
|
||||
}
|
||||
|
|
|
@ -423,7 +423,10 @@ void QQuickTextNodeEngine::addImage(const QRectF &rect, const QImage &image, qre
|
|||
QRectF searchRect = rect;
|
||||
if (layoutPosition == QTextFrameFormat::InFlow) {
|
||||
if (m_currentLineTree.isEmpty()) {
|
||||
searchRect.moveTopLeft(m_position + m_currentLine.position() + QPointF(0,1));
|
||||
if (m_currentTextDirection == Qt::RightToLeft)
|
||||
searchRect.moveTopRight(m_position + m_currentLine.rect().topRight() + QPointF(0, 1));
|
||||
else
|
||||
searchRect.moveTopLeft(m_position + m_currentLine.position() + QPointF(0,1));
|
||||
} else {
|
||||
const BinaryTreeNode *lastNode = m_currentLineTree.data() + m_currentLineTree.size() - 1;
|
||||
if (lastNode->glyphRun.isRightToLeft()) {
|
||||
|
@ -952,6 +955,8 @@ void QQuickTextNodeEngine::addTextBlock(QTextDocument *textDocument, const QText
|
|||
int preeditPosition = block.isValid() ? block.layout()->preeditAreaPosition() : -1;
|
||||
#endif
|
||||
|
||||
setCurrentTextDirection(block.textDirection());
|
||||
|
||||
QVarLengthArray<QTextLayout::FormatRange> colorChanges;
|
||||
mergeFormats(block.layout(), &colorChanges);
|
||||
|
||||
|
|
|
@ -144,7 +144,11 @@ public:
|
|||
int selectionState;
|
||||
};
|
||||
|
||||
QQuickTextNodeEngine() : m_hasSelection(false), m_hasContents(false) {}
|
||||
QQuickTextNodeEngine()
|
||||
: m_currentTextDirection(Qt::LeftToRight)
|
||||
, m_hasSelection(false)
|
||||
, m_hasContents(false)
|
||||
{}
|
||||
|
||||
bool hasContents() const { return m_hasContents; }
|
||||
void addTextBlock(QTextDocument *, const QTextBlock &, const QPointF &position, const QColor &textColor, const QColor& anchorColor, int selectionStart, int selectionEnd);
|
||||
|
@ -158,6 +162,11 @@ public:
|
|||
m_currentLine = currentLine;
|
||||
}
|
||||
|
||||
void setCurrentTextDirection(Qt::LayoutDirection textDirection)
|
||||
{
|
||||
m_currentTextDirection = textDirection;
|
||||
}
|
||||
|
||||
void addBorder(const QRectF &rect, qreal border, QTextFrameFormat::BorderStyle borderStyle,
|
||||
const QBrush &borderBrush);
|
||||
void addFrameDecorations(QTextDocument *document, QTextFrame *frame);
|
||||
|
@ -247,6 +256,7 @@ private:
|
|||
QPointF m_position;
|
||||
|
||||
QTextLine m_currentLine;
|
||||
Qt::LayoutDirection m_currentTextDirection;
|
||||
|
||||
QList<QPair<QRectF, QColor> > m_backgrounds;
|
||||
QList<QRectF> m_selectionRects;
|
||||
|
|
|
@ -111,14 +111,14 @@ void QQuickViewPrivate::execute()
|
|||
}
|
||||
|
||||
void QQuickViewPrivate::itemGeometryChanged(QQuickItem *resizeItem, QQuickGeometryChange change,
|
||||
const QRectF &diff)
|
||||
const QRectF &oldGeometry)
|
||||
{
|
||||
Q_Q(QQuickView);
|
||||
if (resizeItem == root && resizeMode == QQuickView::SizeViewToRootObject) {
|
||||
// wait for both width and height to be changed
|
||||
resizetimer.start(0,q);
|
||||
}
|
||||
QQuickItemChangeListener::itemGeometryChanged(resizeItem, change, diff);
|
||||
QQuickItemChangeListener::itemGeometryChanged(resizeItem, change, oldGeometry);
|
||||
}
|
||||
|
||||
/*!
|
||||
|
|
|
@ -3125,10 +3125,12 @@ void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
|
|||
|
||||
if (itemPriv->paintNode && itemPriv->paintNode->parent() == 0) {
|
||||
QSGNode *before = qquickitem_before_paintNode(itemPriv);
|
||||
if (before)
|
||||
if (before && before->parent()) {
|
||||
Q_ASSERT(before->parent() == itemPriv->childContainerNode());
|
||||
itemPriv->childContainerNode()->insertChildNodeAfter(itemPriv->paintNode, before);
|
||||
else
|
||||
} else {
|
||||
itemPriv->childContainerNode()->prependChildNode(itemPriv->paintNode);
|
||||
}
|
||||
}
|
||||
} else if (itemPriv->paintNode) {
|
||||
delete itemPriv->paintNode;
|
||||
|
|
|
@ -215,7 +215,7 @@ QSGRendererInterface::ShaderSourceTypes QSGSoftwareContext::shaderSourceType() c
|
|||
|
||||
void *QSGSoftwareContext::getResource(QQuickWindow *window, Resource resource) const
|
||||
{
|
||||
if (resource == Painter && window && window->isSceneGraphInitialized())
|
||||
if (resource == PainterResource && window && window->isSceneGraphInitialized())
|
||||
return static_cast<QSGSoftwareRenderContext *>(QQuickWindowPrivate::get(window)->context)->m_activePainter;
|
||||
|
||||
return nullptr;
|
||||
|
|
|
@ -90,7 +90,7 @@ DECLARE_DEBUG_VAR(noclip)
|
|||
static QElapsedTimer qsg_renderer_timer;
|
||||
|
||||
#define QSGNODE_TRAVERSE(NODE) for (QSGNode *child = NODE->firstChild(); child; child = child->nextSibling())
|
||||
#define SHADOWNODE_TRAVERSE(NODE) for (Node *child = NODE->firstChild; child; child = child->nextSibling)
|
||||
#define SHADOWNODE_TRAVERSE(NODE) for (Node *child = NODE->firstChild(); child; child = child->sibling())
|
||||
|
||||
static inline int size_of_type(GLenum type)
|
||||
{
|
||||
|
@ -510,7 +510,7 @@ void Updater::updateRootTransforms(Node *node, Node *root, const QMatrix4x4 &com
|
|||
while (n != root) {
|
||||
if (n->type() == QSGNode::TransformNodeType)
|
||||
m = static_cast<QSGTransformNode *>(n->sgNode)->matrix() * m;
|
||||
n = n->parent;
|
||||
n = n->parent();
|
||||
}
|
||||
|
||||
m = combined * m;
|
||||
|
@ -1013,16 +1013,8 @@ void Renderer::nodeWasAdded(QSGNode *node, Node *shadowParent)
|
|||
Node *snode = m_nodeAllocator.allocate();
|
||||
snode->sgNode = node;
|
||||
m_nodes.insert(node, snode);
|
||||
if (shadowParent) {
|
||||
snode->parent = shadowParent;
|
||||
if (shadowParent->lastChild) {
|
||||
shadowParent->lastChild->nextSibling = snode;
|
||||
shadowParent->lastChild = snode;
|
||||
} else {
|
||||
shadowParent->firstChild = snode;
|
||||
shadowParent->lastChild = snode;
|
||||
}
|
||||
}
|
||||
if (shadowParent)
|
||||
shadowParent->append(snode);
|
||||
|
||||
if (node->type() == QSGNode::GeometryNodeType) {
|
||||
snode->data = m_elementAllocator.allocate();
|
||||
|
@ -1054,17 +1046,12 @@ void Renderer::nodeWasRemoved(Node *node)
|
|||
// here, because we delete 'child' (when recursed, down below), so we'd
|
||||
// have a use-after-free.
|
||||
{
|
||||
Node *child = node->firstChild;
|
||||
Node *nextChild = 0;
|
||||
|
||||
Node *child = node->firstChild();
|
||||
while (child) {
|
||||
// Get the next child now before we proceed
|
||||
nextChild = child->nextSibling;
|
||||
|
||||
// Remove (and delete) child
|
||||
node->remove(child);
|
||||
nodeWasRemoved(child);
|
||||
|
||||
child = nextChild;
|
||||
child = node->firstChild();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1110,6 +1097,7 @@ void Renderer::nodeWasRemoved(Node *node)
|
|||
}
|
||||
|
||||
Q_ASSERT(m_nodes.contains(node->sgNode));
|
||||
|
||||
m_nodeAllocator.release(m_nodes.take(node->sgNode));
|
||||
}
|
||||
|
||||
|
@ -1120,13 +1108,13 @@ void Renderer::turnNodeIntoBatchRoot(Node *node)
|
|||
node->isBatchRoot = true;
|
||||
node->becameBatchRoot = true;
|
||||
|
||||
Node *p = node->parent;
|
||||
Node *p = node->parent();
|
||||
while (p) {
|
||||
if (p->type() == QSGNode::ClipNodeType || p->isBatchRoot) {
|
||||
registerBatchRoot(node, p);
|
||||
break;
|
||||
}
|
||||
p = p->parent;
|
||||
p = p->parent();
|
||||
}
|
||||
|
||||
SHADOWNODE_TRAVERSE(node)
|
||||
|
@ -1255,33 +1243,18 @@ void Renderer::nodeChanged(QSGNode *node, QSGNode::DirtyState state)
|
|||
| QSGNode::DirtyForceUpdate);
|
||||
if (dirtyChain != 0) {
|
||||
dirtyChain = QSGNode::DirtyState(dirtyChain << 16);
|
||||
Node *sn = shadowNode->parent;
|
||||
Node *sn = shadowNode->parent();
|
||||
while (sn) {
|
||||
sn->dirtyState |= dirtyChain;
|
||||
sn = sn->parent;
|
||||
sn = sn->parent();
|
||||
}
|
||||
}
|
||||
|
||||
// Delete happens at the very end because it deletes the shadownode.
|
||||
if (state & QSGNode::DirtyNodeRemoved) {
|
||||
Node *parent = shadowNode->parent;
|
||||
if (parent) {
|
||||
Q_ASSERT(parent->firstChild);
|
||||
Q_ASSERT(parent->lastChild);
|
||||
shadowNode->parent = 0;
|
||||
Node *child = parent->firstChild;
|
||||
if (child == shadowNode) {
|
||||
parent->firstChild = shadowNode->nextSibling;
|
||||
if (parent->lastChild == shadowNode)
|
||||
parent->lastChild = 0;
|
||||
} else {
|
||||
while (child->nextSibling != shadowNode)
|
||||
child = child->nextSibling;
|
||||
child->nextSibling = shadowNode->nextSibling;
|
||||
if (shadowNode == parent->lastChild)
|
||||
parent->lastChild = child;
|
||||
}
|
||||
}
|
||||
Node *parent = shadowNode->parent();
|
||||
if (parent)
|
||||
parent->remove(shadowNode);
|
||||
nodeWasRemoved(shadowNode);
|
||||
Q_ASSERT(m_nodes.value(node) == 0);
|
||||
}
|
||||
|
|
|
@ -451,11 +451,73 @@ struct Batch
|
|||
struct Node
|
||||
{
|
||||
QSGNode *sgNode;
|
||||
Node *parent;
|
||||
void *data;
|
||||
Node *firstChild;
|
||||
Node *nextSibling;
|
||||
Node *lastChild;
|
||||
|
||||
Node *m_parent;
|
||||
Node *m_child;
|
||||
Node *m_next;
|
||||
Node *m_prev;
|
||||
|
||||
Node *parent() const { return m_parent; }
|
||||
|
||||
void append(Node *child) {
|
||||
Q_ASSERT(child);
|
||||
Q_ASSERT(!hasChild(child));
|
||||
Q_ASSERT(child->m_parent == 0);
|
||||
Q_ASSERT(child->m_next == 0);
|
||||
Q_ASSERT(child->m_prev == 0);
|
||||
|
||||
if (!m_child) {
|
||||
child->m_next = child;
|
||||
child->m_prev = child;
|
||||
m_child = child;
|
||||
} else {
|
||||
m_child->m_prev->m_next = child;
|
||||
child->m_prev = m_child->m_prev;
|
||||
m_child->m_prev = child;
|
||||
child->m_next = m_child;
|
||||
}
|
||||
child->setParent(this);
|
||||
}
|
||||
|
||||
void remove(Node *child) {
|
||||
Q_ASSERT(child);
|
||||
Q_ASSERT(hasChild(child));
|
||||
|
||||
// only child..
|
||||
if (child->m_next == child) {
|
||||
m_child = 0;
|
||||
} else {
|
||||
if (m_child == child)
|
||||
m_child = child->m_next;
|
||||
child->m_next->m_prev = child->m_prev;
|
||||
child->m_prev->m_next = child->m_next;
|
||||
}
|
||||
child->m_next = 0;
|
||||
child->m_prev = 0;
|
||||
child->setParent(0);
|
||||
}
|
||||
|
||||
Node *firstChild() const { return m_child; }
|
||||
|
||||
Node *sibling() const {
|
||||
Q_ASSERT(m_parent);
|
||||
return m_next == m_parent->m_child ? 0 : m_next;
|
||||
}
|
||||
|
||||
void setParent(Node *p) {
|
||||
Q_ASSERT(m_parent == 0 || p == 0);
|
||||
m_parent = p;
|
||||
}
|
||||
|
||||
bool hasChild(Node *child) const {
|
||||
Node *n = m_child;
|
||||
while (n && n != child)
|
||||
n = n->sibling();
|
||||
return n;
|
||||
}
|
||||
|
||||
|
||||
|
||||
QSGNode::DirtyState dirtyState;
|
||||
|
||||
|
|
|
@ -81,10 +81,10 @@ QT_BEGIN_NAMESPACE
|
|||
|
||||
/*!
|
||||
\enum QSGRendererInterface::Resource
|
||||
\value Device The graphics device, when applicable.
|
||||
\value CommandQueue The graphics command queue used by the scenegraph, when applicable.
|
||||
\value CommandList The command list or buffer used by the scenegraph, when applicable.
|
||||
\value Painter The active QPainter used by the scenegraph, when running with the software backend.
|
||||
\value DeviceResource The graphics device, when applicable.
|
||||
\value CommandQueueResource The graphics command queue used by the scenegraph, when applicable.
|
||||
\value CommandListResource The command list or buffer used by the scenegraph, when applicable.
|
||||
\value PainterResource The active QPainter used by the scenegraph, when running with the software backend.
|
||||
*/
|
||||
|
||||
/*!
|
||||
|
|
|
@ -57,10 +57,10 @@ public:
|
|||
};
|
||||
|
||||
enum Resource {
|
||||
Device,
|
||||
CommandQueue,
|
||||
CommandList,
|
||||
Painter
|
||||
DeviceResource,
|
||||
CommandQueueResource,
|
||||
CommandListResource,
|
||||
PainterResource
|
||||
};
|
||||
|
||||
enum ShaderType {
|
||||
|
|
|
@ -117,8 +117,9 @@ QSGTexture *Manager::create(const QImage &image, bool hasAlphaChannel)
|
|||
if (image.width() < m_atlas_size_limit && image.height() < m_atlas_size_limit) {
|
||||
if (!m_atlas)
|
||||
m_atlas = new Atlas(m_atlas_size);
|
||||
// t may be null for atlas allocation failure
|
||||
t = m_atlas->create(image);
|
||||
if (!hasAlphaChannel && t->hasAlphaChannel())
|
||||
if (t && !hasAlphaChannel && t->hasAlphaChannel())
|
||||
t->setHasAlphaChannel(false);
|
||||
}
|
||||
return t;
|
||||
|
|
|
@ -173,33 +173,4 @@ bool QSGDefaultImageNode::ownsTexture() const
|
|||
return m_ownsTexture;
|
||||
}
|
||||
|
||||
void QSGDefaultImageNode::rebuildGeometry(QSGGeometry *g,
|
||||
QSGTexture *texture,
|
||||
const QRectF &rect,
|
||||
QRectF sourceRect,
|
||||
TextureCoordinatesTransformMode texCoordMode)
|
||||
{
|
||||
if (!texture)
|
||||
return;
|
||||
|
||||
if (!sourceRect.width() || !sourceRect.height()) {
|
||||
QSize ts = texture->textureSize();
|
||||
sourceRect = QRectF(0, 0, ts.width(), ts.height());
|
||||
}
|
||||
|
||||
// Maybe transform the texture coordinates
|
||||
if (texCoordMode.testFlag(QSGImageNode::MirrorHorizontally)) {
|
||||
float tmp = sourceRect.left();
|
||||
sourceRect.setLeft(sourceRect.right());
|
||||
sourceRect.setRight(tmp);
|
||||
}
|
||||
if (texCoordMode.testFlag(QSGImageNode::MirrorVertically)) {
|
||||
float tmp = sourceRect.top();
|
||||
sourceRect.setTop(sourceRect.bottom());
|
||||
sourceRect.setBottom(tmp);
|
||||
}
|
||||
|
||||
QSGGeometry::updateTexturedRectGeometry(g, rect, texture->convertToNormalizedSourceRect(sourceRect));
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
|
|
@ -85,12 +85,6 @@ public:
|
|||
void setOwnsTexture(bool owns) override;
|
||||
bool ownsTexture() const override;
|
||||
|
||||
static void rebuildGeometry(QSGGeometry *g,
|
||||
QSGTexture *texture,
|
||||
const QRectF &rect,
|
||||
QRectF sourceRect,
|
||||
TextureCoordinatesTransformMode texCoordMode);
|
||||
|
||||
private:
|
||||
QSGGeometry m_geometry;
|
||||
QSGOpaqueTextureMaterial m_opaque_material;
|
||||
|
|
|
@ -81,56 +81,4 @@ void QSGDefaultNinePatchNode::update()
|
|||
markDirty(QSGNode::DirtyGeometry | QSGNode::DirtyMaterial);
|
||||
}
|
||||
|
||||
void QSGDefaultNinePatchNode::rebuildGeometry(QSGTexture *texture, QSGGeometry *geometry, const QVector4D &padding,
|
||||
const QRectF &bounds, qreal dpr)
|
||||
{
|
||||
if (padding.x() <= 0 && padding.y() <= 0 && padding.z() <= 0 && padding.w() <= 0) {
|
||||
geometry->allocate(4, 0);
|
||||
QSGGeometry::updateTexturedRectGeometry(geometry, bounds, texture->normalizedTextureSubRect());
|
||||
return;
|
||||
}
|
||||
|
||||
QRectF tc = texture->normalizedTextureSubRect();
|
||||
QSize ts = texture->textureSize();
|
||||
ts.setHeight(ts.height() / dpr);
|
||||
ts.setWidth(ts.width() / dpr);
|
||||
|
||||
qreal invtw = tc.width() / ts.width();
|
||||
qreal invth = tc.height() / ts.height();
|
||||
|
||||
struct Coord { qreal p; qreal t; };
|
||||
Coord cx[4] = { { bounds.left(), tc.left() },
|
||||
{ bounds.left() + padding.x(), tc.left() + padding.x() * invtw },
|
||||
{ bounds.right() - padding.z(), tc.right() - padding.z() * invtw },
|
||||
{ bounds.right(), tc.right() }
|
||||
};
|
||||
Coord cy[4] = { { bounds.top(), tc.top() },
|
||||
{ bounds.top() + padding.y(), tc.top() + padding.y() * invth },
|
||||
{ bounds.bottom() - padding.w(), tc.bottom() - padding.w() * invth },
|
||||
{ bounds.bottom(), tc.bottom() }
|
||||
};
|
||||
|
||||
geometry->allocate(16, 28);
|
||||
QSGGeometry::TexturedPoint2D *v = geometry->vertexDataAsTexturedPoint2D();
|
||||
for (int y = 0; y < 4; ++y) {
|
||||
for (int x = 0; x < 4; ++x) {
|
||||
v->set(cx[x].p, cy[y].p, cx[x].t, cy[y].t);
|
||||
++v;
|
||||
}
|
||||
}
|
||||
|
||||
quint16 *i = geometry->indexDataAsUShort();
|
||||
for (int r = 0; r < 3; ++r) {
|
||||
if (r > 0)
|
||||
*i++ = 4 * r;
|
||||
for (int c = 0; c < 4; ++c) {
|
||||
i[0] = 4 * r + c;
|
||||
i[1] = 4 * r + c + 4;
|
||||
i += 2;
|
||||
}
|
||||
if (r < 2)
|
||||
*i++ = 4 * r + 3 + 4;
|
||||
}
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
|
|
@ -70,9 +70,6 @@ public:
|
|||
void setPadding(qreal left, qreal top, qreal right, qreal bottom) override;
|
||||
void update() override;
|
||||
|
||||
static void rebuildGeometry(QSGTexture *texture, QSGGeometry *geometry, const QVector4D &padding,
|
||||
const QRectF &bounds, qreal dpr);
|
||||
|
||||
private:
|
||||
QRectF m_bounds;
|
||||
qreal m_devicePixelRatio;
|
||||
|
|
|
@ -84,32 +84,12 @@ QSGDistanceFieldGlyphCacheManager::~QSGDistanceFieldGlyphCacheManager()
|
|||
|
||||
QSGDistanceFieldGlyphCache *QSGDistanceFieldGlyphCacheManager::cache(const QRawFont &font)
|
||||
{
|
||||
return m_caches.value(fontKey(font), 0);
|
||||
return m_caches.value(font, 0);
|
||||
}
|
||||
|
||||
void QSGDistanceFieldGlyphCacheManager::insertCache(const QRawFont &font, QSGDistanceFieldGlyphCache *cache)
|
||||
{
|
||||
m_caches.insert(fontKey(font), cache);
|
||||
}
|
||||
|
||||
QString QSGDistanceFieldGlyphCacheManager::fontKey(const QRawFont &font)
|
||||
{
|
||||
QFontEngine *fe = QRawFontPrivate::get(font)->fontEngine;
|
||||
if (!fe->faceId().filename.isEmpty()) {
|
||||
QByteArray keyName = fe->faceId().filename;
|
||||
if (font.style() != QFont::StyleNormal)
|
||||
keyName += QByteArray(" I");
|
||||
if (font.weight() != QFont::Normal)
|
||||
keyName += ' ' + QByteArray::number(font.weight());
|
||||
keyName += QByteArray(" DF");
|
||||
return QString::fromUtf8(keyName);
|
||||
} else {
|
||||
return QString::fromLatin1("%1_%2_%3_%4")
|
||||
.arg(font.familyName())
|
||||
.arg(font.styleName())
|
||||
.arg(font.weight())
|
||||
.arg(font.style());
|
||||
}
|
||||
m_caches.insert(font, cache);
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
|
|
@ -80,9 +80,7 @@ public:
|
|||
void setAntialiasingSpreadFunc(AntialiasingSpreadFunc func) { m_antialiasingSpread_func = func; }
|
||||
|
||||
private:
|
||||
static QString fontKey(const QRawFont &font);
|
||||
|
||||
QHash<QString, QSGDistanceFieldGlyphCache *> m_caches;
|
||||
QHash<QRawFont, QSGDistanceFieldGlyphCache *> m_caches;
|
||||
|
||||
ThresholdFunc m_threshold_func;
|
||||
AntialiasingSpreadFunc m_antialiasingSpread_func;
|
||||
|
|
|
@ -187,4 +187,33 @@ QT_BEGIN_NAMESPACE
|
|||
\return \c true if the node takes ownership of the texture; otherwise \c false.
|
||||
*/
|
||||
|
||||
void QSGImageNode::rebuildGeometry(QSGGeometry *g,
|
||||
QSGTexture *texture,
|
||||
const QRectF &rect,
|
||||
QRectF sourceRect,
|
||||
TextureCoordinatesTransformMode texCoordMode)
|
||||
{
|
||||
if (!texture)
|
||||
return;
|
||||
|
||||
if (!sourceRect.width() || !sourceRect.height()) {
|
||||
QSize ts = texture->textureSize();
|
||||
sourceRect = QRectF(0, 0, ts.width(), ts.height());
|
||||
}
|
||||
|
||||
// Maybe transform the texture coordinates
|
||||
if (texCoordMode.testFlag(QSGImageNode::MirrorHorizontally)) {
|
||||
float tmp = sourceRect.left();
|
||||
sourceRect.setLeft(sourceRect.right());
|
||||
sourceRect.setRight(tmp);
|
||||
}
|
||||
if (texCoordMode.testFlag(QSGImageNode::MirrorVertically)) {
|
||||
float tmp = sourceRect.top();
|
||||
sourceRect.setTop(sourceRect.bottom());
|
||||
sourceRect.setBottom(tmp);
|
||||
}
|
||||
|
||||
QSGGeometry::updateTexturedRectGeometry(g, rect, texture->convertToNormalizedSourceRect(sourceRect));
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
|
|
@ -79,6 +79,12 @@ public:
|
|||
|
||||
virtual void setOwnsTexture(bool owns) = 0;
|
||||
virtual bool ownsTexture() const = 0;
|
||||
|
||||
static void rebuildGeometry(QSGGeometry *g,
|
||||
QSGTexture *texture,
|
||||
const QRectF &rect,
|
||||
QRectF sourceRect,
|
||||
TextureCoordinatesTransformMode texCoordMode);
|
||||
};
|
||||
|
||||
Q_DECLARE_OPERATORS_FOR_FLAGS(QSGImageNode::TextureCoordinatesTransformMode)
|
||||
|
|
|
@ -74,4 +74,56 @@ QT_BEGIN_NAMESPACE
|
|||
\internal
|
||||
*/
|
||||
|
||||
void QSGNinePatchNode::rebuildGeometry(QSGTexture *texture, QSGGeometry *geometry, const QVector4D &padding,
|
||||
const QRectF &bounds, qreal dpr)
|
||||
{
|
||||
if (padding.x() <= 0 && padding.y() <= 0 && padding.z() <= 0 && padding.w() <= 0) {
|
||||
geometry->allocate(4, 0);
|
||||
QSGGeometry::updateTexturedRectGeometry(geometry, bounds, texture->normalizedTextureSubRect());
|
||||
return;
|
||||
}
|
||||
|
||||
QRectF tc = texture->normalizedTextureSubRect();
|
||||
QSize ts = texture->textureSize();
|
||||
ts.setHeight(ts.height() / dpr);
|
||||
ts.setWidth(ts.width() / dpr);
|
||||
|
||||
qreal invtw = tc.width() / ts.width();
|
||||
qreal invth = tc.height() / ts.height();
|
||||
|
||||
struct Coord { qreal p; qreal t; };
|
||||
Coord cx[4] = { { bounds.left(), tc.left() },
|
||||
{ bounds.left() + padding.x(), tc.left() + padding.x() * invtw },
|
||||
{ bounds.right() - padding.z(), tc.right() - padding.z() * invtw },
|
||||
{ bounds.right(), tc.right() }
|
||||
};
|
||||
Coord cy[4] = { { bounds.top(), tc.top() },
|
||||
{ bounds.top() + padding.y(), tc.top() + padding.y() * invth },
|
||||
{ bounds.bottom() - padding.w(), tc.bottom() - padding.w() * invth },
|
||||
{ bounds.bottom(), tc.bottom() }
|
||||
};
|
||||
|
||||
geometry->allocate(16, 28);
|
||||
QSGGeometry::TexturedPoint2D *v = geometry->vertexDataAsTexturedPoint2D();
|
||||
for (int y = 0; y < 4; ++y) {
|
||||
for (int x = 0; x < 4; ++x) {
|
||||
v->set(cx[x].p, cy[y].p, cx[x].t, cy[y].t);
|
||||
++v;
|
||||
}
|
||||
}
|
||||
|
||||
quint16 *i = geometry->indexDataAsUShort();
|
||||
for (int r = 0; r < 3; ++r) {
|
||||
if (r > 0)
|
||||
*i++ = 4 * r;
|
||||
for (int c = 0; c < 4; ++c) {
|
||||
i[0] = 4 * r + c;
|
||||
i[1] = 4 * r + c + 4;
|
||||
i += 2;
|
||||
}
|
||||
if (r < 2)
|
||||
*i++ = 4 * r + 3 + 4;
|
||||
}
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
|
|
@ -55,6 +55,10 @@ public:
|
|||
virtual void setDevicePixelRatio(qreal ratio) = 0;
|
||||
virtual void setPadding(qreal left, qreal top, qreal right, qreal bottom) = 0;
|
||||
virtual void update() = 0;
|
||||
|
||||
static void rebuildGeometry(QSGTexture *texture, QSGGeometry *geometry,
|
||||
const QVector4D &padding,
|
||||
const QRectF &bounds, qreal dpr);
|
||||
};
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
|
|
@ -245,14 +245,14 @@ void QQuickWidgetPrivate::execute()
|
|||
}
|
||||
|
||||
void QQuickWidgetPrivate::itemGeometryChanged(QQuickItem *resizeItem, QQuickGeometryChange change,
|
||||
const QRectF &diff)
|
||||
const QRectF &oldGeometry)
|
||||
{
|
||||
Q_Q(QQuickWidget);
|
||||
if (resizeItem == root && resizeMode == QQuickWidget::SizeViewToRootObject) {
|
||||
// wait for both width and height to be changed
|
||||
resizetimer.start(0,q);
|
||||
}
|
||||
QQuickItemChangeListener::itemGeometryChanged(resizeItem, change, diff);
|
||||
QQuickItemChangeListener::itemGeometryChanged(resizeItem, change, oldGeometry);
|
||||
}
|
||||
|
||||
void QQuickWidgetPrivate::render(bool needsSync)
|
||||
|
|
|
@ -87,7 +87,7 @@ public:
|
|||
~QQuickWidgetPrivate();
|
||||
|
||||
void execute();
|
||||
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change, const QRectF &diff) Q_DECL_OVERRIDE;
|
||||
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change, const QRectF &oldGeometry) Q_DECL_OVERRIDE;
|
||||
void initResize();
|
||||
void updateSize();
|
||||
void updatePosition();
|
||||
|
|
11
sync.profile
11
sync.profile
|
@ -13,14 +13,3 @@
|
|||
);
|
||||
%deprecatedheaders = (
|
||||
);
|
||||
# Module dependencies.
|
||||
# Every module that is required to build this module should have one entry.
|
||||
# Each of the module version specifiers can take one of the following values:
|
||||
# - A specific Git revision.
|
||||
# - any git symbolic ref resolvable from the module's repository (e.g. "refs/heads/master" to track master branch)
|
||||
# - an empty string to use the same branch under test (dependencies will become "refs/heads/master" if we are in the master branch)
|
||||
#
|
||||
%dependencies = (
|
||||
"qtbase" => "",
|
||||
"qtxmlpatterns" => "",
|
||||
);
|
||||
|
|
|
@ -1372,6 +1372,33 @@ void tst_QJSValue::hasProperty_changePrototype()
|
|||
QVERIFY(obj.hasOwnProperty("foo"));
|
||||
}
|
||||
|
||||
void tst_QJSValue::hasProperty_QTBUG56830_data()
|
||||
{
|
||||
QTest::addColumn<QString>("key");
|
||||
QTest::addColumn<QString>("lookup");
|
||||
|
||||
QTest::newRow("bugreport-1") << QStringLiteral("240000000000") << QStringLiteral("3776798720");
|
||||
QTest::newRow("bugreport-2") << QStringLiteral("240000000001") << QStringLiteral("3776798721");
|
||||
QTest::newRow("biggest-ok-before-bug") << QStringLiteral("238609294221") << QStringLiteral("2386092941");
|
||||
QTest::newRow("smallest-bugged") << QStringLiteral("238609294222") << QStringLiteral("2386092942");
|
||||
QTest::newRow("biggest-bugged") << QStringLiteral("249108103166") << QStringLiteral("12884901886");
|
||||
QTest::newRow("smallest-ok-after-bug") << QStringLiteral("249108103167") << QStringLiteral("12884901887");
|
||||
}
|
||||
|
||||
void tst_QJSValue::hasProperty_QTBUG56830()
|
||||
{
|
||||
QFETCH(QString, key);
|
||||
QFETCH(QString, lookup);
|
||||
|
||||
QJSEngine eng;
|
||||
const QJSValue value(42);
|
||||
|
||||
QJSValue obj = eng.newObject();
|
||||
obj.setProperty(key, value);
|
||||
QVERIFY(obj.hasProperty(key));
|
||||
QVERIFY(!obj.hasProperty(lookup));
|
||||
}
|
||||
|
||||
void tst_QJSValue::deleteProperty_basic()
|
||||
{
|
||||
QJSEngine eng;
|
||||
|
|
|
@ -92,6 +92,8 @@ private slots:
|
|||
void hasProperty_basic();
|
||||
void hasProperty_globalObject();
|
||||
void hasProperty_changePrototype();
|
||||
void hasProperty_QTBUG56830_data();
|
||||
void hasProperty_QTBUG56830();
|
||||
|
||||
void deleteProperty_basic();
|
||||
void deleteProperty_globalObject();
|
||||
|
|
|
@ -0,0 +1,9 @@
|
|||
import QtQuick 2.0
|
||||
|
||||
Item {
|
||||
width: 50
|
||||
|
||||
property bool tested: false
|
||||
|
||||
Connections { onWidthChanged: tested = true }
|
||||
}
|
|
@ -52,6 +52,7 @@ private slots:
|
|||
void rewriteErrors();
|
||||
void singletonTypeTarget();
|
||||
void enableDisable_QTBUG_36350();
|
||||
void clearImplicitTarget();
|
||||
|
||||
private:
|
||||
QQmlEngine engine;
|
||||
|
@ -352,6 +353,32 @@ void tst_qqmlconnections::enableDisable_QTBUG_36350()
|
|||
delete item;
|
||||
}
|
||||
|
||||
//QTBUG-56499
|
||||
void tst_qqmlconnections::clearImplicitTarget()
|
||||
{
|
||||
QQmlEngine engine;
|
||||
QQmlComponent c(&engine, testFileUrl("test-connection-implicit.qml"));
|
||||
QQuickItem *item = qobject_cast<QQuickItem*>(c.create());
|
||||
|
||||
QVERIFY(item != 0);
|
||||
|
||||
// normal case: fire Connections
|
||||
item->setWidth(100.);
|
||||
QCOMPARE(item->property("tested").toBool(), true);
|
||||
|
||||
item->setProperty("tested", false);
|
||||
// clear the implicit target
|
||||
QQmlConnections *connections = item->findChild<QQmlConnections*>();
|
||||
QVERIFY(connections);
|
||||
connections->setTarget(0);
|
||||
|
||||
// target cleared: no longer fire Connections
|
||||
item->setWidth(150.);
|
||||
QCOMPARE(item->property("tested").toBool(), false);
|
||||
|
||||
delete item;
|
||||
}
|
||||
|
||||
QTEST_MAIN(tst_qqmlconnections)
|
||||
|
||||
#include "tst_qqmlconnections.moc"
|
||||
|
|
|
@ -2726,9 +2726,9 @@ struct TestListener : public QQuickItemChangeListener
|
|||
{
|
||||
TestListener(bool remove = false) : remove(remove) { }
|
||||
|
||||
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange, const QRectF &diff) override
|
||||
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange, const QRectF &oldGeometry) override
|
||||
{
|
||||
record(item, QQuickItemPrivate::Geometry, diff);
|
||||
record(item, QQuickItemPrivate::Geometry, oldGeometry);
|
||||
}
|
||||
void itemSiblingOrderChanged(QQuickItem *item) override
|
||||
{
|
||||
|
@ -2810,20 +2810,20 @@ void tst_QQuickItem::changeListener()
|
|||
item->setImplicitWidth(10);
|
||||
QCOMPARE(itemListener.count(QQuickItemPrivate::ImplicitWidth), 1);
|
||||
QCOMPARE(itemListener.count(QQuickItemPrivate::Geometry), 1);
|
||||
QCOMPARE(itemListener.value(QQuickItemPrivate::Geometry), QVariant(QRectF(0,0,10,0)));
|
||||
QCOMPARE(itemListener.value(QQuickItemPrivate::Geometry), QVariant(QRectF(0,0,0,0)));
|
||||
|
||||
item->setImplicitHeight(20);
|
||||
QCOMPARE(itemListener.count(QQuickItemPrivate::ImplicitHeight), 1);
|
||||
QCOMPARE(itemListener.count(QQuickItemPrivate::Geometry), 2);
|
||||
QCOMPARE(itemListener.value(QQuickItemPrivate::Geometry), QVariant(QRectF(0,0,0,20)));
|
||||
QCOMPARE(itemListener.value(QQuickItemPrivate::Geometry), QVariant(QRectF(0,0,10,0)));
|
||||
|
||||
item->setWidth(item->width() + 30);
|
||||
QCOMPARE(itemListener.count(QQuickItemPrivate::Geometry), 3);
|
||||
QCOMPARE(itemListener.value(QQuickItemPrivate::Geometry), QVariant(QRectF(0,0,30,0)));
|
||||
QCOMPARE(itemListener.value(QQuickItemPrivate::Geometry), QVariant(QRectF(0,0,10,20)));
|
||||
|
||||
item->setHeight(item->height() + 40);
|
||||
QCOMPARE(itemListener.count(QQuickItemPrivate::Geometry), 4);
|
||||
QCOMPARE(itemListener.value(QQuickItemPrivate::Geometry), QVariant(QRectF(0,0,0,40)));
|
||||
QCOMPARE(itemListener.value(QQuickItemPrivate::Geometry), QVariant(QRectF(0,0,40,20)));
|
||||
|
||||
item->setOpacity(0.5);
|
||||
QCOMPARE(itemListener.count(QQuickItemPrivate::Opacity), 1);
|
||||
|
|
|
@ -0,0 +1,20 @@
|
|||
import QtQuick 2.0
|
||||
|
||||
Rectangle {
|
||||
width: 300
|
||||
height: 300
|
||||
color: "white"
|
||||
|
||||
TextEdit {
|
||||
objectName: "textEditObject"
|
||||
width: 300
|
||||
height: 300
|
||||
text: "<span style=\"font-size:20pt;\">Blah</span><br>blah"
|
||||
textFormat: TextEdit.RichText
|
||||
cursorDelegate: Rectangle {
|
||||
objectName: "cursorInstance"
|
||||
color: "red"
|
||||
width: 2
|
||||
}
|
||||
}
|
||||
}
|
|
@ -140,6 +140,7 @@ private slots:
|
|||
void cursorVisible();
|
||||
void delegateLoading_data();
|
||||
void delegateLoading();
|
||||
void cursorDelegateHeight();
|
||||
void navigation();
|
||||
void readOnly();
|
||||
#ifndef QT_NO_CLIPBOARD
|
||||
|
@ -2848,6 +2849,43 @@ void tst_qquicktextedit::delegateLoading()
|
|||
//QVERIFY(!delegate);
|
||||
}
|
||||
|
||||
void tst_qquicktextedit::cursorDelegateHeight()
|
||||
{
|
||||
QQuickView view(testFileUrl("cursorHeight.qml"));
|
||||
view.show();
|
||||
view.requestActivate();
|
||||
QTest::qWaitForWindowActive(&view);
|
||||
QQuickTextEdit *textEditObject = view.rootObject()->findChild<QQuickTextEdit*>("textEditObject");
|
||||
QVERIFY(textEditObject);
|
||||
// Delegate creation is deferred until focus in or cursor visibility is forced.
|
||||
QVERIFY(!textEditObject->findChild<QQuickItem*>("cursorInstance"));
|
||||
QVERIFY(!textEditObject->isCursorVisible());
|
||||
|
||||
// Test that the delegate gets created.
|
||||
textEditObject->setFocus(true);
|
||||
QVERIFY(textEditObject->isCursorVisible());
|
||||
QQuickItem* delegateObject = textEditObject->findChild<QQuickItem*>("cursorInstance");
|
||||
QVERIFY(delegateObject);
|
||||
|
||||
const int largerHeight = textEditObject->cursorRectangle().height();
|
||||
|
||||
textEditObject->setCursorPosition(0);
|
||||
QCOMPARE(delegateObject->x(), textEditObject->cursorRectangle().x());
|
||||
QCOMPARE(delegateObject->y(), textEditObject->cursorRectangle().y());
|
||||
QCOMPARE(delegateObject->height(), textEditObject->cursorRectangle().height());
|
||||
|
||||
// Move the cursor to the next line, which has a smaller font.
|
||||
textEditObject->setCursorPosition(5);
|
||||
QCOMPARE(delegateObject->x(), textEditObject->cursorRectangle().x());
|
||||
QCOMPARE(delegateObject->y(), textEditObject->cursorRectangle().y());
|
||||
QVERIFY(textEditObject->cursorRectangle().height() < largerHeight);
|
||||
QCOMPARE(delegateObject->height(), textEditObject->cursorRectangle().height());
|
||||
|
||||
// Test that the delegate gets deleted
|
||||
textEditObject->setCursorDelegate(0);
|
||||
QVERIFY(!textEditObject->findChild<QQuickItem*>("cursorInstance"));
|
||||
}
|
||||
|
||||
/*
|
||||
TextEdit element should only handle left/right keys until the cursor reaches
|
||||
the extent of the text, then they should ignore the keys.
|
||||
|
|
|
@ -0,0 +1,14 @@
|
|||
import QtQuick 2.0
|
||||
|
||||
Item {
|
||||
width: 320
|
||||
height: 480
|
||||
|
||||
Text {
|
||||
anchors.centerIn: parent
|
||||
font.family: "Arial"
|
||||
font.pixelSize: 16
|
||||
textFormat: Text.RichText
|
||||
text: "<img width=16 height=16 src=\"data/logo.png\" />This image is in the start of the text"
|
||||
}
|
||||
}
|
|
@ -0,0 +1,14 @@
|
|||
import QtQuick 2.0
|
||||
|
||||
Item {
|
||||
width: 320
|
||||
height: 480
|
||||
|
||||
Text {
|
||||
anchors.centerIn: parent
|
||||
font.family: "Arial"
|
||||
font.pixelSize: 16
|
||||
textFormat: Text.RichText
|
||||
text: "<img width=16 height=16 src=\"data/logo.png\" />هو أمّا حكومة"
|
||||
}
|
||||
}
|
|
@ -453,6 +453,7 @@ int main(int argc, char *argv[])
|
|||
app->setApplicationName("Qml Runtime");
|
||||
app->setOrganizationName("QtProject");
|
||||
app->setOrganizationDomain("qt-project.org");
|
||||
QCoreApplication::setApplicationVersion(QLatin1String(QT_VERSION_STR));
|
||||
|
||||
qmlRegisterType<Config>("QmlRuntime.Config", 1, 0, "Configuration");
|
||||
qmlRegisterType<PartialScene>("QmlRuntime.Config", 1, 0, "PartialScene");
|
||||
|
|
|
@ -33,6 +33,7 @@
|
|||
int main(int argc, char ** argv)
|
||||
{
|
||||
QApplication app(argc, argv);
|
||||
QCoreApplication::setApplicationVersion(QLatin1String(QT_VERSION_STR));
|
||||
|
||||
MainWindow mainWindow;
|
||||
mainWindow.show();
|
||||
|
|
|
@ -485,6 +485,7 @@ QVariantList findQmlImportsRecursively(const QStringList &qmlDirs, const QString
|
|||
int main(int argc, char *argv[])
|
||||
{
|
||||
QCoreApplication app(argc, argv);
|
||||
QCoreApplication::setApplicationVersion(QLatin1String(QT_VERSION_STR));
|
||||
QStringList args = app.arguments();
|
||||
const QString appName = QFileInfo(app.applicationFilePath()).baseName();
|
||||
if (args.size() < 2) {
|
||||
|
@ -529,7 +530,12 @@ int main(int argc, char *argv[])
|
|||
if (arg.startsWith(QLatin1Char('-')) && arg != QLatin1String("-"))
|
||||
break;
|
||||
++i;
|
||||
*argReceiver += arg;
|
||||
if (!QFile::exists(arg)) {
|
||||
std::cerr << "No such file or directory: \"" << qPrintable(arg) << "\"\n";
|
||||
return 1;
|
||||
} else {
|
||||
*argReceiver += arg;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -135,6 +135,7 @@ static void showException(QV4::ExecutionContext *ctx, const QV4::Value &exceptio
|
|||
int main(int argc, char *argv[])
|
||||
{
|
||||
QCoreApplication app(argc, argv);
|
||||
QCoreApplication::setApplicationVersion(QLatin1String(QT_VERSION_STR));
|
||||
QStringList args = app.arguments();
|
||||
args.removeFirst();
|
||||
|
||||
|
|
|
@ -533,6 +533,7 @@ static void usage(bool showHelp = false)
|
|||
int runQmlmin(int argc, char *argv[])
|
||||
{
|
||||
QCoreApplication app(argc, argv);
|
||||
QCoreApplication::setApplicationVersion(QLatin1String(QT_VERSION_STR));
|
||||
|
||||
const QStringList args = app.arguments();
|
||||
|
||||
|
|
|
@ -987,6 +987,7 @@ int main(int argc, char *argv[])
|
|||
QCoreApplication::setAttribute(Qt::AA_ShareOpenGLContexts, true);
|
||||
|
||||
QGuiApplication app(argc, argv);
|
||||
QCoreApplication::setApplicationVersion(QLatin1String(QT_VERSION_STR));
|
||||
const QStringList args = app.arguments();
|
||||
const QString appName = QFileInfo(app.applicationFilePath()).baseName();
|
||||
if (args.size() < 2) {
|
||||
|
|
|
@ -467,6 +467,7 @@ int main(int argc, char ** argv)
|
|||
app.setApplicationName("QtQmlViewer");
|
||||
app.setOrganizationName("QtProject");
|
||||
app.setOrganizationDomain("qt-project.org");
|
||||
QCoreApplication::setApplicationVersion(QLatin1String(QT_VERSION_STR));
|
||||
|
||||
const QStringList arguments = QCoreApplication::arguments();
|
||||
for (int i = 1, size = arguments.size(); i < size; ++i) {
|
||||
|
|
|
@ -205,6 +205,7 @@ void usage(const char *name)
|
|||
int main(int argc, char ** argv)
|
||||
{
|
||||
QGuiApplication app(argc, argv);
|
||||
QCoreApplication::setApplicationVersion(QLatin1String(QT_VERSION_STR));
|
||||
|
||||
qmlRegisterType<Timer>("QmlTime", 1, 0, "Timer");
|
||||
|
||||
|
|
Loading…
Reference in New Issue