aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLiang Qi <liang.qi@theqtcompany.com>2015-06-30 09:08:35 +0200
committerLiang Qi <liang.qi@theqtcompany.com>2015-06-30 09:08:35 +0200
commit5112821a37ab749f758e354e84703df2d09d5471 (patch)
tree8f19ba6e7661109675b5e1e9b0ddae94b4c96d4f
parent5d2ea1d5e9d6e29a16d0e9333cfc2dc8e7c5b677 (diff)
parenta3f686cf7cc14ff481b972b1170a7ff76d0e0fd0 (diff)
Merge remote-tracking branch 'origin/5.5' into dev
Conflicts: .qmake.conf src/qml/qml/qqmlengine.cpp src/quick/items/qquickitemsmodule.cpp tools/qml/main.cpp Change-Id: Ida8daf6b4d7e675385f2f5514c446e52dedaf136
-rw-r--r--dist/changes-5.5.0105
-rw-r--r--src/qml/compiler/qqmltypecompiler.cpp6
-rw-r--r--src/qml/compiler/qv4ssa.cpp240
-rw-r--r--src/qml/debugger/qqmldebug.h7
-rw-r--r--src/qml/debugger/qqmldebugserver.cpp25
-rw-r--r--src/qml/doc/snippets/qml/createQmlObject.qml3
-rw-r--r--src/qml/doc/snippets/qml/integrating-javascript/includejs/script.js3
-rw-r--r--src/qml/doc/src/cppintegration/contextproperties.qdoc3
-rw-r--r--src/qml/doc/src/cppintegration/data.qdoc5
-rw-r--r--src/qml/doc/src/cppintegration/exposecppattributes.qdoc3
-rw-r--r--src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc10
-rw-r--r--src/qml/doc/src/javascript/dynamicobjectcreation.qdoc13
-rw-r--r--src/qml/doc/src/qmllanguageref/modules/qmldir.qdoc2
-rw-r--r--src/qml/doc/src/qmltypereference.qdoc3
-rw-r--r--src/qml/jsruntime/qv4internalclass.cpp5
-rw-r--r--src/qml/qml/qqmlcomponent.cpp4
-rw-r--r--src/qml/qml/qqmlvaluetype.cpp39
-rw-r--r--src/qml/qml/qqmlvaluetype_p.h18
-rw-r--r--src/qml/qml/qqmlvaluetypewrapper.cpp10
-rw-r--r--src/qml/types/qqmlitemselectionmodel.qdoc19
-rw-r--r--src/quick/doc/snippets/qml/loader/KeyReader.qml3
-rw-r--r--src/quick/doc/snippets/qml/loader/sizeitem.qml29
-rw-r--r--src/quick/doc/snippets/qml/loader/sizeloader.qml29
-rw-r--r--src/quick/doc/snippets/qml/propertyanimation.qml6
-rw-r--r--src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc4
-rw-r--r--src/quick/doc/src/concepts/visualcanvas/visualparent.qdoc8
-rw-r--r--src/quick/doc/src/qmltypereference.qdoc56
-rw-r--r--src/quick/items/qquickimage.cpp1
-rw-r--r--src/quick/items/qquickimage_p.h2
-rw-r--r--src/quick/items/qquickimagebase.cpp6
-rw-r--r--src/quick/items/qquickimagebase_p.h5
-rw-r--r--src/quick/items/qquickitemsmodule.cpp1
-rw-r--r--src/quick/items/qquicklistview.cpp30
-rw-r--r--src/quick/items/qquickloader.cpp11
-rw-r--r--src/quick/items/qquickmousearea.cpp1
-rw-r--r--src/quick/items/qquickmousearea_p.h4
-rw-r--r--src/quick/items/qquickshadereffect.cpp11
-rw-r--r--src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp5
-rw-r--r--src/quick/scenegraph/qsgdefaultglyphnode_p.cpp49
-rw-r--r--src/quick/scenegraph/qsgdefaultrectanglenode.cpp8
-rw-r--r--src/quick/scenegraph/scenegraph.qrc2
-rw-r--r--src/quick/scenegraph/shaders/32bitcolortext.frag9
-rw-r--r--src/quick/scenegraph/shaders/32bitcolortext_core.frag13
-rw-r--r--src/quick/scenegraph/shaders/smoothtexture_core.vert7
-rw-r--r--src/quick/scenegraph/util/qsgatlastexture.cpp11
-rw-r--r--src/quick/util/qquickanimation.cpp5
-rw-r--r--src/quickwidgets/qquickwidget.cpp9
-rw-r--r--tests/auto/qml/debugger/qqmldebuggingenabler/qqmldebuggingenablerserver/qqmldebuggingenablerserver.cpp4
-rw-r--r--tests/auto/qml/qqmllanguage/data/invalidAlias.10.errors.txt2
-rw-r--r--tests/auto/qml/qqmllanguage/data/invalidAlias.6.errors.txt2
-rw-r--r--tests/auto/qml/qqmllanguage/data/invalidAlias.7.errors.txt2
-rw-r--r--tests/auto/qml/qqmllanguage/data/invalidAlias.8.errors.txt2
-rw-r--r--tests/auto/qml/qqmllanguage/data/invalidAlias.9.errors.txt2
-rw-r--r--tests/auto/qml/qqmlvaluetypes/data/rect_compare.qml4
-rw-r--r--tests/auto/qml/qqmlvaluetypes/data/rect_read.qml4
-rw-r--r--tests/auto/qml/qqmlvaluetypes/data/rectf_compare.qml4
-rw-r--r--tests/auto/qml/qqmlvaluetypes/data/rectf_read.qml4
-rw-r--r--tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp8
-rw-r--r--tests/auto/quick/qquicklistview/data/listview-sections_delegate.qml3
-rw-r--r--tests/auto/quick/qquicklistview/tst_qquicklistview.cpp62
-rw-r--r--tests/auto/quick/qquickrectangle/data/gradient-border.qml21
-rw-r--r--tests/auto/quick/qquickrectangle/tst_qquickrectangle.cpp11
-rw-r--r--tests/manual/scenegraph_lancelot/data/text/text_emoji.qml45
-rw-r--r--tools/qml/Info.plist2
-rw-r--r--tools/qml/main.cpp82
-rw-r--r--tools/qmlscene/main.cpp112
66 files changed, 970 insertions, 254 deletions
diff --git a/dist/changes-5.5.0 b/dist/changes-5.5.0
new file mode 100644
index 0000000000..fc1607dc25
--- /dev/null
+++ b/dist/changes-5.5.0
@@ -0,0 +1,105 @@
+Qt 5.5 introduces many new features and improvements as well as bugfixes
+over the 5.4.x series. For more details, refer to the online documentation
+included in this distribution. The documentation is also available online:
+
+ http://qt-project.org/doc/qt-5
+
+The Qt version 5.5 series is binary compatible with the 5.4.x series.
+Applications compiled for 5.4 will continue to run with 5.5.
+
+Some of the changes listed in this file include issue tracking numbers
+corresponding to tasks in the Qt Bug Tracker:
+
+ http://bugreports.qt-project.org/
+
+Each of these identifiers can be entered in the bug tracker to obtain more
+information about a particular change.
+
+****************************************************************************
+* Important Behavior Changes *
+****************************************************************************
+
+QtQml
+-----
+
+ * [QTBUG-44934] Assigning a char to a string will now create a string
+ with the actual character instead of a string representation of the
+ character's code-point. A side effect of this change is that a
+ one-character string also can be assigned to a character type.
+
+QtQuick
+-------
+
+ * Flickable.DragAndOvershootBounds value changed from 2 to 3. This will
+ only affect you if you've worked around enum type checking and have
+ the integer value explicitly in your code.
+
+
+****************************************************************************
+* Library *
+****************************************************************************
+
+
+Android
+-------
+
+ - [QTBUG-43515] Fixed a vertex shader compilation issue on certain OpenGL
+ drivers.
+
+QtQml
+-----
+
+ - [QTBUG-29769] Custom C++ value types annotated with Q_GADGET are now
+ fully accessible in the QML and QJSEngine JavaScript environment.
+
+ - Added qjsEngine(QObject*) getter similar to qmlEngine(object) that
+ allows retrieving the engine for an exposed object.
+
+ - Added Qt.hsva() function
+
+ - XMLHttpRequest:
+ * [QTBUG-35892] XMLHttpRequest now supports the OPTION method in
+ HTTP requests.
+ * QQmlXMLHttpRequest now supports "arraybuffer" binary response type.
+ * Support for synchronous requests
+
+QtQuick
+-------
+
+ - BorderImage: Add support for @2x HiDPI border images. This means, no more need to
+ multiply the border sizes by the device pixel ratio.
+
+ - [QTBUG-37946] Image: An autoTransform property has been added to control
+ whether metadata image transforms such as EXIF orientation are
+ automatically applied. By default it enabled for TIFF images and
+ disabled for JPEG.
+
+ - Changed to use the threaded render loop by default on Windows when
+ running with desktop OpenGL (opengl32.dll).
+ - [QTBUG-42813] QQuickRenderControl can now be used to render the Qt Quick
+ scene on a dedicated render thread, similarly to how the built-in
+ threaded render loop operates.
+ - Added Window.width and Window.height attached properties
+ - Added a Shortcut utility type for catching keyboard shortcuts
+
+ - Flickable:
+ * Introduced Flickable.OvershootBounds behavior that allows content
+ overshooting the boundary when flicked, but does not allow dragging
+ content beyond the boundary of Flickable.
+ * [QTBUG-22407] Flickable handles pixel deltas from trackpad gestures as
+ drags, for a more native feel
+
+ - PinchArea:
+ * Pinch gestures are recognized by the operating system on OSX
+ * Fix infinite recursion when TouchCancel events are received.
+
+ - TextInput:
+ * SetFocusOnTouchRelease is honored
+
+ - [QTBUG-44743] Text: Fixed assert when setting an invalid width or height on an
+ <img> tag in a text element.
+
+ - TextEdit:
+ * [QTBUG-44492] Fixed positioning of text decoration with some fonts.
+ * [QTBUG-45032] Fixed issues with using other vertical alignments than
+ AlignTop.
diff --git a/src/qml/compiler/qqmltypecompiler.cpp b/src/qml/compiler/qqmltypecompiler.cpp
index 9731f3bc12..61b538e726 100644
--- a/src/qml/compiler/qqmltypecompiler.cpp
+++ b/src/qml/compiler/qqmltypecompiler.cpp
@@ -1622,7 +1622,7 @@ bool QQmlComponentAndAliasResolver::resolveAliases()
QQmlPropertyData *targetProperty = resolver.property(property.toString());
if (!targetProperty || targetProperty->coreIndex > 0x0000FFFF) {
- recordError(p->aliasLocation, tr("Invalid alias location"));
+ recordError(p->aliasLocation, tr("Invalid alias target location: %1").arg(property.toString()));
return false;
}
@@ -1636,7 +1636,7 @@ bool QQmlComponentAndAliasResolver::resolveAliases()
if (!subProperty.isEmpty()) {
const QMetaObject *valueTypeMetaObject = QQmlValueTypeFactory::metaObjectForMetaType(type);
if (!valueTypeMetaObject) {
- recordError(p->aliasLocation, tr("Invalid alias location"));
+ recordError(p->aliasLocation, tr("Invalid alias target location: %1").arg(subProperty.toString()));
return false;
}
@@ -1645,7 +1645,7 @@ bool QQmlComponentAndAliasResolver::resolveAliases()
int valueTypeIndex =
valueTypeMetaObject->indexOfProperty(subProperty.toString().toUtf8().constData());
if (valueTypeIndex == -1) {
- recordError(p->aliasLocation, tr("Invalid alias location"));
+ recordError(p->aliasLocation, tr("Invalid alias target location: %1").arg(subProperty.toString()));
return false;
}
Q_ASSERT(valueTypeIndex <= 0x0000FFFF);
diff --git a/src/qml/compiler/qv4ssa.cpp b/src/qml/compiler/qv4ssa.cpp
index a0ed77ffc1..e61a602e64 100644
--- a/src/qml/compiler/qv4ssa.cpp
+++ b/src/qml/compiler/qv4ssa.cpp
@@ -81,16 +81,129 @@ static void showMeTheCode(IR::Function *function, const char *marker)
}
}
-class ProcessedBlocks
+#if !defined(BROKEN_STD_VECTOR_BOOL_OR_BROKEN_STD_FIND)
+// Sanity:
+class BitVector
{
- QBitArray processed;
+ std::vector<bool> bits;
public:
- ProcessedBlocks(IR::Function *function)
+ BitVector(int size = 0, bool value = false)
+ : bits(size, value)
+ {}
+
+ void reserve(int size)
+ { bits.reserve(size); }
+
+ int size() const
{
- processed = QBitArray(function->basicBlockCount(), false);
+ Q_ASSERT(bits.size() < INT_MAX);
+ return static_cast<int>(bits.size());
}
+ void resize(int newSize)
+ { bits.resize(newSize); }
+
+ void assign(int newSize, bool value)
+ { bits.assign(newSize, value); }
+
+ int findNext(int start, bool value, bool wrapAround) const
+ {
+ // The ++operator of std::vector<bool>::iterator in libc++ has a bug when using it on an
+ // iterator pointing to the last element. It will not be set to ::end(), but beyond
+ // that. (It will be set to the first multiple of the native word size that is bigger
+ // than size().)
+ //
+ // See http://llvm.org/bugs/show_bug.cgi?id=19663
+ //
+ // The work-around is to calculate the distance, and compare it to the size() to see if it's
+ // beyond the end, or take the minimum of the distance and the size.
+
+ size_t pos = std::distance(bits.begin(),
+ std::find(bits.begin() + start, bits.end(), value));
+ if (wrapAround && pos >= static_cast<size_t>(size()))
+ pos = std::distance(bits.begin(),
+ std::find(bits.begin(), bits.begin() + start, value));
+
+ pos = qMin(pos, static_cast<size_t>(size()));
+
+ Q_ASSERT(pos <= static_cast<size_t>(size()));
+ Q_ASSERT(pos < INT_MAX);
+
+ return static_cast<int>(pos);
+ }
+
+ bool at(int idx) const
+ { return bits.at(idx); }
+
+ void setBit(int idx)
+ { bits[idx] = true; }
+
+ void clearBit(int idx)
+ { bits[idx] = false; }
+};
+#else // Insanity:
+class BitVector
+{
+ QBitArray bits;
+
+public:
+ BitVector(int size = 0, bool value = false)
+ : bits(size, value)
+ {}
+
+ void reserve(int size)
+ { Q_UNUSED(size); }
+
+ int size() const
+ { return bits.size(); }
+
+ void resize(int newSize)
+ { bits.resize(newSize); }
+
+ void assign(int newSize, bool value)
+ {
+ bits.resize(newSize);
+ bits.fill(value);
+ }
+
+ int findNext(int start, bool value, bool wrapAround) const
+ {
+ for (int i = start, ei = size(); i < ei; ++i) {
+ if (at(i) == value)
+ return i;
+ }
+
+ if (wrapAround) {
+ for (int i = 0, ei = start; i < ei; ++i) {
+ if (at(i) == value)
+ return i;
+ }
+ }
+
+ return size();
+ }
+
+ bool at(int idx) const
+ { return bits.at(idx); }
+
+ void setBit(int idx)
+ { bits[idx] = true; }
+
+ void clearBit(int idx)
+ { bits[idx] = false; }
+};
+#endif
+
+class ProcessedBlocks
+{
+ BitVector processed;
+
+public:
+ ProcessedBlocks(IR::Function *function)
+ : processed(function->basicBlockCount(), false)
+ {}
+
bool alreadyProcessed(BasicBlock *bb) const
{
Q_ASSERT(bb);
@@ -106,7 +219,7 @@ public:
class BasicBlockSet
{
- typedef std::vector<bool> Flags;
+ typedef BitVector Flags;
QVarLengthArray<int, 8> blockNumbers;
Flags *blockFlags;
@@ -119,7 +232,7 @@ public:
const BasicBlockSet &set;
// ### These two members could go into a union, but clang won't compile (https://codereview.qt-project.org/#change,74259)
QVarLengthArray<int, 8>::const_iterator numberIt;
- size_t flagIt;
+ int flagIt;
friend class BasicBlockSet;
const_iterator(const BasicBlockSet &set, bool end)
@@ -138,24 +251,9 @@ public:
}
}
- void findNextWithFlags(size_t start)
+ void findNextWithFlags(int start)
{
- flagIt = std::distance(set.blockFlags->begin(),
- std::find(set.blockFlags->begin() + start,
- set.blockFlags->end(),
- true));
-
- // The ++operator of std::vector<bool>::iterator in libc++ has a bug when using it on an
- // iterator pointing to the last element. It will not be set to ::end(), but beyond
- // that. (It will be set to the first multiple of the native word size that is bigger
- // than size().)
- //
- // See http://llvm.org/bugs/show_bug.cgi?id=19663
- //
- // As we use the size to for our end() iterator, take the minimum of the size and the
- // distance for the flagIt:
- flagIt = qMin(flagIt, set.blockFlags->size());
-
+ flagIt = set.blockFlags->findNext(start, true, /*wrapAround = */false);
Q_ASSERT(flagIt <= set.blockFlags->size());
}
@@ -165,8 +263,8 @@ public:
if (!set.blockFlags) {
return set.function->basicBlock(*numberIt);
} else {
- Q_ASSERT(flagIt <= static_cast<size_t>(set.function->basicBlockCount()));
- return set.function->basicBlock(static_cast<int>(flagIt));
+ Q_ASSERT(flagIt <= set.function->basicBlockCount());
+ return set.function->basicBlock(flagIt);
}
}
@@ -256,7 +354,7 @@ public:
Q_ASSERT(function);
if (blockFlags) {
- (*blockFlags)[bb->index()] = true;
+ blockFlags->setBit(bb->index());
return;
}
@@ -268,10 +366,10 @@ public:
if (blockNumbers.size() == MaxVectorCapacity) {
blockFlags = new Flags(function->basicBlockCount(), false);
for (int i = 0; i < blockNumbers.size(); ++i) {
- blockFlags->operator[](blockNumbers[i]) = true;
+ blockFlags->setBit(blockNumbers[i]);
}
blockNumbers.clear();
- blockFlags->operator[](bb->index()) = true;
+ blockFlags->setBit(bb->index());
} else {
blockNumbers.append(bb->index());
}
@@ -282,7 +380,7 @@ public:
Q_ASSERT(function);
if (blockFlags) {
- (*blockFlags)[bb->index()] = false;
+ blockFlags->clearBit(bb->index());
return;
}
@@ -310,7 +408,7 @@ public:
Q_ASSERT(function);
if (blockFlags)
- return (*blockFlags)[bb->index()];
+ return blockFlags->at(bb->index());
for (int i = 0; i < blockNumbers.size(); ++i) {
if (blockNumbers[i] == bb->index())
@@ -539,12 +637,12 @@ public:
np.todo = children[nodeIndex];
}
- std::vector<bool> DF_done(function->basicBlockCount(), false);
+ BitVector DF_done(function->basicBlockCount(), false);
while (!worklist.empty()) {
BasicBlockIndex node = worklist.back();
- if (DF_done[node]) {
+ if (DF_done.at(node)) {
worklist.pop_back();
continue;
}
@@ -552,7 +650,7 @@ public:
NodeProgress &np = nodeStatus[node];
std::vector<BasicBlockIndex>::iterator it = np.todo.begin();
while (it != np.todo.end()) {
- if (DF_done[*it]) {
+ if (DF_done.at(*it)) {
it = np.todo.erase(it);
} else {
worklist.push_back(*it);
@@ -575,7 +673,7 @@ public:
S.insert(w);
}
}
- DF_done[node] = true;
+ DF_done.setBit(node);
worklist.pop_back();
}
}
@@ -914,8 +1012,8 @@ class VariableCollector: public StmtVisitor, ExprVisitor {
std::vector<Temp> _allTemps;
std::vector<BasicBlockSet> _defsites;
std::vector<std::vector<int> > A_orig;
- std::vector<bool> nonLocals;
- std::vector<bool> killed;
+ BitVector nonLocals;
+ BitVector killed;
BasicBlock *currentBB;
bool isCollectable(Temp *t) const
@@ -979,8 +1077,8 @@ public:
bool isNonLocal(const Temp &var) const
{
Q_ASSERT(!var.isInvalid());
- Q_ASSERT(var.index < nonLocals.size());
- return nonLocals[var.index];
+ Q_ASSERT(static_cast<int>(var.index) < nonLocals.size());
+ return nonLocals.at(var.index);
}
protected:
@@ -1025,7 +1123,7 @@ protected:
addDefInCurrentBlock(t);
// For semi-pruned SSA:
- killed[t->index] = true;
+ killed.setBit(t->index);
}
} else {
s->target->accept(this);
@@ -1037,8 +1135,8 @@ protected:
addTemp(t);
if (isCollectable(t))
- if (!killed[t->index])
- nonLocals[t->index] = true;
+ if (!killed.at(t->index))
+ nonLocals.setBit(t->index);
}
};
@@ -1619,7 +1717,7 @@ void convertToSSA(IR::Function *function, const DominatorTree &df, DefUses &defU
VariableCollector variables(function);
// Prepare for phi node insertion:
- std::vector<std::vector<bool> > A_phi;
+ std::vector<BitVector > A_phi;
const size_t ei = function->basicBlockCount();
A_phi.resize(ei);
for (size_t i = 0; i != ei; ++i)
@@ -1646,7 +1744,7 @@ void convertToSSA(IR::Function *function, const DominatorTree &df, DefUses &defU
BasicBlock *y = *it;
if (!A_phi.at(y->index()).at(a.index)) {
insertPhiNode(a, y, function);
- A_phi[y->index()].at(a.index) = true;
+ A_phi[y->index()].setBit(a.index);
const std::vector<int> &varsInBlockY = variables.inBlock(y);
if (std::find(varsInBlockY.begin(), varsInBlockY.end(), a.index) == varsInBlockY.end())
W.push_back(y);
@@ -1723,10 +1821,10 @@ class StatementWorklist
{
IR::Function *theFunction;
std::vector<Stmt *> stmts;
- std::vector<bool> worklist;
+ BitVector worklist;
unsigned worklistSize;
std::vector<int> replaced;
- std::vector<bool> removed;
+ BitVector removed;
Q_DISABLE_COPY(StatementWorklist)
@@ -1750,7 +1848,7 @@ public:
continue;
stmts[s->id()] = s;
- worklist[s->id()] = true;
+ worklist.setBit(s->id());
++worklistSize;
}
}
@@ -1765,7 +1863,7 @@ public:
if (!s)
continue;
- worklist[s->id()] = true;
+ worklist.setBit(s->id());
++worklistSize;
}
@@ -1776,10 +1874,9 @@ public:
void remove(Stmt *stmt)
{
replaced[stmt->id()] = Stmt::InvalidId;
- removed[stmt->id()] = true;
- std::vector<bool>::reference inWorklist = worklist[stmt->id()];
- if (inWorklist) {
- inWorklist = false;
+ removed.setBit(stmt->id());
+ if (worklist.at(stmt->id())) {
+ worklist.clearBit(stmt->id());
Q_ASSERT(worklistSize > 0);
--worklistSize;
}
@@ -1789,15 +1886,15 @@ public:
{
Q_ASSERT(oldStmt);
Q_ASSERT(replaced[oldStmt->id()] == Stmt::InvalidId);
- Q_ASSERT(removed[oldStmt->id()] == false);
+ Q_ASSERT(removed.at(oldStmt->id()) == false);
Q_ASSERT(newStmt);
registerNewStatement(newStmt);
Q_ASSERT(replaced[newStmt->id()] == Stmt::InvalidId);
- Q_ASSERT(removed[newStmt->id()] == false);
+ Q_ASSERT(removed.at(newStmt->id()) == false);
replaced[oldStmt->id()] = newStmt->id();
- worklist[oldStmt->id()] = false;
+ worklist.clearBit(oldStmt->id());
}
void applyToFunction()
@@ -1818,7 +1915,7 @@ public:
Q_ASSERT(id != Stmt::InvalidId);
Q_ASSERT(static_cast<unsigned>(stmt->id()) < stmts.size());
- if (removed[id]) {
+ if (removed.at(id)) {
bb->removeStatement(i);
} else {
if (id != stmt->id())
@@ -1847,10 +1944,10 @@ public:
return *this;
Q_ASSERT(s->id() >= 0);
- Q_ASSERT(static_cast<unsigned>(s->id()) < worklist.size());
+ Q_ASSERT(s->id() < worklist.size());
- if (!worklist[s->id()]) {
- worklist[s->id()] = true;
+ if (!worklist.at(s->id())) {
+ worklist.setBit(s->id());
++worklistSize;
}
@@ -1860,11 +1957,10 @@ public:
StatementWorklist &operator-=(Stmt *s)
{
Q_ASSERT(s->id() >= 0);
- Q_ASSERT(static_cast<unsigned>(s->id()) < worklist.size());
+ Q_ASSERT(s->id() < worklist.size());
- std::vector<bool>::reference inWorklist = worklist[s->id()];
- if (inWorklist) {
- inWorklist = false;
+ if (worklist.at(s->id())) {
+ worklist.clearBit(s->id());
Q_ASSERT(worklistSize > 0);
--worklistSize;
}
@@ -1884,18 +1980,13 @@ public:
const int startAt = last ? last->id() + 1 : 0;
Q_ASSERT(startAt >= 0);
- Q_ASSERT(static_cast<unsigned>(startAt) <= worklist.size());
+ Q_ASSERT(startAt <= worklist.size());
- Q_ASSERT(worklist.size() == stmts.size());
+ Q_ASSERT(static_cast<size_t>(worklist.size()) == stmts.size());
- // Do not compare the result of find with the end iterator, because some libc++ versions
- // have a bug where the result of the ++operator is past-the-end of the vector, but unequal
- // to end().
- size_t pos = std::find(worklist.begin() + startAt, worklist.end(), true) - worklist.begin();
- if (pos >= worklist.size())
- pos = std::find(worklist.begin(), worklist.begin() + startAt, true) - worklist.begin();
+ int pos = worklist.findNext(startAt, true, /*wrapAround = */true);
- worklist[pos] = false;
+ worklist.clearBit(pos);
Q_ASSERT(worklistSize > 0);
--worklistSize;
Stmt *s = stmts.at(pos);
@@ -1917,9 +2008,9 @@ public:
int newSize = s->id() + 1;
stmts.resize(newSize, 0);
- worklist.resize(newSize, false);
+ worklist.resize(newSize);
replaced.resize(newSize, Stmt::InvalidId);
- removed.resize(newSize, false);
+ removed.resize(newSize);
}
stmts[s->id()] = s;
@@ -1928,7 +2019,8 @@ public:
private:
void grow()
{
- size_t newCapacity = ((stmts.capacity() + 1) * 3) / 2;
+ Q_ASSERT(stmts.capacity() < INT_MAX / 2);
+ int newCapacity = ((static_cast<int>(stmts.capacity()) + 1) * 3) / 2;
stmts.reserve(newCapacity);
worklist.reserve(newCapacity);
replaced.reserve(newCapacity);
diff --git a/src/qml/debugger/qqmldebug.h b/src/qml/debugger/qqmldebug.h
index 421c6968b9..58afa004a0 100644
--- a/src/qml/debugger/qqmldebug.h
+++ b/src/qml/debugger/qqmldebug.h
@@ -42,8 +42,13 @@ QT_BEGIN_NAMESPACE
struct Q_QML_EXPORT QQmlDebuggingEnabler
{
+ enum StartMode {
+ DoNotWaitForClient,
+ WaitForClient
+ };
+
QQmlDebuggingEnabler(bool printWarning = true);
- static bool startTcpDebugServer(int port, bool block = false,
+ static bool startTcpDebugServer(int port, StartMode mode = DoNotWaitForClient,
const QString &hostName = QString());
static bool connectToLocalDebugger(const QString &socketFileName, bool block = false);
};
diff --git a/src/qml/debugger/qqmldebugserver.cpp b/src/qml/debugger/qqmldebugserver.cpp
index 7323d3bf46..0e6a182b1a 100644
--- a/src/qml/debugger/qqmldebugserver.cpp
+++ b/src/qml/debugger/qqmldebugserver.cpp
@@ -835,18 +835,29 @@ bool QQmlDebugServerPrivate::enable(Action action)
}
/*!
+ * \enum QQmlDebuggingEnabler::StartMode
+ *
+ * Defines the debug server's start behavior. You can interrupt QML engines starting while a debug
+ * client is connecting, in order to set breakpoints in or profile startup code.
+ *
+ * \value DoNotWaitForClient Run any QML engines as usual while the debug services are connecting.
+ * \value WaitForClient If a QML engine starts while the debug services are connecting,
+ * interrupt it until they are done.
+ */
+
+/*!
* Enables debugging for QML engines created after calling this function. The debug server will
* listen on \a port at \a hostName and block the QML engine until it receives a connection if
- * \a block is true. If \a block is not specified it won't block and if \a hostName isn't specified
- * it will listen on all available interfaces. You can only start one debug server at a time. A
- * debug server may have already been started if the -qmljsdebugger= command line argument was
- * given. This method returns \c true if a new debug server was successfully started, or \c false
- * otherwise.
+ * \a mode is \c WaitForClient. If \a mode is not specified it won't block and if \a hostName is not
+ * specified it will listen on all available interfaces. You can only start one debug server at a
+ * time. A debug server may have already been started if the -qmljsdebugger= command line argument
+ * was given. This method returns \c true if a new debug server was successfully started, or
+ * \c false otherwise.
*/
-bool QQmlDebuggingEnabler::startTcpDebugServer(int port, bool block, const QString &hostName)
+bool QQmlDebuggingEnabler::startTcpDebugServer(int port, StartMode mode, const QString &hostName)
{
#ifndef QQML_NO_DEBUG_PROTOCOL
- return QQmlDebugServerPrivate::enable(StartTcpServerAction(port, port, block, hostName));
+ return QQmlDebugServerPrivate::enable(StartTcpServerAction(port, port, mode == WaitForClient, hostName));
#else
Q_UNUSED(port);
Q_UNUSED(block);
diff --git a/src/qml/doc/snippets/qml/createQmlObject.qml b/src/qml/doc/snippets/qml/createQmlObject.qml
index a6753823b9..b12c6c2ea5 100644
--- a/src/qml/doc/snippets/qml/createQmlObject.qml
+++ b/src/qml/doc/snippets/qml/createQmlObject.qml
@@ -49,7 +49,8 @@ Rectangle {
function createIt() {
//![0]
var newObject = Qt.createQmlObject('import QtQuick 2.0; Rectangle {color: "red"; width: 20; height: 20}',
- parentItem, "dynamicSnippet1");
+ parentItem,
+ "dynamicSnippet1");
//![0]
//![destroy]
diff --git a/src/qml/doc/snippets/qml/integrating-javascript/includejs/script.js b/src/qml/doc/snippets/qml/integrating-javascript/includejs/script.js
index 0073e4df8f..814e0b444f 100644
--- a/src/qml/doc/snippets/qml/integrating-javascript/includejs/script.js
+++ b/src/qml/doc/snippets/qml/integrating-javascript/includejs/script.js
@@ -42,7 +42,8 @@
Qt.include("factorial.js")
function showCalculations(value) {
- console.log("Call factorial() from script.js:",
+ console.log(
+ "Call factorial() from script.js:",
factorial(value));
}
//![0]
diff --git a/src/qml/doc/src/cppintegration/contextproperties.qdoc b/src/qml/doc/src/cppintegration/contextproperties.qdoc
index 48532ccae2..83f49bdcf0 100644
--- a/src/qml/doc/src/cppintegration/contextproperties.qdoc
+++ b/src/qml/doc/src/cppintegration/contextproperties.qdoc
@@ -65,10 +65,13 @@ QML code invokes a method on the object instance:
\table
\row
+\li C++
\li
\snippet qml/qtbinding/context-advanced/applicationdata.h 0
\codeline
\snippet qml/qtbinding/context-advanced/main.cpp 0
+\row
+\li QML
\li
\snippet qml/qtbinding/context-advanced/MyItem.qml 0
\endtable
diff --git a/src/qml/doc/src/cppintegration/data.qdoc b/src/qml/doc/src/cppintegration/data.qdoc
index a11d8ba510..e153ca3d8b 100644
--- a/src/qml/doc/src/cppintegration/data.qdoc
+++ b/src/qml/doc/src/cppintegration/data.qdoc
@@ -176,7 +176,10 @@ converted to JavaScript array and object values, repectively:
\table
\header
\row
+\li QML
\li \snippet qml/qtbinding/variantlistmap/MyItem.qml 0
+\row
+\li C++
\li \snippet qml/qtbinding/variantlistmap/main.cpp 0
\endtable
@@ -223,7 +226,7 @@ Item {
}
}
\endqml
-
+\row
\li
\code
// C++
diff --git a/src/qml/doc/src/cppintegration/exposecppattributes.qdoc b/src/qml/doc/src/cppintegration/exposecppattributes.qdoc
index 0d81930592..e1db5c9d57 100644
--- a/src/qml/doc/src/cppintegration/exposecppattributes.qdoc
+++ b/src/qml/doc/src/cppintegration/exposecppattributes.qdoc
@@ -395,6 +395,7 @@ methods, as shown below right:
\table
\row
+\li C++
\li
\code
int main(int argc, char *argv[]) {
@@ -409,6 +410,8 @@ methods, as shown below right:
return app.exec();
}
\endcode
+\row
+\li QML
\li
\qml
// MyItem.qml
diff --git a/src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc b/src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc
index 25d98dbc0d..2a644cafff 100644
--- a/src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc
+++ b/src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc
@@ -170,7 +170,10 @@ QMetaObject::invokeMethod():
\table
\row
+\li QML
\li \snippet qml/qtbinding/functions-qml/MyItem.qml 0
+\row
+\li C++
\li \snippet qml/qtbinding/functions-qml/main.cpp 0
\endtable
@@ -195,6 +198,7 @@ QObject::connect(), so that the \c cppSlot() method is called whenever the
\row
\li
\snippet qml/qtbinding/signals-qml/MyItem.qml 0
+\row
\li
\snippet qml/qtbinding/signals-qml/myclass.h 0
\codeline
@@ -235,8 +239,10 @@ QVariant type:
void cppSlot(const QVariant &v) {
qDebug() << "Called the C++ slot with value:" << v;
- QQuickItem *item = qobject_cast<QQuickItem*>(v.value<QObject*>());
- qDebug() << "Item dimensions:" << item->width() << item->height();
+ QQuickItem *item =
+ qobject_cast<QQuickItem*>(v.value<QObject*>());
+ qDebug() << "Item dimensions:" << item->width()
+ << item->height();
}
};
diff --git a/src/qml/doc/src/javascript/dynamicobjectcreation.qdoc b/src/qml/doc/src/javascript/dynamicobjectcreation.qdoc
index 2988f3a684..acd7188db7 100644
--- a/src/qml/doc/src/javascript/dynamicobjectcreation.qdoc
+++ b/src/qml/doc/src/javascript/dynamicobjectcreation.qdoc
@@ -143,6 +143,15 @@ If the string of QML imports files using relative paths, the path should be
relative to the file in which the parent object (the second argument to the
method) is defined.
+\important When building static QML applications, which is enforced on platforms like iOS,
+QML files are scanned to detect import dependencies. That way, all
+necessary plugins and resources are resolved at compile time.
+However, only explicit import statements are considered (those found at
+the top of a QML file), and not import statements enclosed within string literals.
+To support static builds, you therefore need to ensure that QML files
+using \l{QtQml::Qt::createQmlObject()}{Qt.createQmlObject()},
+explicitly contain all necessary imports at the top of the file in addition
+to inside the string literals.
\section1 Maintaining Dynamically Created Objects
@@ -191,10 +200,10 @@ destroy itself:
\table
\row
\li \c application.qml
-\li \c SelfDestroyingRect.qml
+\li \snippet qml/dynamicObjects-destroy.qml 0
\row
-\li \snippet qml/dynamicObjects-destroy.qml 0
+\li \c SelfDestroyingRect.qml
\li \snippet qml/SelfDestroyingRect.qml 0
\endtable
diff --git a/src/qml/doc/src/qmllanguageref/modules/qmldir.qdoc b/src/qml/doc/src/qmllanguageref/modules/qmldir.qdoc
index ed73a2b9ba..201cee16e6 100644
--- a/src/qml/doc/src/qmllanguageref/modules/qmldir.qdoc
+++ b/src/qml/doc/src/qmllanguageref/modules/qmldir.qdoc
@@ -46,7 +46,7 @@ documentation about
A \c qmldir file is a plain-text file that contains
the following commands:
-\table
+\table 70%
\header
\li Syntax
\li Usage
diff --git a/src/qml/doc/src/qmltypereference.qdoc b/src/qml/doc/src/qmltypereference.qdoc
index 48f7ba1bae..31133c862f 100644
--- a/src/qml/doc/src/qmltypereference.qdoc
+++ b/src/qml/doc/src/qmltypereference.qdoc
@@ -208,6 +208,9 @@ Or use the \l{QtQml::Qt::rect()}{Qt.rect()} function:
CustomObject { myRectProperty: Qt.rect(50, 50, 100, 100) }
\endqml
+The \c rect type also exposes read-only \c left, \c right, \c top and \c bottom
+attributes. These are the same as their \l {QRectF}{C++ counterparts}.
+
When integrating with C++, note that any QRect or QRectF value
\l{qtqml-cppintegration-data.html}{passed into QML from C++} is automatically
converted into a \c rect value, and vice-versa. When a \c rect value is passed to C++, it
diff --git a/src/qml/jsruntime/qv4internalclass.cpp b/src/qml/jsruntime/qv4internalclass.cpp
index 49b284b979..a90e8e3689 100644
--- a/src/qml/jsruntime/qv4internalclass.cpp
+++ b/src/qml/jsruntime/qv4internalclass.cpp
@@ -199,10 +199,7 @@ InternalClass *InternalClass::nonExtensible()
if (!extensible)
return this;
- Transition temp;
- temp.lookup = 0;
- temp.flags = Transition::NotExtensible;
-
+ Transition temp = { Q_NULLPTR, Q_NULLPTR, Transition::NotExtensible};
Transition &t = lookupOrInsertTransition(temp);
if (t.lookup)
return t.lookup;
diff --git a/src/qml/qml/qqmlcomponent.cpp b/src/qml/qml/qqmlcomponent.cpp
index 425c5e507c..d46f612e40 100644
--- a/src/qml/qml/qqmlcomponent.cpp
+++ b/src/qml/qml/qqmlcomponent.cpp
@@ -246,9 +246,9 @@ V4_DEFINE_EXTENSION(QQmlComponentExtension, componentExtension);
\table
\row
\li MyItem.qml
- \li main.qml
- \row
\li \snippet qml/component/MyItem.qml 0
+ \row
+ \li main.qml
\li \snippet qml/component/main.qml 0
\endtable
*/
diff --git a/src/qml/qml/qqmlvaluetype.cpp b/src/qml/qml/qqmlvaluetype.cpp
index cc4a9bebc5..7ebfcd64b7 100644
--- a/src/qml/qml/qqmlvaluetype.cpp
+++ b/src/qml/qml/qqmlvaluetype.cpp
@@ -388,6 +388,26 @@ void QQmlRectFValueType::setHeight(qreal h)
v.setHeight(h);
}
+qreal QQmlRectFValueType::left() const
+{
+ return v.left();
+}
+
+qreal QQmlRectFValueType::right() const
+{
+ return v.right();
+}
+
+qreal QQmlRectFValueType::top() const
+{
+ return v.top();
+}
+
+qreal QQmlRectFValueType::bottom() const
+{
+ return v.bottom();
+}
+
int QQmlRectValueType::x() const
{
return v.x();
@@ -428,6 +448,25 @@ void QQmlRectValueType::setHeight(int h)
v.setHeight(h);
}
+int QQmlRectValueType::left() const
+{
+ return v.left();
+}
+
+int QQmlRectValueType::right() const
+{
+ return v.right();
+}
+
+int QQmlRectValueType::top() const
+{
+ return v.top();
+}
+
+int QQmlRectValueType::bottom() const
+{
+ return v.bottom();
+}
QQmlEasingValueType::Type QQmlEasingValueType::type() const
{
diff --git a/src/qml/qml/qqmlvaluetype_p.h b/src/qml/qml/qqmlvaluetype_p.h
index 0dcf78c519..abd73d7f35 100644
--- a/src/qml/qml/qqmlvaluetype_p.h
+++ b/src/qml/qml/qqmlvaluetype_p.h
@@ -153,6 +153,10 @@ struct QQmlRectFValueType
Q_PROPERTY(qreal y READ y WRITE setY FINAL)
Q_PROPERTY(qreal width READ width WRITE setWidth FINAL)
Q_PROPERTY(qreal height READ height WRITE setHeight FINAL)
+ Q_PROPERTY(qreal left READ left DESIGNABLE false FINAL)
+ Q_PROPERTY(qreal right READ right DESIGNABLE false FINAL)
+ Q_PROPERTY(qreal top READ top DESIGNABLE false FINAL)
+ Q_PROPERTY(qreal bottom READ bottom DESIGNABLE false FINAL)
Q_GADGET
public:
Q_INVOKABLE QString toString() const;
@@ -165,6 +169,11 @@ public:
qreal height() const;
void setWidth(qreal);
void setHeight(qreal);
+
+ qreal left() const;
+ qreal right() const;
+ qreal top() const;
+ qreal bottom() const;
};
struct QQmlRectValueType
@@ -174,6 +183,10 @@ struct QQmlRectValueType
Q_PROPERTY(int y READ y WRITE setY FINAL)
Q_PROPERTY(int width READ width WRITE setWidth FINAL)
Q_PROPERTY(int height READ height WRITE setHeight FINAL)
+ Q_PROPERTY(int left READ left DESIGNABLE false FINAL)
+ Q_PROPERTY(int right READ right DESIGNABLE false FINAL)
+ Q_PROPERTY(int top READ top DESIGNABLE false FINAL)
+ Q_PROPERTY(int bottom READ bottom DESIGNABLE false FINAL)
Q_GADGET
public:
int x() const;
@@ -185,6 +198,11 @@ public:
int height() const;
void setWidth(int);
void setHeight(int);
+
+ int left() const;
+ int right() const;
+ int top() const;
+ int bottom() const;
};
struct QQmlEasingValueType
diff --git a/src/qml/qml/qqmlvaluetypewrapper.cpp b/src/qml/qml/qqmlvaluetypewrapper.cpp
index 58b6937432..b0ab85199d 100644
--- a/src/qml/qml/qqmlvaluetypewrapper.cpp
+++ b/src/qml/qml/qqmlvaluetypewrapper.cpp
@@ -314,10 +314,12 @@ ReturnedValue QQmlValueTypeWrapper::method_toString(CallContext *ctx)
const QMetaObject *mo = w->d()->propertyCache->metaObject();
const int propCount = mo->propertyCount();
for (int i = 0; i < propCount; ++i) {
- QVariant value = mo->property(i).readOnGadget(w->d()->gadgetPtr);
- result += value.toString();
- if (i < propCount - 1)
- result += QStringLiteral(", ");
+ if (mo->property(i).isDesignable()) {
+ QVariant value = mo->property(i).readOnGadget(w->d()->gadgetPtr);
+ if (i > 0)
+ result += QLatin1String(", ");
+ result += value.toString();
+ }
}
result += QLatin1Char(')');
}
diff --git a/src/qml/types/qqmlitemselectionmodel.qdoc b/src/qml/types/qqmlitemselectionmodel.qdoc
index 7a61416153..185ffb5fa4 100644
--- a/src/qml/types/qqmlitemselectionmodel.qdoc
+++ b/src/qml/types/qqmlitemselectionmodel.qdoc
@@ -50,22 +50,31 @@
/*!
\qmlproperty bool ItemSelectionModel::hasSelection
+ \readonly
- Read-only property. It will trigger property binding updates every time
- \l selectionChanged() is emitted, even though its value hasn't changed.
+ It will trigger property binding updates every time \l selectionChanged()
+ is emitted, even though its value hasn't changed.
\sa selection(), selectedIndexes(), select(), selectionChanged()
*/
/*!
\qmlproperty QModelIndex ItemSelectionModel::currentIndex
+ \readonly
- Read-only property. Use \l setCurrentIndex() to set its value.
+ Use \l setCurrentIndex() to set its value.
\sa setCurrentIndex(), currentChanged()
*/
/*!
+ \qmlproperty QModelIndexList ItemSelectionModel::selectedIndexes
+ \readonly
+
+ Contains the list of all the indexes in the selection model.
+*/
+
+/*!
\qmlmethod bool ItemSelectionModel::isSelected(QModelIndex index)
*/
@@ -86,10 +95,6 @@
*/
/*!
- \qmlmethod QModelIndexList ItemSelectionModel::selectedIndexes()
-*/
-
-/*!
\qmlmethod QModelIndexList ItemSelectionModel::selectedRows(int column)
*/
diff --git a/src/quick/doc/snippets/qml/loader/KeyReader.qml b/src/quick/doc/snippets/qml/loader/KeyReader.qml
index a61d2bd11a..eebd72b96d 100644
--- a/src/quick/doc/snippets/qml/loader/KeyReader.qml
+++ b/src/quick/doc/snippets/qml/loader/KeyReader.qml
@@ -37,7 +37,8 @@ Item {
Item {
focus: true
Keys.onPressed: {
- console.log("Loaded item captured:", event.text);
+ console.log("Loaded item captured:",
+ event.text);
event.accepted = true;
}
}
diff --git a/src/quick/doc/snippets/qml/loader/sizeitem.qml b/src/quick/doc/snippets/qml/loader/sizeitem.qml
index db79e28816..750ea9f58a 100644
--- a/src/quick/doc/snippets/qml/loader/sizeitem.qml
+++ b/src/quick/doc/snippets/qml/loader/sizeitem.qml
@@ -34,21 +34,22 @@
import QtQuick 2.0
Item {
- width: 200; height: 200
+ width: 200; height: 200
- Loader {
- // position the Loader in the center of the parent
- anchors.centerIn: parent
- sourceComponent: rect
- }
+ Loader {
+ // position the Loader in the center
+ // of the parent
+ anchors.centerIn: parent
+ sourceComponent: rect
+ }
- Component {
- id: rect
- Rectangle {
- width: 50
- height: 50
- color: "red"
- }
- }
+ Component {
+ id: rect
+ Rectangle {
+ width: 50
+ height: 50
+ color: "red"
+ }
+ }
}
//![0]
diff --git a/src/quick/doc/snippets/qml/loader/sizeloader.qml b/src/quick/doc/snippets/qml/loader/sizeloader.qml
index d691f460cb..9643768774 100644
--- a/src/quick/doc/snippets/qml/loader/sizeloader.qml
+++ b/src/quick/doc/snippets/qml/loader/sizeloader.qml
@@ -34,21 +34,22 @@
import QtQuick 2.0
Item {
- width: 200; height: 200
+ width: 200; height: 200
- Loader {
- // Explicitly set the size of the Loader to the parent item's size
- anchors.fill: parent
- sourceComponent: rect
- }
+ Loader {
+ // Explicitly set the size of the
+ // Loader to the parent item's size
+ anchors.fill: parent
+ sourceComponent: rect
+ }
- Component {
- id: rect
- Rectangle {
- width: 50
- height: 50
- color: "red"
- }
- }
+ Component {
+ id: rect
+ Rectangle {
+ width: 50
+ height: 50
+ color: "red"
+ }
+ }
}
//![0]
diff --git a/src/quick/doc/snippets/qml/propertyanimation.qml b/src/quick/doc/snippets/qml/propertyanimation.qml
index 2d8a3744ce..1cbb84e1db 100644
--- a/src/quick/doc/snippets/qml/propertyanimation.qml
+++ b/src/quick/doc/snippets/qml/propertyanimation.qml
@@ -92,7 +92,11 @@ Rectangle {
color: "red"
// this is a standalone animation, it's not running by default
- PropertyAnimation { id: animation; target: theRect; property: "width"; to: 30; duration: 500 }
+ PropertyAnimation { id: animation;
+ target: theRect;
+ property: "width";
+ to: 30;
+ duration: 500 }
MouseArea { anchors.fill: parent; onClicked: animation.running = true }
}
diff --git a/src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc b/src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc
index 40190051e2..dffcabbd5b 100644
--- a/src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc
+++ b/src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc
@@ -169,6 +169,7 @@ created directly as types within QML:
\table
\row
+\li C++
\li
\code
class MyModelPlugin : public QQmlExtensionPlugin
@@ -183,7 +184,8 @@ public:
}
}
\endcode
-
+\row
+\li QML
\li
\qml
MyModel {
diff --git a/src/quick/doc/src/concepts/visualcanvas/visualparent.qdoc b/src/quick/doc/src/concepts/visualcanvas/visualparent.qdoc
index 9ccb0b53b3..fd5bf51307 100644
--- a/src/quick/doc/src/concepts/visualcanvas/visualparent.qdoc
+++ b/src/quick/doc/src/concepts/visualcanvas/visualparent.qdoc
@@ -63,7 +63,9 @@ import QtQuick 2.0
Item {
width: 100; height: 100
- Rectangle { width: 50; height: 50; color: "red" }
+ Rectangle { width: 50;
+ height: 50;
+ color: "red" }
}
\endcode
@@ -75,7 +77,9 @@ Item {
width: 100; height: 100
data: [
- Rectangle { width: 50; height: 50; color: "red" }
+ Rectangle { width: 50;
+ height: 50;
+ color: "red" }
]
}
\endcode
diff --git a/src/quick/doc/src/qmltypereference.qdoc b/src/quick/doc/src/qmltypereference.qdoc
index e3641f2d76..630e0f58bc 100644
--- a/src/quick/doc/src/qmltypereference.qdoc
+++ b/src/quick/doc/src/qmltypereference.qdoc
@@ -252,7 +252,7 @@ available when you import \c QtQuick.
The vector2d type has the following idempotent functions which can be
invoked in QML:
- \table
+ \table 60%
\header
\li Function Signature
\li Description
@@ -430,9 +430,11 @@ console.log(c); // 32
the 4x4 \c matrix with the matrix applied post-vector
\li \code
var a = Qt.vector3d(1,2,3);
-var b = Qt.matrix4x4(4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19);
+var b = Qt.matrix4x4(4,5,6,7,8,9,10,11,
+ 12,13,14,15,16,17,18,19);
var c = a.times(b);
-console.log(c.toString()); // QVector3D(0.774194, 0.849462, 0.924731)
+console.log(c.toString());
+// QVector3D(0.774194, 0.849462, 0.924731)
\endcode
\row
@@ -481,7 +483,8 @@ console.log(c.toString()); // QVector3D(-3, -3, -3)
\li \code
var a = Qt.vector3d(1,2,3);
var b = a.normalized();
-console.log(b.toString()); // QVector3D(0.267261, 0.534522, 0.801784)
+console.log(b.toString());
+// QVector3D(0.267261, 0.534522, 0.801784)
\endcode
\row
@@ -515,7 +518,8 @@ console.log(b.toString()); // QVector4D(1, 2, 3, 0)
\li bool fuzzyEquals(vector3d other, real epsilon)
\li Returns true if \c this vector3d is approximately equal to the \c other vector3d.
The approximation will be true if each attribute of \c this is within \c epsilon
- of \c other. Note that \c epsilon is an optional argument, the default \c epsilon
+ of \c other.
+ Note that \c epsilon is an optional argument, the default \c epsilon
is 0.00001.
\li \code
var a = Qt.vector3d(1,2,3);
@@ -591,7 +595,8 @@ console.log(c.toString()); // QVector4D(5, 12, 21, 32)
var a = Qt.vector4d(1,2,3,4);
var b = 4.48;
var c = a.times(b);
-console.log(c.toString()); // QVector3D(4.48, 8.96, 13.44, 17.92)
+console.log(c.toString()); // QVector3D(4.48, 8.96,
+ 13.44, 17.92)
\endcode
\row
@@ -620,7 +625,8 @@ console.log(c.toString()); // QVector4D(-4, -4, -4, -4)
\li \code
var a = Qt.vector4d(1,2,3,4);
var b = a.normalized();
-console.log(b.toString()); // QVector4D(0.182574, 0.365148, 0.547723, 0.730297)
+console.log(b.toString());
+// QVector4D(0.182574, 0.365148, 0.547723, 0.730297)
\endcode
\row
@@ -701,7 +707,7 @@ console.log(c + " " + d); // false true
The matrix4x4 type has the following idempotent functions which can be
invoked in QML:
- \table
+ \table 70 %
\header
\li Function Signature
\li Description
@@ -715,7 +721,9 @@ console.log(c + " " + d); // false true
var a = Qt.matrix4x4(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16);
var b = Qt.matrix4x4(4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19);
var c = a.times(b);
-console.log(c.toString()); // QMatrix4x4(120, 130, 140, 150, 280, 306, 332, 358, 440, 482, 524, 566, 600, 658, 716, 774)
+console.log(c.toString());
+// QMatrix4x4(120, 130, 140, 150, 280, 306, 332, 358, 440, 482,
+//524, 566, 600, 658, 716, 774)
\endcode
\row
@@ -749,7 +757,9 @@ console.log(c.toString()); // QVector3D(0.155556, 0.437037, 0.718518)
var a = Qt.matrix4x4(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16);
var b = 4.48;
var c = a.times(b);
-console.log(c.toString()); // QMatrix4x4(4.48, 8.96, 13.44, 17.92, 22.4, 26.88, 31.36, 35.84, 40.32, 44.8, 49.28, 53.76, 58.24, 62.72, 67.2, 71.68)
+console.log(c.toString());
+// QMatrix4x4(4.48, 8.96, 13.44, 17.92, 22.4, 26.88, 31.36, 35.84,
+// 40.32, 44.8, 49.28, 53.76, 58.24, 62.72, 67.2, 71.68)
\endcode
\row
@@ -759,7 +769,9 @@ console.log(c.toString()); // QMatrix4x4(4.48, 8.96, 13.44, 17.92, 22.4, 26.88,
var a = Qt.matrix4x4(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16);
var b = Qt.matrix4x4(5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20);
var c = a.plus(b);
-console.log(c.toString()); // QMatrix4x4(6, 8, 10, 12, 14, 16, 18, 20, 22, 24, 26, 28, 30, 32, 34, 36)
+console.log(c.toString());
+// QMatrix4x4(6, 8, 10, 12, 14, 16, 18, 20, 22,
+// 24, 26, 28, 30, 32, 34, 36)
\endcode
\row
@@ -769,7 +781,9 @@ console.log(c.toString()); // QMatrix4x4(6, 8, 10, 12, 14, 16, 18, 20, 22, 24, 2
var a = Qt.matrix4x4(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16);
var b = Qt.matrix4x4(5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20);
var c = a.minus(b);
-console.log(c.toString()); // QMatrix4x4(-4, -4, -4, -4, -4, -4, -4, -4, -4, -4, -4, -4, -4, -4, -4, -4)
+console.log(c.toString());
+// QMatrix4x4(-4, -4, -4, -4, -4, -4, -4, -4, -4,
+// -4, -4, -4, -4, -4, -4, -4)
\endcode
\row
@@ -780,7 +794,8 @@ console.log(c.toString()); // QMatrix4x4(-4, -4, -4, -4, -4, -4, -4, -4, -4, -4,
var a = Qt.matrix4x4(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16);
var b = Qt.vector4d(a.m21, a.m22, a.m23, a.m24);
var c = a.row(2); // zero based access! so not equal to b
-console.log(b.toString() + " " + c.toString()); // QVector4D(5, 6, 7, 8) QVector4D(9, 10, 11, 12)
+console.log(b.toString() + " " + c.toString());
+// QVector4D(5, 6, 7, 8) QVector4D(9, 10, 11, 12)
\endcode
\row
@@ -791,7 +806,8 @@ console.log(b.toString() + " " + c.toString()); // QVector4D(5, 6, 7, 8) QVector
var a = Qt.matrix4x4(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16);
var b = Qt.vector4d(a.m12, a.m22, a.m32, a.m42);
var c = a.column(2); // zero based access! so not equal to b
-console.log(b.toString() + " " + c.toString()); // QVector4D(2, 6, 10, 14) QVector4D(3, 7, 11, 15)
+console.log(b.toString() + " " + c.toString());
+// QVector4D(2, 6, 10, 14) QVector4D(3, 7, 11, 15)
\endcode
\row
@@ -809,7 +825,9 @@ console.log(b); // 6
\li \code
var a = Qt.matrix4x4(1,0,0,0,0,2,0,0,0,0,3,0,100,200,300,1);
var b = a.inverted();
-console.log(b.toString()); // QMatrix4x4(1, 0, 0, 0, 0, 0.5, 0, 0, 0, 0, 0.333333, 0, -100, -100, -100, 1)
+console.log(b.toString());
+// QMatrix4x4(1, 0, 0, 0, 0, 0.5, 0, 0, 0, 0, 0.333333, 0, -100,
+// -100, -100, 1)
\endcode
\row
@@ -818,7 +836,8 @@ console.log(b.toString()); // QMatrix4x4(1, 0, 0, 0, 0, 0.5, 0, 0, 0, 0, 0.33333
\li \code
var a = Qt.matrix4x4(1,0,0,0,0,2,0,0,0,0,3,0,100,200,300,1);
var b = a.transposed();
-console.log(b.toString()); // QMatrix4x4(1, 0, 0, 100, 0, 2, 0, 200, 0, 0, 3, 300, 0, 0, 0, 1)
+console.log(b.toString());
+// QMatrix4x4(1, 0, 0, 100, 0, 2, 0, 200, 0, 0, 3, 300, 0, 0, 0, 1)
\endcode
\row
@@ -829,7 +848,10 @@ console.log(b.toString()); // QMatrix4x4(1, 0, 0, 100, 0, 2, 0, 200, 0, 0, 3, 30
argument, the default \c epsilon is 0.00001.
\li \code
var a = Qt.matrix4x4(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16);
-var b = Qt.matrix4x4(1.0001,2.0001,3.0002,4.0003,5.0001,6.0002,7.0002,8.0004,9.0001,10.0003,11.0003,12.0004,13.0001,14.0002,15.0003,16.0004);
+var b = Qt.matrix4x4(1.0001,2.0001,3.0002,4.0003,5.0001,6.0002,
+ 7.0002,8.0004, 9.0001,10.0003,
+ 11.0003,12.0004,13.0001,
+ 14.0002,15.0003,16.0004);
var c = a.fuzzyEquals(b); // default epsilon
var d = a.fuzzyEquals(b, 0.005); // supplied epsilon
console.log(c + " " + d); // false true
diff --git a/src/quick/items/qquickimage.cpp b/src/quick/items/qquickimage.cpp
index f0f17551b7..3ba09f9cea 100644
--- a/src/quick/items/qquickimage.cpp
+++ b/src/quick/items/qquickimage.cpp
@@ -152,7 +152,6 @@ QQuickImagePrivate::QQuickImagePrivate()
QQuickImage::QQuickImage(QQuickItem *parent)
: QQuickImageBase(*(new QQuickImagePrivate), parent)
{
- connect(this, SIGNAL(autoTransformBaseChanged()), SIGNAL(autoTransformChanged()));
}
QQuickImage::QQuickImage(QQuickImagePrivate &dd, QQuickItem *parent)
diff --git a/src/quick/items/qquickimage_p.h b/src/quick/items/qquickimage_p.h
index b8a0b3b86f..a780f9a626 100644
--- a/src/quick/items/qquickimage_p.h
+++ b/src/quick/items/qquickimage_p.h
@@ -88,6 +88,8 @@ public:
bool mipmap() const;
void setMipmap(bool use);
+ virtual void emitAutoTransformBaseChanged() { emit autoTransformChanged(); }
+
Q_SIGNALS:
void fillModeChanged();
void paintedGeometryChanged();
diff --git a/src/quick/items/qquickimagebase.cpp b/src/quick/items/qquickimagebase.cpp
index cb2bf574b5..e54f5bb9c9 100644
--- a/src/quick/items/qquickimagebase.cpp
+++ b/src/quick/items/qquickimagebase.cpp
@@ -197,7 +197,7 @@ void QQuickImageBase::load()
}
if (autoTransform() != d->oldAutoTransform) {
d->oldAutoTransform = autoTransform();
- emit autoTransformBaseChanged();
+ emitAutoTransformBaseChanged();
}
update();
@@ -296,7 +296,7 @@ void QQuickImageBase::requestFinished()
}
if (autoTransform() != d->oldAutoTransform) {
d->oldAutoTransform = autoTransform();
- emit autoTransformBaseChanged();
+ emitAutoTransformBaseChanged();
}
update();
}
@@ -402,7 +402,7 @@ void QQuickImageBase::setAutoTransform(bool transform)
if (d->autoTransform != UsePluginDefault && transform == (d->autoTransform == ApplyTransform))
return;
d->autoTransform = transform ? ApplyTransform : DoNotApplyTransform;
- emit autoTransformBaseChanged();
+ emitAutoTransformBaseChanged();
}
QT_END_NAMESPACE
diff --git a/src/quick/items/qquickimagebase_p.h b/src/quick/items/qquickimagebase_p.h
index 638b8dbdcf..98943a235c 100644
--- a/src/quick/items/qquickimagebase_p.h
+++ b/src/quick/items/qquickimagebase_p.h
@@ -83,6 +83,10 @@ public:
void resolve2xLocalFile(const QUrl &url, qreal targetDevicePixelRatio, QUrl *sourceUrl, qreal *sourceDevicePixelRatio);
+ // Use a virtual rather than a signal->signal to avoid the huge
+ // connect/conneciton overhead for this rare case.
+ virtual void emitAutoTransformBaseChanged() { }
+
Q_SIGNALS:
void sourceChanged(const QUrl &);
void sourceSizeChanged();
@@ -91,7 +95,6 @@ Q_SIGNALS:
void asynchronousChanged();
void cacheChanged();
void mirrorChanged();
- void autoTransformBaseChanged();
protected:
virtual void load();
diff --git a/src/quick/items/qquickitemsmodule.cpp b/src/quick/items/qquickitemsmodule.cpp
index 6e50a9a77b..8a6766770e 100644
--- a/src/quick/items/qquickitemsmodule.cpp
+++ b/src/quick/items/qquickitemsmodule.cpp
@@ -260,6 +260,7 @@ static void qt_quickitems_defineModule(const char *uri, int major, int minor)
qmlRegisterType<QQuickPinchArea, 1>(uri, 2, 5,"PinchArea");
qmlRegisterType<QQuickImage, 2>(uri, 2, 5,"Image");
+ qmlRegisterType<QQuickMouseArea, 2>(uri, 2, 5, "MouseArea");
qmlRegisterType<QQuickText, 6>(uri, 2, 6, "Text");
qmlRegisterType<QQuickTextEdit, 6>(uri, 2, 6, "TextEdit");
diff --git a/src/quick/items/qquicklistview.cpp b/src/quick/items/qquicklistview.cpp
index c14419dbee..a2920f8bad 100644
--- a/src/quick/items/qquicklistview.cpp
+++ b/src/quick/items/qquicklistview.cpp
@@ -1157,9 +1157,11 @@ void QQuickListViewPrivate::updateSections()
if (visibleIndex > 0)
prevSection = sectionAt(visibleIndex-1);
QQuickListViewAttached *prevAtt = 0;
+ int prevIdx = -1;
int idx = -1;
for (int i = 0; i < visibleItems.count(); ++i) {
- QQuickListViewAttached *attached = static_cast<QQuickListViewAttached*>(visibleItems.at(i)->attached);
+ FxViewItem *item = visibleItems.at(i);
+ QQuickListViewAttached *attached = static_cast<QQuickListViewAttached*>(item->attached);
attached->setPrevSection(prevSection);
if (visibleItems.at(i)->index != -1) {
QString propValue = model->stringValue(visibleItems.at(i)->index, sectionCriteria->property());
@@ -1168,9 +1170,10 @@ void QQuickListViewPrivate::updateSections()
}
updateInlineSection(static_cast<FxListItemSG*>(visibleItems.at(i)));
if (prevAtt)
- prevAtt->setNextSection(attached->section());
+ prevAtt->setNextSection(sectionAt(prevIdx+1));
prevSection = attached->section();
prevAtt = attached;
+ prevIdx = item->index;
}
if (prevAtt) {
if (idx > 0 && idx < model->count()-1)
@@ -3088,6 +3091,18 @@ bool QQuickListViewPrivate::applyInsertionChange(const QQmlChangeSet::Change &ch
: visibleItems.last()->endPosition()+spacing;
}
+ // Update the indexes of the following visible items.
+ for (int i = 0; i < visibleItems.count(); ++i) {
+ FxViewItem *item = visibleItems.at(i);
+ if (item->index != -1 && item->index >= modelIndex) {
+ item->index += count;
+ if (change.isMove())
+ item->transitionNextReposition(transitioner, QQuickItemViewTransitioner::MoveTransition, false);
+ else
+ item->transitionNextReposition(transitioner, QQuickItemViewTransitioner::AddTransition, false);
+ }
+ }
+
int prevVisibleCount = visibleItems.count();
if (insertResult->visiblePos.isValid() && pos < insertResult->visiblePos) {
// Insert items before the visible item.
@@ -3153,17 +3168,6 @@ bool QQuickListViewPrivate::applyInsertionChange(const QQmlChangeSet::Change &ch
}
}
- for (; index < visibleItems.count(); ++index) {
- FxViewItem *item = visibleItems.at(index);
- if (item->index != -1) {
- item->index += count;
- if (change.isMove())
- item->transitionNextReposition(transitioner, QQuickItemViewTransitioner::MoveTransition, false);
- else
- item->transitionNextReposition(transitioner, QQuickItemViewTransitioner::AddTransition, false);
- }
- }
-
updateVisibleIndex();
return visibleItems.count() > prevVisibleCount;
diff --git a/src/quick/items/qquickloader.cpp b/src/quick/items/qquickloader.cpp
index c1e3fbb4e0..df09780895 100644
--- a/src/quick/items/qquickloader.cpp
+++ b/src/quick/items/qquickloader.cpp
@@ -217,7 +217,7 @@ qreal QQuickLoaderPrivate::getImplicitHeight() const
loads \c MyItem.qml, and is able to receive the \c message signal from
the loaded item through a \l Connections object:
- \table
+ \table 70%
\row
\li application.qml
\li MyItem.qml
@@ -263,7 +263,6 @@ qreal QQuickLoaderPrivate::getImplicitHeight() const
In some cases you may wish to use a Loader within a view delegate to improve delegate
loading performance. This works well in most cases, but there is one important issue to
- be aware of related to the \l{QtQml::Component#Creation Context}{creation context} of a Component.
In the following example, the \c index context property inserted by the ListView into \c delegateComponent's
context will be inaccessible to Text, as the Loader will use the creation context of \c myComponent as the parent
@@ -516,7 +515,7 @@ void QQuickLoader::loadFromSourceComponent()
is changed after calling this function but prior to setting the loader \l active.
Example:
- \table
+ \table 70%
\row
\li
\qml
@@ -545,11 +544,13 @@ void QQuickLoader::loadFromSourceComponent()
Item {
Loader {
id: squareLoader
- onLoaded: console.log(squareLoader.item.width); // prints [10], not [30]
+ onLoaded: console.log(squareLoader.item.width);
+ // prints [10], not [30]
}
Component.onCompleted: {
- squareLoader.setSource("ExampleComponent.qml", { "color": "blue" });
+ squareLoader.setSource("ExampleComponent.qml",
+ { "color": "blue" });
// will trigger the onLoaded code when complete.
}
}
diff --git a/src/quick/items/qquickmousearea.cpp b/src/quick/items/qquickmousearea.cpp
index 9b1d54173a..4a44760035 100644
--- a/src/quick/items/qquickmousearea.cpp
+++ b/src/quick/items/qquickmousearea.cpp
@@ -498,6 +498,7 @@ void QQuickMouseArea::setEnabled(bool a)
/*!
\qmlproperty bool QtQuick::MouseArea::scrollGestureEnabled
+ \since 5.5
This property controls whether this MouseArea responds to scroll gestures
from non-mouse devices, such as the 2-finger flick gesture on a trackpad.
diff --git a/src/quick/items/qquickmousearea_p.h b/src/quick/items/qquickmousearea_p.h
index 9fa213c254..4ad14e6bdd 100644
--- a/src/quick/items/qquickmousearea_p.h
+++ b/src/quick/items/qquickmousearea_p.h
@@ -54,7 +54,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickMouseArea : public QQuickItem
Q_PROPERTY(bool containsMouse READ hovered NOTIFY hoveredChanged)
Q_PROPERTY(bool pressed READ pressed NOTIFY pressedChanged)
Q_PROPERTY(bool enabled READ isEnabled WRITE setEnabled NOTIFY enabledChanged)
- Q_PROPERTY(bool scrollGestureEnabled READ isScrollGestureEnabled WRITE setScrollGestureEnabled NOTIFY scrollGestureEnabledChanged)
+ Q_PROPERTY(bool scrollGestureEnabled READ isScrollGestureEnabled WRITE setScrollGestureEnabled NOTIFY scrollGestureEnabledChanged REVISION 2)
Q_PROPERTY(Qt::MouseButtons pressedButtons READ pressedButtons NOTIFY pressedButtonsChanged)
Q_PROPERTY(Qt::MouseButtons acceptedButtons READ acceptedButtons WRITE setAcceptedButtons NOTIFY acceptedButtonsChanged)
Q_PROPERTY(bool hoverEnabled READ hoverEnabled WRITE setHoverEnabled NOTIFY hoverEnabledChanged)
@@ -112,7 +112,7 @@ Q_SIGNALS:
void hoveredChanged();
void pressedChanged();
void enabledChanged();
- void scrollGestureEnabledChanged();
+ Q_REVISION(2) void scrollGestureEnabledChanged();
void pressedButtonsChanged();
void acceptedButtonsChanged();
void hoverEnabledChanged();
diff --git a/src/quick/items/qquickshadereffect.cpp b/src/quick/items/qquickshadereffect.cpp
index 5903052dbd..0be305b693 100644
--- a/src/quick/items/qquickshadereffect.cpp
+++ b/src/quick/items/qquickshadereffect.cpp
@@ -601,7 +601,7 @@ void QQuickShaderEffectCommon::propertyChanged(QQuickItem *item, int mappedId,
\l blending is enabled, source-over blending is used. However, additive
blending can be achieved by outputting zero in the alpha channel.
- \table
+ \table 70%
\row
\li \image declarative-shadereffectitem.png
\li \qml
@@ -610,7 +610,8 @@ void QQuickShaderEffectCommon::propertyChanged(QQuickItem *item, int mappedId,
Rectangle {
width: 200; height: 100
Row {
- Image { id: img; sourceSize { width: 100; height: 100 } source: "qt-logo.png" }
+ Image { id: img;
+ sourceSize { width: 100; height: 100 } source: "qt-logo.png" }
ShaderEffect {
width: 100; height: 100
property variant src: img
@@ -629,7 +630,9 @@ void QQuickShaderEffectCommon::propertyChanged(QQuickItem *item, int mappedId,
uniform lowp float qt_Opacity;
void main() {
lowp vec4 tex = texture2D(src, coord);
- gl_FragColor = vec4(vec3(dot(tex.rgb, vec3(0.344, 0.5, 0.156))), tex.a) * qt_Opacity;
+ gl_FragColor = vec4(vec3(dot(tex.rgb,
+ vec3(0.344, 0.5, 0.156))),
+ tex.a) * qt_Opacity;
}"
}
}
@@ -649,6 +652,7 @@ void QQuickShaderEffectCommon::propertyChanged(QQuickItem *item, int mappedId,
\row
\li \b {Layer with effect disabled} \inlineimage qml-shadereffect-nolayereffect.png
\li \b {Layer with effect enabled} \inlineimage qml-shadereffect-layereffect.png
+ \row
\li \snippet qml/layerwitheffect.qml 1
\endtable
@@ -657,6 +661,7 @@ void QQuickShaderEffectCommon::propertyChanged(QQuickItem *item, int mappedId,
\table
\row
\li \inlineimage qml-shadereffect-opacitymask.png
+ \row
\li \snippet qml/opacitymask.qml 1
\endtable
diff --git a/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp b/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp
index 136f23f339..dcc485ce17 100644
--- a/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp
+++ b/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp
@@ -38,6 +38,7 @@
#include <QtQml/private/qqmlglobal_p.h>
#include <QtQuick/private/qsgdistancefieldutil_p.h>
#include <qopenglfunctions.h>
+#include <qopenglframebufferobject.h>
#include <qmath.h>
#if !defined(QT_OPENGL_ES_2)
@@ -324,7 +325,7 @@ void QSGDefaultDistanceFieldGlyphCache::resizeTexture(TextureInfo *texInfo, int
GL_COLOR_BUFFER_BIT, GL_NEAREST);
// Reset the default framebuffer
- m_coreFuncs->glBindFramebuffer(GL_FRAMEBUFFER, 0);
+ QOpenGLFramebufferObject::bindDefault();
return;
} else if (useTextureResizeWorkaround()) {
@@ -449,7 +450,7 @@ void QSGDefaultDistanceFieldGlyphCache::resizeTexture(TextureInfo *texInfo, int
m_funcs->glDeleteTextures(1, &tmp_texture);
m_funcs->glDeleteTextures(1, &oldTexture);
- m_funcs->glBindFramebuffer(GL_FRAMEBUFFER, 0);
+ QOpenGLFramebufferObject::bindDefault();
// restore render states
if (stencilTestEnabled)
diff --git a/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp b/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
index 9f1a44154c..14bc0fad07 100644
--- a/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
+++ b/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
@@ -267,6 +267,30 @@ void QSG24BitTextMaskShader::updateState(const RenderState &state, QSGMaterial *
}
}
+class QSG32BitColorTextShader : public QSGTextMaskShader
+{
+public:
+ QSG32BitColorTextShader(QFontEngine::GlyphFormat glyphFormat)
+ : QSGTextMaskShader(glyphFormat)
+ {
+ setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/scenegraph/shaders/32bitcolortext.frag"));
+ }
+
+ void updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect) Q_DECL_OVERRIDE;
+};
+
+void QSG32BitColorTextShader::updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect)
+{
+ QSGTextMaskShader::updateState(state, newEffect, oldEffect);
+ QSGTextMaskMaterial *material = static_cast<QSGTextMaskMaterial *>(newEffect);
+ QSGTextMaskMaterial *oldMaterial = static_cast<QSGTextMaskMaterial *>(oldEffect);
+
+ if (oldMaterial == Q_NULLPTR || material->color() != oldMaterial->color() || state.isOpacityDirty()) {
+ float opacity = material->color().w() * state.opacity();
+ program()->setUniformValue(m_color_id, opacity);
+ }
+}
+
class QSGStyledTextShader : public QSG8BitTextMaskShader
{
public:
@@ -497,8 +521,16 @@ void QSGTextMaskMaterial::populate(const QPointF &p,
QSGMaterialType *QSGTextMaskMaterial::type() const
{
- static QSGMaterialType rgb, gray;
- return glyphCache()->glyphFormat() == QFontEngine::Format_A32 ? &rgb : &gray;
+ static QSGMaterialType argb, rgb, gray;
+ switch (glyphCache()->glyphFormat()) {
+ case QFontEngine::Format_ARGB:
+ return &argb;
+ case QFontEngine::Format_A32:
+ return &rgb;
+ case QFontEngine::Format_A8:
+ default:
+ return &gray;
+ }
}
QOpenGLTextureGlyphCache *QSGTextMaskMaterial::glyphCache() const
@@ -508,10 +540,15 @@ QOpenGLTextureGlyphCache *QSGTextMaskMaterial::glyphCache() const
QSGMaterialShader *QSGTextMaskMaterial::createShader() const
{
- QFontEngine::GlyphFormat glyphFormat = glyphCache()->glyphFormat();
- return glyphFormat == QFontEngine::Format_A32
- ? (QSGMaterialShader *) new QSG24BitTextMaskShader(glyphFormat)
- : (QSGMaterialShader *) new QSG8BitTextMaskShader(glyphFormat);
+ switch (QFontEngine::GlyphFormat glyphFormat = glyphCache()->glyphFormat()) {
+ case QFontEngine::Format_ARGB:
+ return new QSG32BitColorTextShader(glyphFormat);
+ case QFontEngine::Format_A32:
+ return new QSG24BitTextMaskShader(glyphFormat);
+ case QFontEngine::Format_A8:
+ default:
+ return new QSG8BitTextMaskShader(glyphFormat);
+ }
}
static inline int qsg_colorDiff(const QVector4D &a, const QVector4D &b)
diff --git a/src/quick/scenegraph/qsgdefaultrectanglenode.cpp b/src/quick/scenegraph/qsgdefaultrectanglenode.cpp
index 3e251a4051..f3f5c7f79f 100644
--- a/src/quick/scenegraph/qsgdefaultrectanglenode.cpp
+++ b/src/quick/scenegraph/qsgdefaultrectanglenode.cpp
@@ -323,11 +323,11 @@ void QSGDefaultRectangleNode::updateGeometry()
const QGradientStops &stops = m_gradient_stops;
int nextGradientStop = 0;
- float gradientPos = 0.5f * penWidth / height;
+ float gradientPos = penWidth / height;
while (nextGradientStop < stops.size() && stops.at(nextGradientStop).first <= gradientPos)
++nextGradientStop;
int lastGradientStop = stops.size() - 1;
- float lastGradientPos = 1.0f - 0.5f * penWidth / height;
+ float lastGradientPos = 1.0f - penWidth / height;
while (lastGradientStop >= nextGradientStop && stops.at(lastGradientStop).first >= lastGradientPos)
--lastGradientStop;
int gradientIntersections = (lastGradientStop - nextGradientStop + 1);
@@ -643,11 +643,11 @@ void QSGDefaultRectangleNode::updateGeometry()
for (int part = -1; part <= 1; part += 2) {
float y = (part == 1 ? innerRect.bottom() : innerRect.top());
float Y = (part == 1 ? outerRect.bottom() : outerRect.top());
- gradientPos = (y - innerRect.top() + 0.5f * penWidth) / height;
+ gradientPos = (y - innerRect.top() + penWidth) / height;
while (nextGradientStop <= lastGradientStop && stops.at(nextGradientStop).first <= gradientPos) {
// Insert vertices at gradient stops.
- float gy = (innerRect.top() - 0.5f * penWidth) + stops.at(nextGradientStop).first * height;
+ float gy = (innerRect.top() - penWidth) + stops.at(nextGradientStop).first * height;
fillColor = colorToColor4ub(stops.at(nextGradientStop).second);
diff --git a/src/quick/scenegraph/scenegraph.qrc b/src/quick/scenegraph/scenegraph.qrc
index e6a90c9120..5db242e46b 100644
--- a/src/quick/scenegraph/scenegraph.qrc
+++ b/src/quick/scenegraph/scenegraph.qrc
@@ -4,6 +4,7 @@
<file>shaders/flatcolor.vert</file>
<file>shaders/8bittextmask.frag</file>
<file>shaders/24bittextmask.frag</file>
+ <file>shaders/32bitcolortext.frag</file>
<file>shaders/opaquetexture.frag</file>
<file>shaders/opaquetexture.vert</file>
<file>shaders/outlinedtext.frag</file>
@@ -34,6 +35,7 @@
<file>shaders/stencilclip.vert</file>
<file>shaders/8bittextmask_core.frag</file>
<file>shaders/24bittextmask_core.frag</file>
+ <file>shaders/32bitcolortext_core.frag</file>
<file>shaders/distancefieldoutlinetext_core.frag</file>
<file>shaders/distancefieldshiftedtext_core.frag</file>
<file>shaders/distancefieldshiftedtext_core.vert</file>
diff --git a/src/quick/scenegraph/shaders/32bitcolortext.frag b/src/quick/scenegraph/shaders/32bitcolortext.frag
new file mode 100644
index 0000000000..6fdb6e6aeb
--- /dev/null
+++ b/src/quick/scenegraph/shaders/32bitcolortext.frag
@@ -0,0 +1,9 @@
+varying highp vec2 sampleCoord;
+
+uniform sampler2D _qt_texture;
+uniform lowp float color; // just the alpha, really...
+
+void main()
+{
+ gl_FragColor = texture2D(_qt_texture, sampleCoord) * color;
+}
diff --git a/src/quick/scenegraph/shaders/32bitcolortext_core.frag b/src/quick/scenegraph/shaders/32bitcolortext_core.frag
new file mode 100644
index 0000000000..010aca97b4
--- /dev/null
+++ b/src/quick/scenegraph/shaders/32bitcolortext_core.frag
@@ -0,0 +1,13 @@
+#version 150 core
+
+in vec2 sampleCoord;
+
+out vec4 fragColor;
+
+uniform sampler2D _qt_texture;
+uniform float color; // just the alpha, really...
+
+void main()
+{
+ fragColor = texture(_qt_texture, sampleCoord) * color;
+}
diff --git a/src/quick/scenegraph/shaders/smoothtexture_core.vert b/src/quick/scenegraph/shaders/smoothtexture_core.vert
index a2489a39c5..6821398e57 100644
--- a/src/quick/scenegraph/shaders/smoothtexture_core.vert
+++ b/src/quick/scenegraph/shaders/smoothtexture_core.vert
@@ -50,5 +50,8 @@ void main()
bool onEdge = any(notEqual(vertexOffset, vec2(0.)));
bool outerEdge = all(equal(texCoordOffset, vec2(0.)));
- vertexOpacity = onEdge && outerEdge ? 0. : opacity;
-} \ No newline at end of file
+ if (onEdge && outerEdge)
+ vertexOpacity = 0.;
+ else
+ vertexOpacity = opacity;
+}
diff --git a/src/quick/scenegraph/util/qsgatlastexture.cpp b/src/quick/scenegraph/util/qsgatlastexture.cpp
index 7a2587dacd..8c649fb6bd 100644
--- a/src/quick/scenegraph/util/qsgatlastexture.cpp
+++ b/src/quick/scenegraph/util/qsgatlastexture.cpp
@@ -148,8 +148,15 @@ Atlas::Atlas(const QSize &size)
|| deviceName->compare(QStringLiteral("samsung SM-T215"), Qt::CaseInsensitive) == 0);
#else
static bool wrongfullyReportsBgra8888Support = false;
+ // The Raspberry Pi (both 1 and 2) GPU refuses framebuffers with BGRA color attachments.
+ const GLubyte *renderer = QOpenGLContext::currentContext()->functions()->glGetString(GL_RENDERER);
+ if (renderer && strstr((const char *) renderer, "VideoCore IV"))
+ wrongfullyReportsBgra8888Support = true;
#endif // ANDROID
+ if (qEnvironmentVariableIsSet("QSG_ATLAS_NO_BGRA_WORKAROUNDS"))
+ wrongfullyReportsBgra8888Support = false;
+
const char *ext = (const char *) QOpenGLContext::currentContext()->functions()->glGetString(GL_EXTENSIONS);
if (!wrongfullyReportsBgra8888Support
&& (strstr(ext, "GL_EXT_bgra")
@@ -484,7 +491,11 @@ QSGTexture *Texture::removedFromAtlas() const
f->glBindTexture(GL_TEXTURE_2D, texture);
QRect r = atlasSubRectWithoutPadding();
// and copy atlas into our texture.
+ while (f->glGetError() != GL_NO_ERROR) ;
f->glCopyTexImage2D(GL_TEXTURE_2D, 0, m_atlas->internalFormat(), r.x(), r.y(), r.width(), r.height(), 0);
+ // BGRA may have been rejected by some GLES implementations
+ if (f->glGetError() != GL_NO_ERROR)
+ f->glCopyTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, r.x(), r.y(), r.width(), r.height(), 0);
m_nonatlas_texture = new QSGPlainTexture();
m_nonatlas_texture->setTextureId(texture);
diff --git a/src/quick/util/qquickanimation.cpp b/src/quick/util/qquickanimation.cpp
index 3a0c19e3d2..ec3abf7090 100644
--- a/src/quick/util/qquickanimation.cpp
+++ b/src/quick/util/qquickanimation.cpp
@@ -2144,7 +2144,10 @@ void QQuickPropertyAnimation::setTo(const QVariant &t)
\c Easing.Linear.
\qml
- PropertyAnimation { properties: "y"; easing.type: Easing.InOutElastic; easing.amplitude: 2.0; easing.period: 1.5 }
+ PropertyAnimation { properties: "y";
+ easing.type: Easing.InOutElastic;
+ easing.amplitude: 2.0;
+ easing.period: 1.5 }
\endqml
Available types are:
diff --git a/src/quickwidgets/qquickwidget.cpp b/src/quickwidgets/qquickwidget.cpp
index 1afea402fd..955abfddb2 100644
--- a/src/quickwidgets/qquickwidget.cpp
+++ b/src/quickwidgets/qquickwidget.cpp
@@ -202,7 +202,12 @@ void QQuickWidgetPrivate::itemGeometryChanged(QQuickItem *resizeItem, const QRec
void QQuickWidgetPrivate::render(bool needsSync)
{
- context->makeCurrent(offscreenSurface);
+ if (!context->makeCurrent(offscreenSurface)) {
+ qWarning("QQuickWidget: Cannot render due to failing makeCurrent()");
+ return;
+ }
+
+ QOpenGLContextPrivate::get(context)->defaultFboRedirect = fbo->handle();
if (needsSync) {
renderControl->polishItems();
@@ -217,6 +222,8 @@ void QQuickWidgetPrivate::render(bool needsSync)
}
static_cast<QOpenGLExtensions *>(context->functions())->flushShared();
+
+ QOpenGLContextPrivate::get(context)->defaultFboRedirect = 0;
}
void QQuickWidgetPrivate::renderSceneGraph()
diff --git a/tests/auto/qml/debugger/qqmldebuggingenabler/qqmldebuggingenablerserver/qqmldebuggingenablerserver.cpp b/tests/auto/qml/debugger/qqmldebuggingenabler/qqmldebuggingenablerserver/qqmldebuggingenablerserver.cpp
index 68279413e0..bddece6452 100644
--- a/tests/auto/qml/debugger/qqmldebuggingenabler/qqmldebuggingenablerserver/qqmldebuggingenablerserver.cpp
+++ b/tests/auto/qml/debugger/qqmldebuggingenabler/qqmldebuggingenablerserver/qqmldebuggingenablerserver.cpp
@@ -36,7 +36,7 @@
int main(int argc, char *argv[])
{
- bool block = false;
+ QQmlDebuggingEnabler::StartMode block = QQmlDebuggingEnabler::DoNotWaitForClient;
int portFrom = 0;
int portTo = 0;
@@ -45,7 +45,7 @@ int main(int argc, char *argv[])
arguments.removeFirst();
if (arguments.size() && arguments.first() == QLatin1String("-block")) {
- block = true;
+ block = QQmlDebuggingEnabler::WaitForClient;
arguments.removeFirst();
}
diff --git a/tests/auto/qml/qqmllanguage/data/invalidAlias.10.errors.txt b/tests/auto/qml/qqmllanguage/data/invalidAlias.10.errors.txt
index 93652a7042..1ac78f2fc2 100644
--- a/tests/auto/qml/qqmllanguage/data/invalidAlias.10.errors.txt
+++ b/tests/auto/qml/qqmllanguage/data/invalidAlias.10.errors.txt
@@ -1 +1 @@
-5:23:Invalid alias location
+5:23:Invalid alias target location: blah
diff --git a/tests/auto/qml/qqmllanguage/data/invalidAlias.6.errors.txt b/tests/auto/qml/qqmllanguage/data/invalidAlias.6.errors.txt
index 93652a7042..5b467ebc31 100644
--- a/tests/auto/qml/qqmllanguage/data/invalidAlias.6.errors.txt
+++ b/tests/auto/qml/qqmllanguage/data/invalidAlias.6.errors.txt
@@ -1 +1 @@
-5:23:Invalid alias location
+5:23:Invalid alias target location: foobar
diff --git a/tests/auto/qml/qqmllanguage/data/invalidAlias.7.errors.txt b/tests/auto/qml/qqmllanguage/data/invalidAlias.7.errors.txt
index 93652a7042..8334f30ede 100644
--- a/tests/auto/qml/qqmllanguage/data/invalidAlias.7.errors.txt
+++ b/tests/auto/qml/qqmllanguage/data/invalidAlias.7.errors.txt
@@ -1 +1 @@
-5:23:Invalid alias location
+5:23:Invalid alias target location: nonScriptable
diff --git a/tests/auto/qml/qqmllanguage/data/invalidAlias.8.errors.txt b/tests/auto/qml/qqmllanguage/data/invalidAlias.8.errors.txt
index 93652a7042..c77182f3ba 100644
--- a/tests/auto/qml/qqmllanguage/data/invalidAlias.8.errors.txt
+++ b/tests/auto/qml/qqmllanguage/data/invalidAlias.8.errors.txt
@@ -1 +1 @@
-5:23:Invalid alias location
+5:23:Invalid alias target location: imaginary
diff --git a/tests/auto/qml/qqmllanguage/data/invalidAlias.9.errors.txt b/tests/auto/qml/qqmllanguage/data/invalidAlias.9.errors.txt
index 93652a7042..33ba4d293e 100644
--- a/tests/auto/qml/qqmllanguage/data/invalidAlias.9.errors.txt
+++ b/tests/auto/qml/qqmllanguage/data/invalidAlias.9.errors.txt
@@ -1 +1 @@
-5:23:Invalid alias location
+5:23:Invalid alias target location: x
diff --git a/tests/auto/qml/qqmlvaluetypes/data/rect_compare.qml b/tests/auto/qml/qqmlvaluetypes/data/rect_compare.qml
index c511c2dfc4..104e7ba1e9 100644
--- a/tests/auto/qml/qqmlvaluetypes/data/rect_compare.qml
+++ b/tests/auto/qml/qqmlvaluetypes/data/rect_compare.qml
@@ -1,10 +1,6 @@
import Test 1.0
MyTypeObject {
- property int r_x: rect.x
- property int r_y: rect.y
- property int r_width: rect.width
- property int r_height: rect.height
property variant copy: rect
property string tostring: rect.toString()
diff --git a/tests/auto/qml/qqmlvaluetypes/data/rect_read.qml b/tests/auto/qml/qqmlvaluetypes/data/rect_read.qml
index c3b37a7099..da6deddd75 100644
--- a/tests/auto/qml/qqmlvaluetypes/data/rect_read.qml
+++ b/tests/auto/qml/qqmlvaluetypes/data/rect_read.qml
@@ -5,6 +5,10 @@ MyTypeObject {
property int r_y: rect.y
property int r_width: rect.width
property int r_height: rect.height
+ property int r_left: rect.left
+ property int r_right: rect.right
+ property int r_top: rect.top
+ property int r_bottom: rect.bottom
property variant copy: rect
}
diff --git a/tests/auto/qml/qqmlvaluetypes/data/rectf_compare.qml b/tests/auto/qml/qqmlvaluetypes/data/rectf_compare.qml
index 6ac4049558..eb61755bcf 100644
--- a/tests/auto/qml/qqmlvaluetypes/data/rectf_compare.qml
+++ b/tests/auto/qml/qqmlvaluetypes/data/rectf_compare.qml
@@ -1,10 +1,6 @@
import Test 1.0
MyTypeObject {
- property real r_x: rectf.x
- property real r_y: rectf.y
- property real r_width: rectf.width
- property real r_height: rectf.height
property variant copy: rectf
property string tostring: rectf.toString()
diff --git a/tests/auto/qml/qqmlvaluetypes/data/rectf_read.qml b/tests/auto/qml/qqmlvaluetypes/data/rectf_read.qml
index 6ff3ce30bf..878868254d 100644
--- a/tests/auto/qml/qqmlvaluetypes/data/rectf_read.qml
+++ b/tests/auto/qml/qqmlvaluetypes/data/rectf_read.qml
@@ -5,6 +5,10 @@ MyTypeObject {
property real r_y: rectf.y
property real r_width: rectf.width
property real r_height: rectf.height
+ property real r_left: rectf.left
+ property real r_right: rectf.right
+ property real r_top: rectf.top
+ property real r_bottom: rectf.bottom
property variant copy: rectf
}
diff --git a/tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp b/tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp
index 2892e746da..578004b0a1 100644
--- a/tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp
+++ b/tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp
@@ -371,6 +371,10 @@ void tst_qqmlvaluetypes::rect()
QCOMPARE(object->property("r_y").toInt(), 3);
QCOMPARE(object->property("r_width").toInt(), 109);
QCOMPARE(object->property("r_height").toInt(), 102);
+ QCOMPARE(object->property("r_left").toInt(), 2);
+ QCOMPARE(object->property("r_right").toInt(), 110);
+ QCOMPARE(object->property("r_top").toInt(), 3);
+ QCOMPARE(object->property("r_bottom").toInt(), 104);
QCOMPARE(object->property("copy"), QVariant(QRect(2, 3, 109, 102)));
delete object;
@@ -418,6 +422,10 @@ void tst_qqmlvaluetypes::rectf()
QCOMPARE(float(object->property("r_y").toDouble()), float(99.2));
QCOMPARE(float(object->property("r_width").toDouble()), float(88.1));
QCOMPARE(float(object->property("r_height").toDouble()), float(77.6));
+ QCOMPARE(float(object->property("r_left").toDouble()), float(103.8));
+ QCOMPARE(float(object->property("r_right").toDouble()), float(191.9));
+ QCOMPARE(float(object->property("r_top").toDouble()), float(99.2));
+ QCOMPARE(float(object->property("r_bottom").toDouble()), float(176.8));
QCOMPARE(object->property("copy"), QVariant(QRectF(103.8, 99.2, 88.1, 77.6)));
delete object;
diff --git a/tests/auto/quick/qquicklistview/data/listview-sections_delegate.qml b/tests/auto/quick/qquicklistview/data/listview-sections_delegate.qml
index 7245025bac..11da286f4d 100644
--- a/tests/auto/quick/qquicklistview/data/listview-sections_delegate.qml
+++ b/tests/auto/quick/qquicklistview/data/listview-sections_delegate.qml
@@ -12,6 +12,9 @@ Rectangle {
Item {
id: wrapper
objectName: "wrapper"
+ property string section: ListView.section
+ property string nextSection: ListView.nextSection
+ property string prevSection: ListView.previousSection
height: 20;
width: 240
Rectangle {
diff --git a/tests/auto/quick/qquicklistview/tst_qquicklistview.cpp b/tests/auto/quick/qquicklistview/tst_qquicklistview.cpp
index b25fc5402b..6377650696 100644
--- a/tests/auto/quick/qquicklistview/tst_qquicklistview.cpp
+++ b/tests/auto/quick/qquicklistview/tst_qquicklistview.cpp
@@ -133,6 +133,7 @@ private slots:
void sectionsDelegate_headerVisibility();
void sectionPropertyChange();
void sectionDelegateChange();
+ void sectionsItemInsertion();
void cacheBuffer();
void positionViewAtBeginningEnd();
void positionViewAtIndex();
@@ -2544,6 +2545,67 @@ void tst_QQuickListView::sectionDelegateChange()
delete window;
}
+// QTBUG-43873
+void tst_QQuickListView::sectionsItemInsertion()
+{
+ QQuickView *window = createView();
+
+ QaimModel model;
+ for (int i = 0; i < 30; i++)
+ model.addItem("Item" + QString::number(i), QString::number(i/5));
+
+ QQmlContext *ctxt = window->rootContext();
+ ctxt->setContextProperty("testModel", &model);
+
+ window->setSource(testFileUrl("listview-sections_delegate.qml"));
+ window->show();
+ QVERIFY(QTest::qWaitForWindowExposed(window));
+
+ QQuickListView *listview = findItem<QQuickListView>(window->rootObject(), "list");
+ QTRY_VERIFY(listview != 0);
+ QQuickItem *contentItem = listview->contentItem();
+ QTRY_VERIFY(contentItem != 0);
+ QTRY_COMPARE(QQuickItemPrivate::get(listview)->polishScheduled, false);
+
+ for (int i = 0; i < 3; ++i) {
+ QQuickItem *item = findItem<QQuickItem>(contentItem, "sect_" + QString::number(i));
+ QVERIFY(item);
+ QTRY_COMPARE(item->y(), qreal(i*20*6));
+ }
+
+ QQuickItem *topItem = findVisibleChild(contentItem, "sect_0"); // section header
+ QVERIFY(topItem);
+ QCOMPARE(topItem->y(), 0.);
+
+ // Insert a full screen of items at the beginning.
+ for (int i = 0; i < 10; i++)
+ model.insertItem(i, "Item" + QString::number(i), QLatin1String("A"));
+
+ QTRY_COMPARE(QQuickItemPrivate::get(listview)->polishScheduled, false);
+
+ int itemCount = findItems<QQuickItem>(contentItem, "wrapper").count();
+ QVERIFY(itemCount > 10);
+
+ // Verify that the new items are postioned correctly, and have the correct attached section properties
+ for (int i = 0; i < 10 && i < itemCount; ++i) {
+ QQuickItem *item = findItem<QQuickItem>(contentItem, "wrapper", i);
+ QVERIFY(item);
+ QTRY_COMPARE(item->y(), 20+i*20.0);
+ QCOMPARE(item->property("section").toString(), QLatin1String("A"));
+ QCOMPARE(item->property("nextSection").toString(), i < 9 ? QLatin1String("A") : QLatin1String("0"));
+ QCOMPARE(item->property("prevSection").toString(), i > 0 ? QLatin1String("A") : QLatin1String(""));
+ }
+ // Verify that the exiting items are postioned correctly, and have the correct attached section properties
+ for (int i = 10; i < 15 && i < itemCount; ++i) {
+ QQuickItem *item = findItem<QQuickItem>(contentItem, "wrapper", i);
+ QVERIFY(item);
+ QTRY_COMPARE(item->y(), 40+i*20.0);
+ QCOMPARE(item->property("section").toString(), QLatin1String("0"));
+ QCOMPARE(item->property("nextSection").toString(), i < 14 ? QLatin1String("0") : QLatin1String("1"));
+ QCOMPARE(item->property("prevSection").toString(), i > 10 ? QLatin1String("0") : QLatin1String("A"));
+ }
+}
+
void tst_QQuickListView::currentIndex_delayedItemCreation()
{
QFETCH(bool, setCurrentToZero);
diff --git a/tests/auto/quick/qquickrectangle/data/gradient-border.qml b/tests/auto/quick/qquickrectangle/data/gradient-border.qml
new file mode 100644
index 0000000000..1d45fb2799
--- /dev/null
+++ b/tests/auto/quick/qquickrectangle/data/gradient-border.qml
@@ -0,0 +1,21 @@
+import QtQuick 2.0
+
+Item {
+ Rectangle {
+ width: 100
+ height: 100
+ border.width: 10
+ radius: 10
+
+ gradient: Gradient {
+ GradientStop {
+ position: 0.00
+ color: '#ffffff'
+ }
+ GradientStop {
+ position: 0.94
+ color: '#000000'
+ }
+ }
+ }
+}
diff --git a/tests/auto/quick/qquickrectangle/tst_qquickrectangle.cpp b/tests/auto/quick/qquickrectangle/tst_qquickrectangle.cpp
index 8a24636647..a7e82e272f 100644
--- a/tests/auto/quick/qquickrectangle/tst_qquickrectangle.cpp
+++ b/tests/auto/quick/qquickrectangle/tst_qquickrectangle.cpp
@@ -35,6 +35,7 @@
#include <QtQml/qqmlengine.h>
#include <QtQml/qqmlcomponent.h>
+#include <QtQuick/qquickview.h>
#include <private/qquickrectangle_p.h>
#include "../../shared/util.h"
@@ -47,6 +48,7 @@ public:
private slots:
void gradient();
+ void gradient_border();
void antialiasing();
private:
@@ -88,6 +90,15 @@ void tst_qquickrectangle::gradient()
delete rect;
}
+void tst_qquickrectangle::gradient_border()
+{
+ QQuickView view;
+ view.setSource(testFileUrl("gradient-border.qml"));
+ view.show();
+
+ QVERIFY(QTest::qWaitForWindowExposed(&view));
+}
+
void tst_qquickrectangle::antialiasing()
{
QQmlComponent component(&engine);
diff --git a/tests/manual/scenegraph_lancelot/data/text/text_emoji.qml b/tests/manual/scenegraph_lancelot/data/text/text_emoji.qml
new file mode 100644
index 0000000000..d50f6d6715
--- /dev/null
+++ b/tests/manual/scenegraph_lancelot/data/text/text_emoji.qml
@@ -0,0 +1,45 @@
+import QtQuick 2.0
+
+Item {
+ width: 320
+ height: 480
+
+ Component {
+ id: component
+ Column {
+ property variant listModel: model
+ Repeater {
+ model: [Text.NativeRendering, Text.QtRendering]
+ Rectangle {
+ width: text.implicitWidth
+ height: text.implicitHeight
+ color: listModel.backGroundColor ? listModel.backGroundColor : "white"
+
+ Text {
+ id: text
+ font.pixelSize: 32
+ renderType: modelData
+ text: "e😃m😇o😍j😜i😸!"
+
+ color: listModel.color ? listModel.color : "black"
+ opacity: listModel.opacity ? listModel.opacity : 1.0
+ }
+ }
+ }
+ }
+ }
+
+ Column {
+ anchors.centerIn: parent
+ Repeater {
+ model: ListModel {
+ ListElement { color: "black" }
+ ListElement { color: "blue" }
+ ListElement { color: "#990000ff" }
+ ListElement { opacity: 0.5 }
+ ListElement { backGroundColor: "green" }
+ }
+ delegate: component
+ }
+ }
+}
diff --git a/tools/qml/Info.plist b/tools/qml/Info.plist
index 42d074a3af..567c5bf8fd 100644
--- a/tools/qml/Info.plist
+++ b/tools/qml/Info.plist
@@ -2,6 +2,8 @@
<!DOCTYPE plist SYSTEM "file://localhost/System/Library/DTDs/PropertyList.dtd">
<plist version="0.1">
<dict>
+ <key>NSPrincipalClass</key>
+ <string>NSApplication</string>
<key>CFBundleIconFile</key>
<string>@ICON@</string>
<key>CFBundleIdentifier</key>
diff --git a/tools/qml/main.cpp b/tools/qml/main.cpp
index ea601ba946..206788c061 100644
--- a/tools/qml/main.cpp
+++ b/tools/qml/main.cpp
@@ -39,6 +39,8 @@
#include <QGuiApplication>
#include <QWindow>
#include <QFileOpenEvent>
+#include <QOpenGLContext>
+#include <QOpenGLFunctions>
#ifdef QT_WIDGETS_LIB
#include <QApplication>
#endif // QT_WIDGETS_LIB
@@ -56,6 +58,7 @@
#include <QStandardPaths>
#include <QTranslator>
#include <QtGlobal>
+#include <QLibraryInfo>
#include <qqml.h>
#include <qqmldebug.h>
#include <private/qabstractanimation_p.h>
@@ -73,6 +76,7 @@
static Config *conf = 0;
static QQmlApplicationEngine *qae = 0;
static int exitTimerId = -1;
+bool verboseMode = false;
static void loadConf(const QString &override, bool quiet) // Terminates app on failure
{
@@ -101,6 +105,7 @@ static void loadConf(const QString &override, bool quiet) // Terminates app on f
}
if (!quiet) {
+ printf("qml: %s\n", QLibraryInfo::build());
if (builtIn)
printf("qml: Using built-in configuration.\n");
else
@@ -121,20 +126,6 @@ static void loadConf(const QString &override, bool quiet) // Terminates app on f
}
}
-void contain(QObject *o, const QUrl &containPath)
-{
- QQmlComponent c(qae, containPath);
- QObject *o2 = c.create();
- if (!o2)
- return;
- bool success = false;
- int idx;
- if ((idx = o2->metaObject()->indexOfProperty("containedObject")) != -1)
- success = o2->metaObject()->property(idx).write(o2, QVariant::fromValue<QObject*>(o));
- if (!success)
- o->setParent(o2); //Set QObject parent, and assume container will react as needed
-}
-
#ifdef QT_GUI_LIB
void noFilesGiven();
@@ -188,6 +179,9 @@ public:
bool earlyExit;
private:
+ void contain(QObject *o, const QUrl &containPath);
+ void checkForWindow(QObject *o);
+
int expect;
bool haveOne;
@@ -195,6 +189,7 @@ public Q_SLOTS:
void checkFinished(QObject *o)
{
if (o) {
+ checkForWindow(o);
haveOne = true;
if (conf && qae)
foreach (PartialScene *ps, conf->completers)
@@ -214,8 +209,56 @@ public Q_SLOTS:
//Will be checked before calling exec()
earlyExit = true;
}
+#ifdef QT_GUI_LIB
+ void onOpenGlContextCreated(QOpenGLContext *context);
+#endif
};
+void LoadWatcher::contain(QObject *o, const QUrl &containPath)
+{
+ QQmlComponent c(qae, containPath);
+ QObject *o2 = c.create();
+ if (!o2)
+ return;
+ checkForWindow(o2);
+ bool success = false;
+ int idx;
+ if ((idx = o2->metaObject()->indexOfProperty("containedObject")) != -1)
+ success = o2->metaObject()->property(idx).write(o2, QVariant::fromValue<QObject*>(o));
+ if (!success)
+ o->setParent(o2); //Set QObject parent, and assume container will react as needed
+}
+
+void LoadWatcher::checkForWindow(QObject *o)
+{
+#ifdef QT_GUI_LIB
+ if (verboseMode && o->isWindowType() && o->inherits("QQuickWindow")) {
+ connect(o, SIGNAL(openglContextCreated(QOpenGLContext*)),
+ this, SLOT(onOpenGlContextCreated(QOpenGLContext*)));
+ }
+#else
+ Q_UNUSED(o)
+#endif // QT_GUI_LIB
+}
+
+#ifdef QT_GUI_LIB
+void LoadWatcher::onOpenGlContextCreated(QOpenGLContext *context)
+{
+ context->makeCurrent(qobject_cast<QWindow *>(sender()));
+ QOpenGLFunctions functions(context);
+ QByteArray output = "Vendor : ";
+ output += reinterpret_cast<const char *>(functions.glGetString(GL_VENDOR));
+ output += "\nRenderer: ";
+ output += reinterpret_cast<const char *>(functions.glGetString(GL_RENDERER));
+ output += "\nVersion : ";
+ output += reinterpret_cast<const char *>(functions.glGetString(GL_VERSION));
+ output += "\nLanguage: ";
+ output += reinterpret_cast<const char *>(functions.glGetString(GL_SHADING_LANGUAGE_VERSION));
+ puts(output.constData());
+ context->doneCurrent();
+}
+#endif // QT_GUI_LIB
+
void quietMessageHandler(QtMsgType type, const QMessageLogContext &ctxt, const QString &msg)
{
Q_UNUSED(ctxt);
@@ -251,7 +294,6 @@ QmlApplicationType applicationType = QmlApplicationTypeCore;
QmlApplicationType applicationType = QmlApplicationTypeGui;
#endif // QT_GUI_LIB
bool quietMode = false;
-bool verboseMode = false;
void printVersion()
{
printf("qml binary version ");
@@ -286,6 +328,10 @@ void printUsage()
printf("\t-f [file] .................... Load the given file as a QML file.\n");
printf("\t-config [file] ............... Load the given file as the configuration file.\n");
printf("\t-- ........................... Arguments after this one are ignored by the launcher, but may be used within the QML application.\n");
+ printf("\tGL options:\n");
+ printf("\t-desktop.......................Force use of desktop GL (AA_UseDesktopOpenGL)\n");
+ printf("\t-gles..........................Force use of GLES (AA_UseOpenGLES)\n");
+ printf("\t-software......................Force use of software rendering (AA_UseOpenGLES)\n");
printf("\tDebugging options:\n");
printf("\t-verbose ..................... Print information about what qml is doing, like specific file urls being loaded.\n");
printf("\t-translation [file] .......... Load the given file as the translations file.\n");
@@ -451,6 +497,12 @@ int main(int argc, char *argv[])
continue;//Invalid usage, but just ignore it
dummyDir = argList[i+1];
i++;
+ } else if (arg == QLatin1String("-gles")) {
+ QCoreApplication::setAttribute(Qt::AA_UseOpenGLES);
+ } else if (arg == QLatin1String("-software")) {
+ QCoreApplication::setAttribute(Qt::AA_UseSoftwareOpenGL);
+ } else if (arg == QLatin1String("-desktop")) {
+ QCoreApplication::setAttribute(Qt::AA_UseDesktopOpenGL);
} else {
files << arg;
}
diff --git a/tools/qmlscene/main.cpp b/tools/qmlscene/main.cpp
index b8920cd853..fe01b92244 100644
--- a/tools/qmlscene/main.cpp
+++ b/tools/qmlscene/main.cpp
@@ -40,6 +40,7 @@
#include <QtCore/qtextstream.h>
#include <QtGui/QGuiApplication>
+#include <QtGui/QOpenGLFunctions>
#include <QtQml/qqml.h>
#include <QtQml/qqmlengine.h>
@@ -148,8 +149,11 @@ struct Options
, quitImmediately(false)
, resizeViewToRootItem(false)
, multisample(false)
- , contextSharing(true)
+ , verbose(false)
{
+ // QtWebEngine needs a shared context in order for the GPU thread to
+ // upload textures.
+ applicationAttributes.append(Qt::AA_ShareOpenGLContexts);
}
QUrl file;
@@ -164,7 +168,8 @@ struct Options
bool quitImmediately;
bool resizeViewToRootItem;
bool multisample;
- bool contextSharing;
+ bool verbose;
+ QVector<Qt::ApplicationAttribute> applicationAttributes;
QString translationFile;
};
@@ -340,23 +345,77 @@ static void usage()
puts("Usage: qmlscene [options] <filename>");
puts(" ");
puts(" Options:");
- puts(" --maximized ............................... Run maximized");
- puts(" --fullscreen .............................. Run fullscreen");
- puts(" --transparent ............................. Make the window transparent");
- puts(" --multisample ............................. Enable multisampling (OpenGL anti-aliasing)");
- puts(" --no-version-detection .................... Do not try to detect the version of the .qml file");
- puts(" --slow-animations ......................... Run all animations in slow motion");
- puts(" --resize-to-root .......................... Resize the window to the size of the root item");
- puts(" --quit .................................... Quit immediately after starting");
- puts(" --disable-context-sharing ................. Disable the use of a shared GL context for QtQuick Windows");
- puts(" -I <path> ................................. Add <path> to the list of import paths");
- puts(" -P <path> ................................. Add <path> to the list of plugin paths");
- puts(" -translation <translationfile> ............ Set the language to run in");
+ puts(" --maximized ...................... Run maximized");
+ puts(" --fullscreen ..................... Run fullscreen");
+ puts(" --transparent .................... Make the window transparent");
+ puts(" --multisample .................... Enable multisampling (OpenGL anti-aliasing)");
+ puts(" --no-version-detection ........... Do not try to detect the version of the .qml file");
+ puts(" --slow-animations ................ Run all animations in slow motion");
+ puts(" --resize-to-root ................. Resize the window to the size of the root item");
+ puts(" --quit ........................... Quit immediately after starting");
+ puts(" --disable-context-sharing ........ Disable the use of a shared GL context for QtQuick Windows\n"
+ " .........(remove AA_ShareOpenGLContexts)");
+ puts(" --desktop..........................Force use of desktop GL (AA_UseDesktopOpenGL)");
+ puts(" --gles.............................Force use of GLES (AA_UseOpenGLES)");
+ puts(" --software.........................Force use of software rendering (AA_UseOpenGLES)");
+ puts(" --verbose..........................Print version and graphical diagnostics for the run-time");
+ puts(" -I <path> ........................ Add <path> to the list of import paths");
+ puts(" -P <path> ........................ Add <path> to the list of plugin paths");
+ puts(" -translation <translationfile> ... Set the language to run in");
puts(" ");
exit(1);
}
+// Listen on GL context creation of the QQuickWindow in order to print diagnostic output.
+class DiagnosticGlContextCreationListener : public QObject {
+ Q_OBJECT
+public:
+ explicit DiagnosticGlContextCreationListener(QQuickWindow *window) : QObject(window)
+ {
+ connect(window, &QQuickWindow::openglContextCreated,
+ this, &DiagnosticGlContextCreationListener::onOpenGlContextCreated);
+ }
+
+private slots:
+ void onOpenGlContextCreated(QOpenGLContext *context)
+ {
+ context->makeCurrent(qobject_cast<QQuickWindow *>(parent()));
+ QOpenGLFunctions functions(context);
+ QByteArray output = "Vendor : ";
+ output += reinterpret_cast<const char *>(functions.glGetString(GL_VENDOR));
+ output += "\nRenderer: ";
+ output += reinterpret_cast<const char *>(functions.glGetString(GL_RENDERER));
+ output += "\nVersion : ";
+ output += reinterpret_cast<const char *>(functions.glGetString(GL_VERSION));
+ output += "\nLanguage: ";
+ output += reinterpret_cast<const char *>(functions.glGetString(GL_SHADING_LANGUAGE_VERSION));
+ puts(output.constData());
+ context->doneCurrent();
+ deleteLater();
+ }
+};
+
+static void setWindowTitle(bool verbose, const QObject *topLevel, QWindow *window)
+{
+ const QString oldTitle = window->title();
+ QString newTitle = oldTitle;
+ if (newTitle.isEmpty()) {
+ newTitle = QLatin1String("qmlscene");
+ if (!qobject_cast<const QWindow *>(topLevel) && !topLevel->objectName().isEmpty())
+ newTitle += QLatin1String(": ") + topLevel->objectName();
+ }
+ if (verbose) {
+ newTitle += QLatin1String(" [Qt ") + QLatin1String(QT_VERSION_STR) + QLatin1Char(' ')
+ + QGuiApplication::platformName() + QLatin1Char(' ');
+ newTitle += QOpenGLContext::openGLModuleType() == QOpenGLContext::LibGL
+ ? QLatin1String("GL") : QLatin1String("GLES");
+ newTitle += QLatin1Char(']');
+ }
+ if (oldTitle != newTitle)
+ window->setTitle(newTitle);
+}
+
int main(int argc, char ** argv)
{
Options options;
@@ -389,7 +448,15 @@ int main(int argc, char ** argv)
else if (lowerArgument == QLatin1String("--multisample"))
options.multisample = true;
else if (lowerArgument == QLatin1String("--disable-context-sharing"))
- options.contextSharing = false;
+ options.applicationAttributes.removeAll(Qt::AA_ShareOpenGLContexts);
+ else if (lowerArgument == QLatin1String("--gles"))
+ options.applicationAttributes.append(Qt::AA_UseOpenGLES);
+ else if (lowerArgument == QLatin1String("--software"))
+ options.applicationAttributes.append(Qt::AA_UseSoftwareOpenGL);
+ else if (lowerArgument == QLatin1String("--desktop"))
+ options.applicationAttributes.append(Qt::AA_UseDesktopOpenGL);
+ else if (lowerArgument == QLatin1String("--verbose"))
+ options.verbose = true;
else if (lowerArgument == QLatin1String("-i") && i + 1 < argc)
imports.append(QString::fromLatin1(argv[++i]));
else if (lowerArgument == QLatin1String("-p") && i + 1 < argc)
@@ -402,9 +469,8 @@ int main(int argc, char ** argv)
}
}
- // QtWebEngine needs a shared context in order for the GPU thread to
- // upload textures.
- QCoreApplication::setAttribute(Qt::AA_ShareOpenGLContexts, options.contextSharing);
+ foreach (Qt::ApplicationAttribute a, options.applicationAttributes)
+ QCoreApplication::setAttribute(a);
#ifdef QT_WIDGETS_LIB
QApplication app(argc, argv);
#else
@@ -445,6 +511,9 @@ int main(int argc, char ** argv)
int exitCode = 0;
+ if (options.verbose)
+ puts(QLibraryInfo::build());
+
if (!options.file.isEmpty()) {
if (!options.versionDetection || checkVersion(options.file)) {
#ifndef QT_NO_TRANSLATION
@@ -487,8 +556,6 @@ int main(int argc, char ** argv)
QQuickView* qxView = new QQuickView(&engine, NULL);
window.reset(qxView);
// Set window default properties; the qml can still override them
- QString oname = contentItem->objectName();
- window->setTitle(oname.isEmpty() ? QString::fromLatin1("qmlscene") : QString::fromLatin1("qmlscene: ") + oname);
if (options.resizeViewToRootItem)
qxView->setResizeMode(QQuickView::SizeViewToRootObject);
else
@@ -498,6 +565,9 @@ int main(int argc, char ** argv)
}
if (window) {
+ setWindowTitle(options.verbose, topLevel, window.data());
+ if (options.verbose)
+ new DiagnosticGlContextCreationListener(window.data());
QSurfaceFormat surfaceFormat = window->requestedFormat();
if (options.multisample)
surfaceFormat.setSamples(16);
@@ -539,3 +609,5 @@ int main(int argc, char ** argv)
return exitCode;
}
+
+#include "main.moc"