aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorMorten Johan Sørvig <morten.sorvig@qt.io>2018-03-08 18:35:03 +0100
committerMorten Johan Sørvig <morten.sorvig@qt.io>2018-03-08 18:35:03 +0100
commitd9ea4917ca97aeee050a86151fbfa069771b498d (patch)
tree21fd6960d8a866bf6f5a5a8f9db9be801f8065c1 /src
parentf9beafddd256cd0b79bf2478a812053ef61241fc (diff)
parentc6a26c248e8abc421b87c3dd6b2466d490ea902e (diff)
Merge remote-tracking branch 'gerrit/5.11' into wip/webassembly
Diffstat (limited to 'src')
-rw-r--r--src/3rdparty/masm/assembler/ARM64Assembler.h7
-rw-r--r--src/3rdparty/masm/masm.pri2
-rw-r--r--src/3rdparty/masm/wtf/Compiler.h6
-rw-r--r--src/3rdparty/masm/wtf/MathExtras.h5
-rw-r--r--src/3rdparty/masm/wtf/Platform.h12
-rw-r--r--src/3rdparty/masm/yarr/YarrPattern.cpp2
-rw-r--r--src/imports/builtins/builtins.qmltypes5
-rw-r--r--src/imports/folderlistmodel/fileinfothread.cpp7
-rw-r--r--src/imports/folderlistmodel/fileinfothread_p.h2
-rw-r--r--src/imports/folderlistmodel/plugin.cpp8
-rw-r--r--src/imports/folderlistmodel/plugins.qmltypes15
-rw-r--r--src/imports/folderlistmodel/qquickfolderlistmodel.cpp71
-rw-r--r--src/imports/folderlistmodel/qquickfolderlistmodel.h7
-rw-r--r--src/imports/handlers/plugin.cpp19
-rw-r--r--src/imports/handlers/plugins.qmltypes308
-rw-r--r--src/imports/layouts/plugin.cpp2
-rw-r--r--src/imports/layouts/qquickgridlayoutengine.cpp2
-rw-r--r--src/imports/layouts/qquicklayout.cpp9
-rw-r--r--src/imports/layouts/qquicklinearlayout.cpp8
-rw-r--r--src/imports/layouts/qquickstacklayout.cpp4
-rw-r--r--src/imports/localstorage/plugin.cpp114
-rw-r--r--src/imports/models/plugin.cpp2
-rw-r--r--src/imports/particles/plugin.cpp2
-rw-r--r--src/imports/qtquick2/plugin.cpp4
-rw-r--r--src/imports/qtquick2/plugins.qmltypes13
-rw-r--r--src/imports/settings/plugin.cpp2
-rw-r--r--src/imports/settings/qqmlsettings.cpp11
-rw-r--r--src/imports/shapes/plugin.cpp10
-rw-r--r--src/imports/shapes/plugins.qmltypes39
-rw-r--r--src/imports/shapes/qquickshape.cpp105
-rw-r--r--src/imports/shapes/qquickshape_p.h13
-rw-r--r--src/imports/shapes/qquickshape_p_p.h21
-rw-r--r--src/imports/shapes/qquickshapegenericrenderer.cpp6
-rw-r--r--src/imports/shapes/qquickshapenvprrenderer.cpp2
-rw-r--r--src/imports/shapes/qquickshapesoftwarerenderer.cpp2
-rw-r--r--src/imports/shapes/qtquickshapesplugin.qrc (renamed from src/imports/shapes/shapes.qrc)0
-rw-r--r--src/imports/shapes/shapes.pro4
-rw-r--r--src/imports/sharedimage/plugin.cpp2
-rw-r--r--src/imports/sharedimage/plugins.qmltypes11
-rw-r--r--src/imports/sharedimage/qsharedimageloader.cpp13
-rw-r--r--src/imports/statemachine/plugin.cpp2
-rw-r--r--src/imports/statemachine/signaltransition.cpp8
-rw-r--r--src/imports/statemachine/state.cpp2
-rw-r--r--src/imports/statemachine/statemachine.cpp2
-rw-r--r--src/imports/testlib/SignalSpy.qml2
-rw-r--r--src/imports/testlib/TestCase.qml28
-rw-r--r--src/imports/testlib/main.cpp13
-rw-r--r--src/imports/testlib/plugins.qmltypes12
-rw-r--r--src/imports/testlib/qmldir1
-rw-r--r--src/imports/window/plugin.cpp2
-rw-r--r--src/imports/window/plugins.qmltypes33
-rw-r--r--src/imports/xmllistmodel/qqmlxmllistmodel.cpp9
-rw-r--r--src/particles/qquickangledirection.cpp4
-rw-r--r--src/particles/qquickcustomaffector.cpp2
-rw-r--r--src/particles/qquickcustomparticle.cpp16
-rw-r--r--src/particles/qquickellipseextruder.cpp4
-rw-r--r--src/particles/qquickimageparticle.cpp48
-rw-r--r--src/particles/qquickitemparticle.cpp6
-rw-r--r--src/particles/qquicklineextruder.cpp4
-rw-r--r--src/particles/qquickmaskextruder.cpp2
-rw-r--r--src/particles/qquickparticleaffector.cpp2
-rw-r--r--src/particles/qquickparticleemitter.cpp14
-rw-r--r--src/particles/qquickparticleextruder.cpp4
-rw-r--r--src/particles/qquickparticlegroup.cpp6
-rw-r--r--src/particles/qquickparticlepainter.cpp4
-rw-r--r--src/particles/qquickparticlesystem.cpp38
-rw-r--r--src/particles/qquickparticlesystem_p.h11
-rw-r--r--src/particles/qquickpointdirection.cpp4
-rw-r--r--src/particles/qquickrectangleextruder.cpp14
-rw-r--r--src/particles/qquickspritegoal.cpp4
-rw-r--r--src/particles/qquicktargetdirection.cpp8
-rw-r--r--src/particles/qquicktrailemitter.cpp10
-rw-r--r--src/particles/qquickturbulence.cpp2
-rw-r--r--src/particles/qquickv4particledata.cpp60
-rw-r--r--src/particles/qquickv4particledata_p.h2
-rw-r--r--src/particles/qquickwander.cpp12
-rw-r--r--src/plugins/qmltooling/packetprotocol/qpacketprotocol.cpp2
-rw-r--r--src/plugins/qmltooling/packetprotocol/qpacketprotocol_p.h2
-rw-r--r--src/plugins/qmltooling/qmldbg_debugger/qqmldebuggerservicefactory.cpp2
-rw-r--r--src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp49
-rw-r--r--src/plugins/qmltooling/qmldbg_debugger/qqmlwatcher.cpp8
-rw-r--r--src/plugins/qmltooling/qmldbg_debugger/qv4datacollector.cpp20
-rw-r--r--src/plugins/qmltooling/qmldbg_debugger/qv4debugger.cpp16
-rw-r--r--src/plugins/qmltooling/qmldbg_debugger/qv4debuggeragent.cpp4
-rw-r--r--src/plugins/qmltooling/qmldbg_debugger/qv4debugjob.cpp2
-rw-r--r--src/plugins/qmltooling/qmldbg_debugger/qv4debugservice.cpp6
-rw-r--r--src/plugins/qmltooling/qmldbg_inspector/highlight.cpp2
-rw-r--r--src/plugins/qmltooling/qmldbg_inspector/inspecttool.cpp4
-rw-r--r--src/plugins/qmltooling/qmldbg_inspector/qqmlinspectorservice.cpp8
-rw-r--r--src/plugins/qmltooling/qmldbg_inspector/qquickwindowinspector.cpp36
-rw-r--r--src/plugins/qmltooling/qmldbg_local/qlocalclientconnection.cpp19
-rw-r--r--src/plugins/qmltooling/qmldbg_messages/qdebugmessageservice.cpp2
-rw-r--r--src/plugins/qmltooling/qmldbg_messages/qdebugmessageservicefactory.cpp2
-rw-r--r--src/plugins/qmltooling/qmldbg_native/qqmlnativedebugconnector.cpp4
-rw-r--r--src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservice.cpp10
-rw-r--r--src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservicefactory.cpp2
-rw-r--r--src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp49
-rw-r--r--src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservicefactory.cpp2
-rw-r--r--src/plugins/qmltooling/qmldbg_quickprofiler/qquickprofileradapterfactory.cpp2
-rw-r--r--src/plugins/qmltooling/qmldbg_server/qqmldebugserver.cpp12
-rw-r--r--src/plugins/qmltooling/qmldbg_tcp/qtcpserverconnection.cpp28
-rw-r--r--src/plugins/qmltooling/qmltooling.pro19
-rw-r--r--src/plugins/scenegraph/d3d12/qsgd3d12engine.cpp2
-rw-r--r--src/plugins/scenegraph/d3d12/qsgd3d12renderloop.cpp3
-rw-r--r--src/plugins/scenegraph/openvg/qsgopenvgrenderloop.cpp1
-rw-r--r--src/qml/animations/qabstractanimationjob.cpp81
-rw-r--r--src/qml/animations/qabstractanimationjob_p.h11
-rw-r--r--src/qml/animations/qanimationgroupjob.cpp18
-rw-r--r--src/qml/animations/qanimationgroupjob_p.h6
-rw-r--r--src/qml/animations/qcontinuinganimationgroupjob.cpp1
-rw-r--r--src/qml/animations/qparallelanimationgroupjob_p.h4
-rw-r--r--src/qml/animations/qpauseanimationjob.cpp3
-rw-r--r--src/qml/animations/qpauseanimationjob_p.h2
-rw-r--r--src/qml/animations/qsequentialanimationgroupjob.cpp10
-rw-r--r--src/qml/animations/qsequentialanimationgroupjob_p.h12
-rw-r--r--src/qml/compiler/compiler.pri13
-rw-r--r--src/qml/compiler/qqmlirbuilder.cpp109
-rw-r--r--src/qml/compiler/qqmlirbuilder_p.h56
-rw-r--r--src/qml/compiler/qqmlpropertycachecreator.cpp56
-rw-r--r--src/qml/compiler/qqmlpropertycachecreator_p.h97
-rw-r--r--src/qml/compiler/qqmlpropertyvalidator.cpp34
-rw-r--r--src/qml/compiler/qqmltypecompiler.cpp62
-rw-r--r--src/qml/compiler/qqmltypecompiler_p.h12
-rw-r--r--src/qml/compiler/qv4bytecodegenerator.cpp32
-rw-r--r--src/qml/compiler/qv4bytecodegenerator_p.h2
-rw-r--r--src/qml/compiler/qv4codegen.cpp102
-rw-r--r--src/qml/compiler/qv4codegen_p.h72
-rw-r--r--src/qml/compiler/qv4compileddata.cpp55
-rw-r--r--src/qml/compiler/qv4compileddata_p.h28
-rw-r--r--src/qml/compiler/qv4compiler.cpp4
-rw-r--r--src/qml/compiler/qv4compilercontext_p.h18
-rw-r--r--src/qml/compiler/qv4compilercontrolflow_p.h12
-rw-r--r--src/qml/compiler/qv4compilerscanfunctions.cpp22
-rw-r--r--src/qml/compiler/qv4compilerscanfunctions_p.h4
-rw-r--r--src/qml/compiler/qv4instr_moth.cpp10
-rw-r--r--src/qml/compiler/qv4instr_moth_p.h40
-rw-r--r--src/qml/configure.json9
-rw-r--r--src/qml/debugger/qqmlabstractprofileradapter_p.h6
-rw-r--r--src/qml/debugger/qqmlconfigurabledebugservice_p.h2
-rw-r--r--src/qml/debugger/qqmldebugconnector.cpp10
-rw-r--r--src/qml/debugger/qqmldebugconnector_p.h4
-rw-r--r--src/qml/debugger/qqmldebugserverconnection_p.h2
-rw-r--r--src/qml/debugger/qqmldebugservice_p.h4
-rw-r--r--src/qml/debugger/qqmlprofiler_p.h47
-rw-r--r--src/qml/debugger/qqmlprofilerdefinitions_p.h21
-rw-r--r--src/qml/doc/qtqml.qdocconf2
-rw-r--r--src/qml/doc/snippets/code/src_script_qjsengine.cpp20
-rw-r--r--src/qml/doc/src/cppintegration/definetypes.qdoc2
-rw-r--r--src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc12
-rw-r--r--src/qml/doc/src/cppintegration/topic.qdoc2
-rw-r--r--src/qml/doc/src/cppintegration/warning.qdocinc6
-rw-r--r--src/qml/doc/src/includes/qqmlcomponent.qdoc58
-rw-r--r--src/qml/doc/src/javascript/dynamicobjectcreation.qdoc2
-rw-r--r--src/qml/doc/src/qmlfunctions.qdoc27
-rw-r--r--src/qml/doc/src/qmllanguageref/syntax/basics.qdoc2
-rw-r--r--src/qml/doc/src/qmllanguageref/syntax/objectattributes.qdoc39
-rw-r--r--src/qml/doc/src/qmllanguageref/typesystem/objecttypes.qdoc2
-rw-r--r--src/qml/doc/src/qtqml.qdoc5
-rw-r--r--src/qml/jit/qv4assembler.cpp341
-rw-r--r--src/qml/jit/qv4assembler_p.h1
-rw-r--r--src/qml/jit/qv4jit.cpp64
-rw-r--r--src/qml/jit/qv4jit_p.h230
-rw-r--r--src/qml/jsapi/qjsengine.cpp83
-rw-r--r--src/qml/jsapi/qjsengine.h9
-rw-r--r--src/qml/jsapi/qjsengine_p.h4
-rw-r--r--src/qml/jsapi/qjsvalue.cpp106
-rw-r--r--src/qml/jsapi/qjsvalue_p.h8
-rw-r--r--src/qml/jsruntime/jsruntime.pri13
-rw-r--r--src/qml/jsruntime/qv4arraybuffer.cpp4
-rw-r--r--src/qml/jsruntime/qv4arraybuffer_p.h4
-rw-r--r--src/qml/jsruntime/qv4arraydata.cpp45
-rw-r--r--src/qml/jsruntime/qv4arraydata_p.h9
-rw-r--r--src/qml/jsruntime/qv4context.cpp2
-rw-r--r--src/qml/jsruntime/qv4context_p.h10
-rw-r--r--src/qml/jsruntime/qv4dataview.cpp6
-rw-r--r--src/qml/jsruntime/qv4dateobject.cpp4
-rw-r--r--src/qml/jsruntime/qv4dateobject_p.h2
-rw-r--r--src/qml/jsruntime/qv4debugging_p.h2
-rw-r--r--src/qml/jsruntime/qv4engine.cpp84
-rw-r--r--src/qml/jsruntime/qv4engine_p.h25
-rw-r--r--src/qml/jsruntime/qv4enginebase_p.h3
-rw-r--r--src/qml/jsruntime/qv4errorobject_p.h4
-rw-r--r--src/qml/jsruntime/qv4executableallocator.cpp6
-rw-r--r--src/qml/jsruntime/qv4executableallocator_p.h18
-rw-r--r--src/qml/jsruntime/qv4function_p.h2
-rw-r--r--src/qml/jsruntime/qv4functionobject.cpp27
-rw-r--r--src/qml/jsruntime/qv4functionobject_p.h47
-rw-r--r--src/qml/jsruntime/qv4global_p.h8
-rw-r--r--src/qml/jsruntime/qv4globalobject.cpp6
-rw-r--r--src/qml/jsruntime/qv4identifier.cpp26
-rw-r--r--src/qml/jsruntime/qv4identifier_p.h104
-rw-r--r--src/qml/jsruntime/qv4identifiertable.cpp4
-rw-r--r--src/qml/jsruntime/qv4include.cpp30
-rw-r--r--src/qml/jsruntime/qv4include_p.h2
-rw-r--r--src/qml/jsruntime/qv4internalclass.cpp19
-rw-r--r--src/qml/jsruntime/qv4internalclass_p.h8
-rw-r--r--src/qml/jsruntime/qv4jscall_p.h4
-rw-r--r--src/qml/jsruntime/qv4jsonobject.cpp20
-rw-r--r--src/qml/jsruntime/qv4jsonobject_p.h4
-rw-r--r--src/qml/jsruntime/qv4managed.cpp8
-rw-r--r--src/qml/jsruntime/qv4managed_p.h2
-rw-r--r--src/qml/jsruntime/qv4mathobject.cpp2
-rw-r--r--src/qml/jsruntime/qv4memberdata_p.h6
-rw-r--r--src/qml/jsruntime/qv4object.cpp76
-rw-r--r--src/qml/jsruntime/qv4object_p.h32
-rw-r--r--src/qml/jsruntime/qv4objectiterator.cpp8
-rw-r--r--src/qml/jsruntime/qv4objectiterator_p.h4
-rw-r--r--src/qml/jsruntime/qv4objectproto.cpp6
-rw-r--r--src/qml/jsruntime/qv4persistent.cpp50
-rw-r--r--src/qml/jsruntime/qv4persistent_p.h24
-rw-r--r--src/qml/jsruntime/qv4profiling.cpp3
-rw-r--r--src/qml/jsruntime/qv4profiling_p.h40
-rw-r--r--src/qml/jsruntime/qv4property_p.h4
-rw-r--r--src/qml/jsruntime/qv4qmlcontext.cpp22
-rw-r--r--src/qml/jsruntime/qv4qmlcontext_p.h2
-rw-r--r--src/qml/jsruntime/qv4qobjectwrapper.cpp131
-rw-r--r--src/qml/jsruntime/qv4qobjectwrapper_p.h8
-rw-r--r--src/qml/jsruntime/qv4regexp.cpp10
-rw-r--r--src/qml/jsruntime/qv4regexp_p.h4
-rw-r--r--src/qml/jsruntime/qv4regexpobject.cpp42
-rw-r--r--src/qml/jsruntime/qv4runtime.cpp53
-rw-r--r--src/qml/jsruntime/qv4runtimeapi_p.h2
-rw-r--r--src/qml/jsruntime/qv4runtimecodegen.cpp7
-rw-r--r--src/qml/jsruntime/qv4scopedvalue_p.h6
-rw-r--r--src/qml/jsruntime/qv4script.cpp49
-rw-r--r--src/qml/jsruntime/qv4script_p.h11
-rw-r--r--src/qml/jsruntime/qv4sequenceobject.cpp45
-rw-r--r--src/qml/jsruntime/qv4sequenceobject_p.h4
-rw-r--r--src/qml/jsruntime/qv4sparsearray.cpp42
-rw-r--r--src/qml/jsruntime/qv4sparsearray_p.h8
-rw-r--r--src/qml/jsruntime/qv4string.cpp106
-rw-r--r--src/qml/jsruntime/qv4string_p.h88
-rw-r--r--src/qml/jsruntime/qv4stringobject.cpp25
-rw-r--r--src/qml/jsruntime/qv4typedarray.cpp10
-rw-r--r--src/qml/jsruntime/qv4value_p.h101
-rw-r--r--src/qml/jsruntime/qv4variantobject.cpp18
-rw-r--r--src/qml/jsruntime/qv4variantobject_p.h8
-rw-r--r--src/qml/jsruntime/qv4vme_moth.cpp40
-rw-r--r--src/qml/jsruntime/qv4vme_moth_p.h2
-rw-r--r--src/qml/memory/qv4heap_p.h44
-rw-r--r--src/qml/memory/qv4mm.cpp242
-rw-r--r--src/qml/memory/qv4mm_p.h55
-rw-r--r--src/qml/memory/qv4mmdefs_p.h9
-rw-r--r--src/qml/memory/qv4writebarrier_p.h131
-rw-r--r--src/qml/parser/qqmljsast.cpp8
-rw-r--r--src/qml/parser/qqmljsast_p.h65
-rw-r--r--src/qml/parser/qqmljsengine_p.cpp2
-rw-r--r--src/qml/parser/qqmljsengine_p.h5
-rw-r--r--src/qml/parser/qqmljsgrammar.cpp6
-rw-r--r--src/qml/parser/qqmljslexer.cpp18
-rw-r--r--src/qml/parser/qqmljsmemorypool_p.h22
-rw-r--r--src/qml/parser/qqmljsparser.cpp70
-rw-r--r--src/qml/parser/qqmljsparser_p.h6
-rw-r--r--src/qml/qml.pro35
-rw-r--r--src/qml/qml/ftw/qbitfield_p.h4
-rw-r--r--src/qml/qml/ftw/qfieldlist_p.h22
-rw-r--r--src/qml/qml/ftw/qfinitestack_p.h6
-rw-r--r--src/qml/qml/ftw/qflagpointer_p.h6
-rw-r--r--src/qml/qml/ftw/qhashedstring_p.h93
-rw-r--r--src/qml/qml/ftw/qintrusivelist_p.h25
-rw-r--r--src/qml/qml/ftw/qpodvector_p.h14
-rw-r--r--src/qml/qml/ftw/qqmlnullablevalue_p.h4
-rw-r--r--src/qml/qml/ftw/qqmlrefcount_p.h2
-rw-r--r--src/qml/qml/ftw/qqmlthread.cpp14
-rw-r--r--src/qml/qml/ftw/qqmlthread_p.h2
-rw-r--r--src/qml/qml/ftw/qrecursionwatcher_p.h4
-rw-r--r--src/qml/qml/ftw/qrecyclepool_p.h4
-rw-r--r--src/qml/qml/qqml.h2
-rw-r--r--src/qml/qml/qqmlabstractbinding.cpp4
-rw-r--r--src/qml/qml/qqmlabstractbinding_p.h4
-rw-r--r--src/qml/qml/qqmlapplicationengine.cpp2
-rw-r--r--src/qml/qml/qqmlapplicationengine.h2
-rw-r--r--src/qml/qml/qqmlbinding.cpp48
-rw-r--r--src/qml/qml/qqmlbinding_p.h2
-rw-r--r--src/qml/qml/qqmlboundsignal.cpp32
-rw-r--r--src/qml/qml/qqmlboundsignal_p.h6
-rw-r--r--src/qml/qml/qqmlboundsignalexpressionpointer_p.h4
-rw-r--r--src/qml/qml/qqmlcleanup.cpp8
-rw-r--r--src/qml/qml/qqmlcleanup_p.h2
-rw-r--r--src/qml/qml/qqmlcomponent.cpp107
-rw-r--r--src/qml/qml/qqmlcomponent.h2
-rw-r--r--src/qml/qml/qqmlcomponent_p.h2
-rw-r--r--src/qml/qml/qqmlcomponentattached_p.h4
-rw-r--r--src/qml/qml/qqmlcontext.cpp156
-rw-r--r--src/qml/qml/qqmlcontext.h7
-rw-r--r--src/qml/qml/qqmlcontext_p.h28
-rw-r--r--src/qml/qml/qqmlcustomparser.cpp4
-rw-r--r--src/qml/qml/qqmlcustomparser_p.h4
-rw-r--r--src/qml/qml/qqmldata_p.h58
-rw-r--r--src/qml/qml/qqmldelayedcallqueue.cpp23
-rw-r--r--src/qml/qml/qqmldelayedcallqueue_p.h7
-rw-r--r--src/qml/qml/qqmldirparser_p.h18
-rw-r--r--src/qml/qml/qqmlengine.cpp220
-rw-r--r--src/qml/qml/qqmlengine.h2
-rw-r--r--src/qml/qml/qqmlengine_p.h30
-rw-r--r--src/qml/qml/qqmlerror.cpp14
-rw-r--r--src/qml/qml/qqmlexpression.cpp17
-rw-r--r--src/qml/qml/qqmlexpression.h2
-rw-r--r--src/qml/qml/qqmlexpression_p.h6
-rw-r--r--src/qml/qml/qqmlextensioninterface.h2
-rw-r--r--src/qml/qml/qqmlextensionplugin.cpp2
-rw-r--r--src/qml/qml/qqmlextensionplugin.h2
-rw-r--r--src/qml/qml/qqmlfile.cpp10
-rw-r--r--src/qml/qml/qqmlfileselector.cpp6
-rw-r--r--src/qml/qml/qqmlfileselector.h2
-rw-r--r--src/qml/qml/qqmlglobal.cpp18
-rw-r--r--src/qml/qml/qqmlglobal_p.h26
-rw-r--r--src/qml/qml/qqmlguard_p.h17
-rw-r--r--src/qml/qml/qqmlimport.cpp219
-rw-r--r--src/qml/qml/qqmlimport_p.h9
-rw-r--r--src/qml/qml/qqmlincubator.cpp59
-rw-r--r--src/qml/qml/qqmlincubator_p.h3
-rw-r--r--src/qml/qml/qqmlinfo.cpp2
-rw-r--r--src/qml/qml/qqmljavascriptexpression.cpp34
-rw-r--r--src/qml/qml/qqmljavascriptexpression_p.h22
-rw-r--r--src/qml/qml/qqmllist.cpp28
-rw-r--r--src/qml/qml/qqmllist.h30
-rw-r--r--src/qml/qml/qqmllistwrapper.cpp12
-rw-r--r--src/qml/qml/qqmllistwrapper_p.h2
-rw-r--r--src/qml/qml/qqmllocale.cpp318
-rw-r--r--src/qml/qml/qqmllocale_p.h88
-rw-r--r--src/qml/qml/qqmlloggingcategory_p.h2
-rw-r--r--src/qml/qml/qqmlmetatype.cpp138
-rw-r--r--src/qml/qml/qqmlmetatype_p.h10
-rw-r--r--src/qml/qml/qqmlnotifier.cpp6
-rw-r--r--src/qml/qml/qqmlnotifier_p.h19
-rw-r--r--src/qml/qml/qqmlobjectcreator.cpp207
-rw-r--r--src/qml/qml/qqmlobjectcreator_p.h23
-rw-r--r--src/qml/qml/qqmlopenmetaobject.cpp20
-rw-r--r--src/qml/qml/qqmlopenmetaobject_p.h6
-rw-r--r--src/qml/qml/qqmlparserstatus.cpp4
-rw-r--r--src/qml/qml/qqmlplatform_p.h2
-rw-r--r--src/qml/qml/qqmlprivate.h11
-rw-r--r--src/qml/qml/qqmlproperty.cpp216
-rw-r--r--src/qml/qml/qqmlproperty_p.h8
-rw-r--r--src/qml/qml/qqmlpropertycache.cpp75
-rw-r--r--src/qml/qml/qqmlpropertycache_p.h69
-rw-r--r--src/qml/qml/qqmlpropertyvalueinterceptor.cpp2
-rw-r--r--src/qml/qml/qqmlproxymetaobject.cpp6
-rw-r--r--src/qml/qml/qqmlscriptstring_p.h2
-rw-r--r--src/qml/qml/qqmlstringconverters_p.h18
-rw-r--r--src/qml/qml/qqmltypeloader.cpp245
-rw-r--r--src/qml/qml/qqmltypeloader_p.h35
-rw-r--r--src/qml/qml/qqmltypenamecache.cpp20
-rw-r--r--src/qml/qml/qqmltypenamecache_p.h8
-rw-r--r--src/qml/qml/qqmltypewrapper.cpp24
-rw-r--r--src/qml/qml/qqmlvaluetype.cpp14
-rw-r--r--src/qml/qml/qqmlvaluetype_p.h10
-rw-r--r--src/qml/qml/qqmlvaluetypeproxybinding.cpp6
-rw-r--r--src/qml/qml/qqmlvaluetypewrapper.cpp49
-rw-r--r--src/qml/qml/qqmlvaluetypewrapper_p.h2
-rw-r--r--src/qml/qml/qqmlvme.cpp18
-rw-r--r--src/qml/qml/qqmlvme_p.h7
-rw-r--r--src/qml/qml/qqmlvmemetaobject.cpp52
-rw-r--r--src/qml/qml/qqmlvmemetaobject_p.h14
-rw-r--r--src/qml/qml/qqmlxmlhttprequest.cpp346
-rw-r--r--src/qml/qml/v8/qqmlbuiltinfunctions.cpp546
-rw-r--r--src/qml/qml/v8/qqmlbuiltinfunctions_p.h118
-rw-r--r--src/qml/qml/v8/qv8engine.cpp22
-rw-r--r--src/qml/qml/v8/qv8engine_p.h18
-rw-r--r--src/qml/types/qqmlbind.cpp4
-rw-r--r--src/qml/types/qqmlbind_p.h2
-rw-r--r--src/qml/types/qqmlconnections.cpp6
-rw-r--r--src/qml/types/qqmlconnections_p.h2
-rw-r--r--src/qml/types/qqmldelegatemodel.cpp250
-rw-r--r--src/qml/types/qqmldelegatemodel_p.h12
-rw-r--r--src/qml/types/qqmldelegatemodel_p_p.h25
-rw-r--r--src/qml/types/qqmlinstantiator.cpp18
-rw-r--r--src/qml/types/qqmlinstantiator_p.h2
-rw-r--r--src/qml/types/qqmllistmodel.cpp437
-rw-r--r--src/qml/types/qqmllistmodel_p.h24
-rw-r--r--src/qml/types/qqmllistmodel_p_p.h28
-rw-r--r--src/qml/types/qqmllistmodelworkeragent.cpp91
-rw-r--r--src/qml/types/qqmllistmodelworkeragent_p.h29
-rw-r--r--src/qml/types/qqmlobjectmodel.cpp11
-rw-r--r--src/qml/types/qqmlobjectmodel_p.h11
-rw-r--r--src/qml/types/qqmltimer.cpp4
-rw-r--r--src/qml/types/qqmltimer_p.h2
-rw-r--r--src/qml/types/qquickpackage.cpp2
-rw-r--r--src/qml/types/qquickpackage_p.h2
-rw-r--r--src/qml/types/qquickworkerscript.cpp64
-rw-r--r--src/qml/types/qquickworkerscript_p.h4
-rw-r--r--src/qml/util/qqmladaptormodel.cpp78
-rw-r--r--src/qml/util/qqmladaptormodel_p.h4
-rw-r--r--src/qml/util/qqmlchangeset.cpp2
-rw-r--r--src/qml/util/qqmlchangeset_p.h8
-rw-r--r--src/qml/util/qqmllistaccessor.cpp2
-rw-r--r--src/qml/util/qqmllistaccessor_p.h2
-rw-r--r--src/qml/util/qqmllistcompositor.cpp2
-rw-r--r--src/qml/util/qqmllistcompositor_p.h53
-rw-r--r--src/qml/util/qqmlpropertymap.cpp2
-rw-r--r--src/qml/util/qqmlpropertymap.h2
-rw-r--r--src/qmldebug/qmldebug.pro16
-rw-r--r--src/qmldebug/qqmldebugclient.cpp2
-rw-r--r--src/qmldebug/qqmldebugconnection.cpp19
-rw-r--r--src/qmldebug/qqmldebugconnection_p.h2
-rw-r--r--src/qmldebug/qqmldebugmessageclient.cpp95
-rw-r--r--src/qmldebug/qqmldebugmessageclient_p.h87
-rw-r--r--src/qmldebug/qqmlenginecontrolclient.cpp31
-rw-r--r--src/qmldebug/qqmlprofilerclient.cpp509
-rw-r--r--src/qmldebug/qqmlprofilerclient_p.h62
-rw-r--r--src/qmldebug/qqmlprofilerclient_p_p.h61
-rw-r--r--src/qmldebug/qqmlprofilerevent.cpp273
-rw-r--r--src/qmldebug/qqmlprofilerevent_p.h355
-rw-r--r--src/qmldebug/qqmlprofilereventlocation.cpp56
-rw-r--r--src/qmldebug/qqmlprofilereventlocation_p.h121
-rw-r--r--src/qmldebug/qqmlprofilereventreceiver_p.h74
-rw-r--r--src/qmldebug/qqmlprofilereventtype.cpp92
-rw-r--r--src/qmldebug/qqmlprofilereventtype_p.h126
-rw-r--r--src/qmldebug/qqmlprofilertypedevent.cpp226
-rw-r--r--src/qmldebug/qqmlprofilertypedevent_p.h (renamed from src/qmldebug/qqmleventlocation_p.h)31
-rw-r--r--src/qmldevtools/qmldevtools.pro1
-rw-r--r--src/qmltest/doc/qtqmltest.qdocconf42
-rw-r--r--src/qmltest/doc/src/qtquicktest-index.qdoc185
-rw-r--r--src/qmltest/qmltest.pro8
-rw-r--r--src/qmltest/quicktest.cpp32
-rw-r--r--src/qmltest/quicktest.h23
-rw-r--r--src/qmltest/quicktestevent.cpp21
-rw-r--r--src/qmltest/quicktestevent_p.h8
-rw-r--r--src/qmltest/quicktestresult.cpp26
-rw-r--r--src/qmltest/quicktestresult_p.h4
-rw-r--r--src/quick/accessible/qaccessiblequickitem.cpp12
-rw-r--r--src/quick/accessible/qaccessiblequickview.cpp4
-rw-r--r--src/quick/accessible/qquickaccessiblefactory.cpp4
-rw-r--r--src/quick/configure.json9
-rw-r--r--src/quick/designer/qqmldesignermetaobject.cpp10
-rw-r--r--src/quick/designer/qquickdesignercustomobjectdata.cpp2
-rw-r--r--src/quick/designer/qquickdesignersupport.cpp38
-rw-r--r--src/quick/designer/qquickdesignersupportitems.cpp10
-rw-r--r--src/quick/designer/qquickdesignersupportmetainfo.cpp2
-rw-r--r--src/quick/designer/qquickdesignersupportproperties.cpp4
-rw-r--r--src/quick/designer/qquickdesignersupportproperties_p.h4
-rw-r--r--src/quick/designer/qquickdesignersupportpropertychanges.cpp4
-rw-r--r--src/quick/doc/images/animatedsprite-loading-frames.pngbin0 -> 147 bytes
-rw-r--r--src/quick/doc/images/animatedsprite-loading-interpolated.gifbin0 -> 22297 bytes
-rw-r--r--src/quick/doc/images/animatedsprite-loading.gifbin0 -> 3364 bytes
-rw-r--r--src/quick/doc/images/animatedsprite-loading.pngbin0 -> 118 bytes
-rw-r--r--src/quick/doc/qtquick.qdocconf2
-rw-r--r--src/quick/doc/snippets/pointerHandlers/dragHandler.qml14
-rw-r--r--src/quick/doc/snippets/pointerHandlers/dragHandlerDifferentTarget.qml14
-rw-r--r--src/quick/doc/snippets/pointerHandlers/dragHandlerNullTarget.qml14
-rw-r--r--src/quick/doc/snippets/pointerHandlers/pinchHandler.qml14
-rw-r--r--src/quick/doc/snippets/pointerHandlers/pinchHandlerDifferentTarget.qml14
-rw-r--r--src/quick/doc/snippets/pointerHandlers/pinchHandlerNullTarget.qml14
-rw-r--r--src/quick/doc/snippets/pointerHandlers/pointHandler.qml (renamed from src/quick/doc/snippets/qml/localstorage/dbtransaction.js)82
-rw-r--r--src/quick/doc/snippets/qml/layout-simple.qml74
-rw-r--r--src/quick/doc/snippets/qml/path/arcrotation.qml14
-rw-r--r--src/quick/doc/src/concepts/layouts/qtquicklayouts-overview.qdoc25
-rw-r--r--src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc4
-rw-r--r--src/quick/doc/src/concepts/pointerhandlers/qtquickhandlers-index.qdoc2
-rw-r--r--src/quick/doc/src/concepts/visualcanvas/scenegraph.qdoc53
-rw-r--r--src/quick/doc/src/qmltypereference.qdoc2
-rw-r--r--src/quick/doc/src/qtquick.qdoc3
-rw-r--r--src/quick/handlers/handlers.pri2
-rw-r--r--src/quick/handlers/qquickdraghandler.cpp142
-rw-r--r--src/quick/handlers/qquickdraghandler_p.h12
-rw-r--r--src/quick/handlers/qquickhandlersmodule.cpp2
-rw-r--r--src/quick/handlers/qquickmultipointhandler.cpp13
-rw-r--r--src/quick/handlers/qquickmultipointhandler_p.h2
-rw-r--r--src/quick/handlers/qquickpinchhandler.cpp19
-rw-r--r--src/quick/handlers/qquickpinchhandler_p.h2
-rw-r--r--src/quick/handlers/qquickpointerdevicehandler.cpp6
-rw-r--r--src/quick/handlers/qquickpointerdevicehandler_p.h2
-rw-r--r--src/quick/handlers/qquickpointerhandler.cpp138
-rw-r--r--src/quick/handlers/qquickpointerhandler_p.h38
-rw-r--r--src/quick/handlers/qquickpointhandler.cpp164
-rw-r--r--src/quick/handlers/qquickpointhandler_p.h81
-rw-r--r--src/quick/handlers/qquicksinglepointhandler.cpp9
-rw-r--r--src/quick/handlers/qquicksinglepointhandler_p.h2
-rw-r--r--src/quick/handlers/qquicktaphandler.cpp112
-rw-r--r--src/quick/handlers/qquicktaphandler_p.h4
-rw-r--r--src/quick/items/context2d/qquickcanvascontext_p.h2
-rw-r--r--src/quick/items/context2d/qquickcanvasitem.cpp54
-rw-r--r--src/quick/items/context2d/qquickcanvasitem_p.h2
-rw-r--r--src/quick/items/context2d/qquickcontext2d.cpp944
-rw-r--r--src/quick/items/context2d/qquickcontext2d_p.h4
-rw-r--r--src/quick/items/context2d/qquickcontext2dtexture.cpp32
-rw-r--r--src/quick/items/context2d/qquickcontext2dtexture_p.h2
-rw-r--r--src/quick/items/context2d/qquickcontext2dtile.cpp6
-rw-r--r--src/quick/items/items.pri12
-rw-r--r--src/quick/items/qquickaccessibleattached.cpp2
-rw-r--r--src/quick/items/qquickanchors.cpp37
-rw-r--r--src/quick/items/qquickanchors_p.h5
-rw-r--r--src/quick/items/qquickanchors_p_p.h6
-rw-r--r--src/quick/items/qquickanimatedimage.cpp147
-rw-r--r--src/quick/items/qquickanimatedimage_p.h7
-rw-r--r--src/quick/items/qquickanimatedimage_p_p.h22
-rw-r--r--src/quick/items/qquickanimatedsprite.cpp80
-rw-r--r--src/quick/items/qquickanimatedsprite_p.h2
-rw-r--r--src/quick/items/qquickborderimage.cpp8
-rw-r--r--src/quick/items/qquickborderimage_p.h2
-rw-r--r--src/quick/items/qquickdrag.cpp18
-rw-r--r--src/quick/items/qquickdrag_p.h10
-rw-r--r--src/quick/items/qquickdroparea.cpp6
-rw-r--r--src/quick/items/qquickevents.cpp227
-rw-r--r--src/quick/items/qquickevents_p_p.h81
-rw-r--r--src/quick/items/qquickflickable.cpp88
-rw-r--r--src/quick/items/qquickflickable_p.h2
-rw-r--r--src/quick/items/qquickflickable_p_p.h8
-rw-r--r--src/quick/items/qquickflipable.cpp4
-rw-r--r--src/quick/items/qquickflipable_p.h2
-rw-r--r--src/quick/items/qquickfocusscope_p.h2
-rw-r--r--src/quick/items/qquickframebufferobject.cpp31
-rw-r--r--src/quick/items/qquickgenericshadereffect.cpp6
-rw-r--r--src/quick/items/qquickgenericshadereffect_p.h2
-rw-r--r--src/quick/items/qquickgraphicsinfo.cpp2
-rw-r--r--src/quick/items/qquickgridview.cpp44
-rw-r--r--src/quick/items/qquickgridview_p.h2
-rw-r--r--src/quick/items/qquickimage.cpp14
-rw-r--r--src/quick/items/qquickimage_p.h2
-rw-r--r--src/quick/items/qquickimagebase_p.h2
-rw-r--r--src/quick/items/qquickitem.cpp327
-rw-r--r--src/quick/items/qquickitem.h8
-rw-r--r--src/quick/items/qquickitem_p.h71
-rw-r--r--src/quick/items/qquickitemanimation.cpp12
-rw-r--r--src/quick/items/qquickitemanimation_p.h12
-rw-r--r--src/quick/items/qquickitemanimation_p_p.h10
-rw-r--r--src/quick/items/qquickitemchangelistener_p.h2
-rw-r--r--src/quick/items/qquickitemgrabresult.cpp14
-rw-r--r--src/quick/items/qquickitemsmodule.cpp18
-rw-r--r--src/quick/items/qquickitemview.cpp237
-rw-r--r--src/quick/items/qquickitemview_p.h2
-rw-r--r--src/quick/items/qquickitemview_p_p.h2
-rw-r--r--src/quick/items/qquickitemviewtransition.cpp36
-rw-r--r--src/quick/items/qquickitemviewtransition_p.h18
-rw-r--r--src/quick/items/qquicklistview.cpp77
-rw-r--r--src/quick/items/qquicklistview_p.h6
-rw-r--r--src/quick/items/qquickloader.cpp63
-rw-r--r--src/quick/items/qquickloader_p.h3
-rw-r--r--src/quick/items/qquickmousearea.cpp24
-rw-r--r--src/quick/items/qquickmousearea_p.h2
-rw-r--r--src/quick/items/qquickmousearea_p_p.h3
-rw-r--r--src/quick/items/qquickmultipointtoucharea.cpp55
-rw-r--r--src/quick/items/qquickmultipointtoucharea_p.h45
-rw-r--r--src/quick/items/qquickopenglinfo.cpp6
-rw-r--r--src/quick/items/qquickopenglshadereffect.cpp23
-rw-r--r--src/quick/items/qquickopenglshadereffect_p.h4
-rw-r--r--src/quick/items/qquickopenglshadereffectnode.cpp4
-rw-r--r--src/quick/items/qquickopenglshadereffectnode_p.h4
-rw-r--r--src/quick/items/qquickpainteditem.cpp26
-rw-r--r--src/quick/items/qquickpainteditem.h2
-rw-r--r--src/quick/items/qquickpathview.cpp4
-rw-r--r--src/quick/items/qquickpincharea.cpp5
-rw-r--r--src/quick/items/qquickpincharea_p.h4
-rw-r--r--src/quick/items/qquickpositioners.cpp16
-rw-r--r--src/quick/items/qquickpositioners_p.h10
-rw-r--r--src/quick/items/qquickrectangle.cpp4
-rw-r--r--src/quick/items/qquickrectangle_p.h10
-rw-r--r--src/quick/items/qquickrendercontrol.cpp18
-rw-r--r--src/quick/items/qquickrendercontrol.h2
-rw-r--r--src/quick/items/qquickrepeater.cpp36
-rw-r--r--src/quick/items/qquickrepeater_p.h6
-rw-r--r--src/quick/items/qquickrepeater_p_p.h2
-rw-r--r--src/quick/items/qquickscalegrid_p_p.h2
-rw-r--r--src/quick/items/qquickscreen.cpp6
-rw-r--r--src/quick/items/qquickshadereffect_p.h2
-rw-r--r--src/quick/items/qquickshadereffectmesh_p.h6
-rw-r--r--src/quick/items/qquickshadereffectsource.cpp32
-rw-r--r--src/quick/items/qquickshadereffectsource_p.h4
-rw-r--r--src/quick/items/qquicksprite.cpp6
-rw-r--r--src/quick/items/qquicksprite_p.h4
-rw-r--r--src/quick/items/qquickspriteengine.cpp10
-rw-r--r--src/quick/items/qquickspriteengine_p.h27
-rw-r--r--src/quick/items/qquickspritesequence.cpp2
-rw-r--r--src/quick/items/qquickspritesequence_p.h2
-rw-r--r--src/quick/items/qquickstateoperations.cpp46
-rw-r--r--src/quick/items/qquickstateoperations_p.h6
-rw-r--r--src/quick/items/qquicktext.cpp28
-rw-r--r--src/quick/items/qquicktext_p.h6
-rw-r--r--src/quick/items/qquicktext_p_p.h2
-rw-r--r--src/quick/items/qquicktextcontrol.cpp2
-rw-r--r--src/quick/items/qquicktextcontrol_p.h2
-rw-r--r--src/quick/items/qquicktextedit.cpp94
-rw-r--r--src/quick/items/qquicktextedit_p.h4
-rw-r--r--src/quick/items/qquicktextedit_p_p.h18
-rw-r--r--src/quick/items/qquicktextinput.cpp54
-rw-r--r--src/quick/items/qquicktextinput_p.h4
-rw-r--r--src/quick/items/qquicktextinput_p_p.h6
-rw-r--r--src/quick/items/qquicktextnode.cpp12
-rw-r--r--src/quick/items/qquicktextnodeengine.cpp48
-rw-r--r--src/quick/items/qquicktextutil.cpp2
-rw-r--r--src/quick/items/qquicktranslate_p.h8
-rw-r--r--src/quick/items/qquickview.cpp32
-rw-r--r--src/quick/items/qquickview.h3
-rw-r--r--src/quick/items/qquickview_p.h2
-rw-r--r--src/quick/items/qquickwindow.cpp420
-rw-r--r--src/quick/items/qquickwindow.h9
-rw-r--r--src/quick/items/qquickwindow_p.h14
-rw-r--r--src/quick/items/qquickwindowattached.cpp2
-rw-r--r--src/quick/items/qquickwindowmodule.cpp19
-rw-r--r--src/quick/qtquick2.cpp2
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer.cpp28
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer_p.h7
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation.cpp2
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation_p.h2
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarecontext.cpp4
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode.cpp13
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode_p.h2
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode.cpp10
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode_p.h2
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarelayer.cpp9
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarepainternode.cpp2
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarepixmaprenderer.cpp22
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes.cpp2
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes_p.h2
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenode.cpp45
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenodeupdater.cpp4
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarerenderer.cpp4
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarerenderloop.cpp1
-rw-r--r--src/quick/scenegraph/adaptations/software/qsgsoftwarethreadedrenderloop.cpp6
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgcompressedatlastexture.cpp174
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgcompressedatlastexture_p.h119
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgcompressedtexture.cpp246
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgcompressedtexture_p.h126
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgktxhandler.cpp186
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgktxhandler_p.h78
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgpkmhandler.cpp169
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgpkmhandler_p.h34
-rw-r--r--src/quick/scenegraph/compressedtexture/qsgtexturefilehandler_p.h83
-rw-r--r--src/quick/scenegraph/coreapi/qsgabstractrenderer.cpp2
-rw-r--r--src/quick/scenegraph/coreapi/qsgabstractrenderer.h2
-rw-r--r--src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp168
-rw-r--r--src/quick/scenegraph/coreapi/qsgbatchrenderer_p.h74
-rw-r--r--src/quick/scenegraph/coreapi/qsggeometry.cpp21
-rw-r--r--src/quick/scenegraph/coreapi/qsgmaterial.cpp7
-rw-r--r--src/quick/scenegraph/coreapi/qsgnode.cpp91
-rw-r--r--src/quick/scenegraph/coreapi/qsgnode.h45
-rw-r--r--src/quick/scenegraph/coreapi/qsgnode_p.h8
-rw-r--r--src/quick/scenegraph/coreapi/qsgnodeupdater.cpp6
-rw-r--r--src/quick/scenegraph/coreapi/qsgrenderer.cpp8
-rw-r--r--src/quick/scenegraph/coreapi/qsgrenderer_p.h4
-rw-r--r--src/quick/scenegraph/coreapi/qsgrendernode.cpp26
-rw-r--r--src/quick/scenegraph/coreapi/qsgrendernode.h2
-rw-r--r--src/quick/scenegraph/qsgadaptationlayer_p.h46
-rw-r--r--src/quick/scenegraph/qsgbasicglyphnode.cpp6
-rw-r--r--src/quick/scenegraph/qsgcontext.cpp23
-rw-r--r--src/quick/scenegraph/qsgcontext_p.h8
-rw-r--r--src/quick/scenegraph/qsgcontextplugin.cpp14
-rw-r--r--src/quick/scenegraph/qsgcontextplugin_p.h6
-rw-r--r--src/quick/scenegraph/qsgdefaultcontext.cpp23
-rw-r--r--src/quick/scenegraph/qsgdefaultcontext_p.h2
-rw-r--r--src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp10
-rw-r--r--src/quick/scenegraph/qsgdefaultdistancefieldglyphcache_p.h5
-rw-r--r--src/quick/scenegraph/qsgdefaultglyphnode_p.cpp30
-rw-r--r--src/quick/scenegraph/qsgdefaultinternalimagenode.cpp7
-rw-r--r--src/quick/scenegraph/qsgdefaultinternalrectanglenode.cpp5
-rw-r--r--src/quick/scenegraph/qsgdefaultlayer.cpp26
-rw-r--r--src/quick/scenegraph/qsgdefaultrendercontext.cpp15
-rw-r--r--src/quick/scenegraph/qsgdefaultrendercontext_p.h3
-rw-r--r--src/quick/scenegraph/qsgdefaultspritenode.cpp29
-rw-r--r--src/quick/scenegraph/qsgdistancefieldglyphnode.cpp12
-rw-r--r--src/quick/scenegraph/qsgdistancefieldglyphnode_p.cpp76
-rw-r--r--src/quick/scenegraph/qsgrenderloop.cpp18
-rw-r--r--src/quick/scenegraph/qsgthreadedrenderloop.cpp182
-rw-r--r--src/quick/scenegraph/qsgwindowsrenderloop.cpp16
-rw-r--r--src/quick/scenegraph/scenegraph.pri13
-rw-r--r--src/quick/scenegraph/util/qsgareaallocator.cpp18
-rw-r--r--src/quick/scenegraph/util/qsgareaallocator_p.h2
-rw-r--r--src/quick/scenegraph/util/qsgatlastexture.cpp336
-rw-r--r--src/quick/scenegraph/util/qsgatlastexture_p.h88
-rw-r--r--src/quick/scenegraph/util/qsgdefaultpainternode.cpp14
-rw-r--r--src/quick/scenegraph/util/qsgdepthstencilbuffer.cpp6
-rw-r--r--src/quick/scenegraph/util/qsgengine.cpp6
-rw-r--r--src/quick/scenegraph/util/qsgengine.h2
-rw-r--r--src/quick/scenegraph/util/qsgflatcolormaterial.cpp6
-rw-r--r--src/quick/scenegraph/util/qsgimagenode.cpp11
-rw-r--r--src/quick/scenegraph/util/qsgimagenode.h2
-rw-r--r--src/quick/scenegraph/util/qsgninepatchnode.h2
-rw-r--r--src/quick/scenegraph/util/qsgrectanglenode.h2
-rw-r--r--src/quick/scenegraph/util/qsgshadersourcebuilder.cpp10
-rw-r--r--src/quick/scenegraph/util/qsgsimplematerial.cpp16
-rw-r--r--src/quick/scenegraph/util/qsgsimplematerial.h6
-rw-r--r--src/quick/scenegraph/util/qsgsimpletexturenode.cpp3
-rw-r--r--src/quick/scenegraph/util/qsgsimpletexturenode.h2
-rw-r--r--src/quick/scenegraph/util/qsgtexture.cpp4
-rw-r--r--src/quick/scenegraph/util/qsgtexture.h2
-rw-r--r--src/quick/scenegraph/util/qsgtexture_p.h2
-rw-r--r--src/quick/scenegraph/util/qsgtexturematerial.cpp21
-rw-r--r--src/quick/scenegraph/util/qsgtexturereader.cpp61
-rw-r--r--src/quick/scenegraph/util/qsgtexturereader_p.h21
-rw-r--r--src/quick/scenegraph/util/qsgvertexcolormaterial.cpp3
-rw-r--r--src/quick/util/qquickanimation.cpp24
-rw-r--r--src/quick/util/qquickanimation_p.h78
-rw-r--r--src/quick/util/qquickanimation_p_p.h16
-rw-r--r--src/quick/util/qquickanimationcontroller.cpp6
-rw-r--r--src/quick/util/qquickanimationcontroller_p.h2
-rw-r--r--src/quick/util/qquickanimator.cpp10
-rw-r--r--src/quick/util/qquickanimator_p.h16
-rw-r--r--src/quick/util/qquickanimatorcontroller.cpp4
-rw-r--r--src/quick/util/qquickanimatorjob.cpp4
-rw-r--r--src/quick/util/qquickanimatorjob_p.h2
-rw-r--r--src/quick/util/qquickapplication_p.h2
-rw-r--r--src/quick/util/qquickbehavior.cpp2
-rw-r--r--src/quick/util/qquickbehavior_p.h2
-rw-r--r--src/quick/util/qquickfontloader.cpp19
-rw-r--r--src/quick/util/qquickfontloader_p.h2
-rw-r--r--src/quick/util/qquickfontmetrics_p.h2
-rw-r--r--src/quick/util/qquickglobal.cpp6
-rw-r--r--src/quick/util/qquickimageprovider.cpp23
-rw-r--r--src/quick/util/qquickimageprovider.h9
-rw-r--r--src/quick/util/qquickpath.cpp45
-rw-r--r--src/quick/util/qquickpath_p.h95
-rw-r--r--src/quick/util/qquickpath_p_p.h9
-rw-r--r--src/quick/util/qquickpathinterpolator.cpp2
-rw-r--r--src/quick/util/qquickpathinterpolator_p.h2
-rw-r--r--src/quick/util/qquickpixmapcache.cpp170
-rw-r--r--src/quick/util/qquickprofiler.cpp6
-rw-r--r--src/quick/util/qquickprofiler_p.h2
-rw-r--r--src/quick/util/qquickpropertychanges.cpp62
-rw-r--r--src/quick/util/qquickshortcut.cpp6
-rw-r--r--src/quick/util/qquicksmoothedanimation_p.h4
-rw-r--r--src/quick/util/qquicksmoothedanimation_p_p.h6
-rw-r--r--src/quick/util/qquickspringanimation.cpp4
-rw-r--r--src/quick/util/qquickspringanimation_p.h4
-rw-r--r--src/quick/util/qquickstate.cpp19
-rw-r--r--src/quick/util/qquickstate_p.h12
-rw-r--r--src/quick/util/qquickstate_p_p.h10
-rw-r--r--src/quick/util/qquickstatechangescript_p.h2
-rw-r--r--src/quick/util/qquickstategroup.cpp18
-rw-r--r--src/quick/util/qquickstategroup_p.h2
-rw-r--r--src/quick/util/qquickstyledtext.cpp2
-rw-r--r--src/quick/util/qquickstyledtext_p.h12
-rw-r--r--src/quick/util/qquicksvgparser.cpp2
-rw-r--r--src/quick/util/qquicksystempalette_p.h2
-rw-r--r--src/quick/util/qquicktimeline.cpp32
-rw-r--r--src/quick/util/qquicktimeline_p_p.h6
-rw-r--r--src/quick/util/qquicktransition.cpp31
-rw-r--r--src/quick/util/qquicktransition_p.h17
-rw-r--r--src/quick/util/qquicktransitionmanager.cpp6
-rw-r--r--src/quick/util/qquicktransitionmanager_p_p.h2
-rw-r--r--src/quick/util/qquickvalidator_p.h4
-rw-r--r--src/quickwidgets/qquickwidget.cpp127
-rw-r--r--src/quickwidgets/qquickwidget.h2
-rw-r--r--src/src.pro9
734 files changed, 14666 insertions, 8868 deletions
diff --git a/src/3rdparty/masm/assembler/ARM64Assembler.h b/src/3rdparty/masm/assembler/ARM64Assembler.h
index 7390997af1..008f03bccf 100644
--- a/src/3rdparty/masm/assembler/ARM64Assembler.h
+++ b/src/3rdparty/masm/assembler/ARM64Assembler.h
@@ -3032,6 +3032,13 @@ public:
linuxPageFlush(current, current + page);
linuxPageFlush(current, end);
+#elif OS(QNX)
+#if !ENABLE(ASSEMBLER_WX_EXCLUSIVE)
+ msync(code, size, MS_INVALIDATE_ICACHE);
+#else
+ UNUSED_PARAM(code);
+ UNUSED_PARAM(size);
+#endif
#else
#error "The cacheFlush support is missing on this platform."
#endif
diff --git a/src/3rdparty/masm/masm.pri b/src/3rdparty/masm/masm.pri
index 6c301fea38..7dfb24f4b8 100644
--- a/src/3rdparty/masm/masm.pri
+++ b/src/3rdparty/masm/masm.pri
@@ -118,11 +118,9 @@ QMAKE_EXTRA_COMPILERS += retgen
# Don't warn about OVERRIDE and FINAL, since they are feature-checked anyways
clang {
QMAKE_CXXFLAGS += -Wno-c++11-extensions -Wno-c++0x-extensions
- QMAKE_OBJECTIVE_CFLAGS += -Wno-c++11-extensions -Wno-c++0x-extensions
} else: gcc {
greaterThan(QT_GCC_MAJOR_VERSION, 4)|greaterThan(QT_GCC_MINOR_VERSION, 5) {
# We need to deactivate those warnings because some names conflicts with upcoming c++0x types (e.g.nullptr).
- QMAKE_CXXFLAGS_WARN_ON += -Wno-c++0x-compat
QMAKE_CXXFLAGS += -Wno-c++0x-compat
}
}
diff --git a/src/3rdparty/masm/wtf/Compiler.h b/src/3rdparty/masm/wtf/Compiler.h
index da10196cc1..598d7f2c1c 100644
--- a/src/3rdparty/masm/wtf/Compiler.h
+++ b/src/3rdparty/masm/wtf/Compiler.h
@@ -27,13 +27,13 @@
#define WTF_Compiler_h
/* COMPILER() - the compiler being used to build the project */
-#define COMPILER(WTF_FEATURE) (defined WTF_COMPILER_##WTF_FEATURE && WTF_COMPILER_##WTF_FEATURE)
+#define COMPILER(WTF_FEATURE) WTF_COMPILER_##WTF_FEATURE
/* COMPILER_SUPPORTS() - whether the compiler being used to build the project supports the given feature. */
-#define COMPILER_SUPPORTS(WTF_COMPILER_FEATURE) (defined WTF_COMPILER_SUPPORTS_##WTF_COMPILER_FEATURE && WTF_COMPILER_SUPPORTS_##WTF_COMPILER_FEATURE)
+#define COMPILER_SUPPORTS(WTF_COMPILER_FEATURE) WTF_COMPILER_SUPPORTS_##WTF_COMPILER_FEATURE
/* COMPILER_QUIRK() - whether the compiler being used to build the project requires a given quirk. */
-#define COMPILER_QUIRK(WTF_COMPILER_QUIRK) (defined WTF_COMPILER_QUIRK_##WTF_COMPILER_QUIRK && WTF_COMPILER_QUIRK_##WTF_COMPILER_QUIRK)
+#define COMPILER_QUIRK(WTF_COMPILER_QUIRK) WTF_COMPILER_QUIRK_##WTF_COMPILER_QUIRK
/* ==== COMPILER() - the compiler being used to build the project ==== */
diff --git a/src/3rdparty/masm/wtf/MathExtras.h b/src/3rdparty/masm/wtf/MathExtras.h
index 3740d54beb..a529ba7b37 100644
--- a/src/3rdparty/masm/wtf/MathExtras.h
+++ b/src/3rdparty/masm/wtf/MathExtras.h
@@ -147,11 +147,6 @@ inline long lroundf(float num) { return static_cast<long>(roundf(num)); }
#endif
-#if COMPILER(GCC) && OS(QNX) && _CPPLIB_VER < 640
-// The stdlib on QNX < 6.6 doesn't contain long abs(long). See PR #104666.
-inline long long abs(long num) { return labs(num); }
-#endif
-
#if COMPILER(MSVC) && COMPILER(MSVC12_OR_LOWER)
// MSVC's math.h does not currently supply log2 or log2f.
inline double log2(double num)
diff --git a/src/3rdparty/masm/wtf/Platform.h b/src/3rdparty/masm/wtf/Platform.h
index 3d7086b585..a81ef4589a 100644
--- a/src/3rdparty/masm/wtf/Platform.h
+++ b/src/3rdparty/masm/wtf/Platform.h
@@ -38,26 +38,26 @@
/* ==== PLATFORM handles OS, operating environment, graphics API, and
CPU. This macro will be phased out in favor of platform adaptation
macros, policy decision macros, and top-level port definitions. ==== */
-#define PLATFORM(WTF_FEATURE) (defined WTF_PLATFORM_##WTF_FEATURE && WTF_PLATFORM_##WTF_FEATURE)
+#define PLATFORM(WTF_FEATURE) WTF_PLATFORM_##WTF_FEATURE
/* ==== Platform adaptation macros: these describe properties of the target environment. ==== */
/* CPU() - the target CPU architecture */
-#define CPU(WTF_FEATURE) (defined WTF_CPU_##WTF_FEATURE && WTF_CPU_##WTF_FEATURE)
+#define CPU(WTF_FEATURE) WTF_CPU_##WTF_FEATURE
/* HAVE() - specific system features (headers, functions or similar) that are present or not */
-#define HAVE(WTF_FEATURE) (defined HAVE_##WTF_FEATURE && HAVE_##WTF_FEATURE)
+#define HAVE(WTF_FEATURE) HAVE_##WTF_FEATURE
/* OS() - underlying operating system; only to be used for mandated low-level services like
virtual memory, not to choose a GUI toolkit */
-#define OS(WTF_FEATURE) (defined WTF_OS_##WTF_FEATURE && WTF_OS_##WTF_FEATURE)
+#define OS(WTF_FEATURE) WTF_OS_##WTF_FEATURE
/* ==== Policy decision macros: these define policy choices for a particular port. ==== */
/* USE() - use a particular third-party library or optional OS service */
-#define USE(WTF_FEATURE) (defined WTF_USE_##WTF_FEATURE && WTF_USE_##WTF_FEATURE)
+#define USE(WTF_FEATURE) WTF_USE_##WTF_FEATURE
/* ENABLE() - turn on a specific feature of WebKit */
-#define ENABLE(WTF_FEATURE) (defined ENABLE_##WTF_FEATURE && ENABLE_##WTF_FEATURE)
+#define ENABLE(WTF_FEATURE) ENABLE_##WTF_FEATURE
/* ==== CPU() - the target CPU architecture ==== */
diff --git a/src/3rdparty/masm/yarr/YarrPattern.cpp b/src/3rdparty/masm/yarr/YarrPattern.cpp
index ae527f065f..c7e5b6b09b 100644
--- a/src/3rdparty/masm/yarr/YarrPattern.cpp
+++ b/src/3rdparty/masm/yarr/YarrPattern.cpp
@@ -233,7 +233,7 @@ private:
ranges.insert(i, CharacterRange(lo, hi));
return;
}
- // Okay, since we didn't hit the last case, the end of the new range is definitely at or after the begining
+ // Okay, since we didn't hit the last case, the end of the new range is definitely at or after the beginning
// If the new range start at or before the end of the last range, then the overlap (if it starts one after the
// end of the last range they concatenate, which is just as good.
if (lo <= (ranges[i].end + 1)) {
diff --git a/src/imports/builtins/builtins.qmltypes b/src/imports/builtins/builtins.qmltypes
index c2f8f5b521..5fb68d15d9 100644
--- a/src/imports/builtins/builtins.qmltypes
+++ b/src/imports/builtins/builtins.qmltypes
@@ -461,7 +461,10 @@ Module {
"AA_CompressHighFrequencyEvents": 25,
"AA_DontCheckOpenGLContextThreadAffinity": 26,
"AA_DisableShaderDiskCache": 27,
- "AA_AttributeCount": 28
+ "AA_DontShowShortcutsInContextMenus": 28,
+ "AA_CompressTabletEvents": 29,
+ "AA_DisableWindowContextHelpButton": 30,
+ "AA_AttributeCount": 31
}
}
Enum {
diff --git a/src/imports/folderlistmodel/fileinfothread.cpp b/src/imports/folderlistmodel/fileinfothread.cpp
index d3e256bb7e..5b44ed012f 100644
--- a/src/imports/folderlistmodel/fileinfothread.cpp
+++ b/src/imports/folderlistmodel/fileinfothread.cpp
@@ -47,7 +47,7 @@ FileInfoThread::FileInfoThread(QObject *parent)
: QThread(parent),
abort(false),
#if QT_CONFIG(filesystemwatcher)
- watcher(0),
+ watcher(nullptr),
#endif
sortFlags(QDir::Name),
needUpdate(true),
@@ -222,8 +222,10 @@ void FileInfoThread::run()
if (abort) {
return;
}
- if (currentPath.isEmpty() || !needUpdate)
+ if (currentPath.isEmpty() || !needUpdate) {
+ emit statusChanged(currentPath.isEmpty() ? QQuickFolderListModel::Null : QQuickFolderListModel::Ready);
condition.wait(&mutex);
+ }
if (abort) {
return;
@@ -231,6 +233,7 @@ void FileInfoThread::run()
if (!currentPath.isEmpty()) {
updateFiles = true;
+ emit statusChanged(QQuickFolderListModel::Loading);
}
if (updateFiles)
getFileInfos(currentPath);
diff --git a/src/imports/folderlistmodel/fileinfothread_p.h b/src/imports/folderlistmodel/fileinfothread_p.h
index b505ece750..67d2a1f5f7 100644
--- a/src/imports/folderlistmodel/fileinfothread_p.h
+++ b/src/imports/folderlistmodel/fileinfothread_p.h
@@ -59,6 +59,7 @@
#include <QDir>
#include "fileproperty_p.h"
+#include "qquickfolderlistmodel.h"
class FileInfoThread : public QThread
{
@@ -68,6 +69,7 @@ Q_SIGNALS:
void directoryChanged(const QString &directory, const QList<FileProperty> &list) const;
void directoryUpdated(const QString &directory, const QList<FileProperty> &list, int fromIndex, int toIndex) const;
void sortFinished(const QList<FileProperty> &list) const;
+ void statusChanged(QQuickFolderListModel::Status status) const;
public:
FileInfoThread(QObject *parent = 0);
diff --git a/src/imports/folderlistmodel/plugin.cpp b/src/imports/folderlistmodel/plugin.cpp
index 2b58a5677a..5e8b41401f 100644
--- a/src/imports/folderlistmodel/plugin.cpp
+++ b/src/imports/folderlistmodel/plugin.cpp
@@ -58,7 +58,7 @@ class QmlFolderListModelPlugin : public QQmlExtensionPlugin
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QmlFolderListModelPlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QmlFolderListModelPlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QLatin1String(uri) == QLatin1String("Qt.labs.folderlistmodel"));
@@ -66,6 +66,12 @@ public:
qmlRegisterType<QQuickFolderListModel>(uri,2,0,"FolderListModel");
qmlRegisterType<QQuickFolderListModel,1>(uri,2,1,"FolderListModel");
qmlRegisterType<QQuickFolderListModel,2>(uri,2,2,"FolderListModel");
+
+ // Auto-increment the import to stay in sync with ALL future QtQuick minor versions from 5.11 onward
+ qmlRegisterModule(uri, 2, QT_VERSION_MINOR);
+
+ // revision in Qt 5.11: added status property
+ qmlRegisterType<QQuickFolderListModel,11>(uri, 2, 11, "FolderListModel");
}
};
//![class decl]
diff --git a/src/imports/folderlistmodel/plugins.qmltypes b/src/imports/folderlistmodel/plugins.qmltypes
index e77b633932..a336b55022 100644
--- a/src/imports/folderlistmodel/plugins.qmltypes
+++ b/src/imports/folderlistmodel/plugins.qmltypes
@@ -4,7 +4,7 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable Qt.labs.folderlistmodel 2.2'
+// 'qmlplugindump -nonrelocatable Qt.labs.folderlistmodel 2.11'
Module {
dependencies: ["QtQuick 2.8"]
@@ -15,9 +15,10 @@ Module {
"Qt.labs.folderlistmodel/FolderListModel 1.0",
"Qt.labs.folderlistmodel/FolderListModel 2.0",
"Qt.labs.folderlistmodel/FolderListModel 2.1",
+ "Qt.labs.folderlistmodel/FolderListModel 2.11",
"Qt.labs.folderlistmodel/FolderListModel 2.2"
]
- exportMetaObjectRevisions: [0, 0, 1, 2]
+ exportMetaObjectRevisions: [0, 0, 1, 11, 2]
Enum {
name: "SortField"
values: {
@@ -28,6 +29,14 @@ Module {
"Type": 4
}
}
+ Enum {
+ name: "Status"
+ values: {
+ "Null": 0,
+ "Ready": 1,
+ "Loading": 2
+ }
+ }
Property { name: "folder"; type: "QUrl" }
Property { name: "rootFolder"; type: "QUrl" }
Property { name: "parentFolder"; type: "QUrl"; isReadonly: true }
@@ -42,8 +51,10 @@ Module {
Property { name: "showOnlyReadable"; type: "bool" }
Property { name: "caseSensitive"; revision: 2; type: "bool" }
Property { name: "count"; type: "int"; isReadonly: true }
+ Property { name: "status"; revision: 11; type: "Status"; isReadonly: true }
Signal { name: "rowCountChanged" }
Signal { name: "countChanged"; revision: 1 }
+ Signal { name: "statusChanged"; revision: 11 }
Method {
name: "isFolder"
type: "bool"
diff --git a/src/imports/folderlistmodel/qquickfolderlistmodel.cpp b/src/imports/folderlistmodel/qquickfolderlistmodel.cpp
index fdcce9c685..32c709830a 100644
--- a/src/imports/folderlistmodel/qquickfolderlistmodel.cpp
+++ b/src/imports/folderlistmodel/qquickfolderlistmodel.cpp
@@ -55,7 +55,7 @@ public:
: q_ptr(q),
sortField(QQuickFolderListModel::Name), sortReversed(false), showFiles(true),
showDirs(true), showDirsFirst(false), showDotAndDotDot(false), showOnlyReadable(false),
- showHidden(false), caseSensitive(true)
+ showHidden(false), caseSensitive(true), status(QQuickFolderListModel::Null)
{
nameFilters << QLatin1String("*");
}
@@ -77,6 +77,7 @@ public:
bool showOnlyReadable;
bool showHidden;
bool caseSensitive;
+ QQuickFolderListModel::Status status;
~QQuickFolderListModelPrivate() {}
void init();
@@ -86,6 +87,7 @@ public:
void _q_directoryChanged(const QString &directory, const QList<FileProperty> &list);
void _q_directoryUpdated(const QString &directory, const QList<FileProperty> &list, int fromIndex, int toIndex);
void _q_sortFinished(const QList<FileProperty> &list);
+ void _q_statusChanged(QQuickFolderListModel::Status s);
static QString resolvePath(const QUrl &path);
};
@@ -95,12 +97,15 @@ void QQuickFolderListModelPrivate::init()
{
Q_Q(QQuickFolderListModel);
qRegisterMetaType<QList<FileProperty> >("QList<FileProperty>");
+ qRegisterMetaType<QQuickFolderListModel::Status>("QQuickFolderListModel::Status");
q->connect(&fileInfoThread, SIGNAL(directoryChanged(QString,QList<FileProperty>)),
q, SLOT(_q_directoryChanged(QString,QList<FileProperty>)));
q->connect(&fileInfoThread, SIGNAL(directoryUpdated(QString,QList<FileProperty>,int,int)),
q, SLOT(_q_directoryUpdated(QString,QList<FileProperty>,int,int)));
q->connect(&fileInfoThread, SIGNAL(sortFinished(QList<FileProperty>)),
q, SLOT(_q_sortFinished(QList<FileProperty>)));
+ q->connect(&fileInfoThread, SIGNAL(statusChanged(QQuickFolderListModel::Status)),
+ q, SLOT(_q_statusChanged(QQuickFolderListModel::Status)));
q->connect(q, SIGNAL(rowCountChanged()), q, SIGNAL(countChanged()));
}
@@ -109,7 +114,7 @@ void QQuickFolderListModelPrivate::updateSorting()
{
Q_Q(QQuickFolderListModel);
- QDir::SortFlags flags = 0;
+ QDir::SortFlags flags = nullptr;
switch (sortField) {
case QQuickFolderListModel::Unsorted:
@@ -198,6 +203,16 @@ void QQuickFolderListModelPrivate::_q_sortFinished(const QList<FileProperty> &li
q->endInsertRows();
}
+void QQuickFolderListModelPrivate::_q_statusChanged(QQuickFolderListModel::Status s)
+{
+ Q_Q(QQuickFolderListModel);
+
+ if (status != s) {
+ status = s;
+ emit q->statusChanged();
+ }
+}
+
QString QQuickFolderListModelPrivate::resolvePath(const QUrl &path)
{
QString localPath = QQmlFile::urlToLocalFileOrQrc(path);
@@ -209,7 +224,7 @@ QString QQuickFolderListModelPrivate::resolvePath(const QUrl &path)
}
/*!
- \qmlmodule Qt.labs.folderlistmodel 2.1
+ \qmlmodule Qt.labs.folderlistmodel 2.11
\title Qt Labs FolderListModel QML Types
\ingroup qmlmodules
\brief The FolderListModel provides a model of the contents of a file system folder.
@@ -217,7 +232,7 @@ QString QQuickFolderListModelPrivate::resolvePath(const QUrl &path)
To use this module, import the module with the following line:
\code
- import Qt.labs.folderlistmodel 2.1
+ import Qt.labs.folderlistmodel 2.11
\endcode
*/
@@ -236,7 +251,7 @@ QString QQuickFolderListModelPrivate::resolvePath(const QUrl &path)
\e{Elements in the Qt.labs module are not guaranteed to remain compatible
in future versions.}
- \b{import Qt.labs.folderlistmodel 2.1}
+ \b{import Qt.labs.folderlistmodel 2.11}
The \l folder property specifies the folder to access. Information about the
files and directories in the folder is supplied via the model's interface.
@@ -282,7 +297,7 @@ QString QQuickFolderListModelPrivate::resolvePath(const QUrl &path)
\qml
import QtQuick 2.0
- import Qt.labs.folderlistmodel 2.1
+ import Qt.labs.folderlistmodel 2.11
ListView {
width: 200; height: 400
@@ -437,6 +452,10 @@ void QQuickFolderListModel::setFolder(const QUrl &folder)
d->data.clear();
endResetModel();
emit rowCountChanged();
+ if (d->status != QQuickFolderListModel::Null) {
+ d->status = QQuickFolderListModel::Null;
+ emit statusChanged();
+ }
return;
}
@@ -795,6 +814,46 @@ void QQuickFolderListModel::setCaseSensitive(bool on)
}
/*!
+ \qmlproperty enumeration FolderListModel::status
+ \since 5.11
+
+ This property holds the status of folder reading. It can be one of:
+ \list
+ \li FolderListModel.Null - no \a folder has been set
+ \li FolderListModel.Ready - the folder has been loaded
+ \li FolderListModel.Loading - the folder is currently being loaded
+ \endlist
+
+ Use this status to provide an update or respond to the status change in some way.
+ For example, you could:
+
+ \list
+ \li Trigger a state change:
+ \qml
+ State { name: 'loaded'; when: folderModel.status == FolderListModel.Ready }
+ \endqml
+
+ \li Implement an \c onStatusChanged signal handler:
+ \qml
+ FolderListModel {
+ id: folderModel
+ onStatusChanged: if (folderModel.status == FolderListModel.Ready) console.log('Loaded')
+ }
+ \endqml
+
+ \li Bind to the status value:
+ \qml
+ Text { text: folderModel.status == FolderListModel.Ready ? 'Loaded' : 'Not loaded' }
+ \endqml
+ \endlist
+*/
+QQuickFolderListModel::Status QQuickFolderListModel::status() const
+{
+ Q_D(const QQuickFolderListModel);
+ return d->status;
+}
+
+/*!
\qmlmethod var FolderListModel::get(int index, string property)
Get the folder property for the given index. The following properties
diff --git a/src/imports/folderlistmodel/qquickfolderlistmodel.h b/src/imports/folderlistmodel/qquickfolderlistmodel.h
index dee73dff3e..a449f0dd0f 100644
--- a/src/imports/folderlistmodel/qquickfolderlistmodel.h
+++ b/src/imports/folderlistmodel/qquickfolderlistmodel.h
@@ -75,6 +75,7 @@ class QQuickFolderListModel : public QAbstractListModel, public QQmlParserStatus
Q_PROPERTY(bool showOnlyReadable READ showOnlyReadable WRITE setShowOnlyReadable)
Q_PROPERTY(bool caseSensitive READ caseSensitive WRITE setCaseSensitive REVISION 2)
Q_PROPERTY(int count READ count NOTIFY countChanged)
+ Q_PROPERTY(Status status READ status NOTIFY statusChanged REVISION 11)
//![class props]
//![abslistmodel]
@@ -137,6 +138,10 @@ public:
void setShowOnlyReadable(bool on);
bool caseSensitive() const;
void setCaseSensitive(bool on);
+
+ enum Status { Null, Ready, Loading };
+ Q_ENUM(Status)
+ Status status() const;
//![prop funcs]
Q_INVOKABLE bool isFolder(int index) const;
@@ -155,6 +160,7 @@ Q_SIGNALS:
void folderChanged();
void rowCountChanged() const;
Q_REVISION(1) void countChanged() const;
+ Q_REVISION(11) void statusChanged();
//![notifier]
//![class end]
@@ -168,6 +174,7 @@ private:
Q_PRIVATE_SLOT(d_func(), void _q_directoryChanged(const QString &directory, const QList<FileProperty> &list))
Q_PRIVATE_SLOT(d_func(), void _q_directoryUpdated(const QString &directory, const QList<FileProperty> &list, int fromIndex, int toIndex))
Q_PRIVATE_SLOT(d_func(), void _q_sortFinished(const QList<FileProperty> &list))
+ Q_PRIVATE_SLOT(d_func(), void _q_statusChanged(QQuickFolderListModel::Status s))
};
//![class end]
diff --git a/src/imports/handlers/plugin.cpp b/src/imports/handlers/plugin.cpp
index d26ef2b2d4..d1041d6539 100644
--- a/src/imports/handlers/plugin.cpp
+++ b/src/imports/handlers/plugin.cpp
@@ -50,30 +50,13 @@ static void initResources()
QT_BEGIN_NAMESPACE
-/*!
- \qmlmodule Qt.labs.handlers 1.0
- \title Qt Quick Pointer Handlers
- \ingroup qmlmodules
- \brief Provides QML types for handling pointer events.
-
- This QML module contains types for handling pointer events, which are an abstraction
- of mouse, touch and tablet events.
-
- To use the types in this module, import the module with the following line:
-
- \code
- import Qt.labs.handlers 1.0
- \endcode
-*/
-
-
//![class decl]
class QtQuickHandlersPlugin : public QQmlExtensionPlugin
{
Q_OBJECT
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QtQuickHandlersPlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QtQuickHandlersPlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QLatin1String(uri) == QLatin1String("Qt.labs.handlers"));
diff --git a/src/imports/handlers/plugins.qmltypes b/src/imports/handlers/plugins.qmltypes
new file mode 100644
index 0000000000..f51e1e4bf3
--- /dev/null
+++ b/src/imports/handlers/plugins.qmltypes
@@ -0,0 +1,308 @@
+import QtQuick.tooling 1.2
+
+// This file describes the plugin-supplied types contained in the library.
+// It is used for QML tooling purposes only.
+//
+// This file was auto-generated by:
+// 'qmlplugindump -nonrelocatable Qt.labs.handlers 1.0'
+
+Module {
+ dependencies: ["QtQuick 2.8"]
+ Component {
+ name: "QQuickDragAxis"
+ prototype: "QObject"
+ exports: ["Qt.labs.handlers/DragAxis 1.0"]
+ isCreatable: false
+ exportMetaObjectRevisions: [0]
+ Property { name: "minimum"; type: "double" }
+ Property { name: "maximum"; type: "double" }
+ Property { name: "enabled"; type: "bool" }
+ }
+ Component {
+ name: "QQuickDragHandler"
+ prototype: "QQuickSinglePointHandler"
+ exports: ["Qt.labs.handlers/DragHandler 1.0"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "xAxis"; type: "QQuickDragAxis"; isReadonly: true; isPointer: true }
+ Property { name: "yAxis"; type: "QQuickDragAxis"; isReadonly: true; isPointer: true }
+ Property { name: "translation"; type: "QVector2D"; isReadonly: true }
+ Method { name: "enforceConstraints" }
+ }
+ Component {
+ name: "QQuickEventPoint"
+ prototype: "QObject"
+ exports: ["Qt.labs.handlers/EventPoint 1.0"]
+ isCreatable: false
+ exportMetaObjectRevisions: [0]
+ Enum {
+ name: "States"
+ values: {
+ "Pressed": 1,
+ "Updated": 2,
+ "Stationary": 4,
+ "Released": 8
+ }
+ }
+ Enum {
+ name: "GrabState"
+ values: {
+ "GrabPassive": 1,
+ "UngrabPassive": 2,
+ "CancelGrabPassive": 3,
+ "OverrideGrabPassive": 4,
+ "GrabExclusive": 16,
+ "UngrabExclusive": 32,
+ "CancelGrabExclusive": 48
+ }
+ }
+ Property { name: "event"; type: "QQuickPointerEvent"; isReadonly: true; isPointer: true }
+ Property { name: "position"; type: "QPointF"; isReadonly: true }
+ Property { name: "scenePosition"; type: "QPointF"; isReadonly: true }
+ Property { name: "scenePressPosition"; type: "QPointF"; isReadonly: true }
+ Property { name: "sceneGrabPosition"; type: "QPointF"; isReadonly: true }
+ Property { name: "state"; type: "State"; isReadonly: true }
+ Property { name: "pointId"; type: "int"; isReadonly: true }
+ Property { name: "timeHeld"; type: "double"; isReadonly: true }
+ Property { name: "velocity"; type: "QVector2D"; isReadonly: true }
+ Property { name: "accepted"; type: "bool" }
+ Property { name: "exclusiveGrabber"; type: "QObject"; isPointer: true }
+ }
+ Component {
+ name: "QQuickEventTouchPoint"
+ prototype: "QQuickEventPoint"
+ exports: ["Qt.labs.handlers/EventTouchPoint 1.0"]
+ isCreatable: false
+ exportMetaObjectRevisions: [0]
+ Property { name: "rotation"; type: "double"; isReadonly: true }
+ Property { name: "pressure"; type: "double"; isReadonly: true }
+ Property { name: "ellipseDiameters"; type: "QSizeF"; isReadonly: true }
+ Property { name: "uniqueId"; type: "QPointingDeviceUniqueId"; isReadonly: true }
+ }
+ Component {
+ name: "QQuickMultiPointHandler"
+ prototype: "QQuickPointerDeviceHandler"
+ Property { name: "minimumPointCount"; type: "int" }
+ Property { name: "maximumPointCount"; type: "int" }
+ Property { name: "pointDistanceThreshold"; type: "double" }
+ }
+ Component {
+ name: "QQuickPinchHandler"
+ prototype: "QQuickMultiPointHandler"
+ exports: ["Qt.labs.handlers/PinchHandler 1.0"]
+ exportMetaObjectRevisions: [0]
+ Enum {
+ name: "PinchOrigin"
+ values: {
+ "FirstPoint": 0,
+ "PinchCenter": 1,
+ "TargetCenter": 2
+ }
+ }
+ Property { name: "minimumScale"; type: "double" }
+ Property { name: "maximumScale"; type: "double" }
+ Property { name: "minimumRotation"; type: "double" }
+ Property { name: "maximumRotation"; type: "double" }
+ Property { name: "pinchOrigin"; type: "PinchOrigin" }
+ Property { name: "centroid"; type: "QPointF"; isReadonly: true }
+ Property { name: "centroidVelocity"; type: "QVector2D"; isReadonly: true }
+ Property { name: "scale"; type: "double"; isReadonly: true }
+ Property { name: "rotation"; type: "double"; isReadonly: true }
+ Property { name: "translation"; type: "QVector2D"; isReadonly: true }
+ Property { name: "minimumX"; type: "double" }
+ Property { name: "maximumX"; type: "double" }
+ Property { name: "minimumY"; type: "double" }
+ Property { name: "maximumY"; type: "double" }
+ Signal { name: "updated" }
+ }
+ Component {
+ name: "QQuickPointHandler"
+ prototype: "QQuickSinglePointHandler"
+ exports: ["Qt.labs.handlers/PointHandler 1.0"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "translation"; type: "QVector2D"; isReadonly: true }
+ }
+ Component {
+ name: "QQuickPointerDevice"
+ prototype: "QObject"
+ exports: ["Qt.labs.handlers/PointerDevice 1.0"]
+ isCreatable: false
+ exportMetaObjectRevisions: [0]
+ Enum {
+ name: "DeviceType"
+ values: {
+ "UnknownDevice": 0,
+ "Mouse": 1,
+ "TouchScreen": 2,
+ "TouchPad": 4,
+ "Puck": 8,
+ "Stylus": 16,
+ "Airbrush": 32,
+ "AllDevices": 63
+ }
+ }
+ Enum {
+ name: "DeviceTypes"
+ values: {
+ "UnknownDevice": 0,
+ "Mouse": 1,
+ "TouchScreen": 2,
+ "TouchPad": 4,
+ "Puck": 8,
+ "Stylus": 16,
+ "Airbrush": 32,
+ "AllDevices": 63
+ }
+ }
+ Enum {
+ name: "PointerType"
+ values: {
+ "GenericPointer": 1,
+ "Finger": 2,
+ "Pen": 4,
+ "Eraser": 8,
+ "Cursor": 16,
+ "AllPointerTypes": 31
+ }
+ }
+ Enum {
+ name: "PointerTypes"
+ values: {
+ "GenericPointer": 1,
+ "Finger": 2,
+ "Pen": 4,
+ "Eraser": 8,
+ "Cursor": 16,
+ "AllPointerTypes": 31
+ }
+ }
+ Enum {
+ name: "CapabilityFlag"
+ values: {
+ "Position": 1,
+ "Area": 2,
+ "Pressure": 4,
+ "Velocity": 8,
+ "Scroll": 256,
+ "Hover": 512,
+ "Rotation": 1024,
+ "XTilt": 2048,
+ "YTilt": 4096
+ }
+ }
+ Enum {
+ name: "Capabilities"
+ values: {
+ "Position": 1,
+ "Area": 2,
+ "Pressure": 4,
+ "Velocity": 8,
+ "Scroll": 256,
+ "Hover": 512,
+ "Rotation": 1024,
+ "XTilt": 2048,
+ "YTilt": 4096
+ }
+ }
+ Property { name: "type"; type: "DeviceType"; isReadonly: true }
+ Property { name: "pointerType"; type: "PointerType"; isReadonly: true }
+ Property { name: "capabilities"; type: "Capabilities"; isReadonly: true }
+ Property { name: "maximumTouchPoints"; type: "int"; isReadonly: true }
+ Property { name: "buttonCount"; type: "int"; isReadonly: true }
+ Property { name: "name"; type: "string"; isReadonly: true }
+ Property { name: "uniqueId"; type: "QPointingDeviceUniqueId"; isReadonly: true }
+ }
+ Component {
+ name: "QQuickPointerDeviceHandler"
+ prototype: "QQuickPointerHandler"
+ Property { name: "acceptedDevices"; type: "QQuickPointerDevice::DeviceTypes" }
+ Property { name: "acceptedPointerTypes"; type: "QQuickPointerDevice::PointerTypes" }
+ Property { name: "acceptedModifiers"; type: "Qt::KeyboardModifiers" }
+ Method {
+ name: "setAcceptedDevices"
+ Parameter { name: "acceptedDevices"; type: "QQuickPointerDevice::DeviceTypes" }
+ }
+ Method {
+ name: "setAcceptedPointerTypes"
+ Parameter { name: "acceptedPointerTypes"; type: "QQuickPointerDevice::PointerTypes" }
+ }
+ Method {
+ name: "setAcceptedModifiers"
+ Parameter { name: "acceptedModifiers"; type: "Qt::KeyboardModifiers" }
+ }
+ }
+ Component {
+ name: "QQuickPointerEvent"
+ prototype: "QObject"
+ exports: ["Qt.labs.handlers/PointerEvent 1.0"]
+ isCreatable: false
+ exportMetaObjectRevisions: [0]
+ Property { name: "device"; type: "const QQuickPointerDevice"; isReadonly: true; isPointer: true }
+ Property { name: "modifiers"; type: "Qt::KeyboardModifiers"; isReadonly: true }
+ Property { name: "button"; type: "Qt::MouseButtons"; isReadonly: true }
+ Property { name: "buttons"; type: "Qt::MouseButtons"; isReadonly: true }
+ }
+ Component {
+ name: "QQuickPointerHandler"
+ prototype: "QObject"
+ exports: ["Qt.labs.handlers/PointerHandler 1.0"]
+ isCreatable: false
+ exportMetaObjectRevisions: [0]
+ Enum {
+ name: "GrabPermissions"
+ values: {
+ "TakeOverForbidden": 0,
+ "CanTakeOverFromHandlersOfSameType": 1,
+ "CanTakeOverFromHandlersOfDifferentType": 2,
+ "CanTakeOverFromItems": 4,
+ "CanTakeOverFromAnything": 15,
+ "ApprovesTakeOverByHandlersOfSameType": 16,
+ "ApprovesTakeOverByHandlersOfDifferentType": 32,
+ "ApprovesTakeOverByItems": 64,
+ "ApprovesCancellation": 128,
+ "ApprovesTakeOverByAnything": 240
+ }
+ }
+ Property { name: "enabled"; type: "bool" }
+ Property { name: "active"; type: "bool"; isReadonly: true }
+ Property { name: "target"; type: "QQuickItem"; isPointer: true }
+ Property { name: "parent"; type: "QQuickItem"; isReadonly: true; isPointer: true }
+ Property { name: "grabPermissions"; type: "GrabPermissions" }
+ Signal {
+ name: "grabChanged"
+ Parameter { name: "point"; type: "QQuickEventPoint"; isPointer: true }
+ }
+ Signal { name: "grabPermissionChanged" }
+ Signal {
+ name: "canceled"
+ Parameter { name: "point"; type: "QQuickEventPoint"; isPointer: true }
+ }
+ }
+ Component {
+ name: "QQuickSinglePointHandler"
+ prototype: "QQuickPointerDeviceHandler"
+ Property { name: "acceptedButtons"; type: "Qt::MouseButtons" }
+ Property { name: "point"; type: "QQuickHandlerPoint"; isReadonly: true }
+ Signal { name: "singlePointGrabChanged" }
+ }
+ Component {
+ name: "QQuickTapHandler"
+ prototype: "QQuickSinglePointHandler"
+ exports: ["Qt.labs.handlers/TapHandler 1.0"]
+ exportMetaObjectRevisions: [0]
+ Enum {
+ name: "GesturePolicy"
+ values: {
+ "DragThreshold": 0,
+ "WithinBounds": 1,
+ "ReleaseWithinBounds": 2
+ }
+ }
+ Property { name: "pressed"; type: "bool"; isReadonly: true }
+ Property { name: "tapCount"; type: "int"; isReadonly: true }
+ Property { name: "timeHeld"; type: "double"; isReadonly: true }
+ Property { name: "longPressThreshold"; type: "double" }
+ Property { name: "gesturePolicy"; type: "GesturePolicy" }
+ Signal { name: "tapped" }
+ Signal { name: "longPressed" }
+ }
+}
diff --git a/src/imports/layouts/plugin.cpp b/src/imports/layouts/plugin.cpp
index fc3938c5d8..25d5bacc90 100644
--- a/src/imports/layouts/plugin.cpp
+++ b/src/imports/layouts/plugin.cpp
@@ -57,7 +57,7 @@ class QtQuickLayoutsPlugin : public QQmlExtensionPlugin
Q_OBJECT
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QtQuickLayoutsPlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent)
+ QtQuickLayoutsPlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent)
{
initResources();
}
diff --git a/src/imports/layouts/qquickgridlayoutengine.cpp b/src/imports/layouts/qquickgridlayoutengine.cpp
index fe716f0694..6004bb92ca 100644
--- a/src/imports/layouts/qquickgridlayoutengine.cpp
+++ b/src/imports/layouts/qquickgridlayoutengine.cpp
@@ -55,7 +55,7 @@ Qt::Alignment QQuickGridLayoutEngine::alignment(QQuickItem *quickItem) const
{
if (QGridLayoutItem *item = findLayoutItem(quickItem))
return item->alignment();
- return 0;
+ return nullptr;
}
QT_END_NAMESPACE
diff --git a/src/imports/layouts/qquicklayout.cpp b/src/imports/layouts/qquicklayout.cpp
index 7d51ec3ca9..b3a5a2cfc8 100644
--- a/src/imports/layouts/qquicklayout.cpp
+++ b/src/imports/layouts/qquicklayout.cpp
@@ -114,7 +114,7 @@ QQuickLayoutAttached::QQuickLayoutAttached(QObject *parent)
m_isTopMarginSet(false),
m_isRightMarginSet(false),
m_isBottomMarginSet(false),
- m_alignment(0)
+ m_alignment(nullptr)
{
}
@@ -683,7 +683,7 @@ QQuickLayout *QQuickLayoutAttached::parentLayout() const
} else {
qmlWarning(parent()) << "Layout must be attached to Item elements";
}
- return 0;
+ return nullptr;
}
QQuickItem *QQuickLayoutAttached::item() const
@@ -771,8 +771,9 @@ bool QQuickLayout::shouldIgnoreItem(QQuickItem *child, QQuickLayoutAttached *&in
void QQuickLayout::checkAnchors(QQuickItem *item) const
{
- if (QQuickItemPrivate::get(item)->_anchors)
- qmlWarning(item) << "Detected anchors on an item that is part of a layout. This is undefined behavior.";
+ QQuickAnchors *anchors = QQuickItemPrivate::get(item)->_anchors;
+ if (anchors && anchors->activeDirections())
+ qmlWarning(item) << "Detected anchors on an item that is managed by a layout. This is undefined behavior; use Layout.alignment instead.";
}
void QQuickLayout::itemChange(ItemChange change, const ItemChangeData &value)
diff --git a/src/imports/layouts/qquicklinearlayout.cpp b/src/imports/layouts/qquicklinearlayout.cpp
index db983e06ba..fa51ef1f2f 100644
--- a/src/imports/layouts/qquicklinearlayout.cpp
+++ b/src/imports/layouts/qquicklinearlayout.cpp
@@ -653,13 +653,13 @@ void QQuickGridLayout::insertLayoutItems()
const auto items = childItems();
for (QQuickItem *child : items) {
checkAnchors(child);
- QQuickLayoutAttached *info = 0;
+ QQuickLayoutAttached *info = nullptr;
// Will skip all items with effective maximum width/height == 0
if (shouldIgnoreItem(child, info, sizeHints))
continue;
- Qt::Alignment alignment = 0;
+ Qt::Alignment alignment = nullptr;
int row = -1;
int column = -1;
int span[2] = {1,1};
@@ -828,13 +828,13 @@ void QQuickLinearLayout::insertLayoutItems()
for (QQuickItem *child : items) {
Q_ASSERT(child);
checkAnchors(child);
- QQuickLayoutAttached *info = 0;
+ QQuickLayoutAttached *info = nullptr;
// Will skip all items with effective maximum width/height == 0
if (shouldIgnoreItem(child, info, sizeHints))
continue;
- Qt::Alignment alignment = 0;
+ Qt::Alignment alignment = nullptr;
if (info)
alignment = info->alignment();
diff --git a/src/imports/layouts/qquickstacklayout.cpp b/src/imports/layouts/qquickstacklayout.cpp
index cf70856e14..0b51d79bef 100644
--- a/src/imports/layouts/qquickstacklayout.cpp
+++ b/src/imports/layouts/qquickstacklayout.cpp
@@ -213,7 +213,7 @@ QQuickItem *QQuickStackLayout::itemAt(int index) const
return item;
--index;
}
- return 0;
+ return nullptr;
}
int QQuickStackLayout::itemCount() const
@@ -320,7 +320,7 @@ void QQuickStackLayout::rearrange(const QSizeF &newSize)
void QQuickStackLayout::collectItemSizeHints(QQuickItem *item, QSizeF *sizeHints)
{
- QQuickLayoutAttached *info = 0;
+ QQuickLayoutAttached *info = nullptr;
QQuickLayout::effectiveSizeHints_helper(item, sizeHints, &info, true);
if (!info)
return;
diff --git a/src/imports/localstorage/plugin.cpp b/src/imports/localstorage/plugin.cpp
index 9d78773fe1..88121df66c 100644
--- a/src/imports/localstorage/plugin.cpp
+++ b/src/imports/localstorage/plugin.cpp
@@ -97,7 +97,7 @@ class QQmlSqlDatabaseData : public QV8Engine::Deletable
{
public:
QQmlSqlDatabaseData(QV4::ExecutionEngine *engine);
- ~QQmlSqlDatabaseData();
+ ~QQmlSqlDatabaseData() override;
QV4::PersistentValue databaseProto;
QV4::PersistentValue queryProto;
@@ -165,20 +165,20 @@ DEFINE_OBJECT_VTABLE(QV4::QQmlSqlDatabaseWrapper);
-static ReturnedValue qmlsqldatabase_version(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_version(const FunctionObject *b, const Value *thisObject, const QV4::Value *, int)
{
Scope scope(b);
- QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, callData->thisObject.as<QQmlSqlDatabaseWrapper>());
+ QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, thisObject->as<QQmlSqlDatabaseWrapper>());
if (!r || r->d()->type != Heap::QQmlSqlDatabaseWrapper::Database)
V4THROW_REFERENCE("Not a SQLDatabase object");
RETURN_RESULT(Encode(scope.engine->newString(*r->d()->version)));
}
-static ReturnedValue qmlsqldatabase_rows_length(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_rows_length(const FunctionObject *b, const Value *thisObject, const QV4::Value *, int)
{
Scope scope(b);
- QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, callData->thisObject.as<QQmlSqlDatabaseWrapper>());
+ QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, thisObject->as<QQmlSqlDatabaseWrapper>());
if (!r || r->d()->type != Heap::QQmlSqlDatabaseWrapper::Rows)
V4THROW_REFERENCE("Not a SQLDatabase::Rows object");
@@ -194,25 +194,25 @@ static ReturnedValue qmlsqldatabase_rows_length(const QV4::BuiltinFunction *b, Q
RETURN_RESULT(Encode(s));
}
-static ReturnedValue qmlsqldatabase_rows_forwardOnly(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_rows_forwardOnly(const FunctionObject *b, const Value *thisObject, const QV4::Value *, int)
{
Scope scope(b);
- QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, callData->thisObject.as<QQmlSqlDatabaseWrapper>());
+ QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, thisObject->as<QQmlSqlDatabaseWrapper>());
if (!r || r->d()->type != Heap::QQmlSqlDatabaseWrapper::Rows)
V4THROW_REFERENCE("Not a SQLDatabase::Rows object");
RETURN_RESULT(Encode(r->d()->sqlQuery->isForwardOnly()));
}
-static ReturnedValue qmlsqldatabase_rows_setForwardOnly(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_rows_setForwardOnly(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, callData->thisObject.as<QQmlSqlDatabaseWrapper>());
+ QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, thisObject->as<QQmlSqlDatabaseWrapper>());
if (!r || r->d()->type != Heap::QQmlSqlDatabaseWrapper::Rows)
V4THROW_REFERENCE("Not a SQLDatabase::Rows object");
- if (callData->argc() < 1)
+ if (argc < 1)
RETURN_RESULT(scope.engine->throwTypeError());
- r->d()->sqlQuery->setForwardOnly(callData->args[0].toBoolean());
+ r->d()->sqlQuery->setForwardOnly(argv[0].toBoolean());
RETURN_UNDEFINED();
}
@@ -220,7 +220,7 @@ QQmlSqlDatabaseData::~QQmlSqlDatabaseData()
{
}
-static ReturnedValue qmlsqldatabase_rows_index(const QQmlSqlDatabaseWrapper *r, ExecutionEngine *v4, quint32 index, bool *hasProperty = 0)
+static ReturnedValue qmlsqldatabase_rows_index(const QQmlSqlDatabaseWrapper *r, ExecutionEngine *v4, quint32 index, bool *hasProperty = nullptr)
{
Scope scope(v4);
@@ -254,14 +254,14 @@ ReturnedValue QQmlSqlDatabaseWrapper::getIndexed(const Managed *m, uint index, b
return qmlsqldatabase_rows_index(r, r->engine(), index, hasProperty);
}
-static ReturnedValue qmlsqldatabase_rows_item(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_rows_item(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, callData->thisObject.as<QQmlSqlDatabaseWrapper>());
+ QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, thisObject->as<QQmlSqlDatabaseWrapper>());
if (!r || r->d()->type != Heap::QQmlSqlDatabaseWrapper::Rows)
V4THROW_REFERENCE("Not a SQLDatabase::Rows object");
- RETURN_RESULT(qmlsqldatabase_rows_index(r, scope.engine, callData->argc() ? callData->args[0].toUInt32() : 0));
+ RETURN_RESULT(qmlsqldatabase_rows_index(r, scope.engine, argc ? argv[0].toUInt32() : 0));
}
static QVariant toSqlVariant(QV4::ExecutionEngine *engine, const QV4::ScopedValue &value)
@@ -273,10 +273,10 @@ static QVariant toSqlVariant(QV4::ExecutionEngine *engine, const QV4::ScopedValu
return engine->toVariant(value, /*typehint*/-1);
}
-static ReturnedValue qmlsqldatabase_executeSql(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_executeSql(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, callData->thisObject.as<QQmlSqlDatabaseWrapper>());
+ QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, thisObject->as<QQmlSqlDatabaseWrapper>());
if (!r || r->d()->type != Heap::QQmlSqlDatabaseWrapper::Query)
V4THROW_REFERENCE("Not a SQLDatabase::Query object");
@@ -285,7 +285,7 @@ static ReturnedValue qmlsqldatabase_executeSql(const QV4::BuiltinFunction *b, QV
QSqlDatabase db = *r->d()->database;
- QString sql = callData->argc() ? callData->args[0].toQString() : QString();
+ QString sql = argc ? argv[0].toQString() : QString();
if (r->d()->readonly && !sql.startsWith(QLatin1String("SELECT"),Qt::CaseInsensitive)) {
V4THROW_SQL(SQLEXCEPTION_SYNTAX_ERR, QQmlEngine::tr("Read-only Transaction"));
@@ -297,8 +297,8 @@ static ReturnedValue qmlsqldatabase_executeSql(const QV4::BuiltinFunction *b, QV
ScopedValue result(scope, Primitive::undefinedValue());
if (query.prepare(sql)) {
- if (callData->argc() > 1) {
- ScopedValue values(scope, callData->args[1]);
+ if (argc > 1) {
+ ScopedValue values(scope, argv[1]);
if (values->as<ArrayObject>()) {
ScopedArrayObject array(scope, values);
quint32 size = array->getLength();
@@ -376,28 +376,28 @@ struct TransactionRollback {
}
void clear() {
- db = 0;
+ db = nullptr;
if (inTransactionFlag)
*inTransactionFlag = false;
- inTransactionFlag = 0;
+ inTransactionFlag = nullptr;
}
};
-static ReturnedValue qmlsqldatabase_changeVersion(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_changeVersion(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- if (callData->argc() < 2)
+ if (argc < 2)
RETURN_UNDEFINED();
- Scoped<QQmlSqlDatabaseWrapper> r(scope, callData->thisObject);
+ Scoped<QQmlSqlDatabaseWrapper> r(scope, *thisObject);
if (!r || r->d()->type != Heap::QQmlSqlDatabaseWrapper::Database)
V4THROW_REFERENCE("Not a SQLDatabase object");
QSqlDatabase db = *r->d()->database;
- QString from_version = callData->args[0].toQString();
- QString to_version = callData->args[1].toQString();
- ScopedFunctionObject callback(scope, callData->argc() > 2 ? callData->args[2] : Primitive::undefinedValue());
+ QString from_version = argv[0].toQString();
+ QString to_version = argv[1].toQString();
+ ScopedFunctionObject callback(scope, argc > 2 ? argv[2] : Primitive::undefinedValue());
if (from_version != *r->d()->version)
V4THROW_SQL(SQLEXCEPTION_VERSION_ERR, QQmlEngine::tr("Version mismatch: expected %1, found %2").arg(from_version).arg(*r->d()->version));
@@ -441,14 +441,14 @@ static ReturnedValue qmlsqldatabase_changeVersion(const QV4::BuiltinFunction *b,
RETURN_UNDEFINED();
}
-static ReturnedValue qmlsqldatabase_transaction_shared(const QV4::BuiltinFunction *b, QV4::CallData *callData, bool readOnly)
+static ReturnedValue qmlsqldatabase_transaction_shared(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc, bool readOnly)
{
Scope scope(b);
- QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, callData->thisObject.as<QQmlSqlDatabaseWrapper>());
+ QV4::Scoped<QQmlSqlDatabaseWrapper> r(scope, thisObject->as<QQmlSqlDatabaseWrapper>());
if (!r || r->d()->type != Heap::QQmlSqlDatabaseWrapper::Database)
V4THROW_REFERENCE("Not a SQLDatabase object");
- const FunctionObject *callback = callData->argc() ? callData->args[0].as<FunctionObject>() : 0;
+ const FunctionObject *callback = argc ? argv[0].as<FunctionObject>() : nullptr;
if (!callback)
V4THROW_SQL(SQLEXCEPTION_UNKNOWN_ERR, QQmlEngine::tr("transaction: missing callback"));
@@ -478,14 +478,14 @@ static ReturnedValue qmlsqldatabase_transaction_shared(const QV4::BuiltinFunctio
RETURN_UNDEFINED();
}
-static ReturnedValue qmlsqldatabase_transaction(const QV4::BuiltinFunction *f, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_transaction(const FunctionObject *f, const Value *thisObject, const Value *argv, int argc)
{
- return qmlsqldatabase_transaction_shared(f, callData, false);
+ return qmlsqldatabase_transaction_shared(f, thisObject, argv, argc, false);
}
-static ReturnedValue qmlsqldatabase_read_transaction(const QV4::BuiltinFunction *f, QV4::CallData *callData)
+static ReturnedValue qmlsqldatabase_read_transaction(const FunctionObject *f, const Value *thisObject, const Value *argv, int argc)
{
- return qmlsqldatabase_transaction_shared(f, callData, true);
+ return qmlsqldatabase_transaction_shared(f, thisObject, argv, argc, true);
}
QQmlSqlDatabaseData::QQmlSqlDatabaseData(ExecutionEngine *v4)
@@ -495,7 +495,7 @@ QQmlSqlDatabaseData::QQmlSqlDatabaseData(ExecutionEngine *v4)
ScopedObject proto(scope, v4->newObject());
proto->defineDefaultProperty(QStringLiteral("transaction"), qmlsqldatabase_transaction);
proto->defineDefaultProperty(QStringLiteral("readTransaction"), qmlsqldatabase_read_transaction);
- proto->defineAccessorProperty(QStringLiteral("version"), qmlsqldatabase_version, 0);
+ proto->defineAccessorProperty(QStringLiteral("version"), qmlsqldatabase_version, nullptr);
proto->defineDefaultProperty(QStringLiteral("changeVersion"), qmlsqldatabase_changeVersion);
databaseProto = proto;
}
@@ -508,7 +508,7 @@ QQmlSqlDatabaseData::QQmlSqlDatabaseData(ExecutionEngine *v4)
{
ScopedObject proto(scope, v4->newObject());
proto->defineDefaultProperty(QStringLiteral("item"), qmlsqldatabase_rows_item);
- proto->defineAccessorProperty(QStringLiteral("length"), qmlsqldatabase_rows_length, 0);
+ proto->defineAccessorProperty(QStringLiteral("length"), qmlsqldatabase_rows_length, nullptr);
proto->defineAccessorProperty(QStringLiteral("forwardOnly"),
qmlsqldatabase_rows_forwardOnly, qmlsqldatabase_rows_setForwardOnly);
rowsProto = proto;
@@ -611,7 +611,15 @@ May throw exception with code property SQLException.DATABASE_ERR or SQLException
See example below.
-\snippet qml/localstorage/dbtransaction.js 2
+\badcode
+ var db = LocalStorage.openDatabaseSync("ActivityTrackDB", "", "Database tracking sports activities", 1000000);
+ if (db.version == "0.1") {
+ db.changeVersion("0.1", "0.2", function(tx) {
+ tx.executeSql("INSERT INTO trip_log VALUES(?, ?, ?)",
+ [ "01/10/2016","Sylling - Vikersund", "53" ]);
+ }
+ });
+\endcode
\section3 db.transaction(callback(tx))
@@ -621,7 +629,10 @@ you can call \e executeSql on \e tx to read and modify the database.
If the callback throws exceptions, the transaction is rolled back.
Below you will find an example of a database transaction which catches exceptions.
-\snippet qml/localstorage/dbtransaction.js 0
+
+\quotefromfile localstorage/localstorage/Database.js
+\skipuntil dbInit()
+\printto dbGetHandle
In the example you can see an \c insert statement where values are assigned to the fields,
and the record is written into the table. That is an \c insert statement with a syntax that is usual
@@ -631,15 +642,24 @@ store them in a table.
Let's suppose a simple example where we store trips in JSON format using \c date as the unique key.
An example of a table that could be used for that purpose:
-\snippet qml/localstorage/dbtransaction.js 3
+\badcode
+ create table trip_log(date text, data text)
+\endcode
The assignment of values to a JSON object:
-\snippet qml/localstorage/dbtransaction.js 4
+\badcode
+ var obj = {description = "Vikersund - Noresund", distance = "60"}
+\endcode
In that case, the data could be saved in the following way:
-\snippet qml/localstorage/dbtransaction.js 5
+\badcode
+ db.transaction(function(tx) {
+ result = tx.executeSQL("insert into trip_log values (?,?)",
+ ["01/11/2016", JSON.stringify(obj)])
+
+\endcode
\section3 db.readTransaction(callback(tx))
@@ -664,7 +684,9 @@ May throw exception with code property SQLException.DATABASE_ERR, SQLException.S
See below for an example:
-\snippet qml/localstorage/dbtransaction.js 1
+\quotefromfile localstorage/localstorage/Database.js
+\skipto dbReadAll()
+\printto dbUpdate(Pdate
\section1 Method Documentation
@@ -690,10 +712,10 @@ class QQuickLocalStorage : public QObject
{
Q_OBJECT
public:
- QQuickLocalStorage(QObject *parent=0) : QObject(parent)
+ QQuickLocalStorage(QObject *parent=nullptr) : QObject(parent)
{
}
- ~QQuickLocalStorage() {
+ ~QQuickLocalStorage() override {
}
Q_INVOKABLE void openDatabaseSync(QQmlV4Function* args);
@@ -790,7 +812,7 @@ class QQmlLocalStoragePlugin : public QQmlExtensionPlugin
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QQmlLocalStoragePlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent)
+ QQmlLocalStoragePlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent)
{
initResources();
}
diff --git a/src/imports/models/plugin.cpp b/src/imports/models/plugin.cpp
index 5933128713..2f8a9713d2 100644
--- a/src/imports/models/plugin.cpp
+++ b/src/imports/models/plugin.cpp
@@ -77,7 +77,7 @@ class QtQmlModelsPlugin : public QQmlExtensionPlugin
Q_OBJECT
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QtQmlModelsPlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QtQmlModelsPlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QLatin1String(uri) == QLatin1String("QtQml.Models"));
diff --git a/src/imports/particles/plugin.cpp b/src/imports/particles/plugin.cpp
index f7a3472403..a04e115976 100644
--- a/src/imports/particles/plugin.cpp
+++ b/src/imports/particles/plugin.cpp
@@ -56,7 +56,7 @@ class QtQuick2ParticlesPlugin : public QQmlExtensionPlugin
Q_OBJECT
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QtQuick2ParticlesPlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QtQuick2ParticlesPlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QLatin1String(uri) == QLatin1String("QtQuick.Particles"));
diff --git a/src/imports/qtquick2/plugin.cpp b/src/imports/qtquick2/plugin.cpp
index a5b2c8c67e..147f01e81b 100644
--- a/src/imports/qtquick2/plugin.cpp
+++ b/src/imports/qtquick2/plugin.cpp
@@ -56,7 +56,7 @@ class QtQuick2Plugin : public QQmlExtensionPlugin
Q_OBJECT
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QtQuick2Plugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QtQuick2Plugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QLatin1String(uri) == QLatin1String("QtQuick"));
@@ -65,7 +65,7 @@ public:
QQmlQtQuick2Module::defineModule();
}
- ~QtQuick2Plugin()
+ ~QtQuick2Plugin() override
{
if (moduleDefined)
QQmlQtQuick2Module::undefineModule();
diff --git a/src/imports/qtquick2/plugins.qmltypes b/src/imports/qtquick2/plugins.qmltypes
index d23d6cc311..0fce98a212 100644
--- a/src/imports/qtquick2/plugins.qmltypes
+++ b/src/imports/qtquick2/plugins.qmltypes
@@ -1808,6 +1808,7 @@ Module {
Property { name: "wordSpacing"; type: "double" }
Property { name: "hintingPreference"; type: "HintingPreference" }
Property { name: "kerning"; type: "bool" }
+ Property { name: "preferShaping"; type: "bool" }
Method { name: "toString"; type: "string" }
}
Component {
@@ -3994,12 +3995,13 @@ Module {
prototype: "QQuickImplicitSizeItem"
exports: [
"QtQuick/Text 2.0",
+ "QtQuick/Text 2.10",
"QtQuick/Text 2.2",
"QtQuick/Text 2.3",
"QtQuick/Text 2.6",
"QtQuick/Text 2.9"
]
- exportMetaObjectRevisions: [0, 2, 3, 6, 9]
+ exportMetaObjectRevisions: [0, 10, 2, 3, 6, 9]
Enum {
name: "HAlignment"
values: {
@@ -4185,12 +4187,13 @@ Module {
exports: [
"QtQuick/TextEdit 2.0",
"QtQuick/TextEdit 2.1",
+ "QtQuick/TextEdit 2.10",
"QtQuick/TextEdit 2.2",
"QtQuick/TextEdit 2.3",
"QtQuick/TextEdit 2.6",
"QtQuick/TextEdit 2.7"
]
- exportMetaObjectRevisions: [0, 1, 2, 3, 6, 7]
+ exportMetaObjectRevisions: [0, 1, 10, 2, 3, 6, 7]
Enum {
name: "HAlignment"
values: {
@@ -4292,6 +4295,7 @@ Module {
Property { name: "rightPadding"; revision: 6; type: "double" }
Property { name: "bottomPadding"; revision: 6; type: "double" }
Property { name: "preeditText"; revision: 7; type: "string"; isReadonly: true }
+ Property { name: "tabStopDistance"; revision: 10; type: "double" }
Signal { name: "preeditTextChanged"; revision: 7 }
Signal { name: "contentSizeChanged" }
Signal {
@@ -4374,6 +4378,11 @@ Module {
Signal { name: "leftPaddingChanged"; revision: 6 }
Signal { name: "rightPaddingChanged"; revision: 6 }
Signal { name: "bottomPaddingChanged"; revision: 6 }
+ Signal {
+ name: "tabStopDistanceChanged"
+ revision: 10
+ Parameter { name: "distance"; type: "double" }
+ }
Method { name: "selectAll" }
Method { name: "selectWord" }
Method {
diff --git a/src/imports/settings/plugin.cpp b/src/imports/settings/plugin.cpp
index 70d24c12cd..65de78a2f1 100644
--- a/src/imports/settings/plugin.cpp
+++ b/src/imports/settings/plugin.cpp
@@ -57,7 +57,7 @@ class QmlSettingsPlugin : public QQmlExtensionPlugin
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QmlSettingsPlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QmlSettingsPlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QByteArray(uri) == QByteArray("Qt.labs.settings"));
diff --git a/src/imports/settings/qqmlsettings.cpp b/src/imports/settings/qqmlsettings.cpp
index f6040e7a64..2271774643 100644
--- a/src/imports/settings/qqmlsettings.cpp
+++ b/src/imports/settings/qqmlsettings.cpp
@@ -254,18 +254,15 @@ public:
void _q_propertyChanged();
QVariant readProperty(const QMetaProperty &property) const;
- QQmlSettings *q_ptr;
- int timerId;
- bool initialized;
+ QQmlSettings *q_ptr = nullptr;
+ int timerId = 0;
+ bool initialized = false;
QString category;
mutable QPointer<QSettings> settings;
QHash<const char *, QVariant> changedProperties;
};
-QQmlSettingsPrivate::QQmlSettingsPrivate()
- : q_ptr(0), timerId(0), initialized(false)
-{
-}
+QQmlSettingsPrivate::QQmlSettingsPrivate() {}
QSettings *QQmlSettingsPrivate::instance() const
{
diff --git a/src/imports/shapes/plugin.cpp b/src/imports/shapes/plugin.cpp
index c509d28e33..f0e66479b6 100644
--- a/src/imports/shapes/plugin.cpp
+++ b/src/imports/shapes/plugin.cpp
@@ -47,7 +47,7 @@ static void initResources()
#ifdef QT_STATIC
Q_INIT_RESOURCE(qmake_QtQuick_Shapes);
#endif
- Q_INIT_RESOURCE(shapes);
+ Q_INIT_RESOURCE(qtquickshapesplugin);
}
QT_BEGIN_NAMESPACE
@@ -58,7 +58,7 @@ class QmlShapesPlugin : public QQmlExtensionPlugin
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QmlShapesPlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QmlShapesPlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QByteArray(uri) == QByteArray("QtQuick.Shapes"));
@@ -68,6 +68,12 @@ public:
qmlRegisterType<QQuickShapeLinearGradient>(uri, 1, 0, "LinearGradient");
qmlRegisterType<QQuickShapeRadialGradient>(uri, 1, 0, "RadialGradient");
qmlRegisterType<QQuickShapeConicalGradient>(uri, 1, 0, "ConicalGradient");
+
+ // Auto-increment the import to stay in sync with ALL future QtQuick minor versions
+ qmlRegisterModule(uri, 1, QT_VERSION_MINOR);
+
+ // revision in Qt 5.11: added containsMode property
+ qmlRegisterType<QQuickShape, 11>(uri, 1, 11, "Shape");
}
};
diff --git a/src/imports/shapes/plugins.qmltypes b/src/imports/shapes/plugins.qmltypes
index b8a7c532e0..a140644d6d 100644
--- a/src/imports/shapes/plugins.qmltypes
+++ b/src/imports/shapes/plugins.qmltypes
@@ -4,7 +4,7 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable QtQuick.Shapes 1.0'
+// 'qmlplugindump -nonrelocatable QtQuick.Shapes 1.11'
Module {
dependencies: ["QtQuick 2.8"]
@@ -12,8 +12,8 @@ Module {
name: "QQuickShape"
defaultProperty: "data"
prototype: "QQuickItem"
- exports: ["QtQuick.Shapes/Shape 1.0"]
- exportMetaObjectRevisions: [0]
+ exports: ["QtQuick.Shapes/Shape 1.0", "QtQuick.Shapes/Shape 1.11"]
+ exportMetaObjectRevisions: [0, 11]
Enum {
name: "RendererType"
values: {
@@ -31,11 +31,31 @@ Module {
"Processing": 2
}
}
+ Enum {
+ name: "ContainsMode"
+ values: {
+ "BoundingRectContains": 0,
+ "FillContains": 1
+ }
+ }
Property { name: "rendererType"; type: "RendererType"; isReadonly: true }
Property { name: "asynchronous"; type: "bool" }
Property { name: "vendorExtensionsEnabled"; type: "bool" }
Property { name: "status"; type: "Status"; isReadonly: true }
+ Property { name: "containsMode"; revision: 11; type: "ContainsMode" }
Property { name: "data"; type: "QObject"; isList: true; isReadonly: true }
+ Signal { name: "rendererChanged" }
+ Signal { name: "containsModeChanged"; revision: 11 }
+ }
+ Component {
+ name: "QQuickShapeConicalGradient"
+ defaultProperty: "stops"
+ prototype: "QQuickShapeGradient"
+ exports: ["QtQuick.Shapes/ConicalGradient 1.0"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "centerX"; type: "double" }
+ Property { name: "centerY"; type: "double" }
+ Property { name: "angle"; type: "double" }
}
Component {
name: "QQuickShapeGradient"
@@ -114,4 +134,17 @@ Module {
Property { name: "fillGradient"; type: "QQuickShapeGradient"; isPointer: true }
Signal { name: "shapePathChanged" }
}
+ Component {
+ name: "QQuickShapeRadialGradient"
+ defaultProperty: "stops"
+ prototype: "QQuickShapeGradient"
+ exports: ["QtQuick.Shapes/RadialGradient 1.0"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "centerX"; type: "double" }
+ Property { name: "centerY"; type: "double" }
+ Property { name: "centerRadius"; type: "double" }
+ Property { name: "focalX"; type: "double" }
+ Property { name: "focalY"; type: "double" }
+ Property { name: "focalRadius"; type: "double" }
+ }
}
diff --git a/src/imports/shapes/qquickshape.cpp b/src/imports/shapes/qquickshape.cpp
index 6a76743242..067a54736f 100644
--- a/src/imports/shapes/qquickshape.cpp
+++ b/src/imports/shapes/qquickshape.cpp
@@ -46,11 +46,14 @@
#include <private/qquicksvgparser_p.h>
#include <QtGui/private/qdrawhelper_p.h>
#include <QOpenGLFunctions>
+#include <QLoggingCategory>
QT_BEGIN_NAMESPACE
+Q_LOGGING_CATEGORY(QQSHAPE_LOG_TIME_DIRTY_SYNC, "qt.shape.time.sync")
+
/*!
- \qmlmodule QtQuick.Shapes 1.0
+ \qmlmodule QtQuick.Shapes 1.11
\title Qt Quick Shapes QML Types
\ingroup qmlmodules
\brief Provides QML types for drawing stroked and filled shapes.
@@ -58,7 +61,7 @@ QT_BEGIN_NAMESPACE
To use the types in this module, import the module with the following line:
\badcode
- import QtQuick.Shapes 1.0
+ import QtQuick.Shapes 1.11
\endcode
*/
@@ -139,6 +142,8 @@ QQuickShapeStrokeFillParams::QQuickShapeStrokeFillParams()
QQuickShapePathPrivate::QQuickShapePathPrivate()
: dirty(DirtyAll)
{
+ // Set this QQuickPath to be a ShapePath
+ isShapePath = true;
}
QQuickShapePath::QQuickShapePath(QObject *parent)
@@ -628,12 +633,7 @@ void QQuickShapePath::resetFillGradient()
*/
QQuickShapePrivate::QQuickShapePrivate()
- : spChanged(false),
- rendererType(QQuickShape::UnknownRenderer),
- async(false),
- status(QQuickShape::Null),
- renderer(nullptr),
- enableVendorExts(true)
+ : effectRefCount(0)
{
}
@@ -781,6 +781,63 @@ QQuickShape::Status QQuickShape::status() const
return d->status;
}
+/*!
+ \qmlproperty enumeration QtQuick.Shapes::Shape::containsMode
+ \since QtQuick.Shapes 1.11
+
+ This property determines the definition of \l {QQuickItem::contains()}{contains()}
+ for the Shape. It is useful in case you add
+ \l {Qt Quick Pointer Handlers QML Types}{Pointer Handlers} and you
+ want to react only when the mouse or touchpoint is fully inside the Shape.
+
+ \value Shape.BoundingRectContains
+ The default implementation of \l QQuickItem::contains() checks only
+ whether the given point is inside the rectangular bounding box. This is
+ the most efficient implementation, which is why it's the default.
+
+ \value Shape.FillContains
+ Check whether the interior (the part that would be filled if you are
+ rendering it with fill) of any \l ShapePath that makes up this Shape
+ contains the given point. The more complex and numerous ShapePaths you
+ add, the less efficient this is to check, which can potentially slow
+ down event delivery in your application. So it should be used with care.
+
+ One way to speed up the \c FillContains check is to generate an approximate
+ outline with as few points as possible, place that in a transparent Shape
+ on top, and add your Pointer Handlers to that, so that the containment
+ check is cheaper during event delivery.
+*/
+QQuickShape::ContainsMode QQuickShape::containsMode() const
+{
+ Q_D(const QQuickShape);
+ return d->containsMode;
+}
+
+void QQuickShape::setContainsMode(QQuickShape::ContainsMode containsMode)
+{
+ Q_D(QQuickShape);
+ if (d->containsMode == containsMode)
+ return;
+
+ d->containsMode = containsMode;
+ emit containsModeChanged();
+}
+
+bool QQuickShape::contains(const QPointF &point) const
+{
+ Q_D(const QQuickShape);
+ switch (d->containsMode) {
+ case BoundingRectContains:
+ return QQuickItem::contains(point);
+ case FillContains:
+ for (QQuickShapePath *path : d->sp) {
+ if (path->path().contains(point))
+ return true;
+ }
+ }
+ return false;
+}
+
static void vpe_append(QQmlListProperty<QObject> *property, QObject *obj)
{
QQuickShape *item = static_cast<QQuickShape *>(property->object);
@@ -854,10 +911,12 @@ void QQuickShape::updatePolish()
{
Q_D(QQuickShape);
- if (!d->spChanged)
+ const int currentEffectRefCount = d->extra.isAllocated() ? d->extra->recursiveEffectRefCount : 0;
+ if (!d->spChanged && currentEffectRefCount <= d->effectRefCount)
return;
d->spChanged = false;
+ d->effectRefCount = currentEffectRefCount;
if (!d->renderer) {
d->createRenderer();
@@ -869,7 +928,7 @@ void QQuickShape::updatePolish()
// endSync() is where expensive calculations may happen (or get kicked off
// on worker threads), depending on the backend. Therefore do this only
// when the item is visible.
- if (isVisible())
+ if (isVisible() || d->effectRefCount > 0)
d->sync();
update();
@@ -968,18 +1027,26 @@ QSGNode *QQuickShapePrivate::createNode()
return node;
}
-static void q_asyncShapeReady(void *data)
+void QQuickShapePrivate::asyncShapeReady(void *data)
{
QQuickShapePrivate *self = static_cast<QQuickShapePrivate *>(data);
self->setStatus(QQuickShape::Ready);
+ if (self->syncTimingActive)
+ qDebug("[Shape %p] [%d] [dirty=0x%x] async update took %lld ms",
+ self->q_func(), self->syncTimeCounter, self->syncTimingTotalDirty, self->syncTimer.elapsed());
}
void QQuickShapePrivate::sync()
{
+ syncTimingTotalDirty = 0;
+ syncTimingActive = QQSHAPE_LOG_TIME_DIRTY_SYNC().isDebugEnabled();
+ if (syncTimingActive)
+ syncTimer.start();
+
const bool useAsync = async && renderer->flags().testFlag(QQuickAbstractPathRenderer::SupportsAsync);
if (useAsync) {
setStatus(QQuickShape::Processing);
- renderer->setAsyncCallback(q_asyncShapeReady, this);
+ renderer->setAsyncCallback(asyncShapeReady, this);
}
const int count = sp.count();
@@ -988,6 +1055,7 @@ void QQuickShapePrivate::sync()
for (int i = 0; i < count; ++i) {
QQuickShapePath *p = sp[i];
int &dirty(QQuickShapePathPrivate::get(p)->dirty);
+ syncTimingTotalDirty |= dirty;
if (dirty & QQuickShapePathPrivate::DirtyPath)
renderer->setPath(i, p);
@@ -1011,10 +1079,19 @@ void QQuickShapePrivate::sync()
dirty = 0;
}
+ if (syncTimingTotalDirty)
+ ++syncTimeCounter;
+ else
+ syncTimingActive = false;
+
renderer->endSync(useAsync);
- if (!useAsync)
+ if (!useAsync) {
setStatus(QQuickShape::Ready);
+ if (syncTimingActive)
+ qDebug("[Shape %p] [%d] [dirty=0x%x] update took %lld ms",
+ q_func(), syncTimeCounter, syncTimingTotalDirty, syncTimer.elapsed());
+ }
}
// ***** gradient support *****
@@ -1327,7 +1404,7 @@ void QQuickShapeRadialGradient::setFocalRadius(qreal v)
Conical gradients interpolate colors counter-clockwise around a center
point in Shape items.
- \note The \l{ShapeGradient.spread}{spread mode} setting has no effect for
+ \note The \l{ShapeGradient::spread}{spread mode} setting has no effect for
conical gradients.
\note ConicalGradient is only supported in combination with Shape items. It
diff --git a/src/imports/shapes/qquickshape_p.h b/src/imports/shapes/qquickshape_p.h
index 365d9644c7..1dfeaf9228 100644
--- a/src/imports/shapes/qquickshape_p.h
+++ b/src/imports/shapes/qquickshape_p.h
@@ -303,6 +303,7 @@ class QQuickShape : public QQuickItem
Q_PROPERTY(bool asynchronous READ asynchronous WRITE setAsynchronous NOTIFY asynchronousChanged)
Q_PROPERTY(bool vendorExtensionsEnabled READ vendorExtensionsEnabled WRITE setVendorExtensionsEnabled NOTIFY vendorExtensionsEnabledChanged)
Q_PROPERTY(Status status READ status NOTIFY statusChanged)
+ Q_PROPERTY(ContainsMode containsMode READ containsMode WRITE setContainsMode NOTIFY containsModeChanged REVISION 11)
Q_PROPERTY(QQmlListProperty<QObject> data READ data)
Q_CLASSINFO("DefaultProperty", "data")
@@ -322,6 +323,12 @@ public:
};
Q_ENUM(Status)
+ enum ContainsMode {
+ BoundingRectContains,
+ FillContains
+ };
+ Q_ENUM(ContainsMode)
+
QQuickShape(QQuickItem *parent = nullptr);
~QQuickShape();
@@ -335,6 +342,11 @@ public:
Status status() const;
+ ContainsMode containsMode() const;
+ void setContainsMode(ContainsMode containsMode);
+
+ bool contains(const QPointF &point) const override;
+
QQmlListProperty<QObject> data();
protected:
@@ -349,6 +361,7 @@ Q_SIGNALS:
void asynchronousChanged();
void vendorExtensionsEnabledChanged();
void statusChanged();
+ Q_REVISION(11) void containsModeChanged();
private:
Q_DISABLE_COPY(QQuickShape)
diff --git a/src/imports/shapes/qquickshape_p_p.h b/src/imports/shapes/qquickshape_p_p.h
index bbe9a81d4a..ef2775885e 100644
--- a/src/imports/shapes/qquickshape_p_p.h
+++ b/src/imports/shapes/qquickshape_p_p.h
@@ -56,6 +56,7 @@
#include <QPainterPath>
#include <QColor>
#include <QBrush>
+#include <QElapsedTimer>
#include <private/qopenglcontext_p.h>
QT_BEGIN_NAMESPACE
@@ -167,13 +168,21 @@ public:
static QQuickShapePrivate *get(QQuickShape *item) { return item->d_func(); }
- bool spChanged;
- QQuickShape::RendererType rendererType;
- bool async;
- QQuickShape::Status status;
- QQuickAbstractPathRenderer *renderer;
+ static void asyncShapeReady(void *data);
+
+ int effectRefCount;
QVector<QQuickShapePath *> sp;
- bool enableVendorExts;
+ QElapsedTimer syncTimer;
+ QQuickAbstractPathRenderer *renderer = nullptr;
+ int syncTimingTotalDirty = 0;
+ int syncTimeCounter = 0;
+ QQuickShape::Status status = QQuickShape::Null;
+ QQuickShape::RendererType rendererType = QQuickShape::UnknownRenderer;
+ QQuickShape::ContainsMode containsMode = QQuickShape::BoundingRectContains;
+ bool spChanged = false;
+ bool async = false;
+ bool enableVendorExts = true;
+ bool syncTimingActive = false;
};
#if QT_CONFIG(opengl)
diff --git a/src/imports/shapes/qquickshapegenericrenderer.cpp b/src/imports/shapes/qquickshapegenericrenderer.cpp
index 44253a2596..4933aab69e 100644
--- a/src/imports/shapes/qquickshapegenericrenderer.cpp
+++ b/src/imports/shapes/qquickshapegenericrenderer.cpp
@@ -455,14 +455,14 @@ void QQuickShapeGenericRenderer::triangulateStroke(const QPainterPath &path,
stroker.setInvScale(inverseScale);
if (pen.style() == Qt::SolidLine) {
- stroker.process(vp, pen, clip, 0);
+ stroker.process(vp, pen, clip, nullptr);
} else {
QDashedStrokeProcessor dashStroker;
dashStroker.setInvScale(inverseScale);
- dashStroker.process(vp, pen, clip, 0);
+ dashStroker.process(vp, pen, clip, nullptr);
QVectorPath dashStroke(dashStroker.points(), dashStroker.elementCount(),
dashStroker.elementTypes(), 0);
- stroker.process(dashStroke, pen, clip, 0);
+ stroker.process(dashStroke, pen, clip, nullptr);
}
if (!stroker.vertexCount()) {
diff --git a/src/imports/shapes/qquickshapenvprrenderer.cpp b/src/imports/shapes/qquickshapenvprrenderer.cpp
index 88f367fe70..51af0d8961 100644
--- a/src/imports/shapes/qquickshapenvprrenderer.cpp
+++ b/src/imports/shapes/qquickshapenvprrenderer.cpp
@@ -986,7 +986,7 @@ void QQuickNvprBlitter::texturedQuad(GLuint textureId, const QSize &size,
m_program->enableAttributeArray(0);
m_program->enableAttributeArray(1);
- f->glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 4 * sizeof(GLfloat), 0);
+ f->glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 4 * sizeof(GLfloat), nullptr);
f->glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 4 * sizeof(GLfloat), (const void *) (2 * sizeof(GLfloat)));
f->glBindTexture(GL_TEXTURE_2D, textureId);
diff --git a/src/imports/shapes/qquickshapesoftwarerenderer.cpp b/src/imports/shapes/qquickshapesoftwarerenderer.cpp
index ed13afbc7e..0f5c3604b5 100644
--- a/src/imports/shapes/qquickshapesoftwarerenderer.cpp
+++ b/src/imports/shapes/qquickshapesoftwarerenderer.cpp
@@ -266,7 +266,7 @@ void QQuickShapeSoftwareRenderNode::render(const RenderState *state)
QSGRenderNode::StateFlags QQuickShapeSoftwareRenderNode::changedStates() const
{
- return 0;
+ return nullptr;
}
QSGRenderNode::RenderingFlags QQuickShapeSoftwareRenderNode::flags() const
diff --git a/src/imports/shapes/shapes.qrc b/src/imports/shapes/qtquickshapesplugin.qrc
index f139861693..f139861693 100644
--- a/src/imports/shapes/shapes.qrc
+++ b/src/imports/shapes/qtquickshapesplugin.qrc
diff --git a/src/imports/shapes/shapes.pro b/src/imports/shapes/shapes.pro
index 60cc61e974..4d6e9508af 100644
--- a/src/imports/shapes/shapes.pro
+++ b/src/imports/shapes/shapes.pro
@@ -1,7 +1,7 @@
CXX_MODULE = qml
TARGET = qmlshapesplugin
TARGETPATH = QtQuick/Shapes
-IMPORT_VERSION = 1.0
+IMPORT_VERSION = 1.11
QT = core gui-private qml quick-private
@@ -28,6 +28,6 @@ qtConfig(opengl) {
qquickshapenvprrenderer.cpp
}
-RESOURCES += shapes.qrc
+RESOURCES += qtquickshapesplugin.qrc
load(qml_plugin)
diff --git a/src/imports/sharedimage/plugin.cpp b/src/imports/sharedimage/plugin.cpp
index 53e95ef21a..b75e38e303 100644
--- a/src/imports/sharedimage/plugin.cpp
+++ b/src/imports/sharedimage/plugin.cpp
@@ -106,7 +106,7 @@ class QtQuickSharedImagePlugin : public QQmlExtensionPlugin
Q_OBJECT
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QtQuickSharedImagePlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) {}
+ QtQuickSharedImagePlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) {}
void registerTypes(const char *uri) override
{
diff --git a/src/imports/sharedimage/plugins.qmltypes b/src/imports/sharedimage/plugins.qmltypes
new file mode 100644
index 0000000000..46fa24df1a
--- /dev/null
+++ b/src/imports/sharedimage/plugins.qmltypes
@@ -0,0 +1,11 @@
+import QtQuick.tooling 1.2
+
+// This file describes the plugin-supplied types contained in the library.
+// It is used for QML tooling purposes only.
+//
+// This file was auto-generated by:
+// 'qmlplugindump -nonrelocatable Qt.labs.sharedimage 1.0'
+
+Module {
+ dependencies: ["QtQuick 2.8"]
+}
diff --git a/src/imports/sharedimage/qsharedimageloader.cpp b/src/imports/sharedimage/qsharedimageloader.cpp
index fb96a79187..4672ded376 100644
--- a/src/imports/sharedimage/qsharedimageloader.cpp
+++ b/src/imports/sharedimage/qsharedimageloader.cpp
@@ -88,9 +88,7 @@ class QSharedImageLoaderPrivate : public QObjectPrivate
Q_DECLARE_PUBLIC(QSharedImageLoader)
public:
- QSharedImageLoaderPrivate()
- : QObjectPrivate()
- {}
+ QSharedImageLoaderPrivate() {}
QImage load(const QString &path, QSharedImageLoader::ImageParameters *params);
@@ -117,7 +115,7 @@ void QSharedImageLoaderPrivate::storeImageToMem(void *data, const QImage &img)
h->format = img.format();
uchar *p = static_cast<uchar *>(data) + sizeof(SharedImageHeader);
- memcpy(p, img.constBits(), img.byteCount());
+ memcpy(p, img.constBits(), img.sizeInBytes());
}
@@ -174,8 +172,11 @@ QImage QSharedImageLoaderPrivate::load(const QString &path, QSharedImageLoader::
QImage img = q->loadFile(path, params);
if (img.isNull())
return nil;
- int size = sizeof(SharedImageHeader) + img.byteCount();
- if (shm->create(size)) {
+ size_t size = sizeof(SharedImageHeader) + img.sizeInBytes();
+ if (size > std::numeric_limits<int>::max()) {
+ qCDebug(lcSharedImage) << "Image" << path << "to large to load";
+ return nil;
+ } else if (shm->create(int(size))) {
qCDebug(lcSharedImage) << "Created new shm segment of size" << size << "for image" << path;
if (!shm->lock()) {
qCDebug(lcSharedImage) << "Lock1 failed!?" << shm->errorString();
diff --git a/src/imports/statemachine/plugin.cpp b/src/imports/statemachine/plugin.cpp
index 7308df8964..1357743126 100644
--- a/src/imports/statemachine/plugin.cpp
+++ b/src/imports/statemachine/plugin.cpp
@@ -62,7 +62,7 @@ class QtQmlStateMachinePlugin : public QQmlExtensionPlugin
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QtQmlStateMachinePlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QtQmlStateMachinePlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
qmlRegisterType<State>(uri, 1, 0, "State");
diff --git a/src/imports/statemachine/signaltransition.cpp b/src/imports/statemachine/signaltransition.cpp
index aaf32f6d19..63a969c0e8 100644
--- a/src/imports/statemachine/signaltransition.cpp
+++ b/src/imports/statemachine/signaltransition.cpp
@@ -109,7 +109,7 @@ void SignalTransition::setSignal(const QJSValue &signal)
m_signal = signal;
- QV4::ExecutionEngine *jsEngine = QV8Engine::getV4(QQmlEngine::contextForObject(this)->engine());
+ QV4::ExecutionEngine *jsEngine = QQmlEngine::contextForObject(this)->engine()->handle();
QV4::Scope scope(jsEngine);
QObject *sender;
@@ -163,13 +163,13 @@ void SignalTransition::connectTriggered()
QObject *target = senderObject();
QQmlData *ddata = QQmlData::get(this);
- QQmlContextData *ctxtdata = ddata ? ddata->outerContext : 0;
+ QQmlContextData *ctxtdata = ddata ? ddata->outerContext : nullptr;
Q_ASSERT(m_bindings.count() == 1);
const QV4::CompiledData::Binding *binding = m_bindings.at(0);
Q_ASSERT(binding->type == QV4::CompiledData::Binding::Type_Script);
- QV4::ExecutionEngine *jsEngine = QV8Engine::getV4(QQmlEngine::contextForObject(this)->engine());
+ QV4::ExecutionEngine *jsEngine = QQmlEngine::contextForObject(this)->engine()->handle();
QV4::Scope scope(jsEngine);
QV4::Scoped<QV4::QObjectMethod> qobjectSignal(scope, QJSValuePrivate::convertedToValue(jsEngine, m_signal));
Q_ASSERT(qobjectSignal);
@@ -178,7 +178,7 @@ void SignalTransition::connectTriggered()
QQmlBoundSignalExpression *expression = ctxtdata ?
new QQmlBoundSignalExpression(target, signalIndex,
- ctxtdata, this, m_compilationUnit->runtimeFunctions[binding->value.compiledScriptIndex]) : 0;
+ ctxtdata, this, m_compilationUnit->runtimeFunctions[binding->value.compiledScriptIndex]) : nullptr;
if (expression)
expression->setNotifyOnValueChanged(false);
m_signalExpression = expression;
diff --git a/src/imports/statemachine/state.cpp b/src/imports/statemachine/state.cpp
index 2467039d01..af76087256 100644
--- a/src/imports/statemachine/state.cpp
+++ b/src/imports/statemachine/state.cpp
@@ -50,7 +50,7 @@ State::State(QState *parent)
void State::componentComplete()
{
- if (this->machine() == NULL) {
+ if (this->machine() == nullptr) {
static bool once = false;
if (!once) {
once = true;
diff --git a/src/imports/statemachine/statemachine.cpp b/src/imports/statemachine/statemachine.cpp
index 7c8dcbc6b6..ca6c59b6ac 100644
--- a/src/imports/statemachine/statemachine.cpp
+++ b/src/imports/statemachine/statemachine.cpp
@@ -68,7 +68,7 @@ void StateMachine::setRunning(bool running)
void StateMachine::componentComplete()
{
- if (QStateMachine::initialState() == NULL && childMode() == QState::ExclusiveStates)
+ if (QStateMachine::initialState() == nullptr && childMode() == QState::ExclusiveStates)
qmlWarning(this) << "No initial state set for StateMachine";
// Everything is proper setup, now start the state-machine if we got
diff --git a/src/imports/testlib/SignalSpy.qml b/src/imports/testlib/SignalSpy.qml
index 8a8e844a21..85908091a0 100644
--- a/src/imports/testlib/SignalSpy.qml
+++ b/src/imports/testlib/SignalSpy.qml
@@ -74,7 +74,7 @@ import QtTest 1.1
synchronously. For asynchronous signals, the wait() method can be
used to block the test until the signal occurs (or a timeout expires).
- \sa {QtTest::TestCase}{TestCase}, {Qt Quick Test Reference Documentation}
+ \sa {QtTest::TestCase}{TestCase}, {Qt Quick Test}
*/
Item {
diff --git a/src/imports/testlib/TestCase.qml b/src/imports/testlib/TestCase.qml
index 0e7e09c65c..8e9b016444 100644
--- a/src/imports/testlib/TestCase.qml
+++ b/src/imports/testlib/TestCase.qml
@@ -39,7 +39,7 @@
import QtQuick 2.0
import QtQuick.Window 2.0 // used for qtest_verifyItem
-import QtTest 1.1
+import QtTest 1.2
import "testlogger.js" as TestLogger
import Qt.test.qtestroot 1.0
@@ -57,7 +57,7 @@ import Qt.test.qtestroot 1.0
\code
import QtQuick 2.0
- import QtTest 1.0
+ import QtTest 1.2
TestCase {
name: "MathTests"
@@ -108,7 +108,7 @@ import Qt.test.qtestroot 1.0
\code
import QtQuick 2.0
- import QtTest 1.1
+ import QtTest 1.2
TestCase {
name: "DataTests"
@@ -260,7 +260,7 @@ import Qt.test.qtestroot 1.0
For objects that are created via the \l {Component::}{createObject()} function
of \l Component, the \l createTemporaryObject() function can be used.
- \sa {QtTest::SignalSpy}{SignalSpy}, {Qt Quick Test Reference Documentation}
+ \sa {QtTest::SignalSpy}{SignalSpy}, {Qt Quick Test}
*/
@@ -1212,6 +1212,26 @@ Item {
}
/*!
+ \since 5.10
+ \qmlmethod TestCase::keySequence(keySequence)
+
+ Simulates typing of \a keySequence. The key sequence can be set
+ to one of the \l{QKeySequence::StandardKey}{standard keyboard shortcuts}, or
+ it can be described with a string containing a sequence of up to four key
+ presses.
+
+ Each event shall be sent to the TestCase window or, in case of multiple windows,
+ to the current active window. See \l QGuiApplication::focusWindow() for more details.
+
+ \sa keyPress(), keyRelease(), {GNU Emacs Style Key Sequences},
+ {QtQuick::Shortcut::sequence}{Shortcut.sequence}
+ */
+ function keySequence(keySequence) {
+ if (!qtest_events.keySequence(keySequence))
+ qtest_fail("window not shown", 2)
+ }
+
+ /*!
\qmlmethod TestCase::mousePress(item, x = item.width / 2, y = item.height / 2, button = Qt.LeftButton, modifiers = Qt.NoModifier, delay = -1)
Simulates pressing a mouse \a button with an optional \a modifier
diff --git a/src/imports/testlib/main.cpp b/src/imports/testlib/main.cpp
index 2dbe8e08dc..45e9bd2cf6 100644
--- a/src/imports/testlib/main.cpp
+++ b/src/imports/testlib/main.cpp
@@ -69,11 +69,11 @@ class QuickTestUtil : public QObject
Q_PROPERTY(bool printAvailableFunctions READ printAvailableFunctions NOTIFY printAvailableFunctionsChanged)
Q_PROPERTY(int dragThreshold READ dragThreshold NOTIFY dragThresholdChanged)
public:
- QuickTestUtil(QObject *parent = 0)
+ QuickTestUtil(QObject *parent = nullptr)
:QObject(parent)
{}
- ~QuickTestUtil()
+ ~QuickTestUtil() override
{}
bool printAvailableFunctions() const
{
@@ -103,7 +103,7 @@ public Q_SLOTS:
}
QQmlEngine *engine = qmlEngine(this);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine->handle());
+ QV4::ExecutionEngine *v4 = engine->handle();
QV4::Scope scope(v4);
QV4::ScopedValue s(scope, v4->newString(name));
return QQmlV4Handle(s);
@@ -116,7 +116,7 @@ public Q_SLOTS:
QQmlV4Handle callerFile(int frameIndex = 0) const
{
QQmlEngine *engine = qmlEngine(this);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine->handle());
+ QV4::ExecutionEngine *v4 = engine->handle();
QV4::Scope scope(v4);
QVector<QV4::StackFrame> stack = v4->stackTrace(frameIndex + 2);
@@ -129,7 +129,7 @@ public Q_SLOTS:
int callerLine(int frameIndex = 0) const
{
QQmlEngine *engine = qmlEngine(this);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine->handle());
+ QV4::ExecutionEngine *v4 = engine->handle();
QVector<QV4::StackFrame> stack = v4->stackTrace(frameIndex + 2);
if (stack.size() > frameIndex + 1)
@@ -150,13 +150,14 @@ class QTestQmlModule : public QQmlExtensionPlugin
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QTestQmlModule(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QTestQmlModule(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QLatin1String(uri) == QLatin1String("QtTest"));
qmlRegisterType<QuickTestResult, 0>(uri,1,0,"TestResult");
qmlRegisterType<QuickTestResult, 1>(uri,1,1,"TestResult");
qmlRegisterType<QuickTestEvent>(uri,1,0,"TestEvent");
+ qmlRegisterType<QuickTestEvent>(uri,1,2,"TestEvent");
qmlRegisterType<QuickTestUtil>(uri,1,0,"TestUtil");
qmlRegisterType<QQuickTouchEventSequence>();
}
diff --git a/src/imports/testlib/plugins.qmltypes b/src/imports/testlib/plugins.qmltypes
index 5d7ca51adc..7f3140d86b 100644
--- a/src/imports/testlib/plugins.qmltypes
+++ b/src/imports/testlib/plugins.qmltypes
@@ -7,7 +7,7 @@ import QtQuick.tooling 1.2
// 'qmlplugindump -nonrelocatable -noforceqtquick QtTest 1.2'
Module {
- dependencies: ["QtQuick 2.0"]
+ dependencies: ["QtQuick 2.0", "QtQuick.Window 2.0"]
Component {
name: "QQuickTouchEventSequence"
prototype: "QObject"
@@ -45,8 +45,8 @@ Module {
Component {
name: "QuickTestEvent"
prototype: "QObject"
- exports: ["QtTest/TestEvent 1.0"]
- exportMetaObjectRevisions: [0]
+ exports: ["QtTest/TestEvent 1.0", "QtTest/TestEvent 1.2"]
+ exportMetaObjectRevisions: [0, 0]
Property { name: "defaultMouseDelay"; type: "int"; isReadonly: true }
Method {
name: "keyPress"
@@ -91,6 +91,12 @@ Module {
Parameter { name: "delay"; type: "int" }
}
Method {
+ name: "keySequence"
+ revision: 2
+ type: "bool"
+ Parameter { name: "keySequence"; type: "QVariant" }
+ }
+ Method {
name: "mousePress"
type: "bool"
Parameter { name: "item"; type: "QObject"; isPointer: true }
diff --git a/src/imports/testlib/qmldir b/src/imports/testlib/qmldir
index e5757f6a88..be9039abbb 100644
--- a/src/imports/testlib/qmldir
+++ b/src/imports/testlib/qmldir
@@ -5,3 +5,4 @@ typeinfo plugins.qmltypes
TestCase 1.0 TestCase.qml
TestCase 1.2 TestCase.qml
SignalSpy 1.0 SignalSpy.qml
+depends QtQuick.Window 2.0
diff --git a/src/imports/window/plugin.cpp b/src/imports/window/plugin.cpp
index c4ea9a1d04..4e6eedf326 100644
--- a/src/imports/window/plugin.cpp
+++ b/src/imports/window/plugin.cpp
@@ -72,7 +72,7 @@ class QtQuick2WindowPlugin : public QQmlExtensionPlugin
Q_OBJECT
Q_PLUGIN_METADATA(IID QQmlExtensionInterface_iid)
public:
- QtQuick2WindowPlugin(QObject *parent = 0) : QQmlExtensionPlugin(parent) { initResources(); }
+ QtQuick2WindowPlugin(QObject *parent = nullptr) : QQmlExtensionPlugin(parent) { initResources(); }
void registerTypes(const char *uri) override
{
Q_ASSERT(QLatin1String(uri) == QLatin1String("QtQuick.Window"));
diff --git a/src/imports/window/plugins.qmltypes b/src/imports/window/plugins.qmltypes
index cea2a910a7..4ae23a093e 100644
--- a/src/imports/window/plugins.qmltypes
+++ b/src/imports/window/plugins.qmltypes
@@ -4,7 +4,7 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable QtQuick.Window 2.3'
+// 'qmlplugindump -nonrelocatable QtQuick.Window 2.10'
Module {
dependencies: ["QtQuick 2.8"]
@@ -43,10 +43,16 @@ Module {
Component {
name: "QQuickScreenInfo"
prototype: "QObject"
- exports: ["QtQuick.Window/ScreenInfo 2.3"]
+ exports: [
+ "QtQuick.Window/ScreenInfo 2.10",
+ "QtQuick.Window/ScreenInfo 2.3"
+ ]
isCreatable: false
- exportMetaObjectRevisions: [2]
+ exportMetaObjectRevisions: [10, 2]
Property { name: "name"; type: "string"; isReadonly: true }
+ Property { name: "manufacturer"; revision: 10; type: "string"; isReadonly: true }
+ Property { name: "model"; revision: 10; type: "string"; isReadonly: true }
+ Property { name: "serialNumber"; revision: 10; type: "string"; isReadonly: true }
Property { name: "width"; type: "int"; isReadonly: true }
Property { name: "height"; type: "int"; isReadonly: true }
Property { name: "desktopAvailableWidth"; type: "int"; isReadonly: true }
@@ -58,6 +64,9 @@ Module {
Property { name: "orientation"; type: "Qt::ScreenOrientation"; isReadonly: true }
Property { name: "virtualX"; revision: 1; type: "int"; isReadonly: true }
Property { name: "virtualY"; revision: 1; type: "int"; isReadonly: true }
+ Signal { name: "manufacturerChanged"; revision: 10 }
+ Signal { name: "modelChanged"; revision: 10 }
+ Signal { name: "serialNumberChanged"; revision: 10 }
Signal { name: "desktopGeometryChanged" }
Signal { name: "virtualXChanged"; revision: 1 }
Signal { name: "virtualYChanged"; revision: 1 }
@@ -74,6 +83,13 @@ Module {
"ContextNotAvailable": 1
}
}
+ Enum {
+ name: "TextRenderType"
+ values: {
+ "QtTextRendering": 0,
+ "NativeTextRendering": 1
+ }
+ }
Property { name: "data"; type: "QObject"; isList: true; isReadonly: true }
Property { name: "color"; type: "QColor" }
Property { name: "contentItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
@@ -296,6 +312,17 @@ Module {
Parameter { name: "arg"; type: "int" }
}
Method {
+ name: "setGeometry"
+ Parameter { name: "posx"; type: "int" }
+ Parameter { name: "posy"; type: "int" }
+ Parameter { name: "w"; type: "int" }
+ Parameter { name: "h"; type: "int" }
+ }
+ Method {
+ name: "setGeometry"
+ Parameter { name: "rect"; type: "QRect" }
+ }
+ Method {
name: "setMinimumWidth"
Parameter { name: "w"; type: "int" }
}
diff --git a/src/imports/xmllistmodel/qqmlxmllistmodel.cpp b/src/imports/xmllistmodel/qqmlxmllistmodel.cpp
index fc9f73a881..d14810a01b 100644
--- a/src/imports/xmllistmodel/qqmlxmllistmodel.cpp
+++ b/src/imports/xmllistmodel/qqmlxmllistmodel.cpp
@@ -923,8 +923,7 @@ QQmlV4Handle QQuickXmlListModel::get(int index) const
return QQmlV4Handle(Encode::undefined());
QQmlEngine *engine = qmlContext(this)->engine();
- QV8Engine *v8engine = QQmlEnginePrivate::getV8Engine(engine);
- ExecutionEngine *v4engine = QV8Engine::getV4(v8engine);
+ ExecutionEngine *v4engine = engine->handle();
Scope scope(v4engine);
Scoped<Object> o(scope, v4engine->newObject());
ScopedString name(scope);
@@ -1152,8 +1151,6 @@ void QQuickXmlListModel::queryCompleted(const QQuickXmlQueryResult &result)
int origCount = d->size;
bool sizeChanged = result.size != d->size;
- d->size = result.size;
- d->data = result.data;
d->keyRoleResultsCache = result.keyRoleResultsCache;
if (d->src.isEmpty() && d->xml.isEmpty())
d->status = Null;
@@ -1174,6 +1171,8 @@ void QQuickXmlListModel::queryCompleted(const QQuickXmlQueryResult &result)
beginRemoveRows(QModelIndex(), 0, origCount - 1);
endRemoveRows();
}
+ d->size = result.size;
+ d->data = result.data;
if (d->size > 0) {
beginInsertRows(QModelIndex(), 0, d->size - 1);
endInsertRows();
@@ -1187,6 +1186,8 @@ void QQuickXmlListModel::queryCompleted(const QQuickXmlQueryResult &result)
endRemoveRows();
}
}
+ d->size = result.size;
+ d->data = result.data;
for (int i=0; i<result.inserted.count(); i++) {
const int index = result.inserted[i].first;
const int count = result.inserted[i].second;
diff --git a/src/particles/qquickangledirection.cpp b/src/particles/qquickangledirection.cpp
index 11a007ca09..34afd9ce84 100644
--- a/src/particles/qquickangledirection.cpp
+++ b/src/particles/qquickangledirection.cpp
@@ -108,8 +108,8 @@ QPointF QQuickAngleDirection::sample(const QPointF &from)
{
Q_UNUSED(from);
QPointF ret;
- qreal theta = m_angle*CONV - m_angleVariation*CONV + QRandomGenerator::getReal() * m_angleVariation*CONV * 2;
- qreal mag = m_magnitude- m_magnitudeVariation + QRandomGenerator::getReal() * m_magnitudeVariation * 2;
+ qreal theta = m_angle*CONV - m_angleVariation*CONV + QRandomGenerator::global()->generateDouble() * m_angleVariation*CONV * 2;
+ qreal mag = m_magnitude- m_magnitudeVariation + QRandomGenerator::global()->generateDouble() * m_magnitudeVariation * 2;
ret.setX(mag * qCos(theta));
ret.setY(mag * qSin(theta));
return ret;
diff --git a/src/particles/qquickcustomaffector.cpp b/src/particles/qquickcustomaffector.cpp
index e152c436db..53557e1d0b 100644
--- a/src/particles/qquickcustomaffector.cpp
+++ b/src/particles/qquickcustomaffector.cpp
@@ -148,7 +148,7 @@ void QQuickCustomAffector::affectSystem(qreal dt)
dt = 1.0;
QQmlEngine *qmlEngine = ::qmlEngine(this);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(qmlEngine->handle());
+ QV4::ExecutionEngine *v4 = qmlEngine->handle();
QV4::Scope scope(v4);
QV4::ScopedArrayObject array(scope, v4->newArrayObject(toAffect.size()));
diff --git a/src/particles/qquickcustomparticle.cpp b/src/particles/qquickcustomparticle.cpp
index a2bcd91167..0e3c656762 100644
--- a/src/particles/qquickcustomparticle.cpp
+++ b/src/particles/qquickcustomparticle.cpp
@@ -246,7 +246,7 @@ QSGNode *QQuickCustomParticle::updatePaintNode(QSGNode *oldNode, UpdatePaintNode
QQuickOpenGLShaderEffectNode *rootNode = static_cast<QQuickOpenGLShaderEffectNode *>(oldNode);
if (m_pleaseReset){
delete rootNode;//Automatically deletes children
- rootNode = 0;
+ rootNode = nullptr;
m_nodes.clear();
m_pleaseReset = false;
m_dirtyProgram = true;
@@ -270,7 +270,7 @@ QQuickOpenGLShaderEffectNode *QQuickCustomParticle::prepareNextFrame(QQuickOpenG
rootNode = buildCustomNodes();
if (!rootNode)
- return 0;
+ return nullptr;
if (m_dirtyProgram) {
const bool isES = QOpenGLContext::currentContext()->isOpenGLES();
@@ -316,23 +316,23 @@ QQuickOpenGLShaderEffectNode* QQuickCustomParticle::buildCustomNodes()
typedef QHash<int, QQuickOpenGLShaderEffectNode*>::const_iterator NodeHashConstIt;
if (!QOpenGLContext::currentContext())
- return 0;
+ return nullptr;
if (m_count * 4 > 0xffff) {
// Index data is ushort.
qmlInfo(this) << "CustomParticle: Too many particles - maximum 16383 per CustomParticle";
- return 0;
+ return nullptr;
}
if (m_count <= 0) {
qmlInfo(this) << "CustomParticle: Too few particles";
- return 0;
+ return nullptr;
}
if (groups().isEmpty())
- return 0;
+ return nullptr;
- QQuickOpenGLShaderEffectNode *rootNode = 0;
+ QQuickOpenGLShaderEffectNode *rootNode = nullptr;
QQuickOpenGLShaderEffectMaterial *material = new QQuickOpenGLShaderEffectMaterial;
m_dirtyProgram = true;
@@ -425,7 +425,7 @@ void QQuickCustomParticle::buildData(QQuickOpenGLShaderEffectNode *rootNode)
void QQuickCustomParticle::initialize(int gIdx, int pIdx)
{
QQuickParticleData* datum = m_system->groupData[gIdx]->data[pIdx];
- datum->r = QRandomGenerator::getReal();
+ datum->r = QRandomGenerator::global()->generateDouble();
}
void QQuickCustomParticle::commit(int gIdx, int pIdx)
diff --git a/src/particles/qquickellipseextruder.cpp b/src/particles/qquickellipseextruder.cpp
index fbb11b34cc..52fccd6da9 100644
--- a/src/particles/qquickellipseextruder.cpp
+++ b/src/particles/qquickellipseextruder.cpp
@@ -68,8 +68,8 @@ QQuickEllipseExtruder::QQuickEllipseExtruder(QObject *parent) :
QPointF QQuickEllipseExtruder::extrude(const QRectF & r)
{
- qreal theta = QRandomGenerator::bounded(2 * M_PI);
- qreal mag = m_fill ? QRandomGenerator::getReal() : 1;
+ qreal theta = QRandomGenerator::global()->bounded(2 * M_PI);
+ qreal mag = m_fill ? QRandomGenerator::global()->generateDouble() : 1;
return QPointF(r.x() + r.width()/2 + mag * (r.width()/2) * qCos(theta),
r.y() + r.height()/2 + mag * (r.height()/2) * qSin(theta));
}
diff --git a/src/particles/qquickimageparticle.cpp b/src/particles/qquickimageparticle.cpp
index 8f809176a9..d2fb78d72a 100644
--- a/src/particles/qquickimageparticle.cpp
+++ b/src/particles/qquickimageparticle.cpp
@@ -67,7 +67,7 @@ class ImageMaterialData
{
public:
ImageMaterialData()
- : texture(0), colorTable(0)
+ : texture(nullptr), colorTable(nullptr)
{}
~ImageMaterialData(){
@@ -701,7 +701,7 @@ void fillUniformArrayFromImage(float* array, const QImage& img, int size)
QQuickImageParticle::QQuickImageParticle(QQuickItem* parent)
: QQuickParticlePainter(parent)
, m_color_variation(0.0)
- , m_material(0)
+ , m_material(nullptr)
, m_alphaVariation(0.0)
, m_alpha(1.0)
, m_redVariation(0.0)
@@ -712,9 +712,9 @@ QQuickImageParticle::QQuickImageParticle(QQuickItem* parent)
, m_rotationVelocity(0)
, m_rotationVelocityVariation(0)
, m_autoRotation(false)
- , m_xVector(0)
- , m_yVector(0)
- , m_spriteEngine(0)
+ , m_xVector(nullptr)
+ , m_yVector(nullptr)
+ , m_spriteEngine(nullptr)
, m_spritesInterpolate(true)
, m_explicitColor(false)
, m_explicitRotation(false)
@@ -743,7 +743,7 @@ QQmlListProperty<QQuickSprite> QQuickImageParticle::sprites()
void QQuickImageParticle::sceneGraphInvalidated()
{
m_nodes.clear();
- m_material = 0;
+ m_material = nullptr;
}
void QQuickImageParticle::setImage(const QUrl &image)
@@ -1011,7 +1011,7 @@ void QQuickImageParticle::resetColor()
for (auto groupId : groupIds()) {
for (QQuickParticleData* d : qAsConst(m_system->groupData[groupId]->data)) {
if (d->colorOwner == this) {
- d->colorOwner = 0;
+ d->colorOwner = nullptr;
}
}
}
@@ -1030,7 +1030,7 @@ void QQuickImageParticle::resetRotation()
for (auto groupId : groupIds()) {
for (QQuickParticleData* d : qAsConst(m_system->groupData[groupId]->data)) {
if (d->rotationOwner == this) {
- d->rotationOwner = 0;
+ d->rotationOwner = nullptr;
}
}
}
@@ -1047,7 +1047,7 @@ void QQuickImageParticle::resetDeformation()
for (auto groupId : groupIds()) {
for (QQuickParticleData* d : qAsConst(m_system->groupData[groupId]->data)) {
if (d->deformationOwner == this) {
- d->deformationOwner = 0;
+ d->deformationOwner = nullptr;
}
}
}
@@ -1055,8 +1055,8 @@ void QQuickImageParticle::resetDeformation()
delete m_xVector;
if (m_yVector)
delete m_yVector;
- m_xVector = 0;
- m_yVector = 0;
+ m_xVector = nullptr;
+ m_yVector = nullptr;
}
void QQuickImageParticle::reset()
@@ -1076,7 +1076,7 @@ void QQuickImageParticle::createEngine()
this, SLOT(spriteAdvance(int)), Qt::DirectConnection);
m_explicitAnimation = true;
} else {
- m_spriteEngine = 0;
+ m_spriteEngine = nullptr;
m_explicitAnimation = false;
}
reset();
@@ -1298,7 +1298,7 @@ void QQuickImageParticle::finishBuildParticleNodes(QSGNode** node)
clearShadows();
if (m_material)
- m_material = 0;
+ m_material = nullptr;
//Setup material
QImage colortable;
@@ -1473,12 +1473,12 @@ static inline bool isOpenGL(QSGRenderContext *rc)
QSGNode *QQuickImageParticle::updatePaintNode(QSGNode *node, UpdatePaintNodeData *)
{
if (!node && !isOpenGL(QQuickItemPrivate::get(this)->sceneGraphRenderContext()))
- return 0;
+ return nullptr;
if (m_pleaseReset){
if (node)
delete node;
- node = 0;
+ node = nullptr;
m_lastLevel = perfLevel;
m_nodes.clear();
@@ -1487,7 +1487,7 @@ QSGNode *QQuickImageParticle::updatePaintNode(QSGNode *node, UpdatePaintNodeData
m_startsIdx.clear();
m_lastIdxStart = 0;
- m_material = 0;
+ m_material = nullptr;
m_pleaseReset = false;
m_startedImageLoading = 0;//Cancel a part-way build (may still have a pending load)
@@ -1509,7 +1509,7 @@ QSGNode *QQuickImageParticle::updatePaintNode(QSGNode *node, UpdatePaintNodeData
void QQuickImageParticle::prepareNextFrame(QSGNode **node)
{
- if (*node == 0){//TODO: Staggered loading (as emitted)
+ if (*node == nullptr){//TODO: Staggered loading (as emitted)
buildParticleNodes(node);
if (m_debugMode) {
qDebug() << "QQuickImageParticle Feature level: " << perfLevel;
@@ -1522,7 +1522,7 @@ void QQuickImageParticle::prepareNextFrame(QSGNode **node)
}
qDebug() << "Total count: " << count;
}
- if (*node == 0)
+ if (*node == nullptr)
return;
}
qint64 timeStamp = m_system->systemSync(this);
@@ -1730,9 +1730,9 @@ void QQuickImageParticle::initialize(int gIdx, int pIdx)
if (!datum->rotationOwner)
datum->rotationOwner = this;
rotation =
- (m_rotation + (m_rotationVariation - 2*QRandomGenerator::bounded(m_rotationVariation)) ) * CONV;
+ (m_rotation + (m_rotationVariation - 2*QRandomGenerator::global()->bounded(m_rotationVariation)) ) * CONV;
rotationVelocity =
- (m_rotationVelocity + (m_rotationVelocityVariation - 2*QRandomGenerator::bounded(m_rotationVelocityVariation)) ) * CONV;
+ (m_rotationVelocity + (m_rotationVelocityVariation - 2*QRandomGenerator::global()->bounded(m_rotationVelocityVariation)) ) * CONV;
autoRotate = m_autoRotation?1.0:0.0;
if (datum->rotationOwner == this) {
datum->rotation = rotation;
@@ -1751,10 +1751,10 @@ void QQuickImageParticle::initialize(int gIdx, int pIdx)
if (m_explicitColor) {
if (!datum->colorOwner)
datum->colorOwner = this;
- color.r = m_color.red() * (1 - redVariation) + QRandomGenerator::bounded(256) * redVariation;
- color.g = m_color.green() * (1 - greenVariation) + QRandomGenerator::bounded(256) * greenVariation;
- color.b = m_color.blue() * (1 - blueVariation) + QRandomGenerator::bounded(256) * blueVariation;
- color.a = m_alpha * m_color.alpha() * (1 - m_alphaVariation) + QRandomGenerator::bounded(256) * m_alphaVariation;
+ color.r = m_color.red() * (1 - redVariation) + QRandomGenerator::global()->bounded(256) * redVariation;
+ color.g = m_color.green() * (1 - greenVariation) + QRandomGenerator::global()->bounded(256) * greenVariation;
+ color.b = m_color.blue() * (1 - blueVariation) + QRandomGenerator::global()->bounded(256) * blueVariation;
+ color.a = m_alpha * m_color.alpha() * (1 - m_alphaVariation) + QRandomGenerator::global()->bounded(256) * m_alphaVariation;
if (datum->colorOwner == this)
datum->color = color;
else
diff --git a/src/particles/qquickitemparticle.cpp b/src/particles/qquickitemparticle.cpp
index 50b66a4d15..412390dffc 100644
--- a/src/particles/qquickitemparticle.cpp
+++ b/src/particles/qquickitemparticle.cpp
@@ -118,7 +118,7 @@ QT_BEGIN_NAMESPACE
*/
QQuickItemParticle::QQuickItemParticle(QQuickItem *parent) :
- QQuickParticlePainter(parent), m_fade(true), m_lastT(0), m_activeCount(0), m_delegate(0)
+ QQuickParticlePainter(parent), m_fade(true), m_lastT(0), m_activeCount(0), m_delegate(nullptr)
{
setFlag(QQuickItem::ItemHasContents);
clock = new Clock(this);
@@ -195,7 +195,7 @@ void QQuickItemParticle::tick(int time)
//remove old item from the particle that is dying to make room for this one
if (d->delegate) {
m_deletables << d->delegate;
- d->delegate = 0;
+ d->delegate = nullptr;
}
if (!m_pendingItems.isEmpty()){
d->delegate = m_pendingItems.front();
@@ -289,7 +289,7 @@ void QQuickItemParticle::prepareNextFrame()
}
if (t >= 1.0f){//Usually happens from load
m_deletables << item;
- data->delegate = 0;
+ data->delegate = nullptr;
}else{//Fade
data->delegate->setVisible(true);
if (m_fade){
diff --git a/src/particles/qquicklineextruder.cpp b/src/particles/qquicklineextruder.cpp
index 6ebd728407..670e656b8e 100644
--- a/src/particles/qquicklineextruder.cpp
+++ b/src/particles/qquicklineextruder.cpp
@@ -69,10 +69,10 @@ QPointF QQuickLineExtruder::extrude(const QRectF &r)
{
qreal x,y;
if (!r.height()){
- x = r.width() * QRandomGenerator::getReal();
+ x = r.width() * QRandomGenerator::global()->generateDouble();
y = 0;
}else{
- y = r.height() * QRandomGenerator::getReal();
+ y = r.height() * QRandomGenerator::global()->generateDouble();
if (!r.width()){
x = 0;
}else{
diff --git a/src/particles/qquickmaskextruder.cpp b/src/particles/qquickmaskextruder.cpp
index 60c23c55a8..6ab6dcc6a4 100644
--- a/src/particles/qquickmaskextruder.cpp
+++ b/src/particles/qquickmaskextruder.cpp
@@ -103,7 +103,7 @@ QPointF QQuickMaskExtruder::extrude(const QRectF &r)
ensureInitialized(r);
if (!m_mask.count() || m_img.isNull())
return r.topLeft();
- const QPointF p = m_mask[QRandomGenerator::bounded(m_mask.count())];
+ const QPointF p = m_mask[QRandomGenerator::global()->bounded(m_mask.count())];
//### Should random sub-pixel positioning be added?
return p + r.topLeft();
}
diff --git a/src/particles/qquickparticleaffector.cpp b/src/particles/qquickparticleaffector.cpp
index 30716ecb80..76089c1abd 100644
--- a/src/particles/qquickparticleaffector.cpp
+++ b/src/particles/qquickparticleaffector.cpp
@@ -131,7 +131,7 @@ QT_BEGIN_NAMESPACE
*/
QQuickParticleAffector::QQuickParticleAffector(QQuickItem *parent) :
QQuickItem(parent), m_needsReset(false), m_ignoresTime(false), m_onceOff(false), m_enabled(true)
- , m_system(0), m_updateIntSet(false), m_shape(new QQuickParticleExtruder(this))
+ , m_system(nullptr), m_updateIntSet(false), m_shape(new QQuickParticleExtruder(this))
{
}
diff --git a/src/particles/qquickparticleemitter.cpp b/src/particles/qquickparticleemitter.cpp
index d18250d706..78409d3a44 100644
--- a/src/particles/qquickparticleemitter.cpp
+++ b/src/particles/qquickparticleemitter.cpp
@@ -222,9 +222,9 @@ QQuickParticleEmitter::QQuickParticleEmitter(QQuickItem *parent) :
, m_particleDuration(1000)
, m_particleDurationVariation(0)
, m_enabled(true)
- , m_system(0)
- , m_extruder(0)
- , m_defaultExtruder(0)
+ , m_system(nullptr)
+ , m_extruder(nullptr)
+ , m_defaultExtruder(nullptr)
, m_velocity(&m_nullVector)
, m_acceleration(&m_nullVector)
, m_particleSize(16)
@@ -349,7 +349,7 @@ void QQuickParticleEmitter::reset()
void QQuickParticleEmitter::emitWindow(int timeStamp)
{
- if (m_system == 0)
+ if (m_system == nullptr)
return;
if ((!m_enabled || m_particlesPerSecond <= 0)&& !m_pulseLeft && m_burstQueue.isEmpty()){
m_reset_last = true;
@@ -425,7 +425,7 @@ void QQuickParticleEmitter::emitWindow(int timeStamp)
datum->t = pt;
datum->lifeSpan =
(m_particleDuration
- + (QRandomGenerator::bounded((m_particleDurationVariation*2) + 1) - m_particleDurationVariation))
+ + (QRandomGenerator::global()->bounded((m_particleDurationVariation*2) + 1) - m_particleDurationVariation))
/ 1000.0;
if (datum->lifeSpan >= m_system->maxLife){
@@ -462,7 +462,7 @@ void QQuickParticleEmitter::emitWindow(int timeStamp)
// Particle size
float sizeVariation = -m_particleSizeVariation
- + QRandomGenerator::bounded(m_particleSizeVariation * 2);
+ + QRandomGenerator::global()->bounded(m_particleSizeVariation * 2);
float size = qMax((qreal)0.0 , m_particleSize + sizeVariation);
float endSize = qMax((qreal)0.0 , sizeAtEnd + sizeVariation);
@@ -486,7 +486,7 @@ void QQuickParticleEmitter::emitWindow(int timeStamp)
if (isEmitConnected()) {
QQmlEngine *qmlEngine = ::qmlEngine(this);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(qmlEngine->handle());
+ QV4::ExecutionEngine *v4 = qmlEngine->handle();
QV4::Scope scope(v4);
//Done after emitParticle so that the Painter::load is done first, this allows you to customize its static variables
diff --git a/src/particles/qquickparticleextruder.cpp b/src/particles/qquickparticleextruder.cpp
index 74b450921f..816ff34960 100644
--- a/src/particles/qquickparticleextruder.cpp
+++ b/src/particles/qquickparticleextruder.cpp
@@ -59,8 +59,8 @@ QQuickParticleExtruder::QQuickParticleExtruder(QObject *parent) :
QPointF QQuickParticleExtruder::extrude(const QRectF &rect)
{
- return QPointF(QRandomGenerator::getReal() * rect.width() + rect.x(),
- QRandomGenerator::getReal() * rect.height() + rect.y());
+ return QPointF(QRandomGenerator::global()->generateDouble() * rect.width() + rect.x(),
+ QRandomGenerator::global()->generateDouble() * rect.height() + rect.y());
}
bool QQuickParticleExtruder::contains(const QRectF &bounds, const QPointF &point)
diff --git a/src/particles/qquickparticlegroup.cpp b/src/particles/qquickparticlegroup.cpp
index 2ee2a1d0a3..a42d2bcb13 100644
--- a/src/particles/qquickparticlegroup.cpp
+++ b/src/particles/qquickparticlegroup.cpp
@@ -91,7 +91,7 @@
QQuickParticleGroup::QQuickParticleGroup(QObject* parent)
: QQuickStochasticState(parent)
- , m_system(0)
+ , m_system(nullptr)
{
}
@@ -107,9 +107,9 @@ QQmlListProperty<QObject> QQuickParticleGroup::particleChildren()
{
QQuickParticleSystem* system = qobject_cast<QQuickParticleSystem*>(parent());
if (system)
- return QQmlListProperty<QObject>(this, 0, &QQuickParticleSystem::statePropertyRedirect, 0, 0, 0);
+ return QQmlListProperty<QObject>(this, nullptr, &QQuickParticleSystem::statePropertyRedirect, nullptr, nullptr, nullptr);
else
- return QQmlListProperty<QObject>(this, 0, &delayedRedirect, 0, 0, 0);
+ return QQmlListProperty<QObject>(this, nullptr, &delayedRedirect, nullptr, nullptr, nullptr);
}
void QQuickParticleGroup::setSystem(QQuickParticleSystem* arg)
diff --git a/src/particles/qquickparticlepainter.cpp b/src/particles/qquickparticlepainter.cpp
index 70fc2d59e3..13591be97a 100644
--- a/src/particles/qquickparticlepainter.cpp
+++ b/src/particles/qquickparticlepainter.cpp
@@ -66,10 +66,10 @@ QT_BEGIN_NAMESPACE
*/
QQuickParticlePainter::QQuickParticlePainter(QQuickItem *parent)
: QQuickItem(parent)
- , m_system(0)
+ , m_system(nullptr)
, m_count(0)
, m_pleaseReset(true)
- , m_window(0)
+ , m_window(nullptr)
, m_groupIdsNeedRecalculation(false)
{
}
diff --git a/src/particles/qquickparticlesystem.cpp b/src/particles/qquickparticlesystem.cpp
index cc7d9edbc8..612675fec7 100644
--- a/src/particles/qquickparticlesystem.cpp
+++ b/src/particles/qquickparticlesystem.cpp
@@ -378,7 +378,7 @@ QQuickParticleData* QQuickParticleGroupData::newDatum(bool respectsLimits)
return data[idx];
}
if (respectsLimits)
- return 0;
+ return nullptr;
int oldSize = m_size;
setSize(oldSize + 10);//###+1,10%,+10? Choose something non-arbitrarily
@@ -418,11 +418,11 @@ QQuickParticleData::QQuickParticleData()
: index(0)
, systemIndex(-1)
, groupId(0)
- , colorOwner(0)
- , rotationOwner(0)
- , deformationOwner(0)
- , animationOwner(0)
- , v8Datum(0)
+ , colorOwner(nullptr)
+ , rotationOwner(nullptr)
+ , deformationOwner(nullptr)
+ , animationOwner(nullptr)
+ , v8Datum(nullptr)
{
x = 0;
y = 0;
@@ -455,7 +455,7 @@ QQuickParticleData::QQuickParticleData()
color.b = 255;
color.a = 255;
r = 0;
- delegate = 0;
+ delegate = nullptr;
modelIndex = -1;
}
@@ -477,7 +477,7 @@ QQuickParticleData &QQuickParticleData::operator=(const QQuickParticleData &othe
index = other.index;
systemIndex = other.systemIndex;
// Lazily initialized
- v8Datum = 0;
+ v8Datum = nullptr;
return *this;
}
@@ -526,7 +526,7 @@ void QQuickParticleData::clone(const QQuickParticleData& other)
QQmlV4Handle QQuickParticleData::v4Value(QQuickParticleSystem* particleSystem)
{
if (!v8Datum)
- v8Datum = new QQuickV4ParticleData(QQmlEnginePrivate::getV8Engine(qmlEngine(particleSystem)), this, particleSystem);
+ v8Datum = new QQuickV4ParticleData(qmlEngine(particleSystem)->handle(), this, particleSystem);
return v8Datum->v4Value();
}
@@ -564,9 +564,9 @@ void QQuickParticleData::extendLife(float time, QQuickParticleSystem* particleSy
QQuickParticleSystem::QQuickParticleSystem(QQuickItem *parent) :
QQuickItem(parent),
- stateEngine(0),
+ stateEngine(nullptr),
nextFreeGroupId(0),
- m_animation(0),
+ m_animation(nullptr),
m_running(true),
initialized(0),
particleCount(0),
@@ -768,9 +768,9 @@ void QQuickParticleSystem::reset()
timeInt = 0;
//Clear guarded pointers which have been deleted
int cleared = 0;
- cleared += m_emitters.removeAll(0);
- cleared += m_painters.removeAll(0);
- cleared += m_affectors.removeAll(0);
+ cleared += m_emitters.removeAll(nullptr);
+ cleared += m_painters.removeAll(nullptr);
+ cleared += m_affectors.removeAll(nullptr);
bySysIdx.resize(0);
initGroups();//Also clears all logical particles
@@ -945,7 +945,7 @@ void QQuickParticleSystem::createEngine()
} else {
if (stateEngine)
delete stateEngine;
- stateEngine = 0;
+ stateEngine = nullptr;
}
}
@@ -993,7 +993,7 @@ QQuickParticleData* QQuickParticleSystem::newDatum(int groupId, bool respectLimi
QQuickParticleData* ret = groupData[groupId]->newDatum(respectLimits);
if (!ret) {
- return 0;
+ return nullptr;
}
if (sysIndex == -1) {
if (ret->systemIndex == -1)
@@ -1056,9 +1056,9 @@ void QQuickParticleSystem::updateCurrentTime( int currentTime )
dt = time - dt;
needsReset.clear();
- m_emitters.removeAll(0);
- m_painters.removeAll(0);
- m_affectors.removeAll(0);
+ m_emitters.removeAll(nullptr);
+ m_painters.removeAll(nullptr);
+ m_affectors.removeAll(nullptr);
bool oldClear = m_empty;
m_empty = true;
diff --git a/src/particles/qquickparticlesystem_p.h b/src/particles/qquickparticlesystem_p.h
index 92dca40419..73351fb99a 100644
--- a/src/particles/qquickparticlesystem_p.h
+++ b/src/particles/qquickparticlesystem_p.h
@@ -137,10 +137,7 @@ class Q_QUICKPARTICLES_PRIVATE_EXPORT QQuickParticleGroupData {
class FreeList
{
public:
- FreeList()
- : firstUnused(UINT_MAX)
- , allocated(0)
- {}
+ FreeList() {}
void resize(int newSize)
{
@@ -189,8 +186,8 @@ class Q_QUICKPARTICLES_PRIVATE_EXPORT QQuickParticleGroupData {
private:
QV4::BitVector isUnused;
- unsigned firstUnused;
- int allocated;
+ unsigned firstUnused = UINT_MAX;
+ int allocated = 0;
};
public: // types
@@ -353,7 +350,7 @@ class Q_QUICKPARTICLES_PRIVATE_EXPORT QQuickParticleSystem : public QQuickItem
Q_PROPERTY(bool empty READ isEmpty NOTIFY emptyChanged)
public:
- explicit QQuickParticleSystem(QQuickItem *parent = 0);
+ explicit QQuickParticleSystem(QQuickItem *parent = nullptr);
~QQuickParticleSystem();
bool isRunning() const
diff --git a/src/particles/qquickpointdirection.cpp b/src/particles/qquickpointdirection.cpp
index 7b5c9bada1..f22eea2a76 100644
--- a/src/particles/qquickpointdirection.cpp
+++ b/src/particles/qquickpointdirection.cpp
@@ -78,8 +78,8 @@ QQuickPointDirection::QQuickPointDirection(QObject *parent) :
QPointF QQuickPointDirection::sample(const QPointF &)
{
QPointF ret;
- ret.setX(m_x - m_xVariation + QRandomGenerator::getReal() * m_xVariation * 2);
- ret.setY(m_y - m_yVariation + QRandomGenerator::getReal() * m_yVariation * 2);
+ ret.setX(m_x - m_xVariation + QRandomGenerator::global()->generateDouble() * m_xVariation * 2);
+ ret.setY(m_y - m_yVariation + QRandomGenerator::global()->generateDouble() * m_yVariation * 2);
return ret;
}
diff --git a/src/particles/qquickrectangleextruder.cpp b/src/particles/qquickrectangleextruder.cpp
index 6474f61630..36e4871d29 100644
--- a/src/particles/qquickrectangleextruder.cpp
+++ b/src/particles/qquickrectangleextruder.cpp
@@ -60,21 +60,21 @@ QQuickRectangleExtruder::QQuickRectangleExtruder(QObject *parent) :
QPointF QQuickRectangleExtruder::extrude(const QRectF &rect)
{
if (m_fill)
- return QPointF(QRandomGenerator::getReal() * rect.width() + rect.x(),
- QRandomGenerator::getReal() * rect.height() + rect.y());
- int side = QRandomGenerator::bounded(4);
+ return QPointF(QRandomGenerator::global()->generateDouble() * rect.width() + rect.x(),
+ QRandomGenerator::global()->generateDouble() * rect.height() + rect.y());
+ int side = QRandomGenerator::global()->bounded(4);
switch (side){//TODO: Doesn't this overlap the corners?
case 0:
return QPointF(rect.x(),
- QRandomGenerator::getReal() * rect.height() + rect.y());
+ QRandomGenerator::global()->generateDouble() * rect.height() + rect.y());
case 1:
return QPointF(rect.width() + rect.x(),
- QRandomGenerator::getReal() * rect.height() + rect.y());
+ QRandomGenerator::global()->generateDouble() * rect.height() + rect.y());
case 2:
- return QPointF(QRandomGenerator::getReal() * rect.width() + rect.x(),
+ return QPointF(QRandomGenerator::global()->generateDouble() * rect.width() + rect.x(),
rect.y());
default:
- return QPointF(QRandomGenerator::getReal() * rect.width() + rect.x(),
+ return QPointF(QRandomGenerator::global()->generateDouble() * rect.width() + rect.x(),
rect.height() + rect.y());
}
}
diff --git a/src/particles/qquickspritegoal.cpp b/src/particles/qquickspritegoal.cpp
index 2e420a2840..75d6f8bdf6 100644
--- a/src/particles/qquickspritegoal.cpp
+++ b/src/particles/qquickspritegoal.cpp
@@ -82,7 +82,7 @@ QT_BEGIN_NAMESPACE
QQuickSpriteGoalAffector::QQuickSpriteGoalAffector(QQuickItem *parent) :
QQuickParticleAffector(parent),
m_goalIdx(-1),
- m_lastEngine(0),
+ m_lastEngine(nullptr),
m_jump(false),
m_systemStates(false),
m_notUsingEngine(false)
@@ -121,7 +121,7 @@ void QQuickSpriteGoalAffector::setGoalState(const QString &arg)
bool QQuickSpriteGoalAffector::affectParticle(QQuickParticleData *d, qreal dt)
{
Q_UNUSED(dt);
- QQuickStochasticEngine *engine = 0;
+ QQuickStochasticEngine *engine = nullptr;
if (!m_systemStates){
//TODO: Affect all engines
foreach (QQuickParticlePainter *p, m_system->groupData[d->groupId]->painters)
diff --git a/src/particles/qquicktargetdirection.cpp b/src/particles/qquicktargetdirection.cpp
index 96b78a53b4..5d84f9dc2b 100644
--- a/src/particles/qquicktargetdirection.cpp
+++ b/src/particles/qquicktargetdirection.cpp
@@ -91,7 +91,7 @@ QQuickTargetDirection::QQuickTargetDirection(QObject *parent) :
, m_proportionalMagnitude(false)
, m_magnitude(0)
, m_magnitudeVariation(0)
- , m_targetItem(0)
+ , m_targetItem(nullptr)
{
}
@@ -118,10 +118,10 @@ QPointF QQuickTargetDirection::sample(const QPointF &from)
targetX = m_targetX;
targetY = m_targetY;
}
- targetX += 0 - from.x() - m_targetVariation + QRandomGenerator::getReal() * m_targetVariation*2;
- targetY += 0 - from.y() - m_targetVariation + QRandomGenerator::getReal() * m_targetVariation*2;
+ targetX += 0 - from.x() - m_targetVariation + QRandomGenerator::global()->generateDouble() * m_targetVariation*2;
+ targetY += 0 - from.y() - m_targetVariation + QRandomGenerator::global()->generateDouble() * m_targetVariation*2;
qreal theta = std::atan2(targetY, targetX);
- qreal mag = m_magnitude + QRandomGenerator::getReal() * m_magnitudeVariation * 2 - m_magnitudeVariation;
+ qreal mag = m_magnitude + QRandomGenerator::global()->generateDouble() * m_magnitudeVariation * 2 - m_magnitudeVariation;
if (m_proportionalMagnitude)
mag *= std::sqrt(targetX * targetX + targetY * targetY);
ret.setX(mag * std::cos(theta));
diff --git a/src/particles/qquicktrailemitter.cpp b/src/particles/qquicktrailemitter.cpp
index 14075f6b23..fde5eab617 100644
--- a/src/particles/qquicktrailemitter.cpp
+++ b/src/particles/qquicktrailemitter.cpp
@@ -62,7 +62,7 @@ QQuickTrailEmitter::QQuickTrailEmitter(QQuickItem *parent) :
, m_emitterXVariation(0)
, m_emitterYVariation(0)
, m_followCount(0)
- , m_emissionExtruder(0)
+ , m_emissionExtruder(nullptr)
, m_defaultEmissionExtruder(new QQuickParticleExtruder(this))
{
//TODO: If followed increased their size
@@ -150,7 +150,7 @@ void QQuickTrailEmitter::reset()
void QQuickTrailEmitter::emitWindow(int timeStamp)
{
- if (m_system == 0)
+ if (m_system == nullptr)
return;
if (!m_enabled && !m_pulseLeft && m_burstQueue.isEmpty())
return;
@@ -208,7 +208,7 @@ void QQuickTrailEmitter::emitWindow(int timeStamp)
datum->t = pt;
datum->lifeSpan =
(m_particleDuration
- + (QRandomGenerator::bounded((m_particleDurationVariation*2) + 1) - m_particleDurationVariation))
+ + (QRandomGenerator::global()->bounded((m_particleDurationVariation*2) + 1) - m_particleDurationVariation))
/ 1000.0;
// Particle position
@@ -241,7 +241,7 @@ void QQuickTrailEmitter::emitWindow(int timeStamp)
// Particle size
float sizeVariation = -m_particleSizeVariation
- + QRandomGenerator::getReal() * m_particleSizeVariation * 2;
+ + QRandomGenerator::global()->generateDouble() * m_particleSizeVariation * 2;
float size = qMax((qreal)0.0, m_particleSize + sizeVariation);
float endSize = qMax((qreal)0.0, sizeAtEnd + sizeVariation);
@@ -267,7 +267,7 @@ void QQuickTrailEmitter::emitWindow(int timeStamp)
if (isEmitConnected() || isEmitFollowConnected()) {
QQmlEngine *qmlEngine = ::qmlEngine(this);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(qmlEngine->handle());
+ QV4::ExecutionEngine *v4 = qmlEngine->handle();
QV4::Scope scope(v4);
QV4::ScopedArrayObject array(scope, v4->newArrayObject(toEmit.size()));
diff --git a/src/particles/qquickturbulence.cpp b/src/particles/qquickturbulence.cpp
index f916635358..dc72d884bc 100644
--- a/src/particles/qquickturbulence.cpp
+++ b/src/particles/qquickturbulence.cpp
@@ -81,7 +81,7 @@ QT_BEGIN_NAMESPACE
QQuickTurbulenceAffector::QQuickTurbulenceAffector(QQuickItem *parent) :
QQuickParticleAffector(parent),
- m_strength(10), m_lastT(0), m_gridSize(0), m_field(0), m_vectorField(0), m_inited(false)
+ m_strength(10), m_lastT(0), m_gridSize(0), m_field(nullptr), m_vectorField(nullptr), m_inited(false)
{
}
diff --git a/src/particles/qquickv4particledata.cpp b/src/particles/qquickv4particledata.cpp
index acb37f25bf..c3d1978a2c 100644
--- a/src/particles/qquickv4particledata.cpp
+++ b/src/particles/qquickv4particledata.cpp
@@ -294,15 +294,15 @@ class QV4ParticleDataDeletable : public QV8Engine::Deletable
{
public:
QV4ParticleDataDeletable(QV4::ExecutionEngine *engine);
- ~QV4ParticleDataDeletable();
+ ~QV4ParticleDataDeletable() override;
QV4::PersistentValue proto;
};
-static QV4::ReturnedValue particleData_discard(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static QV4::ReturnedValue particleData_discard(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject);
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject);
if (!r || !r->d()->datum)
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object")));
@@ -311,10 +311,10 @@ static QV4::ReturnedValue particleData_discard(const QV4::BuiltinFunction *b, QV
RETURN_RESULT(QV4::Encode::undefined());
}
-static QV4::ReturnedValue particleData_lifeLeft(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static QV4::ReturnedValue particleData_lifeLeft(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject);
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject);
if (!r || !r->d()->datum)
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object")));
@@ -322,99 +322,99 @@ static QV4::ReturnedValue particleData_lifeLeft(const QV4::BuiltinFunction *b, Q
RETURN_RESULT(QV4::Encode(r->d()->datum->lifeLeft(r->d()->particleSystem)));
}
-static QV4::ReturnedValue particleData_curSize(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+static QV4::ReturnedValue particleData_curSize(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject);
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject);
if (!r || !r->d()->datum)
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object")));
RETURN_RESULT(QV4::Encode(r->d()->datum->curSize(r->d()->particleSystem)));
}
-#define COLOR_GETTER_AND_SETTER(VAR, NAME) static QV4::ReturnedValue particleData_get_ ## NAME (const QV4::BuiltinFunction *b, QV4::CallData *callData) \
+#define COLOR_GETTER_AND_SETTER(VAR, NAME) static QV4::ReturnedValue particleData_get_ ## NAME (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int) \
{ \
QV4::Scope scope(b); \
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject); \
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject); \
if (!r || !r->d()->datum) \
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object"))); \
\
RETURN_RESULT(QV4::Encode((r->d()->datum->color. VAR )/255.0));\
}\
\
-static QV4::ReturnedValue particleData_set_ ## NAME (const QV4::BuiltinFunction *b, QV4::CallData *callData)\
+static QV4::ReturnedValue particleData_set_ ## NAME (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)\
{\
QV4::Scope scope(b); \
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject); \
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject); \
if (!r || !r->d()->datum)\
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object")));\
\
- double d = callData->argc() ? callData->args[0].toNumber() : 0; \
+ double d = argc ? argv[0].toNumber() : 0; \
r->d()->datum->color. VAR = qMin(255, qMax(0, (int)::floor(d * 255.0)));\
RETURN_UNDEFINED(); \
}
-#define SEMIBOOL_GETTER_AND_SETTER(VARIABLE) static QV4::ReturnedValue particleData_get_ ## VARIABLE (const QV4::BuiltinFunction *b, QV4::CallData *callData) \
+#define SEMIBOOL_GETTER_AND_SETTER(VARIABLE) static QV4::ReturnedValue particleData_get_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int) \
{ \
QV4::Scope scope(b); \
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject); \
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject); \
if (!r || !r->d()->datum) \
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object"))); \
\
RETURN_RESULT(QV4::Encode(r->d()->datum-> VARIABLE));\
}\
\
-static QV4::ReturnedValue particleData_set_ ## VARIABLE (const QV4::BuiltinFunction *b, QV4::CallData *callData)\
+static QV4::ReturnedValue particleData_set_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)\
{\
QV4::Scope scope(b); \
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject); \
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject); \
if (!r || !r->d()->datum)\
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object")));\
\
- r->d()->datum-> VARIABLE = (callData->argc() && callData->args[0].toBoolean()) ? 1.0 : 0.0;\
+ r->d()->datum-> VARIABLE = (argc && argv[0].toBoolean()) ? 1.0 : 0.0;\
RETURN_UNDEFINED(); \
}
-#define FLOAT_GETTER_AND_SETTER(VARIABLE) static QV4::ReturnedValue particleData_get_ ## VARIABLE (const QV4::BuiltinFunction *b, QV4::CallData *callData) \
+#define FLOAT_GETTER_AND_SETTER(VARIABLE) static QV4::ReturnedValue particleData_get_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int) \
{ \
QV4::Scope scope(b); \
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject); \
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject); \
if (!r || !r->d()->datum) \
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object"))); \
\
RETURN_RESULT(QV4::Encode(r->d()->datum-> VARIABLE));\
}\
\
-static QV4::ReturnedValue particleData_set_ ## VARIABLE (const QV4::BuiltinFunction *b, QV4::CallData *callData)\
+static QV4::ReturnedValue particleData_set_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)\
{\
QV4::Scope scope(b); \
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject); \
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject); \
if (!r || !r->d()->datum)\
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object")));\
\
- r->d()->datum-> VARIABLE = callData->argc() ? callData->args[0].toNumber() : qt_qnan();\
+ r->d()->datum-> VARIABLE = argc ? argv[0].toNumber() : qt_qnan();\
RETURN_UNDEFINED(); \
}
-#define FAKE_FLOAT_GETTER_AND_SETTER(VARIABLE, GETTER, SETTER) static QV4::ReturnedValue particleData_get_ ## VARIABLE (const QV4::BuiltinFunction *b, QV4::CallData *callData) \
+#define FAKE_FLOAT_GETTER_AND_SETTER(VARIABLE, GETTER, SETTER) static QV4::ReturnedValue particleData_get_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int) \
{ \
QV4::Scope scope(b); \
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject); \
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject); \
if (!r || !r->d()->datum) \
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object"))); \
\
RETURN_RESULT(QV4::Encode(r->d()->datum-> GETTER (r->d()->particleSystem)));\
}\
\
-static QV4::ReturnedValue particleData_set_ ## VARIABLE (const QV4::BuiltinFunction *b, QV4::CallData *callData)\
+static QV4::ReturnedValue particleData_set_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)\
{\
QV4::Scope scope(b); \
- QV4::Scoped<QV4ParticleData> r(scope, callData->thisObject); \
+ QV4::Scoped<QV4ParticleData> r(scope, *thisObject); \
if (!r || !r->d()->datum)\
RETURN_RESULT(scope.engine->throwError(QStringLiteral("Not a valid ParticleData object")));\
\
- r->d()->datum-> SETTER (callData->argc() ? callData->args[0].toNumber() : qt_qnan(), r->d()->particleSystem);\
+ r->d()->datum-> SETTER (argc ? argv[0].toNumber() : qt_qnan(), r->d()->particleSystem);\
RETURN_UNDEFINED(); \
}
@@ -510,12 +510,12 @@ QV4ParticleDataDeletable::~QV4ParticleDataDeletable()
V4_DEFINE_EXTENSION(QV4ParticleDataDeletable, particleV4Data);
-QQuickV4ParticleData::QQuickV4ParticleData(QV8Engine* engine, QQuickParticleData* datum, QQuickParticleSystem *system)
+QQuickV4ParticleData::QQuickV4ParticleData(QV4::ExecutionEngine* v4, QQuickParticleData* datum,
+ QQuickParticleSystem *system)
{
- if (!engine || !datum)
+ if (!v4 || !datum)
return;
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine);
QV4::Scope scope(v4);
QV4ParticleDataDeletable *d = particleV4Data(scope.engine);
QV4::ScopedObject o(scope, v4->memoryManager->allocObject<QV4ParticleData>(datum, system));
diff --git a/src/particles/qquickv4particledata_p.h b/src/particles/qquickv4particledata_p.h
index d73e3b644d..3d682ab297 100644
--- a/src/particles/qquickv4particledata_p.h
+++ b/src/particles/qquickv4particledata_p.h
@@ -61,7 +61,7 @@ class QQuickParticleData;
class QQuickParticleSystem;
class QQuickV4ParticleData {
public:
- QQuickV4ParticleData(QV8Engine*, QQuickParticleData*, QQuickParticleSystem *system);
+ QQuickV4ParticleData(QV4::ExecutionEngine*, QQuickParticleData*, QQuickParticleSystem *system);
~QQuickV4ParticleData();
QQmlV4Handle v4Value() const;
private:
diff --git a/src/particles/qquickwander.cpp b/src/particles/qquickwander.cpp
index cfdede440b..a78482ec84 100644
--- a/src/particles/qquickwander.cpp
+++ b/src/particles/qquickwander.cpp
@@ -103,8 +103,8 @@ WanderData* QQuickWanderAffector::getData(int idx)
d->y_vel = 0;
d->x_peak = m_xVariance;
d->y_peak = m_yVariance;
- d->x_var = m_pace * QRandomGenerator::getReal();
- d->y_var = m_pace * QRandomGenerator::getReal();
+ d->x_var = m_pace * QRandomGenerator::global()->generateDouble();
+ d->y_var = m_pace * QRandomGenerator::global()->generateDouble();
m_wanderData.insert(idx, d);
return d;
@@ -125,7 +125,7 @@ bool QQuickWanderAffector::affectParticle(QQuickParticleData* data, qreal dt)
if (m_xVariance != 0.) {
if ((d->x_vel > d->x_peak && d->x_var > 0.0) || (d->x_vel < -d->x_peak && d->x_var < 0.0)) {
d->x_var = -d->x_var;
- d->x_peak = m_xVariance + m_xVariance * QRandomGenerator::getReal();
+ d->x_peak = m_xVariance + m_xVariance * QRandomGenerator::global()->generateDouble();
}
d->x_vel += d->x_var * dt;
}
@@ -134,7 +134,7 @@ bool QQuickWanderAffector::affectParticle(QQuickParticleData* data, qreal dt)
if (m_yVariance != 0.) {
if ((d->y_vel > d->y_peak && d->y_var > 0.0) || (d->y_vel < -d->y_peak && d->y_var < 0.0)) {
d->y_var = -d->y_var;
- d->y_peak = m_yVariance + m_yVariance * QRandomGenerator::getReal();
+ d->y_peak = m_yVariance + m_yVariance * QRandomGenerator::global()->generateDouble();
}
d->y_vel += d->y_var * dt;
}
@@ -147,8 +147,8 @@ bool QQuickWanderAffector::affectParticle(QQuickParticleData* data, qreal dt)
p->y += dy;
return true;
*/
- qreal dx = dt * m_pace * (2 * QRandomGenerator::getReal() - 1);
- qreal dy = dt * m_pace * (2 * QRandomGenerator::getReal() - 1);
+ qreal dx = dt * m_pace * (2 * QRandomGenerator::global()->generateDouble() - 1);
+ qreal dy = dt * m_pace * (2 * QRandomGenerator::global()->generateDouble() - 1);
qreal newX, newY;
switch (m_affectedParameter){
case Position:
diff --git a/src/plugins/qmltooling/packetprotocol/qpacketprotocol.cpp b/src/plugins/qmltooling/packetprotocol/qpacketprotocol.cpp
index e541810330..5460d617dd 100644
--- a/src/plugins/qmltooling/packetprotocol/qpacketprotocol.cpp
+++ b/src/plugins/qmltooling/packetprotocol/qpacketprotocol.cpp
@@ -247,7 +247,7 @@ void QPacketProtocol::readyToRead()
disconnect(d->dev, &QIODevice::readyRead, this, &QPacketProtocol::readyToRead);
disconnect(d->dev, &QIODevice::aboutToClose, this, &QPacketProtocol::aboutToClose);
disconnect(d->dev, &QIODevice::bytesWritten, this, &QPacketProtocol::bytesWritten);
- d->dev = 0;
+ d->dev = nullptr;
emit invalidPacket();
return;
}
diff --git a/src/plugins/qmltooling/packetprotocol/qpacketprotocol_p.h b/src/plugins/qmltooling/packetprotocol/qpacketprotocol_p.h
index 7fd722f17f..35edb568aa 100644
--- a/src/plugins/qmltooling/packetprotocol/qpacketprotocol_p.h
+++ b/src/plugins/qmltooling/packetprotocol/qpacketprotocol_p.h
@@ -63,7 +63,7 @@ class QPacketProtocol : public QObject
Q_OBJECT
Q_DECLARE_PRIVATE(QPacketProtocol)
public:
- explicit QPacketProtocol(QIODevice *dev, QObject *parent = 0);
+ explicit QPacketProtocol(QIODevice *dev, QObject *parent = nullptr);
void send(const QByteArray &data);
qint64 packetsAvailable() const;
diff --git a/src/plugins/qmltooling/qmldbg_debugger/qqmldebuggerservicefactory.cpp b/src/plugins/qmltooling/qmldbg_debugger/qqmldebuggerservicefactory.cpp
index 9315adf4ce..3851cdc71f 100644
--- a/src/plugins/qmltooling/qmldbg_debugger/qqmldebuggerservicefactory.cpp
+++ b/src/plugins/qmltooling/qmldbg_debugger/qqmldebuggerservicefactory.cpp
@@ -52,7 +52,7 @@ QQmlDebugService *QQmlDebuggerServiceFactory::create(const QString &key)
if (key == QV4DebugServiceImpl::s_key)
return new QV4DebugServiceImpl(this);
- return 0;
+ return nullptr;
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp b/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp
index 182e4257f8..288ad243ce 100644
--- a/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp
+++ b/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp
@@ -61,7 +61,7 @@
QT_BEGIN_NAMESPACE
QQmlEngineDebugServiceImpl::QQmlEngineDebugServiceImpl(QObject *parent) :
- QQmlEngineDebugService(2, parent), m_watch(new QQmlWatcher(this)), m_statesDelegate(0)
+ QQmlEngineDebugService(2, parent), m_watch(new QQmlWatcher(this)), m_statesDelegate(nullptr)
{
connect(m_watch, &QQmlWatcher::propertyChanged,
this, &QQmlEngineDebugServiceImpl::propertyChanged);
@@ -209,19 +209,32 @@ QVariant QQmlEngineDebugServiceImpl::valueContents(QVariant value) const
}
if (QQmlValueTypeFactory::isValueType(userType)) {
+ switch (userType) {
+ case QMetaType::QRect:
+ case QMetaType::QRectF:
+ case QMetaType::QPoint:
+ case QMetaType::QPointF:
+ case QMetaType::QSize:
+ case QMetaType::QSizeF:
+ case QMetaType::QFont:
+ // Don't call the toString() method on those. The stream operators are better.
+ return value;
+ default:
+ break;
+ }
+
const QMetaObject *mo = QQmlValueTypeFactory::metaObjectForMetaType(userType);
if (mo) {
- int toStringIndex = mo->indexOfMethod("toString");
+ int toStringIndex = mo->indexOfMethod("toString()");
if (toStringIndex != -1) {
QMetaMethod mm = mo->method(toStringIndex);
- QMetaType info(userType);
QString s;
- if (info.flags() & QMetaType::IsGadget
- && mm.invokeOnGadget(value.data(), Q_RETURN_ARG(QString, s)))
+ if (mm.invokeOnGadget(value.data(), Q_RETURN_ARG(QString, s)))
return s;
}
}
+ // We expect all QML value types to either have a toString() method or stream operators
return value;
}
@@ -337,6 +350,9 @@ void QQmlEngineDebugServiceImpl::buildObjectList(QDataStream &message,
QQmlContext *ctxt,
const QList<QPointer<QObject> > &instances)
{
+ if (!ctxt->isValid())
+ return;
+
QQmlContextData *p = QQmlContextData::get(ctxt);
QString ctxtName = ctxt->objectName();
@@ -399,11 +415,8 @@ QQmlEngineDebugServiceImpl::objectData(QObject *object)
}
QQmlContext *context = qmlContext(object);
- if (context) {
- QQmlContextData *cdata = QQmlContextData::get(context);
- if (cdata)
- rv.idString = cdata->findObjectId(object);
- }
+ if (context && context->isValid())
+ rv.idString = QQmlContextData::get(context)->findObjectId(object);
rv.objectName = object->objectName();
rv.objectId = QQmlDebugService::idForObject(object);
@@ -564,14 +577,14 @@ void QQmlEngineDebugServiceImpl::processMessage(const QByteArray &message)
QObject *object = QQmlDebugService::objectForId(objectId);
QQmlContext *context = qmlContext(object);
- if (!context) {
+ if (!context || !context->isValid()) {
QQmlEngine *engine = qobject_cast<QQmlEngine *>(
QQmlDebugService::objectForId(engineId));
if (engine && m_engines.contains(engine))
context = engine->rootContext();
}
QVariant result;
- if (context) {
+ if (context && context->isValid()) {
QQmlExpression exprObj(context, object, expr);
bool undefined = false;
QVariant value = exprObj.evaluate(&undefined);
@@ -632,7 +645,7 @@ bool QQmlEngineDebugServiceImpl::setBinding(int objectId,
QObject *object = objectForId(objectId);
QQmlContext *context = qmlContext(object);
- if (object && context) {
+ if (object && context && context->isValid()) {
QQmlProperty property(object, propertyName, context);
if (property.isValid()) {
@@ -677,7 +690,7 @@ bool QQmlEngineDebugServiceImpl::resetBinding(int objectId, const QString &prope
QObject *object = objectForId(objectId);
QQmlContext *context = qmlContext(object);
- if (object && context) {
+ if (object && context && context->isValid()) {
QStringRef parentPropertyRef(&propertyName);
const int idx = parentPropertyRef.indexOf(QLatin1Char('.'));
if (idx != -1)
@@ -713,7 +726,7 @@ bool QQmlEngineDebugServiceImpl::resetBinding(int objectId, const QString &prope
if (hasValidSignal(object, propertyName)) {
QQmlProperty property(object, propertyName, context);
- QQmlPropertyPrivate::setSignalExpression(property, 0);
+ QQmlPropertyPrivate::setSignalExpression(property, nullptr);
return true;
}
@@ -732,11 +745,9 @@ bool QQmlEngineDebugServiceImpl::setMethodBody(int objectId, const QString &meth
{
QObject *object = objectForId(objectId);
QQmlContext *context = qmlContext(object);
- if (!object || !context || !context->engine())
+ if (!object || !context || !context->isValid())
return false;
QQmlContextData *contextData = QQmlContextData::get(context);
- if (!contextData)
- return false;
QQmlPropertyData dummy;
QQmlPropertyData *prop =
@@ -760,7 +771,7 @@ bool QQmlEngineDebugServiceImpl::setMethodBody(int objectId, const QString &meth
QQmlVMEMetaObject *vmeMetaObject = QQmlVMEMetaObject::get(object);
Q_ASSERT(vmeMetaObject); // the fact we found the property above should guarentee this
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(qmlEngine(object)->handle());
+ QV4::ExecutionEngine *v4 = qmlEngine(object)->handle();
QV4::Scope scope(v4);
int lineNumber = 0;
diff --git a/src/plugins/qmltooling/qmldbg_debugger/qqmlwatcher.cpp b/src/plugins/qmltooling/qmldbg_debugger/qqmlwatcher.cpp
index cbbbb2ceb7..86571e6cbe 100644
--- a/src/plugins/qmltooling/qmldbg_debugger/qqmlwatcher.cpp
+++ b/src/plugins/qmltooling/qmldbg_debugger/qqmlwatcher.cpp
@@ -61,12 +61,12 @@ public:
QObject *object,
int debugId,
const QMetaProperty &prop,
- QQmlWatcher *parent = 0);
+ QQmlWatcher *parent = nullptr);
QQmlWatchProxy(int id,
QQmlExpression *exp,
int debugId,
- QQmlWatcher *parent = 0);
+ QQmlWatcher *parent = nullptr);
public slots:
void notifyValueChanged(); // Needs to be a slot because of QQmlPropertyPrivate::connect()
@@ -86,7 +86,7 @@ QQmlWatchProxy::QQmlWatchProxy(int id,
QQmlExpression *exp,
int debugId,
QQmlWatcher *parent)
-: QObject(parent), m_id(id), m_watch(parent), m_object(0), m_debugId(debugId), m_expr(exp)
+: QObject(parent), m_id(id), m_watch(parent), m_object(nullptr), m_debugId(debugId), m_expr(exp)
{
QObject::connect(m_expr, &QQmlExpression::valueChanged,
this, &QQmlWatchProxy::notifyValueChanged);
@@ -97,7 +97,7 @@ QQmlWatchProxy::QQmlWatchProxy(int id,
int debugId,
const QMetaProperty &prop,
QQmlWatcher *parent)
-: QObject(parent), m_id(id), m_watch(parent), m_object(object), m_debugId(debugId), m_property(prop), m_expr(0)
+: QObject(parent), m_id(id), m_watch(parent), m_object(object), m_debugId(debugId), m_property(prop), m_expr(nullptr)
{
static int refreshIdx = -1;
if(refreshIdx == -1)
diff --git a/src/plugins/qmltooling/qmldbg_debugger/qv4datacollector.cpp b/src/plugins/qmltooling/qmldbg_debugger/qv4datacollector.cpp
index a538956e8e..c86f3d1803 100644
--- a/src/plugins/qmltooling/qmldbg_debugger/qv4datacollector.cpp
+++ b/src/plugins/qmltooling/qmldbg_debugger/qv4datacollector.cpp
@@ -69,19 +69,19 @@ QV4::Heap::ExecutionContext *QV4DataCollector::findContext(int frame)
{
QV4::CppStackFrame *f = findFrame(frame);
- return f ? f->context()->d() : 0;
+ return f ? f->context()->d() : nullptr;
}
QV4::Heap::CallContext *QV4DataCollector::findScope(QV4::Heap::ExecutionContext *ctx, int scope)
{
if (!ctx)
- return 0;
+ return nullptr;
for (; scope > 0 && ctx; --scope)
ctx = ctx->outer;
return (ctx && ctx->type == QV4::Heap::ExecutionContext::Type_CallContext) ?
- static_cast<QV4::Heap::CallContext *>(ctx) : 0;
+ static_cast<QV4::Heap::CallContext *>(ctx) : nullptr;
}
QVector<QV4::Heap::ExecutionContext::ContextType> QV4DataCollector::getScopeTypes(int frame)
@@ -139,16 +139,16 @@ const QV4::Object *collectProperty(const QV4::ScopedValue &value, QV4::Execution
switch (value->type()) {
case QV4::Value::Empty_Type:
Q_ASSERT(!"empty Value encountered");
- return 0;
+ return nullptr;
case QV4::Value::Undefined_Type:
dict.insert(valueKey, QJsonValue::Undefined);
- return 0;
+ return nullptr;
case QV4::Value::Null_Type:
dict.insert(valueKey, QJsonValue::Null);
- return 0;
+ return nullptr;
case QV4::Value::Boolean_Type:
dict.insert(valueKey, value->booleanValue());
- return 0;
+ return nullptr;
case QV4::Value::Managed_Type:
if (const QV4::String *s = value->as<QV4::String>()) {
dict.insert(valueKey, s->toQString());
@@ -176,10 +176,10 @@ const QV4::Object *collectProperty(const QV4::ScopedValue &value, QV4::Execution
} else {
Q_UNREACHABLE();
}
- return 0;
+ return nullptr;
case QV4::Value::Integer_Type:
dict.insert(valueKey, value->integerValue());
- return 0;
+ return nullptr;
default: {// double
const double val = value->doubleValue();
if (qIsFinite(val))
@@ -190,7 +190,7 @@ const QV4::Object *collectProperty(const QV4::ScopedValue &value, QV4::Execution
dict.insert(valueKey, QStringLiteral("-Infinity"));
else
dict.insert(valueKey, QStringLiteral("Infinity"));
- return 0;
+ return nullptr;
}
}
}
diff --git a/src/plugins/qmltooling/qmldbg_debugger/qv4debugger.cpp b/src/plugins/qmltooling/qmldbg_debugger/qv4debugger.cpp
index 1581cf637d..a1ed211a55 100644
--- a/src/plugins/qmltooling/qmldbg_debugger/qv4debugger.cpp
+++ b/src/plugins/qmltooling/qmldbg_debugger/qv4debugger.cpp
@@ -71,8 +71,8 @@ QV4Debugger::QV4Debugger(QV4::ExecutionEngine *engine)
, m_haveBreakPoints(false)
, m_breakOnThrow(false)
, m_returnedValue(engine, QV4::Primitive::undefinedValue())
- , m_gatherSources(0)
- , m_runningJob(0)
+ , m_gatherSources(nullptr)
+ , m_runningJob(nullptr)
, m_collector(engine)
{
static int debuggerId = qRegisterMetaType<QV4Debugger*>();
@@ -182,14 +182,14 @@ void QV4Debugger::maybeBreakAtInstruction()
if (m_gatherSources) {
m_gatherSources->run();
delete m_gatherSources;
- m_gatherSources = 0;
+ m_gatherSources = nullptr;
}
switch (m_stepping) {
case StepOver:
if (m_currentFrame != m_engine->currentStackFrame)
break;
- // fall through
+ Q_FALLTHROUGH();
case StepIn:
pauseAndWait(Step);
return;
@@ -295,11 +295,11 @@ bool QV4Debugger::reallyHitTheBreakPoint(const QString &filename, int linenr)
if (condition.isEmpty())
return true;
- Q_ASSERT(m_runningJob == 0);
+ Q_ASSERT(m_runningJob == nullptr);
EvalJob evilJob(m_engine, condition);
m_runningJob = &evilJob;
m_runningJob->run();
- m_runningJob = 0;
+ m_runningJob = nullptr;
return evilJob.resultAsBoolean();
}
@@ -313,7 +313,7 @@ void QV4Debugger::runInEngine(QV4DebugJob *job)
void QV4Debugger::runInEngine_havingLock(QV4DebugJob *job)
{
Q_ASSERT(job);
- Q_ASSERT(m_runningJob == 0);
+ Q_ASSERT(m_runningJob == nullptr);
m_runningJob = job;
if (state() == Paused)
@@ -321,7 +321,7 @@ void QV4Debugger::runInEngine_havingLock(QV4DebugJob *job)
else
emit scheduleJob();
m_jobIsRunning.wait(&m_lock);
- m_runningJob = 0;
+ m_runningJob = nullptr;
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_debugger/qv4debuggeragent.cpp b/src/plugins/qmltooling/qmldbg_debugger/qv4debuggeragent.cpp
index 87e75c49b5..71645579c5 100644
--- a/src/plugins/qmltooling/qmldbg_debugger/qv4debuggeragent.cpp
+++ b/src/plugins/qmltooling/qmldbg_debugger/qv4debuggeragent.cpp
@@ -56,13 +56,13 @@ QV4Debugger *QV4DebuggerAgent::pausedDebugger() const
if (debugger->state() == QV4Debugger::Paused)
return debugger;
}
- return 0;
+ return nullptr;
}
bool QV4DebuggerAgent::isRunning() const
{
// "running" means none of the engines are paused.
- return pausedDebugger() == 0;
+ return pausedDebugger() == nullptr;
}
void QV4DebuggerAgent::debuggerPaused(QV4Debugger *debugger, QV4Debugger::PauseReason reason)
diff --git a/src/plugins/qmltooling/qmldbg_debugger/qv4debugjob.cpp b/src/plugins/qmltooling/qmldbg_debugger/qv4debugjob.cpp
index 6f254c9e28..5b049ab521 100644
--- a/src/plugins/qmltooling/qmldbg_debugger/qv4debugjob.cpp
+++ b/src/plugins/qmltooling/qmldbg_debugger/qv4debugjob.cpp
@@ -208,7 +208,7 @@ void ValueLookupJob::run()
QScopedPointer<QObject> scopeObject;
QV4::ExecutionEngine *engine = collector->engine();
QV4::Scope scope(engine);
- QV4::Heap::ExecutionContext *qmlContext = 0;
+ QV4::Heap::ExecutionContext *qmlContext = nullptr;
if (engine->qmlEngine() && !engine->qmlContext()) {
scopeObject.reset(new QObject);
qmlContext = QV4::QmlContext::create(engine->currentContext(),
diff --git a/src/plugins/qmltooling/qmldbg_debugger/qv4debugservice.cpp b/src/plugins/qmltooling/qmldbg_debugger/qv4debugservice.cpp
index fca811cb28..61209e08cb 100644
--- a/src/plugins/qmltooling/qmldbg_debugger/qv4debugservice.cpp
+++ b/src/plugins/qmltooling/qmldbg_debugger/qv4debugservice.cpp
@@ -98,7 +98,7 @@ public:
debugService->send(response);
}
- debugService = 0;
+ debugService = nullptr;
seq = QJsonValue();
req = QJsonObject();
response = QJsonObject();
@@ -702,7 +702,7 @@ void QV4DebugServiceImpl::engineAdded(QJSEngine *engine)
{
QMutexLocker lock(&m_configMutex);
if (engine) {
- QV4::ExecutionEngine *ee = QV8Engine::getV4(engine->handle());
+ QV4::ExecutionEngine *ee = engine->handle();
if (QQmlDebugConnector *server = QQmlDebugConnector::instance()) {
if (ee) {
QV4Debugger *debugger = new QV4Debugger(ee);
@@ -720,7 +720,7 @@ void QV4DebugServiceImpl::engineAboutToBeRemoved(QJSEngine *engine)
{
QMutexLocker lock(&m_configMutex);
if (engine){
- const QV4::ExecutionEngine *ee = QV8Engine::getV4(engine->handle());
+ const QV4::ExecutionEngine *ee = engine->handle();
if (ee) {
QV4Debugger *debugger = qobject_cast<QV4Debugger *>(ee->debugger());
if (debugger)
diff --git a/src/plugins/qmltooling/qmldbg_inspector/highlight.cpp b/src/plugins/qmltooling/qmldbg_inspector/highlight.cpp
index c7307db240..0d6cd45354 100644
--- a/src/plugins/qmltooling/qmldbg_inspector/highlight.cpp
+++ b/src/plugins/qmltooling/qmldbg_inspector/highlight.cpp
@@ -100,7 +100,7 @@ void Highlight::adjust()
return;
bool success = false;
- m_transform = m_item->itemTransform(0, &success);
+ m_transform = m_item->itemTransform(nullptr, &success);
if (!success)
m_transform = QTransform();
diff --git a/src/plugins/qmltooling/qmldbg_inspector/inspecttool.cpp b/src/plugins/qmltooling/qmldbg_inspector/inspecttool.cpp
index bc146b176c..1781670cf3 100644
--- a/src/plugins/qmltooling/qmldbg_inspector/inspecttool.cpp
+++ b/src/plugins/qmltooling/qmldbg_inspector/inspecttool.cpp
@@ -62,8 +62,8 @@ InspectTool::InspectTool(QQuickWindowInspector *inspector, QQuickWindow *view) :
m_contentItem(view->contentItem()),
m_touchTimestamp(0),
m_hoverHighlight(new HoverHighlight(inspector->overlay())),
- m_lastItem(0),
- m_lastClickedItem(0)
+ m_lastItem(nullptr),
+ m_lastClickedItem(nullptr)
{
//Timer to display selected item's name
m_nameDisplayTimer.setSingleShot(true);
diff --git a/src/plugins/qmltooling/qmldbg_inspector/qqmlinspectorservice.cpp b/src/plugins/qmltooling/qmldbg_inspector/qqmlinspectorservice.cpp
index d0d8d62615..fa27adedfd 100644
--- a/src/plugins/qmltooling/qmldbg_inspector/qqmlinspectorservice.cpp
+++ b/src/plugins/qmltooling/qmldbg_inspector/qqmlinspectorservice.cpp
@@ -49,7 +49,7 @@ class QQmlInspectorServiceImpl : public QQmlInspectorService
{
Q_OBJECT
public:
- QQmlInspectorServiceImpl(QObject *parent = 0);
+ QQmlInspectorServiceImpl(QObject *parent = nullptr);
void addWindow(QQuickWindow *window) override;
void setParentWindow(QQuickWindow *window, QWindow *parent) override;
@@ -72,7 +72,7 @@ private:
};
QQmlInspectorServiceImpl::QQmlInspectorServiceImpl(QObject *parent):
- QQmlInspectorService(1, parent), m_globalInspector(0)
+ QQmlInspectorService(1, parent), m_globalInspector(nullptr)
{
connect(this, &QQmlInspectorServiceImpl::scheduleMessage,
this, &QQmlInspectorServiceImpl::messageFromClient, Qt::QueuedConnection);
@@ -95,7 +95,7 @@ QmlJSDebugger::GlobalInspector *QQmlInspectorServiceImpl::checkInspector()
}
} else if (m_globalInspector) {
delete m_globalInspector;
- m_globalInspector = 0;
+ m_globalInspector = nullptr;
}
return m_globalInspector;
}
@@ -138,7 +138,7 @@ void QQmlInspectorServiceImpl::messageFromClient(const QByteArray &message)
QQmlDebugService *QQmlInspectorServiceFactory::create(const QString &key)
{
- return key == QQmlInspectorServiceImpl::s_key ? new QQmlInspectorServiceImpl(this) : 0;
+ return key == QQmlInspectorServiceImpl::s_key ? new QQmlInspectorServiceImpl(this) : nullptr;
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_inspector/qquickwindowinspector.cpp b/src/plugins/qmltooling/qmldbg_inspector/qquickwindowinspector.cpp
index 16056addbd..09eb6bfc28 100644
--- a/src/plugins/qmltooling/qmldbg_inspector/qquickwindowinspector.cpp
+++ b/src/plugins/qmltooling/qmldbg_inspector/qquickwindowinspector.cpp
@@ -54,14 +54,14 @@ static QQuickItem *itemAt(QQuickItem *item, const QPointF &pos,
QQuickItem *overlay)
{
if (item == overlay)
- return 0;
+ return nullptr;
if (!item->isVisible() || item->opacity() == 0.0)
- return 0;
+ return nullptr;
if (item->flags() & QQuickItem::ItemClipsChildrenToShape) {
if (!QRectF(0, 0, item->width(), item->height()).contains(pos))
- return 0;
+ return nullptr;
}
QList<QQuickItem *> children = QQuickItemPrivate::get(item)->paintOrderChildItems();
@@ -73,10 +73,10 @@ static QQuickItem *itemAt(QQuickItem *item, const QPointF &pos,
}
if (!(item->flags() & QQuickItem::ItemHasContents))
- return 0;
+ return nullptr;
if (!QRectF(0, 0, item->width(), item->height()).contains(pos))
- return 0;
+ return nullptr;
return item;
}
@@ -111,8 +111,8 @@ QQuickWindowInspector::QQuickWindowInspector(QQuickWindow *quickWindow, QObject
QObject(parent),
m_overlay(new QQuickItem),
m_window(quickWindow),
- m_parentWindow(0),
- m_tool(0)
+ m_parentWindow(nullptr),
+ m_tool(nullptr)
{
setParentWindow(quickWindow);
@@ -169,13 +169,29 @@ bool QQuickWindowInspector::eventFilter(QObject *obj, QEvent *event)
return QObject::eventFilter(obj, event);
}
+static Qt::WindowFlags fixFlags(Qt::WindowFlags flags)
+{
+ // If only the type flag is given, some other window flags are automatically assumed. When we
+ // add a flag, we need to make those explicit.
+ switch (flags) {
+ case Qt::Window:
+ return flags | Qt::WindowTitleHint | Qt::WindowSystemMenuHint | Qt::WindowCloseButtonHint
+ | Qt::WindowMinimizeButtonHint | Qt::WindowMaximizeButtonHint;
+ case Qt::Dialog:
+ case Qt::Tool:
+ return flags | Qt::WindowTitleHint | Qt::WindowSystemMenuHint | Qt::WindowCloseButtonHint;
+ default:
+ return flags;
+ }
+}
+
void QQuickWindowInspector::setShowAppOnTop(bool appOnTop)
{
if (!m_parentWindow)
return;
Qt::WindowFlags flags = m_parentWindow->flags();
- Qt::WindowFlags newFlags = appOnTop ? (flags | Qt::WindowStaysOnTopHint) :
+ Qt::WindowFlags newFlags = appOnTop ? (fixFlags(flags) | Qt::WindowStaysOnTopHint) :
(flags & ~Qt::WindowStaysOnTopHint);
if (newFlags != flags)
m_parentWindow->setFlags(newFlags);
@@ -183,7 +199,7 @@ void QQuickWindowInspector::setShowAppOnTop(bool appOnTop)
bool QQuickWindowInspector::isEnabled() const
{
- return m_tool != 0;
+ return m_tool != nullptr;
}
void QQuickWindowInspector::setEnabled(bool enabled)
@@ -192,7 +208,7 @@ void QQuickWindowInspector::setEnabled(bool enabled)
m_tool = new InspectTool(this, m_window);
} else {
delete m_tool;
- m_tool = 0;
+ m_tool = nullptr;
}
}
diff --git a/src/plugins/qmltooling/qmldbg_local/qlocalclientconnection.cpp b/src/plugins/qmltooling/qmldbg_local/qlocalclientconnection.cpp
index e60644518f..1708166a8a 100644
--- a/src/plugins/qmltooling/qmldbg_local/qlocalclientconnection.cpp
+++ b/src/plugins/qmltooling/qmldbg_local/qlocalclientconnection.cpp
@@ -55,7 +55,7 @@ class QLocalClientConnection : public QQmlDebugServerConnection
public:
QLocalClientConnection();
- ~QLocalClientConnection();
+ ~QLocalClientConnection() override;
void setServer(QQmlDebugServer *server) override;
bool setPortRange(int portFrom, int portTo, bool block, const QString &hostaddress) override;
@@ -71,18 +71,13 @@ private:
void connectionEstablished();
bool connectToServer();
- bool m_block;
+ bool m_block = false;
QString m_filename;
- QLocalSocket *m_socket;
- QQmlDebugServer *m_debugServer;
+ QLocalSocket *m_socket = nullptr;
+ QQmlDebugServer *m_debugServer = nullptr;
};
-QLocalClientConnection::QLocalClientConnection() :
- m_block(false),
- m_socket(0),
- m_debugServer(0)
-{
-}
+QLocalClientConnection::QLocalClientConnection() { }
QLocalClientConnection::~QLocalClientConnection()
{
@@ -106,7 +101,7 @@ void QLocalClientConnection::disconnect()
m_socket->waitForBytesWritten();
m_socket->deleteLater();
- m_socket = 0;
+ m_socket = nullptr;
}
bool QLocalClientConnection::setPortRange(int portFrom, int portTo, bool block,
@@ -161,7 +156,7 @@ void QLocalClientConnection::connectionEstablished()
QQmlDebugServerConnection *QLocalClientConnectionFactory::create(const QString &key)
{
- return (key == QLatin1String("QLocalClientConnection") ? new QLocalClientConnection : 0);
+ return (key == QLatin1String("QLocalClientConnection") ? new QLocalClientConnection : nullptr);
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_messages/qdebugmessageservice.cpp b/src/plugins/qmltooling/qmldbg_messages/qdebugmessageservice.cpp
index bdfed03a40..2bf9210b37 100644
--- a/src/plugins/qmltooling/qmldbg_messages/qdebugmessageservice.cpp
+++ b/src/plugins/qmltooling/qmldbg_messages/qdebugmessageservice.cpp
@@ -51,7 +51,7 @@ void DebugMessageHandler(QtMsgType type, const QMessageLogContext &ctxt,
}
QDebugMessageServiceImpl::QDebugMessageServiceImpl(QObject *parent) :
- QDebugMessageService(2, parent), oldMsgHandler(0),
+ QDebugMessageService(2, parent), oldMsgHandler(nullptr),
prevState(QQmlDebugService::NotConnected)
{
// don't execute stateChanged() in parallel
diff --git a/src/plugins/qmltooling/qmldbg_messages/qdebugmessageservicefactory.cpp b/src/plugins/qmltooling/qmldbg_messages/qdebugmessageservicefactory.cpp
index 860d654128..177ca1fe80 100644
--- a/src/plugins/qmltooling/qmldbg_messages/qdebugmessageservicefactory.cpp
+++ b/src/plugins/qmltooling/qmldbg_messages/qdebugmessageservicefactory.cpp
@@ -48,7 +48,7 @@ QQmlDebugService *QDebugMessageServiceFactory::create(const QString &key)
if (key == QDebugMessageServiceImpl::s_key)
return new QDebugMessageServiceImpl(this);
- return 0;
+ return nullptr;
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_native/qqmlnativedebugconnector.cpp b/src/plugins/qmltooling/qmldbg_native/qqmlnativedebugconnector.cpp
index a4b3455eff..93ac875e2d 100644
--- a/src/plugins/qmltooling/qmldbg_native/qqmlnativedebugconnector.cpp
+++ b/src/plugins/qmltooling/qmldbg_native/qqmlnativedebugconnector.cpp
@@ -224,7 +224,7 @@ QQmlDebugService *QQmlNativeDebugConnector::service(const QString &name) const
if ((*i)->name() == name)
return *i;
}
- return 0;
+ return nullptr;
}
void QQmlNativeDebugConnector::addEngine(QJSEngine *engine)
@@ -360,7 +360,7 @@ void QQmlNativeDebugConnector::sendMessages(const QString &name, const QList<QBy
QQmlDebugConnector *QQmlNativeDebugConnectorFactory::create(const QString &key)
{
- return key == QLatin1String("QQmlNativeDebugConnector") ? new QQmlNativeDebugConnector : 0;
+ return key == QLatin1String("QQmlNativeDebugConnector") ? new QQmlNativeDebugConnector : nullptr;
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservice.cpp b/src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservice.cpp
index eeedb59ce6..718975275a 100644
--- a/src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservice.cpp
+++ b/src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservice.cpp
@@ -229,7 +229,7 @@ private:
QV4::ExecutionEngine *m_engine;
QQmlNativeDebugServiceImpl *m_service;
- QV4::CppStackFrame *m_currentFrame = 0;
+ QV4::CppStackFrame *m_currentFrame = nullptr;
Speed m_stepping;
bool m_pauseRequested;
bool m_runningJob;
@@ -457,7 +457,7 @@ void Collector::collect(QJsonArray *out, const QString &parentIName, const QStri
void NativeDebugger::handleVariables(QJsonObject *response, const QJsonObject &arguments)
{
TRACE_PROTOCOL("Build variables");
- QV4::CppStackFrame *frame = 0;
+ QV4::CppStackFrame *frame = nullptr;
decodeFrame(arguments.value(QLatin1String("context")).toString(), &frame);
if (!frame) {
setError(response, QStringLiteral("No stack frame passed"));
@@ -500,7 +500,7 @@ void NativeDebugger::handleVariables(QJsonObject *response, const QJsonObject &a
void NativeDebugger::handleExpressions(QJsonObject *response, const QJsonObject &arguments)
{
TRACE_PROTOCOL("Evaluate expressions");
- QV4::CppStackFrame *frame = 0;
+ QV4::CppStackFrame *frame = nullptr;
decodeFrame(arguments.value(QLatin1String("context")).toString(), &frame);
if (!frame) {
setError(response, QStringLiteral("No stack frame passed"));
@@ -713,7 +713,7 @@ void QQmlNativeDebugServiceImpl::engineAboutToBeAdded(QJSEngine *engine)
{
TRACE_PROTOCOL("Adding engine" << engine);
if (engine) {
- QV4::ExecutionEngine *ee = QV8Engine::getV4(engine->handle());
+ QV4::ExecutionEngine *ee = engine->handle();
TRACE_PROTOCOL("Adding execution engine" << ee);
if (ee) {
NativeDebugger *debugger = new NativeDebugger(this, ee);
@@ -729,7 +729,7 @@ void QQmlNativeDebugServiceImpl::engineAboutToBeRemoved(QJSEngine *engine)
{
TRACE_PROTOCOL("Removing engine" << engine);
if (engine) {
- QV4::ExecutionEngine *executionEngine = QV8Engine::getV4(engine->handle());
+ QV4::ExecutionEngine *executionEngine = engine->handle();
const auto debuggersCopy = m_debuggers;
for (NativeDebugger *debugger : debuggersCopy) {
if (debugger->engine() == executionEngine)
diff --git a/src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservicefactory.cpp b/src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservicefactory.cpp
index 1841c82d5d..c0b74c74ff 100644
--- a/src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservicefactory.cpp
+++ b/src/plugins/qmltooling/qmldbg_nativedebugger/qqmlnativedebugservicefactory.cpp
@@ -48,7 +48,7 @@ QQmlDebugService *QQmlNativeDebugServiceFactory::create(const QString &key)
if (key == QQmlNativeDebugServiceImpl::s_key)
return new QQmlNativeDebugServiceImpl(this);
- return 0;
+ return nullptr;
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp b/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp
index c388c6e74a..eb6fbce101 100644
--- a/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp
+++ b/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp
@@ -126,7 +126,7 @@ void QQmlProfilerServiceImpl::engineAboutToBeAdded(QJSEngine *engine)
= new QQmlProfilerAdapter(this, &(enginePrivate->typeLoader));
addEngineProfiler(compileAdapter, engine);
}
- QV4ProfilerAdapter *v4Adapter = new QV4ProfilerAdapter(this, QV8Engine::getV4(engine->handle()));
+ QV4ProfilerAdapter *v4Adapter = new QV4ProfilerAdapter(this, engine->handle());
addEngineProfiler(v4Adapter, engine);
QQmlConfigurableDebugService<QQmlProfilerService>::engineAboutToBeAdded(engine);
}
@@ -240,9 +240,9 @@ void QQmlProfilerServiceImpl::startProfiling(QJSEngine *engine, quint64 features
QQmlDebugPacket d;
- d << m_timer.nsecsElapsed() << (int)Event << (int)StartTrace;
+ d << m_timer.nsecsElapsed() << static_cast<qint32>(Event) << static_cast<qint32>(StartTrace);
bool startedAny = false;
- if (engine != 0) {
+ if (engine != nullptr) {
const auto range = qAsConst(m_engineProfilers).equal_range(engine);
for (auto it = range.first; it != range.second; ++it) {
QQmlAbstractProfilerAdapter *profiler = *it;
@@ -296,10 +296,11 @@ void QQmlProfilerServiceImpl::stopProfiling(QJSEngine *engine)
for (QMultiHash<QJSEngine *, QQmlAbstractProfilerAdapter *>::iterator i(m_engineProfilers.begin());
i != m_engineProfilers.end(); ++i) {
if (i.value()->isRunning()) {
- if (engine == 0 || i.key() == engine) {
- m_startTimes.insert(-1, i.value());
+ m_startTimes.insert(-1, i.value());
+ if (engine == nullptr || i.key() == engine) {
stopping << i.value();
} else {
+ reporting << i.value();
stillRunning = true;
}
}
@@ -338,7 +339,8 @@ void QQmlProfilerServiceImpl::sendMessages()
QQmlDebugPacket traceEnd;
if (m_waitingForStop) {
- traceEnd << m_timer.nsecsElapsed() << (int)Event << (int)EndTrace;
+ traceEnd << m_timer.nsecsElapsed() << static_cast<qint32>(Event)
+ << static_cast<qint32>(EndTrace);
QSet<QJSEngine *> seen;
for (QQmlAbstractProfilerAdapter *profiler : qAsConst(m_startTimes)) {
@@ -368,25 +370,32 @@ void QQmlProfilerServiceImpl::sendMessages()
}
}
+ bool stillRunning = false;
+ for (const QQmlAbstractProfilerAdapter *profiler : qAsConst(m_engineProfilers)) {
+ if (profiler->isRunning()) {
+ stillRunning = true;
+ break;
+ }
+ }
+
if (m_waitingForStop) {
- //indicate completion
+ // EndTrace can be sent multiple times, as it's engine specific.
messages << traceEnd.data();
- QQmlDebugPacket ds;
- ds << (qint64)-1 << (int)Complete;
- messages << ds.data();
- m_waitingForStop = false;
+ if (!stillRunning) {
+ // Complete is only sent once, when no engines are running anymore.
+ QQmlDebugPacket ds;
+ ds << static_cast<qint64>(-1) << static_cast<qint32>(Complete);
+ messages << ds.data();
+ m_waitingForStop = false;
+ }
}
emit messagesToClient(name(), messages);
// Restart flushing if any profilers are still running
- for (const QQmlAbstractProfilerAdapter *profiler : qAsConst(m_engineProfilers)) {
- if (profiler->isRunning()) {
- emit startFlushTimer();
- break;
- }
- }
+ if (stillRunning)
+ emit startFlushTimer();
}
void QQmlProfilerServiceImpl::stateAboutToBeChanged(QQmlDebugService::State newState)
@@ -414,7 +423,7 @@ void QQmlProfilerServiceImpl::messageReceived(const QByteArray &message)
int engineId = -1;
quint64 features = std::numeric_limits<quint64>::max();
bool enabled;
- uint flushInterval = 0;
+ quint32 flushInterval = 0;
stream >> enabled;
if (!stream.atEnd())
stream >> engineId;
@@ -422,7 +431,9 @@ void QQmlProfilerServiceImpl::messageReceived(const QByteArray &message)
stream >> features;
if (!stream.atEnd()) {
stream >> flushInterval;
- m_flushTimer.setInterval(flushInterval);
+ m_flushTimer.setInterval(
+ static_cast<int>(qMin(flushInterval,
+ static_cast<quint32>(std::numeric_limits<int>::max()))));
auto timerStart = static_cast<void(QTimer::*)()>(&QTimer::start);
if (flushInterval > 0) {
connect(&m_flushTimer, &QTimer::timeout, this, &QQmlProfilerServiceImpl::flush);
diff --git a/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservicefactory.cpp b/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservicefactory.cpp
index 0cd3e0b4ab..81a1a35d18 100644
--- a/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservicefactory.cpp
+++ b/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservicefactory.cpp
@@ -51,7 +51,7 @@ QQmlDebugService *QQmlProfilerServiceFactory::create(const QString &key)
if (key == QQmlEngineControlServiceImpl::s_key)
return new QQmlEngineControlServiceImpl(this);
- return 0;
+ return nullptr;
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_quickprofiler/qquickprofileradapterfactory.cpp b/src/plugins/qmltooling/qmldbg_quickprofiler/qquickprofileradapterfactory.cpp
index f38307b1f7..66addee2e8 100644
--- a/src/plugins/qmltooling/qmldbg_quickprofiler/qquickprofileradapterfactory.cpp
+++ b/src/plugins/qmltooling/qmldbg_quickprofiler/qquickprofileradapterfactory.cpp
@@ -47,7 +47,7 @@ QT_BEGIN_NAMESPACE
QQmlAbstractProfilerAdapter *QQuickProfilerAdapterFactory::create(const QString &key)
{
if (key != QLatin1String("QQuickProfilerAdapter"))
- return 0;
+ return nullptr;
return new QQuickProfilerAdapter(this);
}
diff --git a/src/plugins/qmltooling/qmldbg_server/qqmldebugserver.cpp b/src/plugins/qmltooling/qmldbg_server/qqmldebugserver.cpp
index f87ade568b..1814e28b83 100644
--- a/src/plugins/qmltooling/qmldbg_server/qqmldebugserver.cpp
+++ b/src/plugins/qmltooling/qmldbg_server/qqmldebugserver.cpp
@@ -88,7 +88,7 @@ class QQmlDebugServerImpl;
class QQmlDebugServerThread : public QThread
{
public:
- QQmlDebugServerThread() : m_server(0), m_portFrom(-1), m_portTo(-1) {}
+ QQmlDebugServerThread() : m_server(nullptr), m_portFrom(-1), m_portTo(-1) {}
void setServer(QQmlDebugServerImpl *server)
{
@@ -228,7 +228,7 @@ void QQmlDebugServerImpl::cleanup()
void QQmlDebugServerThread::run()
{
- Q_ASSERT_X(m_server != 0, Q_FUNC_INFO, "There should always be a debug server available here.");
+ Q_ASSERT_X(m_server != nullptr, Q_FUNC_INFO, "There should always be a debug server available here.");
QQmlDebugServerConnection *connection = loadQQmlDebugServerConnection(m_pluginName);
if (connection) {
{
@@ -274,7 +274,7 @@ static void cleanupOnShutdown()
}
QQmlDebugServerImpl::QQmlDebugServerImpl() :
- m_connection(0),
+ m_connection(nullptr),
m_gotHello(false),
m_blockingMode(false),
m_clientSupportsMultiPackets(false)
@@ -570,7 +570,7 @@ void QQmlDebugServerImpl::removeThread()
QThread *parentThread = m_thread.thread();
delete m_connection;
- m_connection = 0;
+ m_connection = nullptr;
// Move it back to the parent thread so that we can potentially restart it on a new thread.
moveToThread(parentThread);
@@ -755,13 +755,13 @@ void QQmlDebugServerImpl::invalidPacket()
m_connection->disconnect();
// protocol might still be processing packages at this point
m_protocol->deleteLater();
- m_protocol = 0;
+ m_protocol = nullptr;
}
QQmlDebugConnector *QQmlDebugServerFactory::create(const QString &key)
{
// Cannot parent it to this because it gets moved to another thread
- return (key == QLatin1String("QQmlDebugServer") ? new QQmlDebugServerImpl : 0);
+ return (key == QLatin1String("QQmlDebugServer") ? new QQmlDebugServerImpl : nullptr);
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmldbg_tcp/qtcpserverconnection.cpp b/src/plugins/qmltooling/qmldbg_tcp/qtcpserverconnection.cpp
index c2aafda863..42442b07e7 100644
--- a/src/plugins/qmltooling/qmldbg_tcp/qtcpserverconnection.cpp
+++ b/src/plugins/qmltooling/qmldbg_tcp/qtcpserverconnection.cpp
@@ -54,7 +54,7 @@ class QTcpServerConnection : public QQmlDebugServerConnection
public:
QTcpServerConnection();
- ~QTcpServerConnection();
+ ~QTcpServerConnection() override;
void setServer(QQmlDebugServer *server) override;
bool setPortRange(int portFrom, int portTo, bool block, const QString &hostaddress) override;
@@ -70,24 +70,16 @@ private:
void newConnection();
bool listen();
- int m_portFrom;
- int m_portTo;
- bool m_block;
+ int m_portFrom = 0;
+ int m_portTo = 0;
+ bool m_block = false;
QString m_hostaddress;
- QTcpSocket *m_socket;
- QTcpServer *m_tcpServer;
- QQmlDebugServer *m_debugServer;
+ QTcpSocket *m_socket = nullptr;
+ QTcpServer *m_tcpServer = nullptr;
+ QQmlDebugServer *m_debugServer = nullptr;
};
-QTcpServerConnection::QTcpServerConnection() :
- m_portFrom(0),
- m_portTo(0),
- m_block(false),
- m_socket(0),
- m_tcpServer(0),
- m_debugServer(0)
-{
-}
+QTcpServerConnection::QTcpServerConnection() {}
QTcpServerConnection::~QTcpServerConnection()
{
@@ -116,7 +108,7 @@ void QTcpServerConnection::disconnect()
}
m_socket->deleteLater();
- m_socket = 0;
+ m_socket = nullptr;
}
bool QTcpServerConnection::setPortRange(int portFrom, int portTo, bool block,
@@ -199,7 +191,7 @@ void QTcpServerConnection::newConnection()
QQmlDebugServerConnection *QTcpServerConnectionFactory::create(const QString &key)
{
- return (key == QLatin1String("QTcpServerConnection") ? new QTcpServerConnection : 0);
+ return (key == QLatin1String("QTcpServerConnection") ? new QTcpServerConnection : nullptr);
}
QT_END_NAMESPACE
diff --git a/src/plugins/qmltooling/qmltooling.pro b/src/plugins/qmltooling/qmltooling.pro
index 5895169ca0..119415372b 100644
--- a/src/plugins/qmltooling/qmltooling.pro
+++ b/src/plugins/qmltooling/qmltooling.pro
@@ -14,26 +14,23 @@ qmldbg_native.depends = packetprotocol
qmldbg_server.depends = packetprotocol
qtConfig(qml-network) {
+ qtConfig(localserver): SUBDIRS += qmldbg_local
+
SUBDIRS += \
- qmldbg_local \
qmldbg_tcp
}
# Services
SUBDIRS += \
qmldbg_messages \
- qmldbg_profiler
+ qmldbg_profiler \
+ qmldbg_debugger \
+ qmldbg_nativedebugger
+
qmldbg_messages.depends = packetprotocol
qmldbg_profiler.depends = packetprotocol
-
-qtConfig(qml-interpreter) {
- SUBDIRS += \
- qmldbg_debugger \
- qmldbg_nativedebugger
-
- qmldbg_debugger.depends = packetprotocol
- qmldbg_nativedebugger.depends = packetprotocol
-}
+qmldbg_debugger.depends = packetprotocol
+qmldbg_nativedebugger.depends = packetprotocol
qtHaveModule(quick) {
SUBDIRS += \
diff --git a/src/plugins/scenegraph/d3d12/qsgd3d12engine.cpp b/src/plugins/scenegraph/d3d12/qsgd3d12engine.cpp
index 82bf9b0433..75bde2c66b 100644
--- a/src/plugins/scenegraph/d3d12/qsgd3d12engine.cpp
+++ b/src/plugins/scenegraph/d3d12/qsgd3d12engine.cpp
@@ -3046,7 +3046,7 @@ void QSGD3D12EnginePrivate::useRenderTargetAsTexture(uint id)
}
tframeData.activeTextures[tframeData.activeTextureCount++] =
- TransientFrameData::ActiveTexture::ActiveTexture(TransientFrameData::ActiveTexture::TypeRenderTarget, id);
+ TransientFrameData::ActiveTexture(TransientFrameData::ActiveTexture::TypeRenderTarget, id);
}
QImage QSGD3D12EnginePrivate::executeAndWaitReadbackRenderTarget(uint id)
diff --git a/src/plugins/scenegraph/d3d12/qsgd3d12renderloop.cpp b/src/plugins/scenegraph/d3d12/qsgd3d12renderloop.cpp
index 0d3f78d95d..0d501f48c0 100644
--- a/src/plugins/scenegraph/d3d12/qsgd3d12renderloop.cpp
+++ b/src/plugins/scenegraph/d3d12/qsgd3d12renderloop.cpp
@@ -145,9 +145,6 @@ void QSGD3D12RenderLoop::windowDestroyed(QQuickWindow *window)
rc->invalidate();
- if (m_windows.isEmpty())
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
-
delete rc;
delete engine;
diff --git a/src/plugins/scenegraph/openvg/qsgopenvgrenderloop.cpp b/src/plugins/scenegraph/openvg/qsgopenvgrenderloop.cpp
index d31156f0eb..9493920100 100644
--- a/src/plugins/scenegraph/openvg/qsgopenvgrenderloop.cpp
+++ b/src/plugins/scenegraph/openvg/qsgopenvgrenderloop.cpp
@@ -91,7 +91,6 @@ void QSGOpenVGRenderLoop::windowDestroyed(QQuickWindow *window)
rc->invalidate();
delete vg;
vg = nullptr;
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
} else if (vg && window == vg->window()) {
vg->doneCurrent();
}
diff --git a/src/qml/animations/qabstractanimationjob.cpp b/src/qml/animations/qabstractanimationjob.cpp
index a931d733d6..2bb5766c7b 100644
--- a/src/qml/animations/qabstractanimationjob.cpp
+++ b/src/qml/animations/qabstractanimationjob.cpp
@@ -92,9 +92,8 @@ QQmlAnimationTimer *QQmlAnimationTimer::instance()
void QQmlAnimationTimer::ensureTimerUpdate()
{
- QQmlAnimationTimer *inst = QQmlAnimationTimer::instance(false);
QUnifiedTimer *instU = QUnifiedTimer::instance(false);
- if (instU && inst && inst->isPaused)
+ if (instU && isPaused)
instU->updateAnimationTimers(-1);
}
@@ -129,9 +128,7 @@ void QQmlAnimationTimer::updateAnimationsTime(qint64 delta)
void QQmlAnimationTimer::updateAnimationTimer()
{
- QQmlAnimationTimer *inst = QQmlAnimationTimer::instance(false);
- if (inst)
- inst->restartAnimationTimer();
+ restartAnimationTimer();
}
void QQmlAnimationTimer::restartAnimationTimer()
@@ -176,45 +173,38 @@ void QQmlAnimationTimer::registerAnimation(QAbstractAnimationJob *animation, boo
if (animation->userControlDisabled())
return;
- QQmlAnimationTimer *inst = instance(true); //we create the instance if needed
- inst->registerRunningAnimation(animation);
+ registerRunningAnimation(animation);
if (isTopLevel) {
Q_ASSERT(!animation->m_hasRegisteredTimer);
animation->m_hasRegisteredTimer = true;
- inst->animationsToStart << animation;
- if (!inst->startAnimationPending) {
- inst->startAnimationPending = true;
- QMetaObject::invokeMethod(inst, "startAnimations", Qt::QueuedConnection);
+ animationsToStart << animation;
+ if (!startAnimationPending) {
+ startAnimationPending = true;
+ QMetaObject::invokeMethod(this, "startAnimations", Qt::QueuedConnection);
}
}
}
void QQmlAnimationTimer::unregisterAnimation(QAbstractAnimationJob *animation)
{
- QQmlAnimationTimer *inst = QQmlAnimationTimer::instance(false);
- if (inst) {
- //at this point the unified timer should have been created
- //but it might also have been already destroyed in case the application is shutting down
+ unregisterRunningAnimation(animation);
- inst->unregisterRunningAnimation(animation);
-
- if (!animation->m_hasRegisteredTimer)
- return;
+ if (!animation->m_hasRegisteredTimer)
+ return;
- int idx = inst->animations.indexOf(animation);
- if (idx != -1) {
- inst->animations.removeAt(idx);
- // this is needed if we unregister an animation while its running
- if (idx <= inst->currentAnimationIdx)
- --inst->currentAnimationIdx;
+ int idx = animations.indexOf(animation);
+ if (idx != -1) {
+ animations.removeAt(idx);
+ // this is needed if we unregister an animation while its running
+ if (idx <= currentAnimationIdx)
+ --currentAnimationIdx;
- if (inst->animations.isEmpty() && !inst->stopTimerPending) {
- inst->stopTimerPending = true;
- QMetaObject::invokeMethod(inst, "stopTimer", Qt::QueuedConnection);
- }
- } else {
- inst->animationsToStart.removeOne(animation);
+ if (animations.isEmpty() && !stopTimerPending) {
+ stopTimerPending = true;
+ QMetaObject::invokeMethod(this, "stopTimer", Qt::QueuedConnection);
}
+ } else {
+ animationsToStart.removeOne(animation);
}
animation->m_hasRegisteredTimer = false;
}
@@ -269,7 +259,7 @@ int QQmlAnimationTimer::closestPauseAnimationTimeToFinish()
QAbstractAnimationJob::QAbstractAnimationJob()
: m_loopCount(1)
- , m_group(0)
+ , m_group(nullptr)
, m_direction(QAbstractAnimationJob::Forward)
, m_state(QAbstractAnimationJob::Stopped)
, m_totalCurrentTime(0)
@@ -277,9 +267,9 @@ QAbstractAnimationJob::QAbstractAnimationJob()
, m_currentLoop(0)
, m_uncontrolledFinishTime(-1)
, m_currentLoopStartTime(0)
- , m_nextSibling(0)
- , m_previousSibling(0)
- , m_wasDeleted(0)
+ , m_nextSibling(nullptr)
+ , m_previousSibling(nullptr)
+ , m_wasDeleted(nullptr)
, m_hasRegisteredTimer(false)
, m_isPause(false)
, m_isGroup(false)
@@ -303,8 +293,10 @@ QAbstractAnimationJob::~QAbstractAnimationJob()
stateChanged(oldState, m_state);
Q_ASSERT(m_state == Stopped);
- if (oldState == Running)
- QQmlAnimationTimer::unregisterAnimation(this);
+ if (oldState == Running) {
+ Q_ASSERT(QQmlAnimationTimer::instance() == m_timer);
+ m_timer->unregisterAnimation(this);
+ }
Q_ASSERT(!m_hasRegisteredTimer);
}
@@ -328,6 +320,9 @@ void QAbstractAnimationJob::setState(QAbstractAnimationJob::State newState)
if (m_loopCount == 0)
return;
+ if (!m_timer)
+ m_timer = QQmlAnimationTimer::instance();
+
State oldState = m_state;
int oldCurrentTime = m_currentTime;
int oldCurrentLoop = m_currentLoop;
@@ -353,11 +348,11 @@ void QAbstractAnimationJob::setState(QAbstractAnimationJob::State newState)
bool isTopLevel = !m_group || m_group->isStopped();
if (oldState == Running) {
if (newState == Paused && m_hasRegisteredTimer)
- QQmlAnimationTimer::ensureTimerUpdate();
+ m_timer->ensureTimerUpdate();
//the animation, is not running any more
- QQmlAnimationTimer::unregisterAnimation(this);
+ m_timer->unregisterAnimation(this);
} else if (newState == Running) {
- QQmlAnimationTimer::registerAnimation(this, isTopLevel);
+ m_timer->registerAnimation(this, isTopLevel);
}
//starting an animation qualifies as a top level loop change
@@ -384,7 +379,7 @@ void QAbstractAnimationJob::setState(QAbstractAnimationJob::State newState)
m_currentLoop = 0;
if (isTopLevel) {
// currentTime needs to be updated if pauseTimer is active
- RETURN_IF_DELETED(QQmlAnimationTimer::ensureTimerUpdate());
+ RETURN_IF_DELETED(m_timer->ensureTimerUpdate());
RETURN_IF_DELETED(setCurrentTime(m_totalCurrentTime));
}
}
@@ -421,14 +416,14 @@ void QAbstractAnimationJob::setDirection(Direction direction)
// the commands order below is important: first we need to setCurrentTime with the old direction,
// then update the direction on this and all children and finally restart the pauseTimer if needed
if (m_hasRegisteredTimer)
- QQmlAnimationTimer::ensureTimerUpdate();
+ m_timer->ensureTimerUpdate();
m_direction = direction;
updateDirection(direction);
if (m_hasRegisteredTimer)
// needed to update the timer interval in case of a pause animation
- QQmlAnimationTimer::updateAnimationTimer();
+ m_timer->updateAnimationTimer();
}
void QAbstractAnimationJob::setLoopCount(int loopCount)
diff --git a/src/qml/animations/qabstractanimationjob_p.h b/src/qml/animations/qabstractanimationjob_p.h
index 95a39b1301..63fd4b0dac 100644
--- a/src/qml/animations/qabstractanimationjob_p.h
+++ b/src/qml/animations/qabstractanimationjob_p.h
@@ -60,6 +60,8 @@ QT_BEGIN_NAMESPACE
class QAnimationGroupJob;
class QAnimationJobChangeListener;
+class QQmlAnimationTimer;
+
class Q_QML_PRIVATE_EXPORT QAbstractAnimationJob
{
Q_DISABLE_COPY(QAbstractAnimationJob)
@@ -168,6 +170,7 @@ protected:
QAbstractAnimationJob *m_nextSibling;
QAbstractAnimationJob *m_previousSibling;
+ QQmlAnimationTimer *m_timer = nullptr;
bool *m_wasDeleted;
bool m_hasRegisteredTimer:1;
@@ -203,20 +206,20 @@ public:
static QQmlAnimationTimer *instance();
static QQmlAnimationTimer *instance(bool create);
- static void registerAnimation(QAbstractAnimationJob *animation, bool isTopLevel);
- static void unregisterAnimation(QAbstractAnimationJob *animation);
+ void registerAnimation(QAbstractAnimationJob *animation, bool isTopLevel);
+ void unregisterAnimation(QAbstractAnimationJob *animation);
/*
this is used for updating the currentTime of all animations in case the pause
timer is active or, otherwise, only of the animation passed as parameter.
*/
- static void ensureTimerUpdate();
+ void ensureTimerUpdate();
/*
this will evaluate the need of restarting the pause timer in case there is still
some pause animations running.
*/
- static void updateAnimationTimer();
+ void updateAnimationTimer();
void restartAnimationTimer() override;
void updateAnimationsTime(qint64 timeStep) override;
diff --git a/src/qml/animations/qanimationgroupjob.cpp b/src/qml/animations/qanimationgroupjob.cpp
index ea6d87952a..344791fd83 100644
--- a/src/qml/animations/qanimationgroupjob.cpp
+++ b/src/qml/animations/qanimationgroupjob.cpp
@@ -42,7 +42,7 @@
QT_BEGIN_NAMESPACE
QAnimationGroupJob::QAnimationGroupJob()
- : QAbstractAnimationJob(), m_firstChild(0), m_lastChild(0)
+ : QAbstractAnimationJob(), m_firstChild(nullptr), m_lastChild(nullptr)
{
m_isGroup = true;
}
@@ -111,25 +111,25 @@ void QAnimationGroupJob::removeAnimation(QAbstractAnimationJob *animation)
else
m_lastChild = prev;
- animation->m_previousSibling = 0;
- animation->m_nextSibling = 0;
+ animation->m_previousSibling = nullptr;
+ animation->m_nextSibling = nullptr;
- animation->m_group = 0;
+ animation->m_group = nullptr;
animationRemoved(animation, prev, next);
}
void QAnimationGroupJob::clear()
{
QAbstractAnimationJob *child = firstChild();
- QAbstractAnimationJob *nextSibling = 0;
- while (child != 0) {
- child->m_group = 0;
+ QAbstractAnimationJob *nextSibling = nullptr;
+ while (child != nullptr) {
+ child->m_group = nullptr;
nextSibling = child->nextSibling();
delete child;
child = nextSibling;
}
- m_firstChild = 0;
- m_lastChild = 0;
+ m_firstChild = nullptr;
+ m_lastChild = nullptr;
}
void QAnimationGroupJob::resetUncontrolledAnimationsFinishTime()
diff --git a/src/qml/animations/qanimationgroupjob_p.h b/src/qml/animations/qanimationgroupjob_p.h
index 26965c0264..fb567dc019 100644
--- a/src/qml/animations/qanimationgroupjob_p.h
+++ b/src/qml/animations/qanimationgroupjob_p.h
@@ -61,7 +61,7 @@ class Q_QML_PRIVATE_EXPORT QAnimationGroupJob : public QAbstractAnimationJob
Q_DISABLE_COPY(QAnimationGroupJob)
public:
QAnimationGroupJob();
- ~QAnimationGroupJob();
+ ~QAnimationGroupJob() override;
void appendAnimation(QAbstractAnimationJob *animation);
void prependAnimation(QAbstractAnimationJob *animation);
@@ -90,8 +90,8 @@ protected:
private:
//definition
- QAbstractAnimationJob *m_firstChild;
- QAbstractAnimationJob *m_lastChild;
+ QAbstractAnimationJob *m_firstChild = nullptr;
+ QAbstractAnimationJob *m_lastChild = nullptr;
};
QT_END_NAMESPACE
diff --git a/src/qml/animations/qcontinuinganimationgroupjob.cpp b/src/qml/animations/qcontinuinganimationgroupjob.cpp
index 02dcaf1313..10096bf19c 100644
--- a/src/qml/animations/qcontinuinganimationgroupjob.cpp
+++ b/src/qml/animations/qcontinuinganimationgroupjob.cpp
@@ -43,7 +43,6 @@
QT_BEGIN_NAMESPACE
QContinuingAnimationGroupJob::QContinuingAnimationGroupJob()
- : QAnimationGroupJob()
{
}
diff --git a/src/qml/animations/qparallelanimationgroupjob_p.h b/src/qml/animations/qparallelanimationgroupjob_p.h
index 358b95ce53..67ba626247 100644
--- a/src/qml/animations/qparallelanimationgroupjob_p.h
+++ b/src/qml/animations/qparallelanimationgroupjob_p.h
@@ -76,8 +76,8 @@ private:
void applyGroupState(QAbstractAnimationJob *animation);
//state
- int m_previousLoop;
- int m_previousCurrentTime;
+ int m_previousLoop = 0;
+ int m_previousCurrentTime = 0;
};
QT_END_NAMESPACE
diff --git a/src/qml/animations/qpauseanimationjob.cpp b/src/qml/animations/qpauseanimationjob.cpp
index 27175580dc..0652ed578b 100644
--- a/src/qml/animations/qpauseanimationjob.cpp
+++ b/src/qml/animations/qpauseanimationjob.cpp
@@ -42,8 +42,7 @@
QT_BEGIN_NAMESPACE
QPauseAnimationJob::QPauseAnimationJob(int duration)
- : QAbstractAnimationJob()
- , m_duration(duration)
+ : m_duration(duration)
{
m_isPause = true;
}
diff --git a/src/qml/animations/qpauseanimationjob_p.h b/src/qml/animations/qpauseanimationjob_p.h
index e228f46daa..d0e8d57fc7 100644
--- a/src/qml/animations/qpauseanimationjob_p.h
+++ b/src/qml/animations/qpauseanimationjob_p.h
@@ -60,7 +60,7 @@ class Q_QML_PRIVATE_EXPORT QPauseAnimationJob : public QAbstractAnimationJob
Q_DISABLE_COPY(QPauseAnimationJob)
public:
explicit QPauseAnimationJob(int duration = 250);
- ~QPauseAnimationJob();
+ ~QPauseAnimationJob() override;
int duration() const override;
void setDuration(int msecs);
diff --git a/src/qml/animations/qsequentialanimationgroupjob.cpp b/src/qml/animations/qsequentialanimationgroupjob.cpp
index 25d31e4042..22e20d9268 100644
--- a/src/qml/animations/qsequentialanimationgroupjob.cpp
+++ b/src/qml/animations/qsequentialanimationgroupjob.cpp
@@ -45,7 +45,7 @@ QT_BEGIN_NAMESPACE
QSequentialAnimationGroupJob::QSequentialAnimationGroupJob()
: QAnimationGroupJob()
- , m_currentAnimation(0)
+ , m_currentAnimation(nullptr)
, m_previousLoop(0)
{
}
@@ -87,7 +87,7 @@ QSequentialAnimationGroupJob::AnimationIndex QSequentialAnimationGroupJob::index
Q_ASSERT(firstChild());
AnimationIndex ret;
- QAbstractAnimationJob *anim = 0;
+ QAbstractAnimationJob *anim = nullptr;
int duration = 0;
for (anim = firstChild(); anim; anim = anim->nextSibling()) {
@@ -283,7 +283,7 @@ void QSequentialAnimationGroupJob::setCurrentAnimation(QAbstractAnimationJob *an
{
if (!anim) {
Q_ASSERT(!firstChild());
- m_currentAnimation = 0;
+ m_currentAnimation = nullptr;
return;
}
@@ -364,7 +364,7 @@ void QSequentialAnimationGroupJob::uncontrolledAnimationFinished(QAbstractAnimat
void QSequentialAnimationGroupJob::animationInserted(QAbstractAnimationJob *anim)
{
- if (m_currentAnimation == 0)
+ if (m_currentAnimation == nullptr)
setCurrentAnimation(firstChild()); // initialize the current animation
if (m_currentAnimation == anim->nextSibling()
@@ -393,7 +393,7 @@ void QSequentialAnimationGroupJob::animationRemoved(QAbstractAnimationJob *anim,
else if (prev)
setCurrentAnimation(prev);
else// case all animations were removed
- setCurrentAnimation(0);
+ setCurrentAnimation(nullptr);
}
// duration of the previous animations up to the current animation
diff --git a/src/qml/animations/qsequentialanimationgroupjob_p.h b/src/qml/animations/qsequentialanimationgroupjob_p.h
index 5fbafcb9ac..800f0c3b90 100644
--- a/src/qml/animations/qsequentialanimationgroupjob_p.h
+++ b/src/qml/animations/qsequentialanimationgroupjob_p.h
@@ -77,12 +77,12 @@ protected:
private:
struct AnimationIndex
{
- AnimationIndex() : afterCurrent(false), timeOffset(0), animation(0) {}
+ AnimationIndex() {}
// AnimationIndex points to the animation at timeOffset, skipping 0 duration animations.
// Note that the index semantic is slightly different depending on the direction.
- bool afterCurrent; //whether animation is before or after m_currentAnimation //TODO: make enum Before/After/Same
- int timeOffset; // time offset when the animation at index starts.
- QAbstractAnimationJob *animation; //points to the animation at timeOffset
+ bool afterCurrent = false; //whether animation is before or after m_currentAnimation //TODO: make enum Before/After/Same
+ int timeOffset = 0; // time offset when the animation at index starts.
+ QAbstractAnimationJob *animation = nullptr; //points to the animation at timeOffset
};
int animationActualTotalDuration(QAbstractAnimationJob *anim) const;
@@ -103,8 +103,8 @@ private:
void advanceForwards(const AnimationIndex &newAnimationIndex);
//state
- QAbstractAnimationJob *m_currentAnimation;
- int m_previousLoop;
+ QAbstractAnimationJob *m_currentAnimation = nullptr;
+ int m_previousLoop = 0;
};
QT_END_NAMESPACE
diff --git a/src/qml/compiler/compiler.pri b/src/qml/compiler/compiler.pri
index 0d63d3b76f..2ca0c39acc 100644
--- a/src/qml/compiler/compiler.pri
+++ b/src/qml/compiler/compiler.pri
@@ -10,7 +10,8 @@ HEADERS += \
$$PWD/qv4compilerscanfunctions_p.h \
$$PWD/qv4codegen_p.h \
$$PWD/qqmlirbuilder_p.h \
- $$PWD/qqmltypecompiler_p.h
+ $$PWD/qqmltypecompiler_p.h \
+ $$PWD/qv4instr_moth_p.h
SOURCES += \
$$PWD/qv4bytecodegenerator.cpp \
@@ -19,7 +20,8 @@ SOURCES += \
$$PWD/qv4compilercontext.cpp \
$$PWD/qv4compilerscanfunctions.cpp \
$$PWD/qv4codegen.cpp \
- $$PWD/qqmlirbuilder.cpp
+ $$PWD/qqmlirbuilder.cpp \
+ $$PWD/qv4instr_moth.cpp
!qmldevtools_build {
@@ -42,13 +44,6 @@ else: SOURCES += $$PWD/qv4compilationunitmapper_win.cpp
qtConfig(private_tests):qtConfig(dlopen): QMAKE_USE_PRIVATE += libdl
}
-qmldevtools_build|qtConfig(qml-interpreter) {
- HEADERS += \
- $$PWD/qv4instr_moth_p.h
- SOURCES += \
- $$PWD/qv4instr_moth.cpp
-}
-
gcc {
equals(QT_GCC_MAJOR_VERSION, 5): QMAKE_CXXFLAGS += -fno-strict-aliasing
}
diff --git a/src/qml/compiler/qqmlirbuilder.cpp b/src/qml/compiler/qqmlirbuilder.cpp
index 128eb2c720..237cd9bf3b 100644
--- a/src/qml/compiler/qqmlirbuilder.cpp
+++ b/src/qml/compiler/qqmlirbuilder.cpp
@@ -93,7 +93,7 @@ void Object::init(QQmlJS::MemoryPool *pool, int typeNameIndex, int idIndex, cons
bindings = pool->New<PoolList<Binding> >();
functions = pool->New<PoolList<Function> >();
functionsAndExpressions = pool->New<PoolList<CompiledFunctionOrExpression> >();
- declarationsOverride = 0;
+ declarationsOverride = nullptr;
}
QString Object::sanityCheckFunctionNames(const QSet<QString> &illegalNames, QQmlJS::AST::SourceLocation *errorLocation)
@@ -233,7 +233,7 @@ Binding *Object::findBinding(quint32 nameIndex) const
for (Binding *b = bindings->first; b; b = b->next)
if (b->propertyNameIndex == nameIndex)
return b;
- return 0;
+ return nullptr;
}
void Object::insertSorted(Binding *b)
@@ -275,7 +275,7 @@ void Document::removeScriptPragmas(QString &script)
const QLatin1String pragma("pragma");
const QLatin1String library("library");
- QQmlJS::Lexer l(0);
+ QQmlJS::Lexer l(nullptr);
l.setCode(script, 0);
int token = l.lex();
@@ -317,7 +317,7 @@ void Document::removeScriptPragmas(QString &script)
Document::Document(bool debugMode)
: jsModule(debugMode)
- , program(0)
+ , program(nullptr)
, jsGenerator(&jsModule)
{
}
@@ -363,16 +363,16 @@ void ScriptDirectivesCollector::importModule(const QString &uri, const QString &
IRBuilder::IRBuilder(const QSet<QString> &illegalNames)
: illegalNames(illegalNames)
- , _object(0)
- , _propertyDeclaration(0)
- , pool(0)
- , jsGenerator(0)
+ , _object(nullptr)
+ , _propertyDeclaration(nullptr)
+ , pool(nullptr)
+ , jsGenerator(nullptr)
{
}
bool IRBuilder::generateFromQml(const QString &code, const QString &url, Document *output)
{
- QQmlJS::AST::UiProgram *program = 0;
+ QQmlJS::AST::UiProgram *program = nullptr;
{
QQmlJS::Lexer lexer(&output->jsParserEngine);
lexer.setCode(code, /*line = */ 1);
@@ -479,7 +479,7 @@ bool IRBuilder::visit(QQmlJS::AST::UiObjectDefinition *node)
appendBinding(nameLocation, nameLocation, emptyStringIndex, idx);
} else {
int idx = 0;
- if (!defineQMLObject(&idx, /*qualfied type name id*/0, node->qualifiedTypeNameId->firstSourceLocation(), node->initializer, /*declarations should go here*/_object))
+ if (!defineQMLObject(&idx, /*qualfied type name id*/nullptr, node->qualifiedTypeNameId->firstSourceLocation(), node->initializer, /*declarations should go here*/_object))
return false;
appendBinding(node->qualifiedTypeNameId, idx);
}
@@ -504,7 +504,7 @@ bool IRBuilder::visit(QQmlJS::AST::UiScriptBinding *node)
bool IRBuilder::visit(QQmlJS::AST::UiArrayBinding *node)
{
const QQmlJS::AST::SourceLocation qualifiedNameLocation = node->qualifiedId->identifierToken;
- Object *object = 0;
+ Object *object = nullptr;
QQmlJS::AST::UiQualifiedId *name = node->qualifiedId;
if (!resolveQualifiedId(&name, &object))
return false;
@@ -513,7 +513,7 @@ bool IRBuilder::visit(QQmlJS::AST::UiArrayBinding *node)
const int propertyNameIndex = registerString(name->name.toString());
- if (bindingsTarget()->findBinding(propertyNameIndex) != 0) {
+ if (bindingsTarget()->findBinding(propertyNameIndex) != nullptr) {
recordError(name->identifierToken, tr("Property value set multiple times"));
return false;
}
@@ -588,7 +588,7 @@ bool IRBuilder::defineQMLObject(int *objectIndex, QQmlJS::AST::UiQualifiedId *qu
_object->declarationsOverride = declarationsOverride;
// A new object is also a boundary for property declarations.
- Property *declaration = 0;
+ Property *declaration = nullptr;
qSwap(_propertyDeclaration, declaration);
accept(initializer);
@@ -831,7 +831,7 @@ bool IRBuilder::visit(QQmlJS::AST::UiPublicMember *node)
return false;
}
- const TypeNameToType *type = 0;
+ const TypeNameToType *type = nullptr;
for (int typeIndex = 0; typeIndex < propTypeNameToTypesCount; ++typeIndex) {
const TypeNameToType *t = propTypeNameToTypes + typeIndex;
if (memberType == QLatin1String(t->name, static_cast<int>(t->nameLength))) {
@@ -1219,7 +1219,7 @@ void IRBuilder::tryGeneratingTranslationBinding(const QStringRef &base, AST::Arg
void IRBuilder::appendBinding(QQmlJS::AST::UiQualifiedId *name, QQmlJS::AST::Statement *value)
{
const QQmlJS::AST::SourceLocation qualifiedNameLocation = name->identifierToken;
- Object *object = 0;
+ Object *object = nullptr;
if (!resolveQualifiedId(&name, &object))
return;
if (_object == object && name->name == QLatin1String("id")) {
@@ -1234,7 +1234,7 @@ void IRBuilder::appendBinding(QQmlJS::AST::UiQualifiedId *name, QQmlJS::AST::Sta
void IRBuilder::appendBinding(QQmlJS::AST::UiQualifiedId *name, int objectIndex, bool isOnAssignment)
{
const QQmlJS::AST::SourceLocation qualifiedNameLocation = name->identifierToken;
- Object *object = 0;
+ Object *object = nullptr;
if (!resolveQualifiedId(&name, &object, isOnAssignment))
return;
qSwap(_object, object);
@@ -1385,7 +1385,7 @@ bool IRBuilder::setId(const QQmlJS::AST::SourceLocation &idLocation, QQmlJS::AST
if (QQmlJS::AST::ExpressionStatement *stmt = QQmlJS::AST::cast<QQmlJS::AST::ExpressionStatement *>(node)) {
if (QQmlJS::AST::StringLiteral *lit = QQmlJS::AST::cast<QQmlJS::AST::StringLiteral *>(stmt->expression)) {
str = lit->value;
- node = 0;
+ node = nullptr;
} else
node = stmt->expression;
}
@@ -1456,9 +1456,9 @@ bool IRBuilder::resolveQualifiedId(QQmlJS::AST::UiQualifiedId **nameToResolve, O
if (binding) {
if (isAttachedProperty) {
if (!binding->isAttachedProperty())
- binding = 0;
+ binding = nullptr;
} else if (!binding->isGroupProperty()) {
- binding = 0;
+ binding = nullptr;
}
}
if (!binding) {
@@ -1480,7 +1480,7 @@ bool IRBuilder::resolveQualifiedId(QQmlJS::AST::UiQualifiedId **nameToResolve, O
binding->type = QV4::CompiledData::Binding::Type_GroupProperty;
int objIndex = 0;
- if (!defineQMLObject(&objIndex, 0, QQmlJS::AST::SourceLocation(), 0, 0))
+ if (!defineQMLObject(&objIndex, nullptr, QQmlJS::AST::SourceLocation(), nullptr, nullptr))
return false;
binding->value.objectIndex = objIndex;
@@ -1582,11 +1582,14 @@ QV4::CompiledData::Unit *QmlUnitGenerator::generate(Document &output, const QV4:
memset(data + unitSize, 0, totalSize - unitSize);
if (jsUnit != compilationUnit->data)
free(jsUnit);
- jsUnit = 0;
+ jsUnit = nullptr;
QV4::CompiledData::Unit *qmlUnit = reinterpret_cast<QV4::CompiledData::Unit *>(data);
qmlUnit->unitSize = totalSize;
qmlUnit->flags |= QV4::CompiledData::Unit::IsQml;
+ // This unit's memory was allocated with malloc on the heap, so it's
+ // definitely not suitable for StaticData access.
+ qmlUnit->flags &= ~QV4::CompiledData::Unit::StaticData;
qmlUnit->offsetToImports = unitSize;
qmlUnit->nImports = output.imports.count();
qmlUnit->offsetToObjects = unitSize + importSize;
@@ -1770,7 +1773,8 @@ char *QmlUnitGenerator::writeBindings(char *bindingPtr, const Object *o, Binding
JSCodeGen::JSCodeGen(const QString &sourceCode, QV4::Compiler::JSUnitGenerator *jsUnitGenerator,
QV4::Compiler::Module *jsModule, QQmlJS::Engine *jsEngine,
- QQmlJS::AST::UiProgram *qmlRoot, QQmlTypeNameCache *imports, const QV4::Compiler::StringTableGenerator *stringPool)
+ QQmlJS::AST::UiProgram *qmlRoot, QQmlTypeNameCache *imports,
+ const QV4::Compiler::StringTableGenerator *stringPool, const QSet<QString> &globalNames)
: QV4::Compiler::Codegen(jsUnitGenerator, /*strict mode*/false)
, sourceCode(sourceCode)
, jsEngine(jsEngine)
@@ -1778,10 +1782,11 @@ JSCodeGen::JSCodeGen(const QString &sourceCode, QV4::Compiler::JSUnitGenerator *
, imports(imports)
, stringPool(stringPool)
, _disableAcceleratedLookups(false)
- , _contextObject(0)
- , _scopeObject(0)
+ , _contextObject(nullptr)
+ , _scopeObject(nullptr)
, _qmlContextSlot(-1)
, _importedScriptsSlot(-1)
+ , m_globalNames(globalNames)
{
_module = jsModule;
_fileNameIsUrl = true;
@@ -1791,7 +1796,7 @@ void JSCodeGen::beginContextScope(const JSCodeGen::ObjectIdMapping &objectIds, Q
{
_idObjects = objectIds;
_contextObject = contextObject;
- _scopeObject = 0;
+ _scopeObject = nullptr;
}
void JSCodeGen::beginObjectScope(QQmlPropertyCache *scopeObject)
@@ -1804,7 +1809,7 @@ QVector<int> JSCodeGen::generateJSCodeForFunctionsAndBindings(const QList<Compil
QVector<int> runtimeFunctionIndices(functions.size());
QV4::Compiler::ScanFunctions scan(this, sourceCode, QV4::Compiler::GlobalCode);
- scan.enterEnvironment(0, QV4::Compiler::QmlBinding);
+ scan.enterEnvironment(nullptr, QV4::Compiler::QmlBinding);
scan.enterQmlScope(qmlRoot, QStringLiteral("context scope"));
for (const CompiledFunctionOrExpression &f : functions) {
Q_ASSERT(f.node != qmlRoot);
@@ -1821,7 +1826,7 @@ QVector<int> JSCodeGen::generateJSCodeForFunctionsAndBindings(const QList<Compil
scan.leaveEnvironment();
scan.leaveEnvironment();
- _context = 0;
+ _context = nullptr;
for (int i = 0; i < functions.count(); ++i) {
const CompiledFunctionOrExpression &qmlFunction = functions.at(i);
@@ -1840,7 +1845,7 @@ QVector<int> JSCodeGen::generateJSCodeForFunctionsAndBindings(const QList<Compil
QQmlJS::AST::SourceElements *body;
if (function)
- body = function->body ? function->body->elements : 0;
+ body = function->body ? function->body->elements : nullptr;
else {
// Synthesize source elements.
QQmlJS::MemoryPool *pool = jsEngine->pool();
@@ -1858,7 +1863,7 @@ QVector<int> JSCodeGen::generateJSCodeForFunctionsAndBindings(const QList<Compil
_disableAcceleratedLookups = qmlFunction.disableAcceleratedLookups;
int idx = defineFunction(name, node,
- function ? function->formals : 0,
+ function ? function->formals : nullptr,
body);
runtimeFunctionIndices[i] = idx;
}
@@ -1884,14 +1889,14 @@ int JSCodeGen::defineFunction(const QString &name, AST::Node *ast, AST::FormalPa
#ifndef V4_BOOTSTRAP
QQmlPropertyData *JSCodeGen::lookupQmlCompliantProperty(QQmlPropertyCache *cache, const QString &name)
{
- QQmlPropertyData *pd = cache->property(name, /*object*/0, /*context*/0);
+ QQmlPropertyData *pd = cache->property(name, /*object*/nullptr, /*context*/nullptr);
// Q_INVOKABLEs can't be FINAL, so we have to look them up at run-time
if (!pd || pd->isFunction())
- return 0;
+ return nullptr;
if (!cache->isAllowedInRevision(pd))
- return 0;
+ return nullptr;
return pd;
}
@@ -2226,20 +2231,34 @@ QV4::Compiler::Codegen::Reference JSCodeGen::fallbackNameLookup(const QString &n
QQmlPropertyData *data = lookupQmlCompliantProperty(_scopeObject, name);
if (!data)
return Reference::fromName(this, name);
+
Reference base = Reference::fromStackSlot(this, _qmlContextSlot);
- bool captureRequired = !data->isConstant() && !data->isQmlBinding();
- return Reference::fromQmlScopeObject(base, data->coreIndex(), data->notifyIndex(),
- captureRequired);
+ Reference::PropertyCapturePolicy capturePolicy;
+ if (!data->isConstant() && !data->isQmlBinding())
+ capturePolicy = Reference::CaptureAtRuntime;
+ else
+ capturePolicy = data->isConstant() ? Reference::DontCapture : Reference::CaptureAheadOfTime;
+ return Reference::fromQmlScopeObject(base, data->coreIndex(), data->notifyIndex(), capturePolicy);
}
if (_contextObject) {
QQmlPropertyData *data = lookupQmlCompliantProperty(_contextObject, name);
if (!data)
return Reference::fromName(this, name);
+
Reference base = Reference::fromStackSlot(this, _qmlContextSlot);
- bool captureRequired = !data->isConstant() && !data->isQmlBinding();
- return Reference::fromQmlContextObject(base, data->coreIndex(), data->notifyIndex(),
- captureRequired);
+ Reference::PropertyCapturePolicy capturePolicy;
+ if (!data->isConstant() && !data->isQmlBinding())
+ capturePolicy = Reference::CaptureAtRuntime;
+ else
+ capturePolicy = data->isConstant() ? Reference::DontCapture : Reference::CaptureAheadOfTime;
+ return Reference::fromQmlContextObject(base, data->coreIndex(), data->notifyIndex(), capturePolicy);
+ }
+
+ if (m_globalNames.contains(name)) {
+ Reference r = Reference::fromName(this, name);
+ r.global = true;
+ return r;
}
#else
Q_UNUSED(name)
@@ -2254,7 +2273,7 @@ QQmlPropertyData *PropertyResolver::property(const QString &name, bool *notInRev
{
if (notInRevision) *notInRevision = false;
- QQmlPropertyData *d = cache->property(name, 0, 0);
+ QQmlPropertyData *d = cache->property(name, nullptr, nullptr);
// Find the first property
while (d && d->isFunction())
@@ -2262,7 +2281,7 @@ QQmlPropertyData *PropertyResolver::property(const QString &name, bool *notInRev
if (check != IgnoreRevision && d && !cache->isAllowedInRevision(d)) {
if (notInRevision) *notInRevision = true;
- return 0;
+ return nullptr;
} else {
return d;
}
@@ -2273,7 +2292,7 @@ QQmlPropertyData *PropertyResolver::signal(const QString &name, bool *notInRevis
{
if (notInRevision) *notInRevision = false;
- QQmlPropertyData *d = cache->property(name, 0, 0);
+ QQmlPropertyData *d = cache->property(name, nullptr, nullptr);
if (notInRevision) *notInRevision = false;
while (d && !(d->isFunction()))
@@ -2281,7 +2300,7 @@ QQmlPropertyData *PropertyResolver::signal(const QString &name, bool *notInRevis
if (d && !cache->isAllowedInRevision(d)) {
if (notInRevision) *notInRevision = true;
- return 0;
+ return nullptr;
} else if (d && d->isSignal()) {
return d;
}
@@ -2294,7 +2313,7 @@ QQmlPropertyData *PropertyResolver::signal(const QString &name, bool *notInRevis
return cache->signal(d->notifyIndex());
}
- return 0;
+ return nullptr;
}
IRLoader::IRLoader(const QV4::CompiledData::Unit *qmlData, QmlIR::Document *output)
@@ -2431,7 +2450,7 @@ QmlIR::Object *IRLoader::loadObject(const QV4::CompiledData::Object *serializedO
f->location = compiledFunction->location;
f->nameIndex = compiledFunction->nameIndex;
- QQmlJS::AST::FormalParameterList *paramList = 0;
+ QQmlJS::AST::FormalParameterList *paramList = nullptr;
const quint32_le *formalNameIdx = compiledFunction->formalsTable();
for (uint i = 0; i < compiledFunction->nFormals; ++i, ++formalNameIdx) {
const QString formal = unit->stringAt(*formalNameIdx);
@@ -2447,7 +2466,7 @@ QmlIR::Object *IRLoader::loadObject(const QV4::CompiledData::Object *serializedO
paramList = paramList->finish();
const QString name = unit->stringAt(compiledFunction->nameIndex);
- f->functionDeclaration = new(pool) QQmlJS::AST::FunctionDeclaration(jsParserEngine->newStringRef(name), paramList, /*body*/0);
+ f->functionDeclaration = new(pool) QQmlJS::AST::FunctionDeclaration(jsParserEngine->newStringRef(name), paramList, /*body*/nullptr);
f->formals.allocate(pool, int(compiledFunction->nFormals));
formalNameIdx = compiledFunction->formalsTable();
diff --git a/src/qml/compiler/qqmlirbuilder_p.h b/src/qml/compiler/qqmlirbuilder_p.h
index 406c939998..c2cf18e3c4 100644
--- a/src/qml/compiler/qqmlirbuilder_p.h
+++ b/src/qml/compiler/qqmlirbuilder_p.h
@@ -80,17 +80,16 @@ template <typename T>
struct PoolList
{
PoolList()
- : first(0)
- , last(0)
- , count(0)
+ : first(nullptr)
+ , last(nullptr)
{}
T *first;
T *last;
- int count;
+ int count = 0;
int append(T *item) {
- item->next = 0;
+ item->next = nullptr;
if (last)
last->next = item;
else
@@ -110,7 +109,7 @@ struct PoolList
template <typename Sortable, typename Base, Sortable Base::*sortMember>
T *findSortedInsertionPoint(T *item) const
{
- T *insertPos = 0;
+ T *insertPos = nullptr;
for (T *it = first; it; it = it->next) {
if (!(it->*sortMember <= item->*sortMember))
@@ -205,11 +204,11 @@ class FixedPoolArray
{
T *data;
public:
- int count;
+ int count = 0;
FixedPoolArray()
- : data(0)
- , count(0)
+ : data(nullptr)
+
{}
void allocate(QQmlJS::MemoryPool *pool, int size)
@@ -343,21 +342,16 @@ struct Function
struct Q_QML_PRIVATE_EXPORT CompiledFunctionOrExpression
{
CompiledFunctionOrExpression()
- : node(0)
- , nameIndex(0)
- , disableAcceleratedLookups(false)
- , next(0)
+
{}
CompiledFunctionOrExpression(QQmlJS::AST::Node *n)
: node(n)
- , nameIndex(0)
- , disableAcceleratedLookups(false)
- , next(0)
+
{}
- QQmlJS::AST::Node *node; // FunctionDeclaration, Statement or Expression
- quint32 nameIndex;
- bool disableAcceleratedLookups;
- CompiledFunctionOrExpression *next;
+ QQmlJS::AST::Node *node = nullptr; // FunctionDeclaration, Statement or Expression
+ quint32 nameIndex = 0;
+ bool disableAcceleratedLookups = false;
+ CompiledFunctionOrExpression *next = nullptr;
};
struct Q_QML_PRIVATE_EXPORT Object
@@ -514,8 +508,8 @@ public:
void accept(QQmlJS::AST::Node *node);
// returns index in _objects
- bool defineQMLObject(int *objectIndex, QQmlJS::AST::UiQualifiedId *qualifiedTypeNameId, const QQmlJS::AST::SourceLocation &location, QQmlJS::AST::UiObjectInitializer *initializer, Object *declarationsOverride = 0);
- bool defineQMLObject(int *objectIndex, QQmlJS::AST::UiObjectDefinition *node, Object *declarationsOverride = 0)
+ bool defineQMLObject(int *objectIndex, QQmlJS::AST::UiQualifiedId *qualifiedTypeNameId, const QQmlJS::AST::SourceLocation &location, QQmlJS::AST::UiObjectInitializer *initializer, Object *declarationsOverride = nullptr);
+ bool defineQMLObject(int *objectIndex, QQmlJS::AST::UiObjectDefinition *node, Object *declarationsOverride = nullptr)
{ return defineQMLObject(objectIndex, node->qualifiedTypeNameId, node->qualifiedTypeNameId->firstSourceLocation(), node->initializer, declarationsOverride); }
static QString asString(QQmlJS::AST::UiQualifiedId *node);
@@ -598,7 +592,7 @@ struct Q_QML_EXPORT PropertyResolver
IgnoreRevision
};
- QQmlPropertyData *property(const QString &name, bool *notInRevision = 0, RevisionCheck check = CheckRevision) const;
+ QQmlPropertyData *property(const QString &name, bool *notInRevision = nullptr, RevisionCheck check = CheckRevision) const;
// This code must match the semantics of QQmlPropertyPrivate::findSignalByName
QQmlPropertyData *signal(const QString &name, bool *notInRevision) const;
@@ -610,8 +604,8 @@ struct Q_QML_EXPORT PropertyResolver
struct Q_QML_PRIVATE_EXPORT JSCodeGen : public QV4::Compiler::Codegen
{
JSCodeGen(const QString &sourceCode, QV4::Compiler::JSUnitGenerator *jsUnitGenerator, QV4::Compiler::Module *jsModule,
- QQmlJS::Engine *jsEngine, QQmlJS::AST::UiProgram *qmlRoot, QQmlTypeNameCache *imports,
- const QV4::Compiler::StringTableGenerator *stringPool);
+ QQmlJS::Engine *jsEngine, QQmlJS::AST::UiProgram *qmlRoot,
+ QQmlTypeNameCache *imports, const QV4::Compiler::StringTableGenerator *stringPool, const QSet<QString> &globalNames);
struct IdMapping
{
@@ -651,6 +645,7 @@ private:
QQmlPropertyCache *_scopeObject;
int _qmlContextSlot;
int _importedScriptsSlot;
+ QSet<QString> m_globalNames;
};
struct Q_QML_PRIVATE_EXPORT IRLoader {
@@ -670,6 +665,17 @@ private:
} // namespace QmlIR
+struct QQmlCompileError
+{
+ QQmlCompileError() {}
+ QQmlCompileError(const QV4::CompiledData::Location &location, const QString &description)
+ : location(location), description(description) {}
+ QV4::CompiledData::Location location;
+ QString description;
+
+ bool isSet() const { return !description.isEmpty(); }
+};
+
QT_END_NAMESPACE
#endif // QQMLIRBUILDER_P_H
diff --git a/src/qml/compiler/qqmlpropertycachecreator.cpp b/src/qml/compiler/qqmlpropertycachecreator.cpp
index f8d63ec634..fd22cd58f1 100644
--- a/src/qml/compiler/qqmlpropertycachecreator.cpp
+++ b/src/qml/compiler/qqmlpropertycachecreator.cpp
@@ -45,26 +45,54 @@ QT_BEGIN_NAMESPACE
QAtomicInt QQmlPropertyCacheCreatorBase::classIndexCounter(0);
-QQmlBindingInstantiationContext::QQmlBindingInstantiationContext()
- : referencingObjectIndex(-1)
- , instantiatingBinding(nullptr)
- , instantiatingProperty(nullptr)
+QQmlBindingInstantiationContext::QQmlBindingInstantiationContext(int referencingObjectIndex, const QV4::CompiledData::Binding *instantiatingBinding,
+ const QString &instantiatingPropertyName, QQmlPropertyCache *referencingObjectPropertyCache)
+ : referencingObjectIndex(referencingObjectIndex)
+ , instantiatingBinding(instantiatingBinding)
+ , instantiatingPropertyName(instantiatingPropertyName)
+ , referencingObjectPropertyCache(referencingObjectPropertyCache)
{
+}
+bool QQmlBindingInstantiationContext::resolveInstantiatingProperty()
+{
+ if (!instantiatingBinding || instantiatingBinding->type != QV4::CompiledData::Binding::Type_GroupProperty)
+ return true;
+
+ Q_ASSERT(referencingObjectIndex >= 0);
+ Q_ASSERT(referencingObjectPropertyCache);
+ Q_ASSERT(instantiatingBinding->propertyNameIndex != 0);
+
+ bool notInRevision = false;
+ instantiatingProperty = QmlIR::PropertyResolver(referencingObjectPropertyCache).property(instantiatingPropertyName, &notInRevision, QmlIR::PropertyResolver::IgnoreRevision);
+ return instantiatingProperty != nullptr;
}
-QQmlBindingInstantiationContext::QQmlBindingInstantiationContext(int referencingObjectIndex, const QV4::CompiledData::Binding *instantiatingBinding, const QString &instantiatingPropertyName, const QQmlPropertyCache *referencingObjectPropertyCache)
- : referencingObjectIndex(referencingObjectIndex)
- , instantiatingBinding(instantiatingBinding)
- , instantiatingProperty(nullptr)
+QQmlRefPointer<QQmlPropertyCache> QQmlBindingInstantiationContext::instantiatingPropertyCache(QQmlEnginePrivate *enginePrivate) const
{
- if (instantiatingBinding && instantiatingBinding->type == QV4::CompiledData::Binding::Type_GroupProperty) {
- Q_ASSERT(referencingObjectIndex >= 0);
- Q_ASSERT(referencingObjectPropertyCache);
- Q_ASSERT(instantiatingBinding->propertyNameIndex != 0);
+ if (instantiatingProperty) {
+ if (instantiatingProperty->isQObject()) {
+ return enginePrivate->rawPropertyCacheForType(instantiatingProperty->propType(), instantiatingProperty->typeMinorVersion());
+ } else if (const QMetaObject *vtmo = QQmlValueTypeFactory::metaObjectForMetaType(instantiatingProperty->propType())) {
+ return enginePrivate->cache(vtmo);
+ }
+ }
+ return QQmlRefPointer<QQmlPropertyCache>();
+}
+
+void QQmlPendingGroupPropertyBindings::resolveMissingPropertyCaches(QQmlEnginePrivate *enginePrivate, QQmlPropertyCacheVector *propertyCaches) const
+{
+ for (QQmlBindingInstantiationContext pendingBinding: *this) {
+ const int groupPropertyObjectIndex = pendingBinding.instantiatingBinding->value.objectIndex;
+
+ if (propertyCaches->at(groupPropertyObjectIndex))
+ continue;
+
+ if (!pendingBinding.resolveInstantiatingProperty())
+ continue;
- bool notInRevision = false;
- instantiatingProperty = QmlIR::PropertyResolver(referencingObjectPropertyCache).property(instantiatingPropertyName, &notInRevision);
+ auto cache = pendingBinding.instantiatingPropertyCache(enginePrivate);
+ propertyCaches->set(groupPropertyObjectIndex, cache);
}
}
diff --git a/src/qml/compiler/qqmlpropertycachecreator_p.h b/src/qml/compiler/qqmlpropertycachecreator_p.h
index 5d6a5c177a..8bbc8291b4 100644
--- a/src/qml/compiler/qqmlpropertycachecreator_p.h
+++ b/src/qml/compiler/qqmlpropertycachecreator_p.h
@@ -50,18 +50,31 @@
// We mean it.
//
-#include "qqmltypecompiler_p.h"
#include <private/qqmlvaluetype_p.h>
#include <private/qqmlengine_p.h>
QT_BEGIN_NAMESPACE
struct QQmlBindingInstantiationContext {
- QQmlBindingInstantiationContext();
- QQmlBindingInstantiationContext(int referencingObjectIndex, const QV4::CompiledData::Binding *instantiatingBinding, const QString &instantiatingPropertyName, const QQmlPropertyCache *referencingObjectPropertyCache);
- int referencingObjectIndex;
- const QV4::CompiledData::Binding *instantiatingBinding;
- QQmlPropertyData *instantiatingProperty;
+ QQmlBindingInstantiationContext() {}
+ QQmlBindingInstantiationContext(int referencingObjectIndex,
+ const QV4::CompiledData::Binding *instantiatingBinding,
+ const QString &instantiatingPropertyName,
+ QQmlPropertyCache *referencingObjectPropertyCache);
+
+ bool resolveInstantiatingProperty();
+ QQmlRefPointer<QQmlPropertyCache> instantiatingPropertyCache(QQmlEnginePrivate *enginePrivate) const;
+
+ int referencingObjectIndex = -1;
+ const QV4::CompiledData::Binding *instantiatingBinding = nullptr;
+ QString instantiatingPropertyName;
+ QQmlRefPointer<QQmlPropertyCache> referencingObjectPropertyCache;
+ QQmlPropertyData *instantiatingProperty = nullptr;
+};
+
+struct QQmlPendingGroupPropertyBindings : public QVector<QQmlBindingInstantiationContext>
+{
+ void resolveMissingPropertyCaches(QQmlEnginePrivate *enginePrivate, QQmlPropertyCacheVector *propertyCaches) const;
};
struct QQmlPropertyCacheCreatorBase
@@ -77,7 +90,10 @@ class QQmlPropertyCacheCreator : public QQmlPropertyCacheCreatorBase
public:
typedef typename ObjectContainer::CompiledObject CompiledObject;
- QQmlPropertyCacheCreator(QQmlPropertyCacheVector *propertyCaches, QQmlEnginePrivate *enginePrivate, const ObjectContainer *objectContainer, const QQmlImports *imports);
+ QQmlPropertyCacheCreator(QQmlPropertyCacheVector *propertyCaches,
+ QQmlPendingGroupPropertyBindings *pendingGroupPropertyBindings,
+ QQmlEnginePrivate *enginePrivate,
+ const ObjectContainer *objectContainer, const QQmlImports *imports);
QQmlCompileError buildMetaObjects();
@@ -92,14 +108,19 @@ protected:
const ObjectContainer * const objectContainer;
const QQmlImports * const imports;
QQmlPropertyCacheVector *propertyCaches;
+ QQmlPendingGroupPropertyBindings *pendingGroupPropertyBindings;
};
template <typename ObjectContainer>
-inline QQmlPropertyCacheCreator<ObjectContainer>::QQmlPropertyCacheCreator(QQmlPropertyCacheVector *propertyCaches, QQmlEnginePrivate *enginePrivate, const ObjectContainer *objectContainer, const QQmlImports *imports)
+inline QQmlPropertyCacheCreator<ObjectContainer>::QQmlPropertyCacheCreator(QQmlPropertyCacheVector *propertyCaches,
+ QQmlPendingGroupPropertyBindings *pendingGroupPropertyBindings,
+ QQmlEnginePrivate *enginePrivate,
+ const ObjectContainer *objectContainer, const QQmlImports *imports)
: enginePrivate(enginePrivate)
, objectContainer(objectContainer)
, imports(imports)
, propertyCaches(propertyCaches)
+ , pendingGroupPropertyBindings(pendingGroupPropertyBindings)
{
propertyCaches->resize(objectContainer->objectCount());
}
@@ -169,6 +190,14 @@ inline QQmlCompileError QQmlPropertyCacheCreator<ObjectContainer>::buildMetaObje
for ( ; binding != end; ++binding)
if (binding->type >= QV4::CompiledData::Binding::Type_Object) {
QQmlBindingInstantiationContext context(objectIndex, &(*binding), stringAt(binding->propertyNameIndex), thisCache);
+
+ // Binding to group property where we failed to look up the type of the
+ // property? Possibly a group property that is an alias that's not resolved yet.
+ // Let's attempt to resolve it after we're done with the aliases and fill in the
+ // propertyCaches entry then.
+ if (!context.resolveInstantiatingProperty())
+ pendingGroupPropertyBindings->append(context);
+
QQmlCompileError error = buildMetaObjectRecursively(binding->value.objectIndex, context);
if (error.isSet())
return error;
@@ -183,11 +212,7 @@ template <typename ObjectContainer>
inline QQmlPropertyCache *QQmlPropertyCacheCreator<ObjectContainer>::propertyCacheForObject(const CompiledObject *obj, const QQmlBindingInstantiationContext &context, QQmlCompileError *error) const
{
if (context.instantiatingProperty) {
- if (context.instantiatingProperty->isQObject()) {
- return enginePrivate->rawPropertyCacheForType(context.instantiatingProperty->propType());
- } else if (const QMetaObject *vtmo = QQmlValueTypeFactory::metaObjectForMetaType(context.instantiatingProperty->propType())) {
- return enginePrivate->cache(vtmo);
- }
+ return context.instantiatingPropertyCache(enginePrivate);
} else if (obj->inheritedTypeNameIndex != 0) {
auto *typeRef = objectContainer->resolvedTypes.value(obj->inheritedTypeNameIndex);
Q_ASSERT(typeRef);
@@ -214,7 +239,7 @@ inline QQmlPropertyCache *QQmlPropertyCacheCreator<ObjectContainer>::propertyCac
QQmlType qmltype = typeRef->type;
if (!qmltype.isValid()) {
QString propertyName = stringAt(context.instantiatingBinding->propertyNameIndex);
- if (imports->resolveType(propertyName, &qmltype, 0, 0, 0)) {
+ if (imports->resolveType(propertyName, &qmltype, nullptr, nullptr, nullptr)) {
if (qmltype.isComposite()) {
QQmlTypeData *tdata = enginePrivate->typeLoader.getType(qmltype.sourceUrl());
Q_ASSERT(tdata);
@@ -411,7 +436,7 @@ inline QQmlCompileError QQmlPropertyCacheCreator<ObjectContainer>::createMetaObj
Q_ASSERT(param->type == QV4::CompiledData::Property::Custom);
const QString customTypeName = stringAt(param->customTypeNameIndex);
QQmlType qmltype;
- if (!imports->resolveType(customTypeName, &qmltype, 0, 0, 0))
+ if (!imports->resolveType(customTypeName, &qmltype, nullptr, nullptr, nullptr))
return QQmlCompileError(s->location, QQmlPropertyCacheCreatorBase::tr("Invalid signal parameter type: %1").arg(customTypeName));
if (qmltype.isComposite()) {
@@ -441,7 +466,7 @@ inline QQmlCompileError QQmlPropertyCacheCreator<ObjectContainer>::createMetaObj
seenSignals.insert(signalName);
cache->appendSignal(signalName, flags, effectiveMethodIndex++,
- paramCount?paramTypes.constData():0, names);
+ paramCount?paramTypes.constData():nullptr, names);
}
@@ -476,6 +501,7 @@ inline QQmlCompileError QQmlPropertyCacheCreator<ObjectContainer>::createMetaObj
pend = obj->propertiesEnd();
for ( ; p != pend; ++p, ++propertyIdx) {
int propertyType = 0;
+ int propertTypeMinorVersion = 0;
QQmlPropertyData::Flags propertyFlags;
if (p->type == QV4::CompiledData::Property::Var) {
@@ -491,7 +517,7 @@ inline QQmlCompileError QQmlPropertyCacheCreator<ObjectContainer>::createMetaObj
p->type == QV4::CompiledData::Property::Custom);
QQmlType qmltype;
- if (!imports->resolveType(stringAt(p->customTypeNameIndex), &qmltype, 0, 0, 0)) {
+ if (!imports->resolveType(stringAt(p->customTypeNameIndex), &qmltype, nullptr, nullptr, nullptr)) {
return QQmlCompileError(p->location, QQmlPropertyCacheCreatorBase::tr("Invalid property type"));
}
@@ -513,6 +539,7 @@ inline QQmlCompileError QQmlPropertyCacheCreator<ObjectContainer>::createMetaObj
} else {
if (p->type == QV4::CompiledData::Property::Custom) {
propertyType = qmltype.typeId();
+ propertTypeMinorVersion = qmltype.minorVersion();
} else {
propertyType = qmltype.qListTypeId();
}
@@ -532,7 +559,7 @@ inline QQmlCompileError QQmlPropertyCacheCreator<ObjectContainer>::createMetaObj
if (!obj->defaultPropertyIsAlias && propertyIdx == obj->indexOfDefaultPropertyOrAlias)
cache->_defaultPropertyName = propertyName;
cache->appendProperty(propertyName, propertyFlags, effectivePropertyIndex++,
- propertyType, effectiveSignalIndex);
+ propertyType, propertTypeMinorVersion, effectiveSignalIndex);
effectiveSignalIndex++;
}
@@ -551,11 +578,11 @@ public:
void appendAliasPropertiesToMetaObjects();
- void appendAliasesToPropertyCache(const CompiledObject &component, int objectIndex);
+ QQmlCompileError appendAliasesToPropertyCache(const CompiledObject &component, int objectIndex);
private:
void appendAliasPropertiesInMetaObjectsWithinComponent(const CompiledObject &component, int firstObjectIndex);
- void propertyDataForAlias(const CompiledObject &component, const QV4::CompiledData::Alias &alias, int *type, QQmlPropertyRawData::Flags *propertyFlags);
+ QQmlCompileError propertyDataForAlias(const CompiledObject &component, const QV4::CompiledData::Alias &alias, int *type, int *rev, QQmlPropertyRawData::Flags *propertyFlags);
void collectObjectsWithAliasesRecursively(int objectIndex, QVector<int> *objectsWithAliases) const;
@@ -666,8 +693,8 @@ inline void QQmlPropertyCacheAliasCreator<ObjectContainer>::collectObjectsWithAl
}
template <typename ObjectContainer>
-inline void QQmlPropertyCacheAliasCreator<ObjectContainer>::propertyDataForAlias(
- const CompiledObject &component, const QV4::CompiledData::Alias &alias, int *type,
+inline QQmlCompileError QQmlPropertyCacheAliasCreator<ObjectContainer>::propertyDataForAlias(
+ const CompiledObject &component, const QV4::CompiledData::Alias &alias, int *type, int *minorVersion,
QQmlPropertyData::Flags *propertyFlags)
{
const int targetObjectIndex = objectForId(component, alias.targetObjectId);
@@ -685,18 +712,24 @@ inline void QQmlPropertyCacheAliasCreator<ObjectContainer>::propertyDataForAlias
auto targetAlias = targetObject.aliasesBegin();
for (uint i = 0; i < alias.localAliasIndex; ++i)
++targetAlias;
- propertyDataForAlias(component, *targetAlias, type, propertyFlags);
- return;
+ return propertyDataForAlias(component, *targetAlias, type, minorVersion, propertyFlags);
} else if (alias.encodedMetaPropertyIndex == -1) {
Q_ASSERT(alias.flags & QV4::CompiledData::Alias::AliasPointsToPointerObject);
auto *typeRef = objectContainer->resolvedTypes.value(targetObject.inheritedTypeNameIndex);
- Q_ASSERT(typeRef);
+ if (!typeRef) {
+ // Can be caused by the alias target not being a valid id or property. E.g.:
+ // property alias dataValue: dataVal
+ // invalidAliasComponent { id: dataVal }
+ return QQmlCompileError(targetObject.location, QQmlPropertyCacheCreatorBase::tr("Invalid alias target"));
+ }
if (typeRef->type.isValid())
*type = typeRef->type.typeId();
else
*type = typeRef->compilationUnit->metaTypeId;
+ *minorVersion = typeRef->minorVersion;
+
propertyFlags->type = QQmlPropertyData::Flags::QObjectDerivedType;
} else {
int coreIndex = QQmlPropertyIndex::fromEncoded(alias.encodedMetaPropertyIndex).coreIndex();
@@ -733,15 +766,16 @@ inline void QQmlPropertyCacheAliasCreator<ObjectContainer>::propertyDataForAlias
propertyFlags->isWritable = !(alias.flags & QV4::CompiledData::Property::IsReadOnly) && writable;
propertyFlags->isResettable = resettable;
+ return QQmlCompileError();
}
template <typename ObjectContainer>
-inline void QQmlPropertyCacheAliasCreator<ObjectContainer>::appendAliasesToPropertyCache(
+inline QQmlCompileError QQmlPropertyCacheAliasCreator<ObjectContainer>::appendAliasesToPropertyCache(
const CompiledObject &component, int objectIndex)
{
const CompiledObject &object = *objectContainer->objectAt(objectIndex);
if (!object.aliasCount())
- return;
+ return QQmlCompileError();
QQmlPropertyCache *propertyCache = propertyCaches->at(objectIndex);
Q_ASSERT(propertyCache);
@@ -756,8 +790,11 @@ inline void QQmlPropertyCacheAliasCreator<ObjectContainer>::appendAliasesToPrope
Q_ASSERT(alias->flags & QV4::CompiledData::Alias::Resolved);
int type = 0;
+ int minorVersion = 0;
QQmlPropertyData::Flags propertyFlags;
- propertyDataForAlias(component, *alias, &type, &propertyFlags);
+ QQmlCompileError error = propertyDataForAlias(component, *alias, &type, &minorVersion, &propertyFlags);
+ if (error.isSet())
+ return error;
const QString propertyName = objectContainer->stringAt(alias->nameIndex);
@@ -765,8 +802,10 @@ inline void QQmlPropertyCacheAliasCreator<ObjectContainer>::appendAliasesToPrope
propertyCache->_defaultPropertyName = propertyName;
propertyCache->appendProperty(propertyName, propertyFlags, effectivePropertyIndex++,
- type, effectiveSignalIndex++);
+ type, minorVersion, effectiveSignalIndex++);
}
+
+ return QQmlCompileError();
}
template <typename ObjectContainer>
diff --git a/src/qml/compiler/qqmlpropertyvalidator.cpp b/src/qml/compiler/qqmlpropertyvalidator.cpp
index 7ea89b378d..00bb694ef4 100644
--- a/src/qml/compiler/qqmlpropertyvalidator.cpp
+++ b/src/qml/compiler/qqmlpropertyvalidator.cpp
@@ -58,7 +58,7 @@ QQmlPropertyValidator::QQmlPropertyValidator(QQmlEnginePrivate *enginePrivate, c
QVector<QQmlCompileError> QQmlPropertyValidator::validate()
{
- return validateObject(/*root object*/0, /*instantiatingBinding*/0);
+ return validateObject(/*root object*/0, /*instantiatingBinding*/nullptr);
}
typedef QVarLengthArray<const QV4::CompiledData::Binding *, 8> GroupPropertyVector;
@@ -94,7 +94,7 @@ QVector<QQmlCompileError> QQmlPropertyValidator::validateObject(int objectIndex,
if (!propertyCache)
return QVector<QQmlCompileError>();
- QQmlCustomParser *customParser = 0;
+ QQmlCustomParser *customParser = nullptr;
if (auto typeRef = resolvedTypes.value(obj->inheritedTypeNameIndex)) {
if (typeRef->type.isValid())
customParser = typeRef->type.customParser();
@@ -124,7 +124,7 @@ QVector<QQmlCompileError> QQmlPropertyValidator::validateObject(int objectIndex,
QmlIR::PropertyResolver propertyResolver(propertyCache);
QString defaultPropertyName;
- QQmlPropertyData *defaultProperty = 0;
+ QQmlPropertyData *defaultProperty = nullptr;
if (obj->indexOfDefaultPropertyOrAlias != -1) {
QQmlPropertyCache *cache = propertyCache->parent();
defaultPropertyName = cache->defaultPropertyName();
@@ -157,7 +157,7 @@ QVector<QQmlCompileError> QQmlPropertyValidator::validateObject(int objectIndex,
bool isGroupProperty = instantiatingBinding && instantiatingBinding->type == QV4::CompiledData::Binding::Type_GroupProperty;
bool notInRevision = false;
- QQmlPropertyData *pd = 0;
+ QQmlPropertyData *pd = nullptr;
if (!name.isEmpty()) {
if (binding->flags & QV4::CompiledData::Binding::IsSignalHandlerExpression
|| binding->flags & QV4::CompiledData::Binding::IsSignalHandlerObject)
@@ -188,15 +188,21 @@ QVector<QQmlCompileError> QQmlPropertyValidator::validateObject(int objectIndex,
if (name.constData()->isUpper() && !binding->isAttachedProperty()) {
QQmlType type;
- QQmlImportNamespace *typeNamespace = 0;
- imports.resolveType(stringAt(binding->propertyNameIndex), &type, 0, 0, &typeNamespace);
+ QQmlImportNamespace *typeNamespace = nullptr;
+ imports.resolveType(stringAt(binding->propertyNameIndex), &type, nullptr, nullptr, &typeNamespace);
if (typeNamespace)
return recordError(binding->location, tr("Invalid use of namespace"));
return recordError(binding->location, tr("Invalid attached object assignment"));
}
if (binding->type >= QV4::CompiledData::Binding::Type_Object && (pd || binding->isAttachedProperty())) {
- const QVector<QQmlCompileError> subObjectValidatorErrors = validateObject(binding->value.objectIndex, binding, pd && QQmlValueTypeFactory::metaObjectForMetaType(pd->propType()));
+ const bool populatingValueTypeGroupProperty
+ = pd
+ && QQmlValueTypeFactory::metaObjectForMetaType(pd->propType())
+ && !(binding->flags & QV4::CompiledData::Binding::IsOnAssignment);
+ const QVector<QQmlCompileError> subObjectValidatorErrors
+ = validateObject(binding->value.objectIndex, binding,
+ populatingValueTypeGroupProperty);
if (!subObjectValidatorErrors.isEmpty())
return subObjectValidatorErrors;
}
@@ -287,6 +293,9 @@ QVector<QQmlCompileError> QQmlPropertyValidator::validateObject(int objectIndex,
}
if (obj->idNameIndex) {
+ if (populatingValueTypeGroupProperty)
+ return recordError(obj->locationOfIdProperty, tr("Invalid use of id property with a value type"));
+
bool notInRevision = false;
collectedBindingPropertyData << propertyResolver.property(QStringLiteral("id"), &notInRevision);
}
@@ -297,9 +306,9 @@ QVector<QQmlCompileError> QQmlPropertyValidator::validateObject(int objectIndex,
customParser->engine = enginePrivate;
customParser->imports = &imports;
customParser->verifyBindings(qmlUnit, customBindings);
- customParser->validator = 0;
- customParser->engine = 0;
- customParser->imports = (QQmlImports*)0;
+ customParser->validator = nullptr;
+ customParser->engine = nullptr;
+ customParser->imports = (QQmlImports*)nullptr;
QVector<QQmlCompileError> parserErrors = customParser->errors();
if (!parserErrors.isEmpty())
return parserErrors;
@@ -665,10 +674,11 @@ QQmlCompileError QQmlPropertyValidator::validateObjectBinding(QQmlPropertyData *
} else if (property->propType() == qMetaTypeId<QQmlScriptString>()) {
return QQmlCompileError(binding->valueLocation, tr("Invalid property assignment: script expected"));
} else {
- // We want to raw metaObject here as the raw metaobject is the
+ // We want to use the raw metaObject here as the raw metaobject is the
// actual property type before we applied any extensions that might
// effect the properties on the type, but don't effect assignability
- QQmlPropertyCache *propertyMetaObject = enginePrivate->rawPropertyCacheForType(property->propType());
+ // Using -1 for the minor version ensures that we get the raw metaObject.
+ QQmlPropertyCache *propertyMetaObject = enginePrivate->rawPropertyCacheForType(property->propType(), -1);
// Will be true if the assgned type inherits propertyMetaObject
bool isAssignable = false;
diff --git a/src/qml/compiler/qqmltypecompiler.cpp b/src/qml/compiler/qqmltypecompiler.cpp
index 97ca597953..a896745b3f 100644
--- a/src/qml/compiler/qqmltypecompiler.cpp
+++ b/src/qml/compiler/qqmltypecompiler.cpp
@@ -45,7 +45,6 @@
#include <private/qqmlvmemetaobject_p.h>
#include <private/qqmlcomponent_p.h>
-#include "qqmlpropertycachecreator_p.h"
//#include "qv4jssimplifier_p.h"
#define COMPILE_EXCEPTION(token, desc) \
@@ -79,8 +78,12 @@ QV4::CompiledData::CompilationUnit *QQmlTypeCompiler::compile()
customParsers.insert(it.key(), customParser);
}
+ QQmlPendingGroupPropertyBindings pendingGroupPropertyBindings;
+
+
{
- QQmlPropertyCacheCreator<QQmlTypeCompiler> propertyCacheBuilder(&m_propertyCaches, engine, this, imports());
+ QQmlPropertyCacheCreator<QQmlTypeCompiler> propertyCacheBuilder(&m_propertyCaches, &pendingGroupPropertyBindings,
+ engine, this, imports());
QQmlCompileError error = propertyCacheBuilder.buildMetaObjects();
if (error.isSet()) {
recordError(error);
@@ -122,6 +125,8 @@ QV4::CompiledData::CompilationUnit *QQmlTypeCompiler::compile()
QQmlComponentAndAliasResolver resolver(this);
if (!resolver.resolve())
return nullptr;
+
+ pendingGroupPropertyBindings.resolveMissingPropertyCaches(engine, &m_propertyCaches);
}
{
@@ -139,10 +144,11 @@ QV4::CompiledData::CompilationUnit *QQmlTypeCompiler::compile()
sss.scan();
}
- document->jsModule.fileName = typeData->finalUrlString();
- QmlIR::JSCodeGen v4CodeGenerator(document->code, &document->jsGenerator, &document->jsModule, &document->jsParserEngine, document->program, typeNameCache, &document->jsGenerator.stringTable);
+ document->jsModule.fileName = typeData->urlString();
+ document->jsModule.finalUrl = typeData->finalUrlString();
+ QmlIR::JSCodeGen v4CodeGenerator(document->code, &document->jsGenerator, &document->jsModule, &document->jsParserEngine,
+ document->program, typeNameCache, &document->jsGenerator.stringTable, engine->v8engine()->illegalNames());
v4CodeGenerator.setUseFastLookups(false);
- // ### v4CodeGenerator.setUseTypeInference(true);
QQmlJSCodeGenerator jsCodeGen(this, &v4CodeGenerator);
if (!jsCodeGen.generateCodeForComponents())
return nullptr;
@@ -295,7 +301,7 @@ SignalHandlerConverter::SignalHandlerConverter(QQmlTypeCompiler *typeCompiler)
, imports(typeCompiler->imports())
, customParsers(typeCompiler->customParserCache())
, resolvedTypes(typeCompiler->resolvedTypes)
- , illegalNames(QV8Engine::get(QQmlEnginePrivate::get(typeCompiler->enginePrivate()))->illegalNames())
+ , illegalNames(typeCompiler->enginePrivate()->v8engine()->illegalNames())
, propertyCaches(typeCompiler->propertyCaches())
{
}
@@ -331,7 +337,7 @@ bool SignalHandlerConverter::convertSignalHandlerExpressionsToFunctionDeclaratio
auto *typeRef = resolvedTypes.value(binding->propertyNameIndex);
QQmlType type = typeRef ? typeRef->type : QQmlType();
if (!type.isValid()) {
- if (imports->resolveType(propertyName, &type, 0, 0, 0)) {
+ if (imports->resolveType(propertyName, &type, nullptr, nullptr, nullptr)) {
if (type.isComposite()) {
QQmlTypeData *tdata = enginePrivate->typeLoader.getType(type.sourceUrl());
Q_ASSERT(tdata);
@@ -396,7 +402,7 @@ bool SignalHandlerConverter::convertSignalHandlerExpressionsToFunctionDeclaratio
} else {
if (notInRevision) {
// Try assinging it as a property later
- if (resolver.property(propertyName, /*notInRevision ptr*/0))
+ if (resolver.property(propertyName, /*notInRevision ptr*/nullptr))
continue;
const QString &originalPropertyName = stringAt(binding->propertyNameIndex);
@@ -456,7 +462,7 @@ bool SignalHandlerConverter::convertSignalHandlerExpressionsToFunctionDeclaratio
QQmlJS::MemoryPool *pool = compiler->memoryPool();
- QQmlJS::AST::FormalParameterList *paramList = 0;
+ QQmlJS::AST::FormalParameterList *paramList = nullptr;
for (const QString &param : qAsConst(parameters)) {
QStringRef paramNameRef = compiler->newStringRef(param);
@@ -470,7 +476,7 @@ bool SignalHandlerConverter::convertSignalHandlerExpressionsToFunctionDeclaratio
paramList = paramList->finish();
QmlIR::CompiledFunctionOrExpression *foe = obj->functionsAndExpressions->slowAt(binding->value.compiledScriptIndex);
- QQmlJS::AST::FunctionDeclaration *functionDeclaration = 0;
+ QQmlJS::AST::FunctionDeclaration *functionDeclaration = nullptr;
if (QQmlJS::AST::ExpressionStatement *es = QQmlJS::AST::cast<QQmlJS::AST::ExpressionStatement*>(foe->node)) {
if (QQmlJS::AST::FunctionExpression *fe = QQmlJS::AST::cast<QQmlJS::AST::FunctionExpression*>(es->expression)) {
functionDeclaration = new (pool) QQmlJS::AST::FunctionDeclaration(fe->name, fe->formals, fe->body);
@@ -610,7 +616,7 @@ bool QQmlEnumTypeResolver::tryQualifiedEnumAssignment(const QmlIR::Object *obj,
return true;
}
QQmlType type;
- imports->resolveType(typeName, &type, 0, 0, 0);
+ imports->resolveType(typeName, &type, nullptr, nullptr, nullptr);
if (!type.isValid() && !isQtObject)
return true;
@@ -662,7 +668,7 @@ int QQmlEnumTypeResolver::evaluateEnum(const QString &scope, const QStringRef &e
if (scope != QLatin1String("Qt")) {
QQmlType type;
- imports->resolveType(scope, &type, 0, 0, 0);
+ imports->resolveType(scope, &type, nullptr, nullptr, nullptr);
if (!type.isValid())
return -1;
if (!enumName.isEmpty())
@@ -813,7 +819,7 @@ void QQmlComponentAndAliasResolver::findAndRegisterImplicitComponents(const QmlI
continue;
}
- QQmlPropertyData *pd = 0;
+ QQmlPropertyData *pd = nullptr;
if (binding->propertyNameIndex != quint32(0)) {
bool notInRevision = false;
pd = propertyResolver.property(stringAt(binding->propertyNameIndex), &notInRevision);
@@ -823,8 +829,8 @@ void QQmlComponentAndAliasResolver::findAndRegisterImplicitComponents(const QmlI
if (!pd || !pd->isQObject())
continue;
- QQmlPropertyCache *pc = enginePrivate->rawPropertyCacheForType(pd->propType());
- const QMetaObject *mo = pc ? pc->firstCppMetaObject() : 0;
+ QQmlPropertyCache *pc = enginePrivate->rawPropertyCacheForType(pd->propType(), pd->typeMinorVersion());
+ const QMetaObject *mo = pc ? pc->firstCppMetaObject() : nullptr;
while (mo) {
if (mo == &QQmlComponent::staticMetaObject)
break;
@@ -1022,7 +1028,11 @@ bool QQmlComponentAndAliasResolver::resolveAliases(int componentIndex)
}
if (result == AllAliasesResolved) {
- aliasCacheCreator.appendAliasesToPropertyCache(*qmlObjects->at(componentIndex), objectIndex);
+ QQmlCompileError error = aliasCacheCreator.appendAliasesToPropertyCache(*qmlObjects->at(componentIndex), objectIndex);
+ if (error.isSet()) {
+ recordError(error);
+ return false;
+ }
atLeastOneAliasResolved = true;
} else if (result == SomeAliasesResolved) {
atLeastOneAliasResolved = true;
@@ -1092,7 +1102,11 @@ QQmlComponentAndAliasResolver::AliasResolutionResult QQmlComponentAndAliasResolv
alias->flags |= QV4::CompiledData::Alias::AliasPointsToPointerObject;
} else {
QQmlPropertyCache *targetCache = propertyCaches.at(targetObjectIndex);
- Q_ASSERT(targetCache);
+ if (!targetCache) {
+ *error = QQmlCompileError(alias->referenceLocation, tr("Invalid alias target location: %1").arg(property.toString()));
+ break;
+ }
+
QmlIR::PropertyResolver resolver(targetCache);
QQmlPropertyData *targetProperty = resolver.property(property.toString());
@@ -1195,7 +1209,7 @@ bool QQmlDeferredAndCustomParserBindingScanner::scanObject(int objectIndex)
return true;
QString defaultPropertyName;
- QQmlPropertyData *defaultProperty = 0;
+ QQmlPropertyData *defaultProperty = nullptr;
if (obj->indexOfDefaultPropertyOrAlias != -1) {
QQmlPropertyCache *cache = propertyCache->parent();
defaultPropertyName = cache->defaultPropertyName();
@@ -1220,7 +1234,7 @@ bool QQmlDeferredAndCustomParserBindingScanner::scanObject(int objectIndex)
}
for (QmlIR::Binding *binding = obj->firstBinding(); binding; binding = binding->next) {
- QQmlPropertyData *pd = 0;
+ QQmlPropertyData *pd = nullptr;
QString name = stringAt(binding->propertyNameIndex);
if (customParser) {
@@ -1325,7 +1339,7 @@ bool QQmlJSCodeGenerator::compileComponent(int contextObject)
auto *tref = resolvedTypes.value(obj->inheritedTypeNameIndex);
if (tref && tref->isFullyDynamicType)
- m.type = 0;
+ m.type = nullptr;
idMapping << m;
}
@@ -1403,10 +1417,10 @@ void QQmlDefaultPropertyMerger::mergeDefaultProperties(int objectIndex)
QmlIR::Object *object = qmlObjects.at(objectIndex);
QString defaultProperty = object->indexOfDefaultPropertyOrAlias != -1 ? propertyCache->parent()->defaultPropertyName() : propertyCache->defaultPropertyName();
- QmlIR::Binding *bindingsToReinsert = 0;
- QmlIR::Binding *tail = 0;
+ QmlIR::Binding *bindingsToReinsert = nullptr;
+ QmlIR::Binding *tail = nullptr;
- QmlIR::Binding *previousBinding = 0;
+ QmlIR::Binding *previousBinding = nullptr;
QmlIR::Binding *binding = object->firstBinding();
while (binding) {
if (binding->propertyNameIndex == quint32(0) || stringAt(binding->propertyNameIndex) != defaultProperty) {
@@ -1425,7 +1439,7 @@ void QQmlDefaultPropertyMerger::mergeDefaultProperties(int objectIndex)
tail->next = toReinsert;
tail = tail->next;
}
- tail->next = 0;
+ tail->next = nullptr;
}
binding = bindingsToReinsert;
diff --git a/src/qml/compiler/qqmltypecompiler_p.h b/src/qml/compiler/qqmltypecompiler_p.h
index d905b956c7..b8eddcb9b2 100644
--- a/src/qml/compiler/qqmltypecompiler_p.h
+++ b/src/qml/compiler/qqmltypecompiler_p.h
@@ -55,6 +55,7 @@
#include <qhash.h>
#include <private/qqmltypeloader_p.h>
#include <private/qqmlirbuilder_p.h>
+#include <private/qqmlpropertycachecreator_p.h>
QT_BEGIN_NAMESPACE
@@ -74,17 +75,6 @@ struct Location;
}
}
-struct QQmlCompileError
-{
- QQmlCompileError() {}
- QQmlCompileError(const QV4::CompiledData::Location &location, const QString &description)
- : location(location), description(description) {}
- QV4::CompiledData::Location location;
- QString description;
-
- bool isSet() const { return !description.isEmpty(); }
-};
-
struct QQmlTypeCompiler
{
Q_DECLARE_TR_FUNCTIONS(QQmlTypeCompiler)
diff --git a/src/qml/compiler/qv4bytecodegenerator.cpp b/src/qml/compiler/qv4bytecodegenerator.cpp
index 05bbf25292..4d50654d27 100644
--- a/src/qml/compiler/qv4bytecodegenerator.cpp
+++ b/src/qml/compiler/qv4bytecodegenerator.cpp
@@ -74,16 +74,20 @@ void BytecodeGenerator::packInstruction(I &i)
Q_ASSERT(type >= MOTH_NUM_INSTRUCTIONS());
if (type >= MOTH_NUM_INSTRUCTIONS())
type -= MOTH_NUM_INSTRUCTIONS();
- int instructionsAsInts[sizeof(Instr)/sizeof(int)];
+ int instructionsAsInts[sizeof(Instr)/sizeof(int)] = {};
int nMembers = Moth::InstrInfo::argumentCount[static_cast<int>(i.type)];
- memcpy(instructionsAsInts, i.packed + 1, nMembers*sizeof(int));
+ for (int j = 0; j < nMembers; ++j) {
+ instructionsAsInts[j] = qFromLittleEndian<qint32>(i.packed + 1 + j * sizeof(int));
+ }
enum {
Normal,
Wide
} width = Normal;
for (int n = 0; n < nMembers; ++n) {
- if (width == Normal && (static_cast<char>(instructionsAsInts[n]) != instructionsAsInts[n]))
+ if (width == Normal && (static_cast<qint8>(instructionsAsInts[n]) != instructionsAsInts[n])) {
width = Wide;
+ break;
+ }
}
char *code = i.packed;
switch (width) {
@@ -91,7 +95,7 @@ void BytecodeGenerator::packInstruction(I &i)
*reinterpret_cast<uchar *>(code) = type;
++code;
for (int n = 0; n < nMembers; ++n) {
- char v = static_cast<char>(instructionsAsInts[n]);
+ qint8 v = static_cast<qint8>(instructionsAsInts[n]);
memcpy(code, &v, 1);
code += 1;
}
@@ -113,17 +117,17 @@ void BytecodeGenerator::adjustJumpOffsets()
continue;
Q_ASSERT(i.linkedLabel != -1 && labels.at(i.linkedLabel) != -1);
const auto &linkedInstruction = instructions.at(labels.at(i.linkedLabel));
- char *c = i.packed + i.offsetForJump;
+ qint8 *c = reinterpret_cast<qint8*>(i.packed + i.offsetForJump);
int jumpOffset = linkedInstruction.position - (i.position + i.size);
// qDebug() << "adjusting jump offset for instruction" << index << i.position << i.size << "offsetForJump" << i.offsetForJump << "target"
// << labels.at(i.linkedLabel) << linkedInstruction.position << "jumpOffset" << jumpOffset;
uchar type = *reinterpret_cast<const uchar *>(i.packed);
if (type >= MOTH_NUM_INSTRUCTIONS()) {
Q_ASSERT(i.offsetForJump == i.size - 4);
- memcpy(c, &jumpOffset, sizeof(int));
+ qToLittleEndian<qint32>(jumpOffset, c);
} else {
Q_ASSERT(i.offsetForJump == i.size - 1);
- char o = jumpOffset;
+ qint8 o = jumpOffset;
Q_ASSERT(o == jumpOffset);
*c = o;
}
@@ -181,6 +185,7 @@ void BytecodeGenerator::finalize(Compiler::Context *context)
}
int BytecodeGenerator::addInstructionHelper(Instr::Type type, const Instr &i, int offsetOfOffset) {
+#if QT_CONFIG(qml_debug)
if (debugMode && type != Instr::Type::Debug) {
QT_WARNING_PUSH
QT_WARNING_DISABLE_GCC("-Wmaybe-uninitialized") // broken gcc warns about Instruction::Debug()
@@ -193,10 +198,14 @@ QT_WARNING_DISABLE_GCC("-Wmaybe-uninitialized") // broken gcc warns about Instru
}
QT_WARNING_POP
}
+#else
+ Q_UNUSED(debugMode);
+#endif
const int pos = instructions.size();
- int s = Moth::InstrInfo::argumentCount[static_cast<int>(type)]*sizeof(int);
+ const int argCount = Moth::InstrInfo::argumentCount[static_cast<int>(type)];
+ int s = argCount*sizeof(int);
if (offsetOfOffset != -1)
offsetOfOffset += 1;
I instr{type, static_cast<short>(s + 1), 0, currentLine, offsetOfOffset, -1, "\0\0" };
@@ -204,7 +213,12 @@ QT_WARNING_POP
*reinterpret_cast<uchar *>(code) = static_cast<uchar>(MOTH_NUM_INSTRUCTIONS() + static_cast<int>(type));
++code;
Q_ASSERT(MOTH_NUM_INSTRUCTIONS() + static_cast<int>(type) < 256);
- memcpy(code, &i, s);
+
+ for (int j = 0; j < argCount; ++j) {
+ qToLittleEndian<qint32>(i.argumentsAsInts[j], code);
+ code += sizeof(int);
+ }
+
instructions.append(instr);
return pos;
diff --git a/src/qml/compiler/qv4bytecodegenerator_p.h b/src/qml/compiler/qv4bytecodegenerator_p.h
index 3d516da922..3b3c766bfe 100644
--- a/src/qml/compiler/qv4bytecodegenerator_p.h
+++ b/src/qml/compiler/qv4bytecodegenerator_p.h
@@ -94,7 +94,7 @@ public:
generator->labels[index] = generator->instructions.size();
}
- BytecodeGenerator *generator = 0;
+ BytecodeGenerator *generator = nullptr;
int index = -1;
};
diff --git a/src/qml/compiler/qv4codegen.cpp b/src/qml/compiler/qv4codegen.cpp
index 6abcf82f44..bc4ca5d6f4 100644
--- a/src/qml/compiler/qv4codegen.cpp
+++ b/src/qml/compiler/qv4codegen.cpp
@@ -89,10 +89,10 @@ static inline void setJumpOutLocation(QV4::Moth::BytecodeGenerator *bytecodeGene
}
Codegen::Codegen(QV4::Compiler::JSUnitGenerator *jsUnitGenerator, bool strict)
- : _module(0)
+ : _module(nullptr)
, _returnAddress(0)
- , _context(0)
- , _labelledStatement(0)
+ , _context(nullptr)
+ , _labelledStatement(nullptr)
, jsUnitGenerator(jsUnitGenerator)
, _strictMode(strict)
, _fileNameIsUrl(false)
@@ -102,6 +102,7 @@ Codegen::Codegen(QV4::Compiler::JSUnitGenerator *jsUnitGenerator, bool strict)
}
void Codegen::generateFromProgram(const QString &fileName,
+ const QString &finalUrl,
const QString &sourceCode,
Program *node,
Module *module,
@@ -110,14 +111,16 @@ void Codegen::generateFromProgram(const QString &fileName,
Q_ASSERT(node);
_module = module;
- _context = 0;
+ _context = nullptr;
+ // ### should be set on the module outside of this method
_module->fileName = fileName;
+ _module->finalUrl = finalUrl;
ScanFunctions scan(this, sourceCode, mode);
scan(node);
- defineFunction(QStringLiteral("%entry"), node, 0, node->elements);
+ defineFunction(QStringLiteral("%entry"), node, nullptr, node->elements);
}
void Codegen::enterContext(Node *node)
@@ -199,6 +202,7 @@ Codegen::Reference Codegen::unop(UnaryOperation op, const Reference &expr)
} else {
// intentionally fall-through: the result is never used, so it's equivalent to
// "expr += 1", which is what a pre-increment does as well.
+ Q_FALLTHROUGH();
}
case PreIncrement: {
Reference e = expr.asLValue();
@@ -224,6 +228,7 @@ Codegen::Reference Codegen::unop(UnaryOperation op, const Reference &expr)
} else {
// intentionally fall-through: the result is never used, so it's equivalent to
// "expr -= 1", which is what a pre-decrement does as well.
+ Q_FALLTHROUGH();
}
case PreDecrement: {
Reference e = expr.asLValue();
@@ -630,14 +635,14 @@ bool Codegen::visit(ArrayLiteral *ast)
for (ElementList *it = ast->elements; it; it = it->next) {
for (Elision *elision = it->elision; elision; elision = elision->next)
- push(0);
+ push(nullptr);
push(it->expression);
if (hasError)
return false;
}
for (Elision *elision = ast->elision; elision; elision = elision->next)
- push(0);
+ push(nullptr);
if (args == -1) {
Q_ASSERT(argc == 0);
@@ -1258,6 +1263,8 @@ bool Codegen::visit(CallExpression *ast)
switch (base.type) {
case Reference::Member:
case Reference::Subscript:
+ case Reference::QmlScopeObject:
+ case Reference::QmlContextObject:
base = base.asLValue();
break;
case Reference::Name:
@@ -1272,7 +1279,21 @@ bool Codegen::visit(CallExpression *ast)
return false;
//### Do we really need all these call instructions? can's we load the callee in a temp?
- if (base.type == Reference::Member) {
+ if (base.type == Reference::QmlScopeObject) {
+ Instruction::CallScopeObjectProperty call;
+ call.base = base.qmlBase.stackSlot();
+ call.name = base.qmlCoreIndex;
+ call.argc = calldata.argc;
+ call.argv = calldata.argv;
+ bytecodeGenerator->addInstruction(call);
+ } else if (base.type == Reference::QmlContextObject) {
+ Instruction::CallContextObjectProperty call;
+ call.base = base.qmlBase.stackSlot();
+ call.name = base.qmlCoreIndex;
+ call.argc = calldata.argc;
+ call.argv = calldata.argv;
+ bytecodeGenerator->addInstruction(call);
+ } else if (base.type == Reference::Member) {
if (useFastLookups) {
Instruction::CallPropertyLookup call;
call.base = base.propertyBase.stackSlot();
@@ -1475,7 +1496,7 @@ bool Codegen::visit(FunctionExpression *ast)
RegisterScope scope(this);
- int function = defineFunction(ast->name.toString(), ast, ast->formals, ast->body ? ast->body->elements : 0);
+ int function = defineFunction(ast->name.toString(), ast, ast->formals, ast->body ? ast->body->elements : nullptr);
loadClosure(function);
_expr.setResult(Reference::fromAccumulator(this));
return false;
@@ -1699,7 +1720,7 @@ bool Codegen::visit(ObjectLiteral *ast)
v.rvalue = value.storeOnStack();
} else if (PropertyGetterSetter *gs = AST::cast<AST::PropertyGetterSetter *>(it->assignment)) {
- const int function = defineFunction(name, gs, gs->formals, gs->functionBody ? gs->functionBody->elements : 0);
+ const int function = defineFunction(name, gs, gs->formals, gs->functionBody ? gs->functionBody->elements : nullptr);
ObjectPropertyValue &v = valueMap[name];
if (v.rvalue.isValid() ||
(gs->type == PropertyGetterSetter::Getter && v.hasGetter()) ||
@@ -2121,7 +2142,7 @@ int Codegen::defineFunction(const QString &name, AST::Node *ast,
for (const Context::Member &member : qAsConst(_context->members)) {
if (member.function) {
const int function = defineFunction(member.function->name.toString(), member.function, member.function->formals,
- member.function->body ? member.function->body->elements : 0);
+ member.function->body ? member.function->body->elements : nullptr);
loadClosure(function);
if (! _context->parent) {
Reference::fromName(this, member.function->name.toString()).storeConsumeAccumulator();
@@ -2333,7 +2354,8 @@ bool Codegen::visit(ForEachStatement *ast)
RegisterScope scope(this);
- Reference obj = Reference::fromStackSlot(this);
+ Reference nextIterObj = Reference::fromStackSlot(this);
+ Reference iterObj = Reference::fromStackSlot(this);
Reference expr = expression(ast->expression);
if (hasError)
return true;
@@ -2341,7 +2363,9 @@ bool Codegen::visit(ForEachStatement *ast)
expr.loadInAccumulator();
Instruction::ForeachIteratorObject iteratorObjInstr;
bytecodeGenerator->addInstruction(iteratorObjInstr);
- obj.storeConsumeAccumulator();
+ iterObj.storeConsumeAccumulator();
+
+ Reference lhs = expression(ast->initialiser).asLValue();
BytecodeGenerator::Label in = bytecodeGenerator->newLabel();
BytecodeGenerator::Label end = bytecodeGenerator->newLabel();
@@ -2352,20 +2376,21 @@ bool Codegen::visit(ForEachStatement *ast)
BytecodeGenerator::Label body = bytecodeGenerator->label();
+ nextIterObj.loadInAccumulator();
+ lhs.storeConsumeAccumulator();
+
statement(ast->statement);
setJumpOutLocation(bytecodeGenerator, ast->statement, ast->forToken);
in.link();
- Reference lhs = expression(ast->initialiser).asLValue();
-
- obj.loadInAccumulator();
+ iterObj.loadInAccumulator();
Instruction::ForeachNextPropertyName nextPropInstr;
bytecodeGenerator->addInstruction(nextPropInstr);
- lhs = lhs.storeRetainAccumulator().storeOnStack();
+ nextIterObj.storeConsumeAccumulator();
Reference::fromConst(this, QV4::Encode::null()).loadInAccumulator();
- bytecodeGenerator->jumpStrictNotEqual(lhs.stackSlot(), body);
+ bytecodeGenerator->jumpStrictNotEqual(nextIterObj.stackSlot(), body);
end.link();
@@ -2477,7 +2502,8 @@ bool Codegen::visit(LocalForEachStatement *ast)
RegisterScope scope(this);
- Reference obj = Reference::fromStackSlot(this);
+ Reference nextIterObj = Reference::fromStackSlot(this);
+ Reference iterObj = Reference::fromStackSlot(this);
Reference expr = expression(ast->expression);
if (hasError)
return true;
@@ -2487,7 +2513,7 @@ bool Codegen::visit(LocalForEachStatement *ast)
expr.loadInAccumulator();
Instruction::ForeachIteratorObject iteratorObjInstr;
bytecodeGenerator->addInstruction(iteratorObjInstr);
- obj.storeConsumeAccumulator();
+ iterObj.storeConsumeAccumulator();
BytecodeGenerator::Label in = bytecodeGenerator->newLabel();
BytecodeGenerator::Label end = bytecodeGenerator->newLabel();
@@ -2498,18 +2524,22 @@ bool Codegen::visit(LocalForEachStatement *ast)
BytecodeGenerator::Label body = bytecodeGenerator->label();
Reference it = referenceForName(ast->declaration->name.toString(), true).asLValue();
+
+ nextIterObj.loadInAccumulator();
+ it.storeConsumeAccumulator();
+
statement(ast->statement);
setJumpOutLocation(bytecodeGenerator, ast->statement, ast->forToken);
in.link();
- obj.loadInAccumulator();
+ iterObj.loadInAccumulator();
Instruction::ForeachNextPropertyName nextPropInstr;
bytecodeGenerator->addInstruction(nextPropInstr);
- auto lhs = it.storeRetainAccumulator().storeOnStack();
+ nextIterObj.storeConsumeAccumulator();
Reference::fromConst(this, QV4::Encode::null()).loadInAccumulator();
- bytecodeGenerator->jumpStrictNotEqual(lhs.stackSlot(), body);
+ bytecodeGenerator->jumpStrictNotEqual(nextIterObj.stackSlot(), body);
end.link();
@@ -2898,43 +2928,43 @@ public:
return locs;
}
- bool visit(ArrayMemberExpression *) Q_DECL_OVERRIDE
+ bool visit(ArrayMemberExpression *) override
{
locs.setAllVolatile();
return false;
}
- bool visit(FieldMemberExpression *) Q_DECL_OVERRIDE
+ bool visit(FieldMemberExpression *) override
{
locs.setAllVolatile();
return false;
}
- bool visit(PostIncrementExpression *e) Q_DECL_OVERRIDE
+ bool visit(PostIncrementExpression *e) override
{
collectIdentifiers(locs.specificLocations, e->base);
return false;
}
- bool visit(PostDecrementExpression *e) Q_DECL_OVERRIDE
+ bool visit(PostDecrementExpression *e) override
{
collectIdentifiers(locs.specificLocations, e->base);
return false;
}
- bool visit(PreIncrementExpression *e) Q_DECL_OVERRIDE
+ bool visit(PreIncrementExpression *e) override
{
collectIdentifiers(locs.specificLocations, e->expression);
return false;
}
- bool visit(PreDecrementExpression *e) Q_DECL_OVERRIDE
+ bool visit(PreDecrementExpression *e) override
{
collectIdentifiers(locs.specificLocations, e->expression);
return false;
}
- bool visit(BinaryExpression *e) Q_DECL_OVERRIDE
+ bool visit(BinaryExpression *e) override
{
switch (e->op) {
case QSOperator::InplaceAnd:
@@ -3073,7 +3103,7 @@ Codegen::Reference &Codegen::Reference::operator =(const Reference &other)
qmlBase = other.qmlBase;
qmlCoreIndex = other.qmlCoreIndex;
qmlNotifyIndex = other.qmlNotifyIndex;
- captureRequired = other.captureRequired;
+ capturePolicy = other.capturePolicy;
break;
}
@@ -3110,7 +3140,7 @@ bool Codegen::Reference::operator==(const Codegen::Reference &other) const
case QmlScopeObject:
case QmlContextObject:
return qmlCoreIndex == other.qmlCoreIndex && qmlNotifyIndex == other.qmlNotifyIndex
- && captureRequired == other.captureRequired;
+ && capturePolicy == other.capturePolicy;
}
return true;
}
@@ -3439,18 +3469,18 @@ QT_WARNING_POP
Instruction::LoadScopeObjectProperty load;
load.base = qmlBase;
load.propertyIndex = qmlCoreIndex;
- load.captureRequired = captureRequired;
+ load.captureRequired = capturePolicy == CaptureAtRuntime;
codegen->bytecodeGenerator->addInstruction(load);
- if (!captureRequired)
+ if (capturePolicy == CaptureAheadOfTime)
codegen->_context->scopeObjectPropertyDependencies.insert(qmlCoreIndex, qmlNotifyIndex);
} return;
case QmlContextObject: {
Instruction::LoadContextObjectProperty load;
load.base = qmlBase;
load.propertyIndex = qmlCoreIndex;
- load.captureRequired = captureRequired;
+ load.captureRequired = capturePolicy == CaptureAtRuntime;
codegen->bytecodeGenerator->addInstruction(load);
- if (!captureRequired)
+ if (capturePolicy == CaptureAheadOfTime)
codegen->_context->contextObjectPropertyDependencies.insert(qmlCoreIndex, qmlNotifyIndex);
} return;
case Invalid:
diff --git a/src/qml/compiler/qv4codegen_p.h b/src/qml/compiler/qv4codegen_p.h
index dba9388292..a46d47cb67 100644
--- a/src/qml/compiler/qv4codegen_p.h
+++ b/src/qml/compiler/qv4codegen_p.h
@@ -97,6 +97,7 @@ public:
void generateFromProgram(const QString &fileName,
+ const QString &finalUrl,
const QString &sourceCode,
AST::Program *ast,
Module *module,
@@ -190,10 +191,7 @@ public:
bool isLValue() const { return !isReadonly; }
Reference(Codegen *cg, Type type = Invalid) : type(type), codegen(cg) {}
- Reference()
- : type(Invalid)
- , codegen(nullptr)
- {}
+ Reference() {}
Reference(const Reference &other);
Reference &operator =(const Reference &other);
@@ -218,6 +216,28 @@ public:
return isStackSlot();
}
+ enum PropertyCapturePolicy {
+ /*
+ We're reading a property from the scope or context object, but it's a CONSTANT property,
+ so we don't need to register a dependency at all.
+ */
+ DontCapture,
+ /*
+ We're reading the property of a QObject, and we know that it's the
+ scope object or context object, which we know very well. Instead of registering a
+ property capture every time, we can do that ahead of time and then register all those
+ captures in one shot in registerQmlDependencies().
+ */
+ CaptureAheadOfTime,
+ /*
+ We're reading the property of a QObject, and we're not quite sure where
+ the QObject comes from or what it is. So, when reading that property at run-time,
+ make sure that we capture where we read that property so that if it changes we can
+ re-evaluate the entire expression.
+ */
+ CaptureAtRuntime
+ };
+
static Reference fromAccumulator(Codegen *cg) {
return Reference(cg, Accumulator);
}
@@ -266,20 +286,20 @@ public:
r.isReadonly = true;
return r;
}
- static Reference fromQmlScopeObject(const Reference &base, qint16 coreIndex, qint16 notifyIndex, bool captureRequired) {
+ static Reference fromQmlScopeObject(const Reference &base, qint16 coreIndex, qint16 notifyIndex, PropertyCapturePolicy capturePolicy) {
Reference r(base.codegen, QmlScopeObject);
r.qmlBase = base.storeOnStack().stackSlot();
r.qmlCoreIndex = coreIndex;
r.qmlNotifyIndex = notifyIndex;
- r.captureRequired = captureRequired;
+ r.capturePolicy = capturePolicy;
return r;
}
- static Reference fromQmlContextObject(const Reference &base, qint16 coreIndex, qint16 notifyIndex, bool captureRequired) {
+ static Reference fromQmlContextObject(const Reference &base, qint16 coreIndex, qint16 notifyIndex, PropertyCapturePolicy capturePolicy) {
Reference r(base.codegen, QmlContextObject);
r.qmlBase = base.storeOnStack().stackSlot();
r.qmlCoreIndex = coreIndex;
r.qmlNotifyIndex = notifyIndex;
- r.captureRequired = captureRequired;
+ r.capturePolicy = capturePolicy;
return r;
}
static Reference fromThis(Codegen *cg) {
@@ -335,7 +355,7 @@ public:
Moth::StackSlot qmlBase;
qint16 qmlCoreIndex;
qint16 qmlNotifyIndex;
- bool captureRequired;
+ PropertyCapturePolicy capturePolicy;
};
};
QString name;
@@ -344,7 +364,7 @@ public:
bool stackSlotIsLocalOrArgument = false;
bool isVolatile = false;
bool global = false;
- Codegen *codegen;
+ Codegen *codegen = nullptr;
private:
void storeAccumulator() const;
@@ -363,16 +383,12 @@ public:
};
struct ObjectPropertyValue {
- ObjectPropertyValue()
- : getter(-1)
- , setter(-1)
- , keyAsIndex(UINT_MAX)
- {}
+ ObjectPropertyValue() {}
Reference rvalue;
- int getter; // index in _module->functions or -1 if not set
- int setter;
- uint keyAsIndex;
+ int getter = -1; // index in _module->functions or -1 if not set
+ int setter = -1;
+ uint keyAsIndex = UINT_MAX;
bool hasGetter() const { return getter >= 0; }
bool hasSetter() const { return setter >= 0; }
@@ -383,34 +399,26 @@ protected:
class Result {
Reference _result;
- const BytecodeGenerator::Label *_iftrue;
- const BytecodeGenerator::Label *_iffalse;
- Format _format;
+ const BytecodeGenerator::Label *_iftrue = nullptr;
+ const BytecodeGenerator::Label *_iffalse = nullptr;
+ Format _format = ex;
Format _requested;
bool _trueBlockFollowsCondition = false;
public:
explicit Result(const Reference &lrvalue)
: _result(lrvalue)
- , _iftrue(nullptr)
- , _iffalse(nullptr)
- , _format(ex)
, _requested(ex)
- {
- }
+ {}
explicit Result(Format requested = ex)
- : _iftrue(0)
- , _iffalse(0)
- , _format(ex)
- , _requested(requested) {}
+ : _requested(requested) {}
explicit Result(const BytecodeGenerator::Label *iftrue,
const BytecodeGenerator::Label *iffalse,
bool trueBlockFollowsCondition)
: _iftrue(iftrue)
, _iffalse(iffalse)
- , _format(ex)
, _requested(cx)
, _trueBlockFollowsCondition(trueBlockFollowsCondition)
{
@@ -648,7 +656,7 @@ protected:
Context *_context;
AST::LabelledStatement *_labelledStatement;
QV4::Compiler::JSUnitGenerator *jsUnitGenerator;
- BytecodeGenerator *bytecodeGenerator = 0;
+ BytecodeGenerator *bytecodeGenerator = nullptr;
bool _strictMode;
bool useFastLookups = true;
bool requiresReturnValue = false;
diff --git a/src/qml/compiler/qv4compileddata.cpp b/src/qml/compiler/qv4compileddata.cpp
index d889e634c0..cc11b250f3 100644
--- a/src/qml/compiler/qv4compileddata.cpp
+++ b/src/qml/compiler/qv4compileddata.cpp
@@ -65,6 +65,9 @@
#include <QCryptographicHash>
#include <QSaveFile>
+// generated by qmake:
+#include "qml_compile_hash_p.h"
+
#include <algorithm>
#if defined(QT_BUILD_INTERNAL)
@@ -84,8 +87,10 @@ static QString cacheFilePath(const QUrl &url)
{
const QString localSourcePath = QQmlFile::urlToLocalFileOrQrc(url);
const QString localCachePath = localSourcePath + QLatin1Char('c');
+#ifndef Q_OS_ANDROID
if (QFile::exists(localCachePath) || QFileInfo(QFileInfo(localSourcePath).dir().absolutePath()).isWritable())
return localCachePath;
+#endif
QCryptographicHash fileNameHash(QCryptographicHash::Sha1);
fileNameHash.addData(localSourcePath.toUtf8());
QString directory = QStandardPaths::writableLocation(QStandardPaths::CacheLocation) + QLatin1String("/qmlcache/");
@@ -94,7 +99,8 @@ static QString cacheFilePath(const QUrl &url)
}
#endif
-CompilationUnit::CompilationUnit()
+CompilationUnit::CompilationUnit(const Unit *unitData)
+ : data(unitData)
{}
#ifndef V4_BOOTSTRAP
@@ -103,7 +109,7 @@ CompilationUnit::~CompilationUnit()
unlink();
if (data && !(data->flags & QV4::CompiledData::Unit::StaticData))
free(const_cast<Unit *>(data));
- data = 0;
+ data = nullptr;
}
QV4::Function *CompilationUnit::linkToEngine(ExecutionEngine *engine)
@@ -195,7 +201,7 @@ QV4::Function *CompilationUnit::linkToEngine(ExecutionEngine *engine)
if (data->indexOfRootFunction != -1)
return runtimeFunctions[data->indexOfRootFunction];
else
- return 0;
+ return nullptr;
}
void CompilationUnit::unlink()
@@ -222,16 +228,16 @@ void CompilationUnit::unlink()
qDeleteAll(resolvedTypes);
resolvedTypes.clear();
- engine = 0;
- qmlEngine = 0;
+ engine = nullptr;
+ qmlEngine = nullptr;
free(runtimeStrings);
- runtimeStrings = 0;
+ runtimeStrings = nullptr;
delete [] runtimeLookups;
- runtimeLookups = 0;
+ runtimeLookups = nullptr;
delete [] runtimeRegularExpressions;
- runtimeRegularExpressions = 0;
+ runtimeRegularExpressions = nullptr;
free(runtimeClasses);
- runtimeClasses = 0;
+ runtimeClasses = nullptr;
qDeleteAll(runtimeFunctions);
runtimeFunctions.clear();
#if Q_BYTE_ORDER == Q_BIG_ENDIAN
@@ -251,11 +257,11 @@ void CompilationUnit::markObjects(QV4::MarkStack *markStack)
}
}
-IdentifierHash<int> CompilationUnit::namedObjectsPerComponent(int componentObjectIndex)
+IdentifierHash CompilationUnit::namedObjectsPerComponent(int componentObjectIndex)
{
auto it = namedObjectsPerComponentCache.find(componentObjectIndex);
if (it == namedObjectsPerComponentCache.end()) {
- IdentifierHash<int> namedObjectCache(engine);
+ IdentifierHash namedObjectCache(engine);
const CompiledData::Object *component = data->objectAt(componentObjectIndex);
const quint32_le *namedObjectIndexPtr = component->namedObjectsInComponentTable();
for (quint32 i = 0; i < component->nNamedObjectsInComponent; ++i, ++namedObjectIndexPtr) {
@@ -354,24 +360,6 @@ bool CompilationUnit::loadFromDisk(const QUrl &url, const QDateTime &sourceTimeS
return false;
}
- {
- const QString foundArchitecture = stringAt(data->architectureIndex);
- const QString expectedArchitecture = QSysInfo::buildAbi();
- if (foundArchitecture != expectedArchitecture) {
- *errorString = QString::fromUtf8("Architecture mismatch. Found %1 expected %2").arg(foundArchitecture).arg(expectedArchitecture);
- return false;
- }
- }
-
- {
- const QString foundCodeGenerator = stringAt(data->codeGeneratorIndex);
- const QString expectedCodeGenerator = QStringLiteral("moth"); // ###
- if (foundCodeGenerator != expectedCodeGenerator) {
- *errorString = QString::fromUtf8("Code generator mismatch. Found code generated by %1 but expected %2").arg(foundCodeGenerator).arg(expectedCodeGenerator);
- return false;
- }
- }
-
dataPtrChange.commit();
free(const_cast<Unit*>(oldDataPtr));
backingFile.reset(cacheFile.take());
@@ -465,6 +453,7 @@ Unit *CompilationUnit::createUnitData(QmlIR::Document *irDocument)
if (jsUnit->sourceFileIndex == quint32(0) || jsUnit->stringAt(jsUnit->sourceFileIndex) != irDocument->jsModule.fileName) {
ensureWritableUnit();
jsUnit->sourceFileIndex = stringTable.registerString(irDocument->jsModule.fileName);
+ jsUnit->finalUrlIndex = stringTable.registerString(irDocument->jsModule.finalUrl);
}
// Collect signals that have had a change in signature (from onClicked to onClicked(mouse) for example)
@@ -687,7 +676,7 @@ bool qtTypeInherits(const QMetaObject *mo) {
void ResolvedTypeReference::doDynamicTypeCheck()
{
- const QMetaObject *mo = 0;
+ const QMetaObject *mo = nullptr;
if (typePropertyCache)
mo = typePropertyCache->firstCppMetaObject();
else if (type.isValid())
@@ -709,7 +698,7 @@ static QByteArray ownLibraryChecksum()
// the cache files may end up being re-used. To avoid that we also add the checksum of
// the QtQml library.
Dl_info libInfo;
- if (dladdr(reinterpret_cast<const void *>(&ownLibraryChecksum), &libInfo) != 0) {
+ if (dladdr(reinterpret_cast<void *>(&ownLibraryChecksum), &libInfo) != 0) {
QFile library(QFile::decodeName(libInfo.dli_fname));
if (library.open(QIODevice::ReadOnly)) {
QCryptographicHash hash(QCryptographicHash::Md5);
@@ -717,10 +706,8 @@ static QByteArray ownLibraryChecksum()
libraryChecksum = hash.result();
}
}
-#elif defined(QML_COMPILE_HASH)
- libraryChecksum = QByteArray(QT_STRINGIFY(QML_COMPILE_HASH));
#else
- // Not implemented.
+ libraryChecksum = QByteArray(QML_COMPILE_HASH);
#endif
return libraryChecksum;
}
diff --git a/src/qml/compiler/qv4compileddata_p.h b/src/qml/compiler/qv4compileddata_p.h
index eb115a590a..a1eefe3988 100644
--- a/src/qml/compiler/qv4compileddata_p.h
+++ b/src/qml/compiler/qv4compileddata_p.h
@@ -72,7 +72,7 @@
QT_BEGIN_NAMESPACE
// Bump this whenever the compiler data structures change in an incompatible way.
-#define QV4_DATA_STRUCTURE_VERSION 0x15
+#define QV4_DATA_STRUCTURE_VERSION 0x17
class QIODevice;
class QQmlPropertyCache;
@@ -691,8 +691,6 @@ struct Unit
char md5Checksum[16]; // checksum of all bytes following this field.
void generateChecksum();
- quint32_le architectureIndex; // string index to QSysInfo::buildAbi()
- quint32_le codeGeneratorIndex;
char dependencyMD5Checksum[16];
enum : unsigned int {
@@ -719,6 +717,7 @@ struct Unit
quint32_le offsetToJSClassTable;
qint32_le indexOfRootFunction;
quint32_le sourceFileIndex;
+ quint32_le finalUrlIndex;
/* QML specific fields */
quint32_le nImports;
@@ -726,6 +725,8 @@ struct Unit
quint32_le nObjects;
quint32_le offsetToObjects;
+ quint32_le padding;
+
const Import *importAt(int idx) const {
return reinterpret_cast<const Import*>((reinterpret_cast<const char *>(this)) + offsetToImports + idx * sizeof(Import));
}
@@ -890,7 +891,7 @@ Q_STATIC_ASSERT(offsetof(CompilationUnitBase, runtimeRegularExpressions) == offs
struct Q_QML_PRIVATE_EXPORT CompilationUnit final : public CompilationUnitBase
{
public:
- CompilationUnit();
+ CompilationUnit(const Unit *unitData = nullptr);
#ifdef V4_BOOTSTRAP
~CompilationUnit() {}
#else
@@ -924,13 +925,28 @@ public:
ExecutionEngine *engine = nullptr;
QQmlEnginePrivate *qmlEngine = nullptr; // only used in QML environment for composite types, not in plain QJSEngine case.
+ // url() and fileName() shall be used to load the actual QML/JS code or to show errors or
+ // warnings about that code. They include any potential URL interceptions and thus represent the
+ // "physical" location of the code.
+ //
+ // finalUrl() and finalUrlString() shall be used to resolve further URLs referred to in the code
+ // They are _not_ intercepted and thus represent the "logical" name for the code.
+
QString fileName() const { return data->stringAt(data->sourceFileIndex); }
+ QString finalUrlString() const { return data->stringAt(data->finalUrlIndex); }
QUrl url() const { if (m_url.isNull) m_url = QUrl(fileName()); return m_url; }
+ QUrl finalUrl() const
+ {
+ if (m_finalUrl.isNull)
+ m_finalUrl = QUrl(finalUrlString());
+ return m_finalUrl;
+ }
QV4::Lookup *runtimeLookups = nullptr;
QV4::InternalClass **runtimeClasses = nullptr;
QVector<QV4::Function *> runtimeFunctions;
mutable QQmlNullableValue<QUrl> m_url;
+ mutable QQmlNullableValue<QUrl> m_finalUrl;
// QML specific fields
QQmlPropertyCacheVector propertyCaches;
@@ -945,8 +961,8 @@ public:
// mapping from component object index (CompiledData::Unit object index that points to component) to identifier hash of named objects
// this is initialized on-demand by QQmlContextData
- QHash<int, IdentifierHash<int>> namedObjectsPerComponentCache;
- IdentifierHash<int> namedObjectsPerComponent(int componentObjectIndex);
+ QHash<int, IdentifierHash> namedObjectsPerComponentCache;
+ IdentifierHash namedObjectsPerComponent(int componentObjectIndex);
void finalizeCompositeType(QQmlEnginePrivate *qmlEngine);
diff --git a/src/qml/compiler/qv4compiler.cpp b/src/qml/compiler/qv4compiler.cpp
index 96c9307513..f2e1f4a0de 100644
--- a/src/qml/compiler/qv4compiler.cpp
+++ b/src/qml/compiler/qv4compiler.cpp
@@ -222,6 +222,7 @@ int QV4::Compiler::JSUnitGenerator::registerJSClass(int count, CompiledData::JSC
QV4::CompiledData::Unit *QV4::Compiler::JSUnitGenerator::generateUnit(GeneratorOption option)
{
registerString(module->fileName);
+ registerString(module->finalUrl);
for (Context *f : qAsConst(module->functions)) {
registerString(f->name);
for (int i = 0; i < f->arguments.size(); ++i)
@@ -394,8 +395,6 @@ QV4::CompiledData::Unit QV4::Compiler::JSUnitGenerator::generateHeader(QV4::Comp
unit.version = QV4_DATA_STRUCTURE_VERSION;
unit.qtVersion = QT_VERSION;
memset(unit.md5Checksum, 0, sizeof(unit.md5Checksum));
- unit.architectureIndex = registerString(module->targetABI.isEmpty() ? QSysInfo::buildAbi() : module->targetABI);
- unit.codeGeneratorIndex = registerString(codeGeneratorName);
memset(unit.dependencyMD5Checksum, 0, sizeof(unit.dependencyMD5Checksum));
quint32 nextOffset = sizeof(CompiledData::Unit);
@@ -448,6 +447,7 @@ QV4::CompiledData::Unit QV4::Compiler::JSUnitGenerator::generateHeader(QV4::Comp
}
unit.indexOfRootFunction = -1;
unit.sourceFileIndex = getStringId(module->fileName);
+ unit.finalUrlIndex = getStringId(module->finalUrl);
unit.sourceTimeStamp = module->sourceTimeStamp.isValid() ? module->sourceTimeStamp.toMSecsSinceEpoch() : 0;
unit.nImports = 0;
unit.offsetToImports = 0;
diff --git a/src/qml/compiler/qv4compilercontext_p.h b/src/qml/compiler/qv4compilercontext_p.h
index 3db30ea23d..a78a66db52 100644
--- a/src/qml/compiler/qv4compilercontext_p.h
+++ b/src/qml/compiler/qv4compilercontext_p.h
@@ -92,10 +92,10 @@ struct Module {
QList<Context *> functions;
Context *rootContext;
QString fileName;
+ QString finalUrl;
QDateTime sourceTimeStamp;
uint unitFlags = 0; // flags merged into CompiledData::Unit::flags
bool debugMode = false;
- QString targetABI; // ### seems unused currently
};
@@ -120,7 +120,7 @@ struct Context {
int index = -1;
QQmlJS::AST::VariableDeclaration::VariableScope scope = QQmlJS::AST::VariableDeclaration::FunctionScope;
mutable bool canEscape = false;
- QQmlJS::AST::FunctionExpression *function = 0;
+ QQmlJS::AST::FunctionExpression *function = nullptr;
bool isLexicallyScoped() const { return this->scope != QQmlJS::AST::VariableDeclaration::FunctionScope; }
};
@@ -128,12 +128,12 @@ struct Context {
MemberMap members;
QSet<QString> usedVariables;
- QQmlJS::AST::FormalParameterList *formals = 0;
+ QQmlJS::AST::FormalParameterList *formals = nullptr;
QStringList arguments;
QStringList locals;
QVector<Context *> nestedContexts;
- ControlFlow *controlFlow = 0;
+ ControlFlow *controlFlow = nullptr;
QByteArray code;
QVector<CompiledData::CodeOffsetToLine> lineNumberMapping;
@@ -173,10 +173,10 @@ struct Context {
// Map from meta property index (existence implies dependency) to notify signal index
struct KeyValuePair
{
- quint32 _key;
- quint32 _value;
+ quint32 _key = 0;
+ quint32 _value = 0;
- KeyValuePair(): _key(0), _value(0) {}
+ KeyValuePair() {}
KeyValuePair(quint32 key, quint32 value): _key(key), _value(value) {}
quint32 key() const { return _key; }
@@ -245,7 +245,7 @@ struct Context {
Q_ASSERT(m);
MemberMap::const_iterator it = members.find(name);
if (it == members.end()) {
- *m = 0;
+ *m = nullptr;
return false;
}
*m = &(*it);
@@ -256,7 +256,7 @@ struct Context {
usedVariables.insert(name);
}
- void addLocalVar(const QString &name, MemberType type, QQmlJS::AST::VariableDeclaration::VariableScope scope, QQmlJS::AST::FunctionExpression *function = 0)
+ void addLocalVar(const QString &name, MemberType type, QQmlJS::AST::VariableDeclaration::VariableScope scope, QQmlJS::AST::FunctionExpression *function = nullptr)
{
if (! name.isEmpty()) {
if (type != FunctionDefinition) {
diff --git a/src/qml/compiler/qv4compilercontrolflow_p.h b/src/qml/compiler/qv4compilercontrolflow_p.h
index 13716fe29f..9bda20905a 100644
--- a/src/qml/compiler/qv4compilercontrolflow_p.h
+++ b/src/qml/compiler/qv4compilercontrolflow_p.h
@@ -159,7 +159,7 @@ struct ControlFlow {
virtual Handler getHandler(HandlerType type, const QString &label = QString()) = 0;
BytecodeGenerator::ExceptionHandler *parentExceptionHandler() {
- return parent ? parent->exceptionHandler() : 0;
+ return parent ? parent->exceptionHandler() : nullptr;
}
virtual BytecodeGenerator::ExceptionHandler *exceptionHandler() {
@@ -184,7 +184,7 @@ protected:
QString label;
if (cg->_labelledStatement) {
label = cg->_labelledStatement->label.toString();
- cg->_labelledStatement = 0;
+ cg->_labelledStatement = nullptr;
}
return label;
}
@@ -196,10 +196,10 @@ protected:
struct ControlFlowLoop : public ControlFlow
{
QString loopLabel;
- BytecodeGenerator::Label *breakLabel = 0;
- BytecodeGenerator::Label *continueLabel = 0;
+ BytecodeGenerator::Label *breakLabel = nullptr;
+ BytecodeGenerator::Label *continueLabel = nullptr;
- ControlFlowLoop(Codegen *cg, BytecodeGenerator::Label *breakLabel, BytecodeGenerator::Label *continueLabel = 0)
+ ControlFlowLoop(Codegen *cg, BytecodeGenerator::Label *breakLabel, BytecodeGenerator::Label *continueLabel = nullptr)
: ControlFlow(cg, Loop), loopLabel(ControlFlow::loopLabel()), breakLabel(breakLabel), continueLabel(continueLabel)
{
}
@@ -407,7 +407,7 @@ struct ControlFlowFinally : public ControlFlowUnwind
ControlFlowFinally(Codegen *cg, AST::Finally *finally)
: ControlFlowUnwind(cg, Finally), finally(finally)
{
- Q_ASSERT(finally != 0);
+ Q_ASSERT(finally != nullptr);
generator()->setExceptionHandler(&unwindLabel);
}
diff --git a/src/qml/compiler/qv4compilerscanfunctions.cpp b/src/qml/compiler/qv4compilerscanfunctions.cpp
index 6a9b064bd8..89f602b409 100644
--- a/src/qml/compiler/qv4compilerscanfunctions.cpp
+++ b/src/qml/compiler/qv4compilerscanfunctions.cpp
@@ -59,7 +59,7 @@ using namespace QQmlJS::AST;
ScanFunctions::ScanFunctions(Codegen *cg, const QString &sourceCode, CompilationMode defaultProgramMode)
: _cg(cg)
, _sourceCode(sourceCode)
- , _context(0)
+ , _context(nullptr)
, _allowFuncDecls(true)
, defaultProgramMode(defaultProgramMode)
{
@@ -130,13 +130,15 @@ void ScanFunctions::checkName(const QStringRef &name, const SourceLocation &loc)
}
}
}
-void ScanFunctions::checkForArguments(AST::FormalParameterList *parameters)
+
+bool ScanFunctions::formalsContainName(AST::FormalParameterList *parameters, const QString &name)
{
while (parameters) {
- if (parameters->name == QLatin1String("arguments"))
- _context->usesArgumentsObject = Context::ArgumentsObjectNotUsed;
+ if (parameters->name == name)
+ return true;
parameters = parameters->next;
}
+ return false;
}
bool ScanFunctions::visit(Program *ast)
@@ -206,7 +208,7 @@ bool ScanFunctions::visit(VariableDeclaration *ast)
return false;
}
QString name = ast->name.toString();
- const Context::Member *m = 0;
+ const Context::Member *m = nullptr;
if (_context->memberInfo(name, &m)) {
if (m->isLexicallyScoped() || ast->isLexicallyScoped()) {
_cg->throwSyntaxError(ast->identifierToken, QStringLiteral("Identifier %1 has already been declared").arg(name));
@@ -256,7 +258,7 @@ void ScanFunctions::enterFunction(FunctionExpression *ast, bool enterName)
{
if (_context->isStrict && (ast->name == QLatin1String("eval") || ast->name == QLatin1String("arguments")))
_cg->throwSyntaxError(ast->identifierToken, QStringLiteral("Function name may not be eval or arguments in strict mode"));
- enterFunction(ast, ast->name.toString(), ast->formals, ast->body, enterName ? ast : 0);
+ enterFunction(ast, ast->name.toString(), ast->formals, ast->body, enterName ? ast : nullptr);
}
void ScanFunctions::endVisit(FunctionExpression *)
@@ -285,7 +287,7 @@ bool ScanFunctions::visit(ObjectLiteral *ast)
bool ScanFunctions::visit(PropertyGetterSetter *ast)
{
TemporaryBoolAssignment allowFuncDecls(_allowFuncDecls, true);
- enterFunction(ast, QString(), ast->formals, ast->functionBody, /*FunctionExpression*/0);
+ enterFunction(ast, QString(), ast->formals, ast->functionBody, /*FunctionExpression*/nullptr);
return true;
}
@@ -398,9 +400,11 @@ void ScanFunctions::enterFunction(Node *ast, const QString &name, FormalParamete
}
enterEnvironment(ast, FunctionCode);
- checkForArguments(formals);
+ if (formalsContainName(formals, QStringLiteral("arguments")))
+ _context->usesArgumentsObject = Context::ArgumentsObjectNotUsed;
+
- if (!name.isEmpty())
+ if (!name.isEmpty() && !formalsContainName(formals, name))
_context->addLocalVar(name, Context::ThisFunctionName, QQmlJS::AST::VariableDeclaration::FunctionScope);
_context->formals = formals;
diff --git a/src/qml/compiler/qv4compilerscanfunctions_p.h b/src/qml/compiler/qv4compilerscanfunctions_p.h
index 0b898e587d..745e9f8a73 100644
--- a/src/qml/compiler/qv4compilerscanfunctions_p.h
+++ b/src/qml/compiler/qv4compilerscanfunctions_p.h
@@ -88,7 +88,7 @@ public:
void leaveEnvironment();
void enterQmlScope(AST::Node *ast, const QString &name)
- { enterFunction(ast, name, /*formals*/0, /*body*/0, /*expr*/0); }
+ { enterFunction(ast, name, /*formals*/nullptr, /*body*/nullptr, /*expr*/nullptr); }
void enterQmlFunction(AST::FunctionDeclaration *ast)
{ enterFunction(ast, false); }
@@ -100,7 +100,7 @@ protected:
void checkDirectivePrologue(AST::SourceElements *ast);
void checkName(const QStringRef &name, const AST::SourceLocation &loc);
- void checkForArguments(AST::FormalParameterList *parameters);
+ bool formalsContainName(AST::FormalParameterList *parameters, const QString &name);
bool visit(AST::Program *ast) override;
void endVisit(AST::Program *) override;
diff --git a/src/qml/compiler/qv4instr_moth.cpp b/src/qml/compiler/qv4instr_moth.cpp
index fbc6902f3d..34953d52ce 100644
--- a/src/qml/compiler/qv4instr_moth.cpp
+++ b/src/qml/compiler/qv4instr_moth.cpp
@@ -369,6 +369,14 @@ void dumpBytecode(const char *code, int len, int nLocals, int nFormals, int /*st
d << index << dumpArguments(argc, argv, nFormals);
MOTH_END_INSTR(CallGlobalLookup)
+ MOTH_BEGIN_INSTR(CallScopeObjectProperty)
+ d << dumpRegister(base, nFormals) << "." << name << dumpArguments(argc, argv, nFormals);
+ MOTH_END_INSTR(CallScopeObjectProperty)
+
+ MOTH_BEGIN_INSTR(CallContextObjectProperty)
+ d << dumpRegister(base, nFormals) << "." << name << dumpArguments(argc, argv, nFormals);
+ MOTH_END_INSTR(CallContextObjectProperty)
+
MOTH_BEGIN_INSTR(SetExceptionHandler)
if (offset)
d << ABSOLUTE_OFFSET();
@@ -616,10 +624,8 @@ void dumpBytecode(const char *code, int len, int nLocals, int nFormals, int /*st
MOTH_BEGIN_INSTR(Ret)
MOTH_END_INSTR(Ret)
-#ifndef QT_NO_QML_DEBUGGER
MOTH_BEGIN_INSTR(Debug)
MOTH_END_INSTR(Debug)
-#endif // QT_NO_QML_DEBUGGER
MOTH_BEGIN_INSTR(LoadQmlContext)
d << dumpRegister(result, nFormals);
diff --git a/src/qml/compiler/qv4instr_moth_p.h b/src/qml/compiler/qv4instr_moth_p.h
index 0c1b5e240c..2d1428bd19 100644
--- a/src/qml/compiler/qv4instr_moth_p.h
+++ b/src/qml/compiler/qv4instr_moth_p.h
@@ -54,19 +54,8 @@
#include <private/qv4value_p.h>
#include <private/qv4runtime_p.h>
-#if !defined(V4_BOOTSTRAP)
-QT_REQUIRE_CONFIG(qml_interpreter);
-#endif
-
QT_BEGIN_NAMESPACE
-#if !QT_CONFIG(qml_debug)
-#define MOTH_DEBUG_INSTR(F)
-#else
-#define MOTH_DEBUG_INSTR(F) \
- F(Debug)
-#endif
-
#define INSTRUCTION(op, name, nargs, ...) \
op##_INSTRUCTION(name, nargs, __VA_ARGS__)
@@ -116,6 +105,8 @@ QT_BEGIN_NAMESPACE
#define INSTR_CallName(op) INSTRUCTION(op, CallName, 3, name, argc, argv)
#define INSTR_CallPossiblyDirectEval(op) INSTRUCTION(op, CallPossiblyDirectEval, 2, argc, argv)
#define INSTR_CallGlobalLookup(op) INSTRUCTION(op, CallGlobalLookup, 3, index, argc, argv)
+#define INSTR_CallScopeObjectProperty(op) INSTRUCTION(op, CallScopeObjectProperty, 4, name, base, argc, argv)
+#define INSTR_CallContextObjectProperty(op) INSTRUCTION(op, CallContextObjectProperty, 4, name, base, argc, argv)
#define INSTR_SetExceptionHandler(op) INSTRUCTION(op, SetExceptionHandler, 1, offset)
#define INSTR_ThrowException(op) INSTRUCTION(op, ThrowException, 0)
#define INSTR_GetException(op) INSTRUCTION(op, GetException, 0)
@@ -232,6 +223,8 @@ QT_BEGIN_NAMESPACE
F(CallName) \
F(CallPossiblyDirectEval) \
F(CallGlobalLookup) \
+ F(CallScopeObjectProperty) \
+ F(CallContextObjectProperty) \
F(SetExceptionHandler) \
F(ThrowException) \
F(GetException) \
@@ -301,7 +294,10 @@ QT_BEGIN_NAMESPACE
F(LoadQmlSingleton)
#define MOTH_NUM_INSTRUCTIONS() (static_cast<int>(Moth::Instr::Type::LoadQmlSingleton) + 1)
-#if defined(Q_CC_GNU) && (!defined(Q_CC_INTEL) || __INTEL_COMPILER >= 1200)
+#if defined(Q_CC_GNU) && !defined(Q_CC_INTEL)
+// icc before version 1200 doesn't support computed goto, and at least up to version 18.0.0 the
+// current use results in an internal compiler error. We could enable this if/when it gets fixed
+// in a later version.
# define MOTH_COMPUTED_GOTO
#endif
@@ -353,7 +349,7 @@ QT_BEGIN_NAMESPACE
nargs,
#define MOTH_DECODE_ARG(arg, type, nargs, offset) \
- arg = reinterpret_cast<const type *>(code)[-nargs + offset];
+ arg = qFromLittleEndian<type>(reinterpret_cast<const type *>(code)[-nargs + offset]);
#define MOTH_ADJUST_CODE(type, nargs) \
code += static_cast<quintptr>(nargs*sizeof(type) + 1)
@@ -363,9 +359,9 @@ QT_BEGIN_NAMESPACE
MOTH_ADJUST_CODE(int, nargs); \
MOTH_DECODE_ARGS(name, int, nargs, __VA_ARGS__) \
goto op_main_##name; \
- op_char_##name: \
- MOTH_ADJUST_CODE(char, nargs); \
- MOTH_DECODE_ARGS(name, char, nargs, __VA_ARGS__) \
+ op_byte_##name: \
+ MOTH_ADJUST_CODE(qint8, nargs); \
+ MOTH_DECODE_ARGS(name, qint8, nargs, __VA_ARGS__) \
op_main_##name: \
; \
@@ -377,10 +373,10 @@ QT_BEGIN_NAMESPACE
MOTH_ADJUST_CODE(int, nargs); \
MOTH_DECODE_ARGS(name, int, nargs, __VA_ARGS__) \
goto op_main_##name; \
- op_char_##name: \
+ op_byte_##name: \
base_ptr = code; \
- MOTH_ADJUST_CODE(char, nargs); \
- MOTH_DECODE_ARGS(name, char, nargs, __VA_ARGS__) \
+ MOTH_ADJUST_CODE(qint8, nargs); \
+ MOTH_DECODE_ARGS(name, qint8, nargs, __VA_ARGS__) \
op_main_##name: \
; \
@@ -405,7 +401,7 @@ QT_BEGIN_NAMESPACE
#define COLLECT_LABELS(instr) \
INSTR_##instr(GET_LABEL)
#define GET_LABEL_INSTRUCTION(name, ...) \
- &&op_char_##name,
+ &&op_byte_##name,
#define COLLECT_LABELS_WIDE(instr) \
INSTR_##instr(GET_LABEL_WIDE)
#define GET_LABEL_WIDE_INSTRUCTION(name, ...) \
@@ -425,7 +421,7 @@ QT_BEGIN_NAMESPACE
#define MOTH_INSTR_CASE_AND_JUMP(instr) \
INSTR_##instr(GET_CASE_AND_JUMP)
#define GET_CASE_AND_JUMP_INSTRUCTION(name, ...) \
- case static_cast<uchar>(Instr::Type::name): goto op_char_##name;
+ case static_cast<uchar>(Instr::Type::name): goto op_byte_##name;
#define MOTH_INSTR_CASE_AND_JUMP_WIDE(instr) \
INSTR_##instr(GET_CASE_AND_JUMP_WIDE)
#define GET_CASE_AND_JUMP_WIDE_INSTRUCTION(name, ...) \
@@ -483,6 +479,8 @@ union Instr
FOR_EACH_MOTH_INSTR(MOTH_EMIT_STRUCTS)
FOR_EACH_MOTH_INSTR(MOTH_EMIT_INSTR_MEMBERS)
+
+ int argumentsAsInts[4];
};
struct InstrInfo
diff --git a/src/qml/configure.json b/src/qml/configure.json
index a589e9f950..b744ea6948 100644
--- a/src/qml/configure.json
+++ b/src/qml/configure.json
@@ -7,23 +7,17 @@
"commandline": {
"options": {
- "qml-interpreter": "boolean",
"qml-network": "boolean",
"qml-debug": "boolean"
}
},
"features": {
- "qml-interpreter": {
- "label": "QML interpreter",
- "purpose": "Provides the QML interpreter.",
- "section": "QML",
- "output": [ "privateFeature" ]
- },
"qml-network": {
"label": "QML network support",
"purpose": "Provides network transparency.",
"section": "QML",
+ "condition": "features.network",
"output": [ "publicFeature" ]
},
"qml-debug": {
@@ -52,7 +46,6 @@
{
"section": "Qt QML",
"entries": [
- "qml-interpreter",
"qml-network",
"qml-debug"
]
diff --git a/src/qml/debugger/qqmlabstractprofileradapter_p.h b/src/qml/debugger/qqmlabstractprofileradapter_p.h
index 5d1b339324..c63e694c7e 100644
--- a/src/qml/debugger/qqmlabstractprofileradapter_p.h
+++ b/src/qml/debugger/qqmlabstractprofileradapter_p.h
@@ -68,9 +68,9 @@ class Q_QML_PRIVATE_EXPORT QQmlAbstractProfilerAdapter : public QObject, public
public:
static const int s_numMessagesPerBatch = 1000;
- QQmlAbstractProfilerAdapter(QObject *parent = 0) :
- QObject(parent), service(0), waiting(true), featuresEnabled(0) {}
- virtual ~QQmlAbstractProfilerAdapter() {}
+ QQmlAbstractProfilerAdapter(QObject *parent = nullptr) :
+ QObject(parent), service(nullptr), waiting(true), featuresEnabled(0) {}
+ ~QQmlAbstractProfilerAdapter() override {}
void setService(QQmlProfilerService *new_service) { service = new_service; }
virtual qint64 sendMessages(qint64 until, QList<QByteArray> &messages, bool trackLocations) = 0;
diff --git a/src/qml/debugger/qqmlconfigurabledebugservice_p.h b/src/qml/debugger/qqmlconfigurabledebugservice_p.h
index e09d5f779a..96ec46f475 100644
--- a/src/qml/debugger/qqmlconfigurabledebugservice_p.h
+++ b/src/qml/debugger/qqmlconfigurabledebugservice_p.h
@@ -63,7 +63,7 @@ template <class Base>
class QQmlConfigurableDebugService : public Base
{
protected:
- QQmlConfigurableDebugService(float version, QObject *parent = 0) :
+ QQmlConfigurableDebugService(float version, QObject *parent = nullptr) :
Base(version, parent), m_configMutex(QMutex::Recursive)
{
init();
diff --git a/src/qml/debugger/qqmldebugconnector.cpp b/src/qml/debugger/qqmldebugconnector.cpp
index 01f74f08be..d9f51ce09f 100644
--- a/src/qml/debugger/qqmldebugconnector.cpp
+++ b/src/qml/debugger/qqmldebugconnector.cpp
@@ -66,7 +66,7 @@ struct QQmlDebugConnectorParams {
QString arguments;
QQmlDebugConnector *instance;
- QQmlDebugConnectorParams() : instance(0)
+ QQmlDebugConnectorParams() : instance(nullptr)
{
if (qApp) {
QCoreApplicationPrivate *appD =
@@ -109,7 +109,7 @@ QQmlDebugConnector *QQmlDebugConnector::instance()
{
QQmlDebugConnectorParams *params = qmlDebugConnectorParams();
if (!params)
- return 0;
+ return nullptr;
if (!QQmlEnginePrivate::qml_debugging_enabled) {
if (!params->arguments.isEmpty()) {
@@ -118,14 +118,14 @@ QQmlDebugConnector *QQmlDebugConnector::instance()
"has not been enabled.").arg(params->arguments);
params->arguments.clear();
}
- return 0;
+ return nullptr;
}
if (!params->instance) {
if (!params->pluginKey.isEmpty()) {
params->instance = loadQQmlDebugConnector(params->pluginKey);
} else if (params->arguments.isEmpty()) {
- return 0; // no explicit class name given and no command line arguments
+ return nullptr; // no explicit class name given and no command line arguments
} else if (params->arguments.startsWith(QLatin1String("connector:"))) {
static const int connectorBegin = int(strlen("connector:"));
@@ -169,7 +169,7 @@ QQmlDebugConnectorFactory::~QQmlDebugConnectorFactory()
params->arguments.clear();
params->services.clear();
delete params->instance;
- params->instance = 0;
+ params->instance = nullptr;
}
}
diff --git a/src/qml/debugger/qqmldebugconnector_p.h b/src/qml/debugger/qqmldebugconnector_p.h
index a2a6f5047d..d1ad90adfd 100644
--- a/src/qml/debugger/qqmldebugconnector_p.h
+++ b/src/qml/debugger/qqmldebugconnector_p.h
@@ -114,7 +114,7 @@ public:
static Service *service()
{
QQmlDebugConnector *inst = instance();
- return inst ? static_cast<Service *>(inst->service(Service::s_key)) : 0;
+ return inst ? static_cast<Service *>(inst->service(Service::s_key)) : nullptr;
}
protected:
@@ -126,7 +126,7 @@ class Q_QML_PRIVATE_EXPORT QQmlDebugConnectorFactory : public QObject {
Q_OBJECT
public:
virtual QQmlDebugConnector *create(const QString &key) = 0;
- ~QQmlDebugConnectorFactory();
+ ~QQmlDebugConnectorFactory() override;
};
#define QQmlDebugConnectorFactory_iid "org.qt-project.Qt.QQmlDebugConnectorFactory"
diff --git a/src/qml/debugger/qqmldebugserverconnection_p.h b/src/qml/debugger/qqmldebugserverconnection_p.h
index 536ad830b4..9c4af4d225 100644
--- a/src/qml/debugger/qqmldebugserverconnection_p.h
+++ b/src/qml/debugger/qqmldebugserverconnection_p.h
@@ -61,7 +61,7 @@ class Q_QML_PRIVATE_EXPORT QQmlDebugServerConnection : public QObject
{
Q_OBJECT
public:
- QQmlDebugServerConnection(QObject *parent = 0) : QObject(parent) {}
+ QQmlDebugServerConnection(QObject *parent = nullptr) : QObject(parent) {}
virtual void setServer(QQmlDebugServer *server) = 0;
virtual bool setPortRange(int portFrom, int portTo, bool block, const QString &hostaddress) = 0;
diff --git a/src/qml/debugger/qqmldebugservice_p.h b/src/qml/debugger/qqmldebugservice_p.h
index 34bbd631ec..c52ba90a79 100644
--- a/src/qml/debugger/qqmldebugservice_p.h
+++ b/src/qml/debugger/qqmldebugservice_p.h
@@ -69,7 +69,7 @@ class Q_QML_PRIVATE_EXPORT QQmlDebugService : public QObject
Q_DECLARE_PRIVATE(QQmlDebugService)
public:
- ~QQmlDebugService();
+ ~QQmlDebugService() override;
const QString &name() const;
float version() const;
@@ -93,7 +93,7 @@ public:
static QObject *objectForId(int id) { return objectsForIds().value(id); }
protected:
- explicit QQmlDebugService(const QString &, float version, QObject *parent = 0);
+ explicit QQmlDebugService(const QString &, float version, QObject *parent = nullptr);
signals:
void attachedToEngine(QJSEngine *);
diff --git a/src/qml/debugger/qqmlprofiler_p.h b/src/qml/debugger/qqmlprofiler_p.h
index f17b1a7528..deb4d107d6 100644
--- a/src/qml/debugger/qqmlprofiler_p.h
+++ b/src/qml/debugger/qqmlprofiler_p.h
@@ -163,9 +163,8 @@ public:
// be available anymore when we send the data.
struct RefLocation : public Location {
RefLocation()
- : Location(), locationType(MaximumRangeType), sent(false)
+ : Location(), locationType(MaximumRangeType), something(nullptr), sent(false)
{
- function = nullptr;
}
RefLocation(QV4::Function *ref)
@@ -226,6 +225,9 @@ public:
void addref()
{
+ if (isNull())
+ return;
+
switch (locationType) {
case Binding:
function->compilationUnit->addref();
@@ -247,6 +249,9 @@ public:
void release()
{
+ if (isNull())
+ return;
+
switch (locationType) {
case Binding:
function->compilationUnit->release();
@@ -271,12 +276,18 @@ public:
return locationType != MaximumRangeType;
}
+ bool isNull() const
+ {
+ return !something;
+ }
+
RangeType locationType;
union {
QV4::Function *function;
QV4::CompiledData::CompilationUnit *unit;
QQmlBoundSignalExpression *boundSignal;
QQmlDataBlob *blob;
+ void *something;
};
bool sent;
};
@@ -287,17 +298,23 @@ public:
{
// Use the QV4::Function as ID, as that is common among different instances of the same
// component. QQmlBinding is per instance.
- // Add 1 to the ID, to make it different from the IDs the V4 profiler produces. The +1 makes
- // the pointer point into the middle of the QV4::Function. Thus it still points to valid
- // memory but we cannot accidentally create a duplicate key from another object.
- quintptr locationId(id(function) + 1);
+ // Add 1 to the ID, to make it different from the IDs the V4 and signal handling profilers
+ // produce. The +1 makes the pointer point into the middle of the QV4::Function. Thus it
+ // still points to valid memory but we cannot accidentally create a duplicate key from
+ // another object.
+ // If there is no function, use a static but valid address: The profiler itself.
+ quintptr locationId = function ? id(function) + 1 : id(this);
m_data.append(QQmlProfilerData(m_timer.nsecsElapsed(),
(1 << RangeStart | 1 << RangeLocation), Binding,
locationId));
RefLocation &location = m_locations[locationId];
- if (!location.isValid())
- location = RefLocation(function);
+ if (!location.isValid()) {
+ if (function)
+ location = RefLocation(function);
+ else // Make it valid without actually providing a location
+ location.locationType = Binding;
+ }
}
// Have toByteArrays() construct another RangeData event from the same QString later.
@@ -316,7 +333,12 @@ public:
void startHandlingSignal(QQmlBoundSignalExpression *expression)
{
- quintptr locationId(id(expression));
+ // Use the QV4::Function as ID, as that is common among different instances of the same
+ // component. QQmlBoundSignalExpression is per instance.
+ // Add 2 to the ID, to make it different from the IDs the V4 and binding profilers produce.
+ // The +2 makes the pointer point into the middle of the QV4::Function. Thus it still points
+ // to valid memory but we cannot accidentally create a duplicate key from another object.
+ quintptr locationId(id(expression->function()) + 2);
m_data.append(QQmlProfilerData(m_timer.nsecsElapsed(),
(1 << RangeStart | 1 << RangeLocation), HandlingSignal,
locationId));
@@ -428,7 +450,7 @@ struct QQmlCompilingProfiler : public QQmlProfilerHelper {
struct QQmlVmeProfiler : public QQmlProfilerDefinitions {
public:
- QQmlVmeProfiler() : profiler(0) {}
+ QQmlVmeProfiler() : profiler(nullptr) {}
void init(QQmlProfiler *p, int maxDepth)
{
@@ -499,7 +521,12 @@ private:
QQmlProfiler *profiler;
};
+#endif // QT_CONFIG(qml_debug)
+
QT_END_NAMESPACE
+
+#if QT_CONFIG(qml_debug)
+
Q_DECLARE_METATYPE(QVector<QQmlProfilerData>)
Q_DECLARE_METATYPE(QQmlProfiler::LocationHash)
diff --git a/src/qml/debugger/qqmlprofilerdefinitions_p.h b/src/qml/debugger/qqmlprofilerdefinitions_p.h
index 91d0376837..f84a2c44e2 100644
--- a/src/qml/debugger/qqmlprofilerdefinitions_p.h
+++ b/src/qml/debugger/qqmlprofilerdefinitions_p.h
@@ -69,6 +69,7 @@ struct QQmlProfilerDefinitions {
PixmapCacheEvent,
SceneGraphFrame,
MemoryAllocation,
+ DebugMessage,
MaximumMessage
};
@@ -161,6 +162,26 @@ struct QQmlProfilerDefinitions {
MaximumInputEventType
};
+
+ static ProfileFeature featureFromRangeType(RangeType range)
+ {
+ switch (range) {
+ case Painting:
+ return ProfilePainting;
+ case Compiling:
+ return ProfileCompiling;
+ case Creating:
+ return ProfileCreating;
+ case Binding:
+ return ProfileBinding;
+ case HandlingSignal:
+ return ProfileHandlingSignal;
+ case Javascript:
+ return ProfileJavaScript;
+ default:
+ return MaximumProfileFeature;
+ }
+ }
};
QT_END_NAMESPACE
diff --git a/src/qml/doc/qtqml.qdocconf b/src/qml/doc/qtqml.qdocconf
index 74b61fd6e1..6161760471 100644
--- a/src/qml/doc/qtqml.qdocconf
+++ b/src/qml/doc/qtqml.qdocconf
@@ -53,6 +53,8 @@ manifestmeta.thumbnail.names += "QtQml/Chapter 4*" \
"QtQml/Chapter 6*" \
"QtQml/C++ Extensions: *"
+manifestmeta.highlighted.names = "QtQml/Writing QML Extensions with C++"
+
navigation.landingpage = "Qt QML"
navigation.cppclassespage = "Qt QML C++ Classes"
navigation.qmltypespage = "Qt QML QML Types"
diff --git a/src/qml/doc/snippets/code/src_script_qjsengine.cpp b/src/qml/doc/snippets/code/src_script_qjsengine.cpp
index 3799189f83..6c58fd8a18 100644
--- a/src/qml/doc/snippets/code/src_script_qjsengine.cpp
+++ b/src/qml/doc/snippets/code/src_script_qjsengine.cpp
@@ -114,3 +114,23 @@ engine.globalObject().setProperty("myObject", myScriptQObject);
qDebug() << engine.evaluate("myObject.dynamicProperty").toInt();
//! [6]
+
+
+//! [7]
+class MyObject : public QObject
+{
+ Q_OBJECT
+
+public:
+ Q_INVOKABLE MyObject() {}
+};
+//! [7]
+
+//! [8]
+QJSValue jsMetaObject = engine.newQMetaObject(&MyObject::staticMetaObject);
+engine.globalObject().setProperty("MyObject", jsMetaObject);
+//! [8]
+
+//! [9]
+engine.evaluate("var myObject = new MyObject()");
+//! [9]
diff --git a/src/qml/doc/src/cppintegration/definetypes.qdoc b/src/qml/doc/src/cppintegration/definetypes.qdoc
index afc76ce31d..027e4b9923 100644
--- a/src/qml/doc/src/cppintegration/definetypes.qdoc
+++ b/src/qml/doc/src/cppintegration/definetypes.qdoc
@@ -620,7 +620,7 @@ signals:
private slots:
void updateProperty() {
- m_targetProperty.write(QRandomGenerator::bounded(m_maxValue));
+ m_targetProperty.write(QRandomGenerator::global()->bounded(m_maxValue));
}
private:
diff --git a/src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc b/src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc
index 4dc32e3588..7c2ff703c6 100644
--- a/src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc
+++ b/src/qml/doc/src/cppintegration/interactqmlfromcpp.qdoc
@@ -114,17 +114,7 @@ multiple children with the same \c objectName. In this case,
QObject::findChildren() can be used to find all children with a matching
\c objectName.
-\warning While it is possible to use C++ to access and manipulate QML objects
-deep into the object tree, we recommend that you do not take this approach
-outside of application testing and prototyping. One strength of QML and C++
-integration is the ability to implement the QML user interface separately
-from the C++ logic and dataset backend, and this strategy breaks if the C++
-side reaches deep into the QML components to manipulate them directly. This
-would make it difficult to, for example, swap a QML view component for
-another view, if the new component was missing a required \c objectName. It
-is better for the C++ implementation to know as little as possible about the
-QML user interface implementation and the composition of the QML object tree.
-
+\include warning.qdocinc
\section1 Accessing Members of a QML Object Type from C++
diff --git a/src/qml/doc/src/cppintegration/topic.qdoc b/src/qml/doc/src/cppintegration/topic.qdoc
index da06c195dc..6b6e308edf 100644
--- a/src/qml/doc/src/cppintegration/topic.qdoc
+++ b/src/qml/doc/src/cppintegration/topic.qdoc
@@ -190,6 +190,8 @@ invoke their methods and receive their signal notifications. This is possible du
all QML object types are implemented using QObject-derived classes, enabling the QML engine to
dynamically load and introspect objects through the Qt meta object system.
+\include warning.qdocinc
+
For more information on accessing QML objects from C++, see the documentation on
\l{qtqml-cppintegration-interactqmlfromcpp.html}{Interacting with QML Objects from C++}.
diff --git a/src/qml/doc/src/cppintegration/warning.qdocinc b/src/qml/doc/src/cppintegration/warning.qdocinc
new file mode 100644
index 0000000000..a5da22b2a7
--- /dev/null
+++ b/src/qml/doc/src/cppintegration/warning.qdocinc
@@ -0,0 +1,6 @@
+\warning Although it is possible to access QML objects from C++ and manipulate
+them, it is not the recommended approach, except for testing and prototyping
+purposes. One of the strengths of QML and C++ integration is the ability to
+implement UIs in QML separate from the C++ logic and dataset backend, and this
+fails if the C++ side starts manipulating QML directly. Such an approach also
+makes changing the QML UI difficult without affecting its C++ counterpart.
diff --git a/src/qml/doc/src/includes/qqmlcomponent.qdoc b/src/qml/doc/src/includes/qqmlcomponent.qdoc
new file mode 100644
index 0000000000..6949d8823a
--- /dev/null
+++ b/src/qml/doc/src/includes/qqmlcomponent.qdoc
@@ -0,0 +1,58 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the documentation of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of The Qt Company Ltd nor the names of its
+** contributors may be used to endorse or promote products derived
+** from this software without specific prior written permission.
+**
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [url-note]
+Ensure that the URL provided is full and correct, in particular, use
+\l QUrl::fromLocalFile() when loading a file from the local filesystem.
+
+Relative paths will be resolved against
+\l {QQmlEngine::baseUrl}{QQmlEngine::baseUrl()}, which is the current working directory
+unless specified.
+//! [url-note]
diff --git a/src/qml/doc/src/javascript/dynamicobjectcreation.qdoc b/src/qml/doc/src/javascript/dynamicobjectcreation.qdoc
index 0471d7db9b..be4db4c917 100644
--- a/src/qml/doc/src/javascript/dynamicobjectcreation.qdoc
+++ b/src/qml/doc/src/javascript/dynamicobjectcreation.qdoc
@@ -157,7 +157,7 @@ to inside the string literals.
When managing dynamically created objects, you must ensure the creation context
outlives the created object. Otherwise, if the creation context is destroyed
-first, the bindings in the dynamic object will no longer work.
+first, the bindings and signal handlers in the dynamic object will no longer work.
The actual creation context depends on how an object is created:
diff --git a/src/qml/doc/src/qmlfunctions.qdoc b/src/qml/doc/src/qmlfunctions.qdoc
index 8a62a18eec..ede213b84a 100644
--- a/src/qml/doc/src/qmlfunctions.qdoc
+++ b/src/qml/doc/src/qmlfunctions.qdoc
@@ -324,6 +324,19 @@
qmlRegisterSingletonType("Qt.example.qjsvalueApi", 1, 0, "MyApi", example_qjsvalue_singletontype_provider);
\endcode
+ Alternatively, you can use a C++11 lambda:
+
+ \code
+ qmlRegisterSingletonType("Qt.example.qjsvalueApi", 1, 0, "MyApi", [](QQmlEngine *engine, QJSEngine *scriptEngine) -> QJSValue {
+ Q_UNUSED(engine)
+
+ static int seedValue = 5;
+ QJSValue example = scriptEngine->newObject();
+ example.setProperty("someProperty", seedValue++);
+ return example;
+ });
+ \endcode
+
In order to use the registered singleton type in QML, you must import the singleton type.
\qml
import QtQuick 2.0
@@ -336,7 +349,7 @@
*/
/*!
- \fn Object *qmlAttachedPropertiesObject(const QObject *attachee, bool create = true)
+ \fn template<typename T> QObject *qmlAttachedPropertiesObject(const QObject *attachee, bool create = true)
\relates QQmlEngine
The form of this template function is:
@@ -423,6 +436,18 @@
qmlRegisterSingletonType<SingletonTypeExample>("Qt.example.qobjectSingleton", 1, 0, "MyApi", example_qobject_singletontype_provider);
\endcode
+ Alternatively, you can use a C++11 lambda:
+
+ \code
+ qmlRegisterSingletonType<SingletonTypeExample>("Qt.example.qjsvalueApi", 1, 0, "MyApi", [](QQmlEngine *engine, QJSEngine *scriptEngine) -> QObject * {
+ Q_UNUSED(engine)
+ Q_UNUSED(scriptEngine)
+
+ SingletonTypeExample *example = new SingletonTypeExample();
+ return example;
+ });
+ \endcode
+
In order to use the registered singleton type in QML, you must import the singleton type.
\qml
import QtQuick 2.0
diff --git a/src/qml/doc/src/qmllanguageref/syntax/basics.qdoc b/src/qml/doc/src/qmllanguageref/syntax/basics.qdoc
index 1b645a94c0..9eb8f72cf2 100644
--- a/src/qml/doc/src/qmllanguageref/syntax/basics.qdoc
+++ b/src/qml/doc/src/qmllanguageref/syntax/basics.qdoc
@@ -38,6 +38,8 @@ imperative code, in the case where complex custom application behavior is needed
QML source code is generally loaded by the engine through QML \e documents, which are
standalone documents of QML code. These can be used to define \l {QML Object Types}{QML object types} that can then be reused throughout an application.
+Note that type names must begin with an uppercase letter in order
+to be declared as QML object types in a QML file.
\section1 Import Statements
diff --git a/src/qml/doc/src/qmllanguageref/syntax/objectattributes.qdoc b/src/qml/doc/src/qmllanguageref/syntax/objectattributes.qdoc
index 207fb53ca0..31650db7c0 100644
--- a/src/qml/doc/src/qmllanguageref/syntax/objectattributes.qdoc
+++ b/src/qml/doc/src/qmllanguageref/syntax/objectattributes.qdoc
@@ -449,13 +449,38 @@ right-hand-side of the property declaration must be a valid alias reference:
[default] property alias <name>: <alias reference>
\endcode
-Unlike an ordinary property, an alias can only refer to an object, or the
-property of an object, that is within the scope of the \l{QML Object Types}
-{type} within which the alias is declared. It cannot contain arbitrary
-JavaScript expressions and it cannot refer to objects declared outside of
-the scope of its type. Also note the \e {alias reference} is not optional,
-unlike the optional default value for an ordinary property; the alias reference
-must be provided when the alias is first declared.
+Unlike an ordinary property, an alias has the following restrictions:
+
+\list
+\li It can only refer to an object, or the
+ property of an object, that is within the scope of the \l{QML Object Types}
+ {type} within which the alias is declared.
+\li It cannot contain arbitrary
+ JavaScript expressions
+\li It cannot refer to objects declared outside of
+ the scope of its type.
+\li The \e {alias reference} is not optional,
+ unlike the optional default value for an ordinary property; the alias reference
+ must be provided when the alias is first declared.
+\li It cannot refer to grouped properties; the following code will not work:
+ \code
+ property alias color: rectangle.border.color
+
+ Rectangle {
+ id: rectangle
+ }
+ \endcode
+
+ However, aliases to \l {QML Basic Types}{value type} properties do work:
+ \code
+ property alias rectX: object.rectProperty.x
+
+ Item {
+ id: object
+ property rect rectProperty
+ }
+ \endcode
+\endlist
For example, below is a \c Button type with a \c buttonText aliased property
which is connected to the \c text object of the \l Text child:
diff --git a/src/qml/doc/src/qmllanguageref/typesystem/objecttypes.qdoc b/src/qml/doc/src/qmllanguageref/typesystem/objecttypes.qdoc
index b74646b7d0..5f089b5ebc 100644
--- a/src/qml/doc/src/qmllanguageref/typesystem/objecttypes.qdoc
+++ b/src/qml/doc/src/qmllanguageref/typesystem/objecttypes.qdoc
@@ -45,6 +45,8 @@ type, as discussed in \l {qtqml-documents-definetypes.html}
{Documents as QML object type definitions}, or by defining a QML type from C++
and registering the type with the QML engine, as discussed in
\l{qtqml-cppintegration-definetypes.html}{Defining QML Types from C++}.
+Note that in both cases, the type name must begin with an uppercase letter in
+order to be declared as a QML object type in a QML file.
\section1 Defining Object Types from QML
diff --git a/src/qml/doc/src/qtqml.qdoc b/src/qml/doc/src/qtqml.qdoc
index 833436a67c..a9f8e2a960 100644
--- a/src/qml/doc/src/qtqml.qdoc
+++ b/src/qml/doc/src/qtqml.qdoc
@@ -134,12 +134,13 @@ the QML code to interact with C++ code.
\section1 Licenses and Attributions
Qt QML is available under commercial licenses from \l{The Qt Company}.
-In addition, it is available under the
+In addition, it is available under free software licenses. Since Qt 5.4,
+these free software licenses are
\l{GNU Lesser General Public License, version 3}, or
the \l{GNU General Public License, version 2}.
See \l{Qt Licensing} for further details.
-Furthermore Qt QML potentially contains third party
+Furthermore Qt QML in Qt \QtVersion may contain third party
modules under following permissive licenses:
\generatelist{groupsbymodule attributions-qtqml}
diff --git a/src/qml/jit/qv4assembler.cpp b/src/qml/jit/qv4assembler.cpp
index b0470ed89d..186e5952da 100644
--- a/src/qml/jit/qv4assembler.cpp
+++ b/src/qml/jit/qv4assembler.cpp
@@ -52,15 +52,6 @@
#undef ENABLE_ALL_ASSEMBLERS_FOR_REFACTORING_PURPOSES
-#ifdef Q_STATIC_ASSERT_FOR_SANE_COMPILERS
-# undef Q_STATIC_ASSERT_FOR_SANE_COMPILERS
-#endif
-#if defined(Q_CC_MSVC) && _MSC_VER < 1900
-# define Q_STATIC_ASSERT_FOR_SANE_COMPILERS(x) // insane
-#else
-# define Q_STATIC_ASSERT_FOR_SANE_COMPILERS(x) Q_STATIC_ASSERT(x)
-#endif
-
#ifdef V4_ENABLE_JIT
QT_BEGIN_NAMESPACE
@@ -70,6 +61,7 @@ namespace JIT {
#define callHelper(x) PlatformAssemblerCommon::callRuntime(#x, reinterpret_cast<void *>(&x))
const QV4::Value::ValueTypeInternal IntegerTag = QV4::Value::ValueTypeInternal::Integer;
+const int IsIntegerConvertible_Shift = QV4::Value::IsIntegerConvertible_Shift;
static ReturnedValue toNumberHelper(ReturnedValue v)
{
@@ -89,6 +81,7 @@ struct PlatformAssembler_X86_64_SysV : JSC::MacroAssembler<JSC::MacroAssemblerX8
static const RegisterID NoRegister = RegisterID(-1);
static const RegisterID ReturnValueRegister = RegisterID::eax;
+ static const RegisterID ReturnValueRegisterValue = ReturnValueRegister;
static const RegisterID AccumulatorRegister = RegisterID::eax;
static const RegisterID AccumulatorRegisterValue = AccumulatorRegister;
static const RegisterID ScratchRegister = RegisterID::r10;
@@ -125,7 +118,6 @@ struct PlatformAssembler_X86_64_SysV : JSC::MacroAssembler<JSC::MacroAssemblerX8
push(EngineRegister);
move(Arg0Reg, CppStackFrameRegister);
move(Arg1Reg, EngineRegister);
- loadPtr(Address(CppStackFrameRegister, offsetof(CppStackFrame, jsFrame)), JSStackFrameRegister);
}
void generatePlatformFunctionExit()
@@ -167,6 +159,7 @@ struct PlatformAssembler_Win64 : JSC::MacroAssembler<JSC::MacroAssemblerX86_64>
static const RegisterID NoRegister = RegisterID(-1);
static const RegisterID ReturnValueRegister = RegisterID::eax;
+ static const RegisterID ReturnValueRegisterValue = ReturnValueRegister;
static const RegisterID AccumulatorRegister = RegisterID::eax;
static const RegisterID AccumulatorRegisterValue = AccumulatorRegister;
static const RegisterID ScratchRegister = RegisterID::r10;
@@ -203,7 +196,6 @@ struct PlatformAssembler_Win64 : JSC::MacroAssembler<JSC::MacroAssemblerX86_64>
push(EngineRegister);
move(Arg0Reg, CppStackFrameRegister);
move(Arg1Reg, EngineRegister);
- loadPtr(Address(CppStackFrameRegister, offsetof(CppStackFrame, jsFrame)), JSStackFrameRegister);
}
void generatePlatformFunctionExit()
@@ -285,7 +277,6 @@ struct PlatformAssembler_X86_All : JSC::MacroAssembler<JSC::MacroAssemblerX86>
push(EngineRegister);
loadPtr(Address(FramePointerRegister, 2 * PointerSize), CppStackFrameRegister);
loadPtr(Address(FramePointerRegister, 3 * PointerSize), EngineRegister);
- loadPtr(Address(CppStackFrameRegister, offsetof(CppStackFrame, jsFrame)), JSStackFrameRegister);
}
void generatePlatformFunctionExit()
@@ -328,6 +319,7 @@ struct PlatformAssembler_ARM64 : JSC::MacroAssembler<JSC::MacroAssemblerARM64>
static const RegisterID NoRegister = RegisterID(-1);
static const RegisterID ReturnValueRegister = JSC::ARM64Registers::x0;
+ static const RegisterID ReturnValueRegisterValue = ReturnValueRegister;
static const RegisterID AccumulatorRegister = JSC::ARM64Registers::x9;
static const RegisterID AccumulatorRegisterValue = AccumulatorRegister;
static const RegisterID ScratchRegister = JSC::ARM64Registers::x10;
@@ -639,7 +631,12 @@ struct PlatformAssembler64 : PlatformAssemblerCommon
{
PlatformAssemblerCommon::callRuntime(functionName, funcPtr);
if (dest == Assembler::ResultInAccumulator)
- move(ReturnValueRegister, AccumulatorRegister);
+ saveReturnValueInAccumulator();
+ }
+
+ void saveReturnValueInAccumulator()
+ {
+ move(ReturnValueRegister, AccumulatorRegister);
}
void loadUndefined(RegisterID dest = AccumulatorRegister)
@@ -689,6 +686,11 @@ struct PlatformAssembler64 : PlatformAssemblerCommon
move(TrustedImm64(value), AccumulatorRegister);
}
+ void storeHeapObject(RegisterID source, Address addr)
+ {
+ store64(source, addr);
+ }
+
void generateCatchTrampoline()
{
PlatformAssemblerCommon::generateCatchTrampoline([this](){loadUndefined();});
@@ -715,25 +717,66 @@ struct PlatformAssembler64 : PlatformAssemblerCommon
void toNumber()
{
+ urshift64(AccumulatorRegister, TrustedImm32(Value::QuickType_Shift), ScratchRegister);
+ auto isNumber = branch32(GreaterThanOrEqual, ScratchRegister, TrustedImm32(Value::QT_Int));
+
move(AccumulatorRegister, registerForArg(0));
callHelper(toNumberHelper);
- move(ReturnValueRegister, AccumulatorRegister);
+ saveReturnValueInAccumulator();
+
+ isNumber.link(this);
+ }
+
+ void toInt32LhsAcc(Address lhs, RegisterID lhsTarget)
+ {
+ load64(lhs, lhsTarget);
+ urshift64(lhsTarget, TrustedImm32(Value::QuickType_Shift), ScratchRegister2);
+ auto lhsIsInt = branch32(Equal, TrustedImm32(Value::QT_Int), ScratchRegister2);
+
+ pushAligned(AccumulatorRegister);
+ move(lhsTarget, registerForArg(0));
+ callHelper(toInt32Helper);
+ move(ReturnValueRegister, lhsTarget);
+ popAligned(AccumulatorRegister);
+
+ lhsIsInt.link(this);
+ urshift64(AccumulatorRegister, TrustedImm32(Value::QuickType_Shift), ScratchRegister2);
+ auto isInt = branch32(Equal, TrustedImm32(Value::QT_Int), ScratchRegister2);
+
+ pushAligned(lhsTarget);
+ move(AccumulatorRegister, registerForArg(0));
+ callHelper(toInt32Helper);
+ saveReturnValueInAccumulator();
+ popAligned(lhsTarget);
+
+ isInt.link(this);
}
void toInt32()
{
+ urshift64(AccumulatorRegister, TrustedImm32(Value::QuickType_Shift), ScratchRegister2);
+ auto isInt = branch32(Equal, TrustedImm32(Value::QT_Int), ScratchRegister2);
+
move(AccumulatorRegister, registerForArg(0));
callRuntime("toInt32Helper", reinterpret_cast<void *>(&toInt32Helper),
Assembler::ResultInAccumulator);
+
+ isInt.link(this);
}
void regToInt32(Address srcReg, RegisterID targetReg)
{
+ load64(srcReg, targetReg);
+ urshift64(targetReg, TrustedImm32(Value::QuickType_Shift), ScratchRegister2);
+ auto isInt = branch32(Equal, TrustedImm32(Value::QT_Int), ScratchRegister2);
+
pushAligned(AccumulatorRegister);
- load64(srcReg, registerForArg(0));
+ move(targetReg, registerForArg(0));
callHelper(toInt32Helper);
move(ReturnValueRegister, targetReg);
popAligned(AccumulatorRegister);
+
+ isInt.link(this);
}
void isNullOrUndefined()
@@ -750,6 +793,12 @@ struct PlatformAssembler64 : PlatformAssemblerCommon
isUndef.link(this);
}
+ Jump isIntOrBool()
+ {
+ urshift64(AccumulatorRegister, TrustedImm32(Value::IsIntegerOrBool_Shift), ScratchRegister);
+ return branch32(Equal, TrustedImm32(3), ScratchRegister);
+ }
+
void jumpStrictEqualStackSlotInt(int lhs, int rhs, int offset)
{
Address lhsAddr(JSStackFrameRegister, lhs * int(sizeof(Value)));
@@ -819,8 +868,8 @@ struct PlatformAssembler64 : PlatformAssemblerCommon
Jump unopIntPath(std::function<Jump(void)> fastPath)
{
- urshift64(AccumulatorRegister, TrustedImm32(32), ScratchRegister);
- Jump accNotInt = branch32(NotEqual, TrustedImm32(int(IntegerTag)), ScratchRegister);
+ urshift64(AccumulatorRegister, TrustedImm32(IsIntegerConvertible_Shift), ScratchRegister);
+ Jump accNotIntConvertible = branch32(NotEqual, TrustedImm32(1), ScratchRegister);
// both integer
Jump failure = fastPath();
@@ -829,10 +878,16 @@ struct PlatformAssembler64 : PlatformAssemblerCommon
// all other cases
if (failure.isSet())
failure.link(this);
- accNotInt.link(this);
+ accNotIntConvertible.link(this);
return done;
}
+
+ void callWithAccumulatorByValueAsFirstArgument(std::function<void()> doCall)
+ {
+ passAsArg(AccumulatorRegister, 0);
+ doCall();
+ }
};
typedef PlatformAssembler64 PlatformAssembler;
@@ -845,10 +900,14 @@ struct PlatformAssembler32 : PlatformAssemblerCommon
Assembler::CallResultDestination dest)
{
PlatformAssemblerCommon::callRuntime(functionName, funcPtr);
- if (dest == Assembler::ResultInAccumulator) {
- move(ReturnValueRegisterValue, AccumulatorRegisterValue);
- move(ReturnValueRegisterTag, AccumulatorRegisterTag);
- }
+ if (dest == Assembler::ResultInAccumulator)
+ saveReturnValueInAccumulator();
+ }
+
+ void saveReturnValueInAccumulator()
+ {
+ move(ReturnValueRegisterValue, AccumulatorRegisterValue);
+ move(ReturnValueRegisterTag, AccumulatorRegisterTag);
}
void loadUndefined()
@@ -909,6 +968,14 @@ struct PlatformAssembler32 : PlatformAssemblerCommon
move(TrustedImm32(Value::fromReturnedValue(value).tag()), AccumulatorRegisterTag);
}
+ void storeHeapObject(RegisterID source, Address addr)
+ {
+ store32(source, addr);
+ addr.offset += 4;
+ store32(TrustedImm32(0), addr);
+ }
+
+
void generateCatchTrampoline()
{
PlatformAssemblerCommon::generateCatchTrampoline([this](){loadUndefined();});
@@ -916,6 +983,9 @@ struct PlatformAssembler32 : PlatformAssemblerCommon
void toNumber()
{
+ urshift32(AccumulatorRegisterTag, TrustedImm32(Value::QuickType_Shift - 32), ScratchRegister);
+ auto isNumber = branch32(GreaterThanOrEqual, ScratchRegister, TrustedImm32(Value::QT_Int));
+
if (ArgInRegCount < 2) {
push(AccumulatorRegisterTag);
push(AccumulatorRegisterValue);
@@ -925,14 +995,71 @@ struct PlatformAssembler32 : PlatformAssemblerCommon
}
callRuntime("toNumberHelper", reinterpret_cast<void *>(&toNumberHelper),
Assembler::ResultInAccumulator);
- move(ReturnValueRegisterValue, AccumulatorRegisterValue);
- move(ReturnValueRegisterTag, AccumulatorRegisterTag);
+ saveReturnValueInAccumulator();
if (ArgInRegCount < 2)
addPtr(TrustedImm32(2 * PointerSize), StackPointerRegister);
+
+ isNumber.link(this);
+ }
+
+ void toInt32LhsAcc(Address lhs, RegisterID lhsTarget)
+ {
+ bool accumulatorNeedsSaving = AccumulatorRegisterValue == ReturnValueRegisterValue
+ || AccumulatorRegisterTag == ReturnValueRegisterTag;
+ lhs.offset += 4;
+ load32(lhs, lhsTarget);
+ lhs.offset -= 4;
+ auto lhsIsNotInt = branch32(NotEqual, TrustedImm32(int(IntegerTag)), lhsTarget);
+ load32(lhs, lhsTarget);
+ auto lhsIsInt = jump();
+
+ lhsIsNotInt.link(this);
+ if (accumulatorNeedsSaving) {
+ push(AccumulatorRegisterTag);
+ push(AccumulatorRegisterValue);
+ }
+ if (ArgInRegCount < 2) {
+ push(lhsTarget);
+ load32(lhs, lhsTarget);
+ push(lhsTarget);
+ } else {
+ move(lhsTarget, registerForArg(1));
+ load32(lhs, registerForArg(0));
+ }
+ callHelper(toInt32Helper);
+ move(ReturnValueRegisterValue, lhsTarget);
+ if (ArgInRegCount < 2)
+ addPtr(TrustedImm32(2 * PointerSize), StackPointerRegister);
+ if (accumulatorNeedsSaving) {
+ pop(AccumulatorRegisterValue);
+ pop(AccumulatorRegisterTag);
+ }
+ lhsIsInt.link(this);
+
+ auto rhsIsInt = branch32(Equal, TrustedImm32(int(IntegerTag)), AccumulatorRegisterTag);
+
+ pushAligned(lhsTarget);
+ if (ArgInRegCount < 2) {
+ push(AccumulatorRegisterTag);
+ push(AccumulatorRegisterValue);
+ } else {
+ move(AccumulatorRegisterValue, registerForArg(0));
+ move(AccumulatorRegisterTag, registerForArg(1));
+ }
+ callRuntime("toInt32Helper", reinterpret_cast<void *>(&toInt32Helper),
+ Assembler::ResultInAccumulator);
+ if (ArgInRegCount < 2)
+ addPtr(TrustedImm32(2 * PointerSize), StackPointerRegister);
+ popAligned(lhsTarget);
+
+ rhsIsInt.link(this);
}
void toInt32()
{
+ urshift32(AccumulatorRegisterTag, TrustedImm32(Value::QuickType_Shift - 32), ScratchRegister);
+ auto isInt = branch32(Equal, TrustedImm32(Value::QT_Int), ScratchRegister);
+
if (ArgInRegCount < 2) {
push(AccumulatorRegisterTag);
push(AccumulatorRegisterValue);
@@ -944,6 +1071,8 @@ struct PlatformAssembler32 : PlatformAssemblerCommon
Assembler::ResultInAccumulator);
if (ArgInRegCount < 2)
addPtr(TrustedImm32(2 * PointerSize), StackPointerRegister);
+
+ isInt.link(this);
}
void regToInt32(Address srcReg, RegisterID targetReg)
@@ -990,6 +1119,12 @@ struct PlatformAssembler32 : PlatformAssemblerCommon
done.link(this);
}
+ Jump isIntOrBool()
+ {
+ urshift32(AccumulatorRegisterTag, TrustedImm32(Value::IsIntegerOrBool_Shift - 32), ScratchRegister);
+ return branch32(Equal, TrustedImm32(3), ScratchRegister);
+ }
+
void pushValue(ReturnedValue v)
{
push(TrustedImm32(v >> 32));
@@ -1123,6 +1258,20 @@ struct PlatformAssembler32 : PlatformAssemblerCommon
return done;
}
+
+ void callWithAccumulatorByValueAsFirstArgument(std::function<void()> doCall)
+ {
+ if (ArgInRegCount < 2) {
+ push(AccumulatorRegisterTag);
+ push(AccumulatorRegisterValue);
+ } else {
+ move(AccumulatorRegisterValue, registerForArg(0));
+ move(AccumulatorRegisterTag, registerForArg(1));
+ }
+ doCall();
+ if (ArgInRegCount < 2)
+ addPtr(TrustedImm32(2 * PointerSize), StackPointerRegister);
+ }
};
typedef PlatformAssembler32 PlatformAssembler;
@@ -1170,7 +1319,7 @@ class QIODevicePrintStream: public FilePrintStream
public:
explicit QIODevicePrintStream(QIODevice *dest)
- : FilePrintStream(0)
+ : FilePrintStream(nullptr)
, dest(dest)
, buf(4096, '0')
{
@@ -1224,7 +1373,7 @@ void Assembler::link(Function *function)
jumpTarget.jump.linkTo(pasm()->labelsByOffset[jumpTarget.offset], pasm());
JSC::JSGlobalData dummy(function->internalClass->engine->executableAllocator);
- JSC::LinkBuffer<PlatformAssembler::MacroAssembler> linkBuffer(dummy, pasm(), 0);
+ JSC::LinkBuffer<PlatformAssembler::MacroAssembler> linkBuffer(dummy, pasm(), nullptr);
for (const auto &ehTarget : pasm()->ehTargets) {
auto targetLabel = pasm()->labelsByOffset.value(ehTarget.offset);
@@ -1321,6 +1470,11 @@ void Assembler::loadValue(ReturnedValue value)
pasm()->loadValue(value);
}
+void JIT::Assembler::storeHeapObject(int reg)
+{
+ pasm()->storeHeapObject(PlatformAssembler::ReturnValueRegisterValue, regAddr(reg));
+}
+
void Assembler::toNumber()
{
pasm()->toNumber();
@@ -1342,9 +1496,14 @@ void Assembler::ucompl()
pasm()->setAccumulatorTag(IntegerTag);
}
-static ReturnedValue incHelper(const Value &v)
+static ReturnedValue incHelper(const Value v)
{
- return Encode(v.toNumber() + 1.);
+ double d;
+ if (Q_LIKELY(v.isDouble()))
+ d = v.doubleValue();
+ else
+ d = v.toNumberImpl();
+ return Encode(d + 1.);
}
void Assembler::inc()
@@ -1359,19 +1518,24 @@ void Assembler::inc()
});
// slow path:
- saveAccumulatorInFrame();
- prepareCallWithArgCount(1);
- passAccumulatorAsArg(0);
- IN_JIT_GENERATE_RUNTIME_CALL(incHelper, ResultInAccumulator);
+ pasm()->callWithAccumulatorByValueAsFirstArgument([this]() {
+ pasm()->callHelper(incHelper);
+ pasm()->saveReturnValueInAccumulator();
+ });
checkException();
// done.
done.link(pasm());
}
-static ReturnedValue decHelper(const Value &v)
+static ReturnedValue decHelper(const Value v)
{
- return Encode(v.toNumber() - 1.);
+ double d;
+ if (Q_LIKELY(v.isDouble()))
+ d = v.doubleValue();
+ else
+ d = v.toNumberImpl();
+ return Encode(d - 1.);
}
void Assembler::dec()
@@ -1386,10 +1550,10 @@ void Assembler::dec()
});
// slow path:
- saveAccumulatorInFrame();
- prepareCallWithArgCount(1);
- passAccumulatorAsArg(0);
- IN_JIT_GENERATE_RUNTIME_CALL(decHelper, ResultInAccumulator);
+ pasm()->callWithAccumulatorByValueAsFirstArgument([this]() {
+ pasm()->callHelper(decHelper);
+ pasm()->saveReturnValueInAccumulator();
+ });
checkException();
// done.
@@ -1432,10 +1596,7 @@ void Assembler::add(int lhs)
void Assembler::bitAnd(int lhs)
{
PlatformAssembler::Address lhsAddr = regAddr(lhs);
- pasm()->regToInt32(lhsAddr, PlatformAssembler::ScratchRegister);
- pasm()->pushAligned(PlatformAssembler::ScratchRegister);
- pasm()->toInt32();
- pasm()->popAligned(PlatformAssembler::ScratchRegister);
+ pasm()->toInt32LhsAcc(lhsAddr, PlatformAssembler::ScratchRegister);
pasm()->and32(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
pasm()->setAccumulatorTag(IntegerTag);
}
@@ -1443,10 +1604,7 @@ void Assembler::bitAnd(int lhs)
void Assembler::bitOr(int lhs)
{
PlatformAssembler::Address lhsAddr = regAddr(lhs);
- pasm()->regToInt32(lhsAddr, PlatformAssembler::ScratchRegister);
- pasm()->pushAligned(PlatformAssembler::ScratchRegister);
- pasm()->toInt32();
- pasm()->popAligned(PlatformAssembler::ScratchRegister);
+ pasm()->toInt32LhsAcc(lhsAddr, PlatformAssembler::ScratchRegister);
pasm()->or32(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
pasm()->setAccumulatorTag(IntegerTag);
}
@@ -1454,10 +1612,7 @@ void Assembler::bitOr(int lhs)
void Assembler::bitXor(int lhs)
{
PlatformAssembler::Address lhsAddr = regAddr(lhs);
- pasm()->regToInt32(lhsAddr, PlatformAssembler::ScratchRegister);
- pasm()->pushAligned(PlatformAssembler::ScratchRegister);
- pasm()->toInt32();
- pasm()->popAligned(PlatformAssembler::ScratchRegister);
+ pasm()->toInt32LhsAcc(lhsAddr, PlatformAssembler::ScratchRegister);
pasm()->xor32(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
pasm()->setAccumulatorTag(IntegerTag);
}
@@ -1465,13 +1620,10 @@ void Assembler::bitXor(int lhs)
void Assembler::ushr(int lhs)
{
PlatformAssembler::Address lhsAddr = regAddr(lhs);
- pasm()->regToInt32(lhsAddr, PlatformAssembler::ScratchRegister);
- pasm()->pushAligned(PlatformAssembler::ScratchRegister);
- pasm()->toInt32();
- pasm()->and32(TrustedImm32(0x1f), PlatformAssembler::AccumulatorRegisterValue,
- PlatformAssembler::ScratchRegister);
- pasm()->popAligned(PlatformAssembler::AccumulatorRegisterValue);
- pasm()->urshift32(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
+ pasm()->toInt32LhsAcc(lhsAddr, PlatformAssembler::ScratchRegister);
+ pasm()->and32(TrustedImm32(0x1f), PlatformAssembler::AccumulatorRegisterValue);
+ pasm()->urshift32(PlatformAssembler::AccumulatorRegisterValue, PlatformAssembler::ScratchRegister);
+ pasm()->move(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
auto doubleEncode = pasm()->branch32(PlatformAssembler::LessThan,
PlatformAssembler::AccumulatorRegisterValue,
TrustedImm32(0));
@@ -1489,26 +1641,20 @@ void Assembler::ushr(int lhs)
void Assembler::shr(int lhs)
{
PlatformAssembler::Address lhsAddr = regAddr(lhs);
- pasm()->regToInt32(lhsAddr, PlatformAssembler::ScratchRegister);
- pasm()->pushAligned(PlatformAssembler::ScratchRegister);
- pasm()->toInt32();
- pasm()->and32(TrustedImm32(0x1f), PlatformAssembler::AccumulatorRegisterValue,
- PlatformAssembler::ScratchRegister);
- pasm()->popAligned(PlatformAssembler::AccumulatorRegisterValue);
- pasm()->rshift32(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
+ pasm()->toInt32LhsAcc(lhsAddr, PlatformAssembler::ScratchRegister);
+ pasm()->and32(TrustedImm32(0x1f), PlatformAssembler::AccumulatorRegisterValue);
+ pasm()->rshift32(PlatformAssembler::AccumulatorRegisterValue, PlatformAssembler::ScratchRegister);
+ pasm()->move(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
pasm()->setAccumulatorTag(IntegerTag);
}
void Assembler::shl(int lhs)
{
PlatformAssembler::Address lhsAddr = regAddr(lhs);
- pasm()->regToInt32(lhsAddr, PlatformAssembler::ScratchRegister);
- pasm()->pushAligned(PlatformAssembler::ScratchRegister);
- pasm()->toInt32();
- pasm()->and32(TrustedImm32(0x1f), PlatformAssembler::AccumulatorRegisterValue,
- PlatformAssembler::ScratchRegister);
- pasm()->popAligned(PlatformAssembler::AccumulatorRegisterValue);
- pasm()->lshift32(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
+ pasm()->toInt32LhsAcc(lhsAddr, PlatformAssembler::ScratchRegister);
+ pasm()->and32(TrustedImm32(0x1f), PlatformAssembler::AccumulatorRegisterValue);
+ pasm()->lshift32(PlatformAssembler::AccumulatorRegisterValue, PlatformAssembler::ScratchRegister);
+ pasm()->move(PlatformAssembler::ScratchRegister, PlatformAssembler::AccumulatorRegisterValue);
pasm()->setAccumulatorTag(IntegerTag);
}
@@ -1537,27 +1683,32 @@ void Assembler::ushrConst(int rhs)
{
rhs &= 0x1f;
pasm()->toInt32();
- if (rhs) // shift with 0 can act weird
+ if (rhs) {
+ // a non zero shift will always give a number encodable as an int
pasm()->urshift32(TrustedImm32(rhs), PlatformAssembler::AccumulatorRegisterValue);
- auto doubleEncode = pasm()->branch32(PlatformAssembler::LessThan,
- PlatformAssembler::AccumulatorRegisterValue,
- TrustedImm32(0));
- pasm()->setAccumulatorTag(IntegerTag);
- auto done = pasm()->jump();
+ pasm()->setAccumulatorTag(IntegerTag);
+ } else {
+ // shift with 0 can lead to a negative result
+ auto doubleEncode = pasm()->branch32(PlatformAssembler::LessThan,
+ PlatformAssembler::AccumulatorRegisterValue,
+ TrustedImm32(0));
+ pasm()->setAccumulatorTag(IntegerTag);
+ auto done = pasm()->jump();
- doubleEncode.link(pasm());
- pasm()->convertUInt32ToDouble(PlatformAssembler::AccumulatorRegisterValue,
- PlatformAssembler::FPScratchRegister,
- PlatformAssembler::ScratchRegister);
- pasm()->encodeDoubleIntoAccumulator(PlatformAssembler::FPScratchRegister);
- done.link(pasm());
+ doubleEncode.link(pasm());
+ pasm()->convertUInt32ToDouble(PlatformAssembler::AccumulatorRegisterValue,
+ PlatformAssembler::FPScratchRegister,
+ PlatformAssembler::ScratchRegister);
+ pasm()->encodeDoubleIntoAccumulator(PlatformAssembler::FPScratchRegister);
+ done.link(pasm());
+ }
}
void Assembler::shrConst(int rhs)
{
rhs &= 0x1f;
pasm()->toInt32();
- if (rhs) // shift with 0 can act weird
+ if (rhs)
pasm()->rshift32(TrustedImm32(rhs), PlatformAssembler::AccumulatorRegisterValue);
pasm()->setAccumulatorTag(IntegerTag);
}
@@ -1566,7 +1717,7 @@ void Assembler::shlConst(int rhs)
{
rhs &= 0x1f;
pasm()->toInt32();
- if (rhs) // shift with 0 can act weird
+ if (rhs)
pasm()->lshift32(TrustedImm32(rhs), PlatformAssembler::AccumulatorRegisterValue);
pasm()->setAccumulatorTag(IntegerTag);
}
@@ -1652,6 +1803,7 @@ void Assembler::cmpneNull()
void Assembler::cmpeqInt(int lhs)
{
+ auto isIntOrBool = pasm()->isIntOrBool();
saveAccumulatorInFrame();
pasm()->pushValueAligned(Encode(lhs));
if (PlatformAssembler::ArgInRegCount < 2)
@@ -1663,10 +1815,18 @@ void Assembler::cmpeqInt(int lhs)
if (PlatformAssembler::ArgInRegCount < 2)
pasm()->addPtr(TrustedImm32(2 * PlatformAssembler::PointerSize), PlatformAssembler::StackPointerRegister);
pasm()->popValueAligned();
+ auto done = pasm()->jump();
+ isIntOrBool.link(pasm());
+ pasm()->compare32(PlatformAssembler::Equal, PlatformAssembler::AccumulatorRegisterValue,
+ TrustedImm32(lhs),
+ PlatformAssembler::AccumulatorRegisterValue);
+ pasm()->setAccumulatorTag(QV4::Value::ValueTypeInternal::Boolean);
+ done.link(pasm());
}
void Assembler::cmpneInt(int lhs)
{
+ auto isIntOrBool = pasm()->isIntOrBool();
saveAccumulatorInFrame();
pasm()->pushValueAligned(Encode(lhs));
if (PlatformAssembler::ArgInRegCount < 2)
@@ -1678,6 +1838,13 @@ void Assembler::cmpneInt(int lhs)
if (PlatformAssembler::ArgInRegCount < 2)
pasm()->addPtr(TrustedImm32(2 * PlatformAssembler::PointerSize), PlatformAssembler::StackPointerRegister);
pasm()->popValueAligned();
+ auto done = pasm()->jump();
+ isIntOrBool.link(pasm());
+ pasm()->compare32(PlatformAssembler::NotEqual, PlatformAssembler::AccumulatorRegisterValue,
+ TrustedImm32(lhs),
+ PlatformAssembler::AccumulatorRegisterValue);
+ pasm()->setAccumulatorTag(QV4::Value::ValueTypeInternal::Boolean);
+ done.link(pasm());
}
void Assembler::cmp(int cond, CmpFunc function, const char *functionName, int lhs)
@@ -1956,7 +2123,7 @@ void Assembler::gotoCatchException()
void Assembler::getException()
{
- Q_STATIC_ASSERT_FOR_SANE_COMPILERS(sizeof(QV4::EngineBase::hasException) == 1);
+ Q_STATIC_ASSERT(sizeof(QV4::EngineBase::hasException) == 1);
Address hasExceptionAddr(PlatformAssembler::EngineRegister,
offsetof(EngineBase, hasException));
@@ -1981,7 +2148,7 @@ void Assembler::setException()
pasm()->loadPtr(addr, PlatformAssembler::ScratchRegister);
pasm()->storeAccumulator(Address(PlatformAssembler::ScratchRegister));
addr.offset = offsetof(EngineBase, hasException);
- Q_STATIC_ASSERT_FOR_SANE_COMPILERS(sizeof(QV4::EngineBase::hasException) == 1);
+ Q_STATIC_ASSERT(sizeof(QV4::EngineBase::hasException) == 1);
pasm()->store8(TrustedImm32(1), addr);
}
diff --git a/src/qml/jit/qv4assembler_p.h b/src/qml/jit/qv4assembler_p.h
index 5cd64096b1..37d4232a17 100644
--- a/src/qml/jit/qv4assembler_p.h
+++ b/src/qml/jit/qv4assembler_p.h
@@ -95,6 +95,7 @@ public:
void storeLocal(int index, int level = 0);
void loadString(int stringId);
void loadValue(ReturnedValue value);
+ void storeHeapObject(int reg);
// numeric ops
void unot();
diff --git a/src/qml/jit/qv4jit.cpp b/src/qml/jit/qv4jit.cpp
index 42ee1ff5df..5dc98a591a 100644
--- a/src/qml/jit/qv4jit.cpp
+++ b/src/qml/jit/qv4jit.cpp
@@ -548,6 +548,32 @@ void BaselineJIT::generate_CallGlobalLookup(int index, int argc, int argv)
as->checkException();
}
+void BaselineJIT::generate_CallScopeObjectProperty(int propIdx, int base, int argc, int argv)
+{
+ STORE_IP();
+ as->prepareCallWithArgCount(5);
+ as->passInt32AsArg(argc, 4);
+ as->passRegAsArg(argv, 3);
+ as->passInt32AsArg(propIdx, 2);
+ as->passRegAsArg(base, 1);
+ as->passEngineAsArg(0);
+ JIT_GENERATE_RUNTIME_CALL(Runtime::method_callQmlScopeObjectProperty, Assembler::ResultInAccumulator);
+ as->checkException();
+}
+
+void BaselineJIT::generate_CallContextObjectProperty(int propIdx, int base, int argc, int argv)
+{
+ STORE_IP();
+ as->prepareCallWithArgCount(5);
+ as->passInt32AsArg(argc, 4);
+ as->passRegAsArg(argv, 3);
+ as->passInt32AsArg(propIdx, 2);
+ as->passRegAsArg(base, 1);
+ as->passEngineAsArg(0);
+ JIT_GENERATE_RUNTIME_CALL(Runtime::method_callQmlContextObjectProperty, Assembler::ResultInAccumulator);
+ as->checkException();
+}
+
void BaselineJIT::generate_SetExceptionHandler(int offset)
{
if (offset)
@@ -570,17 +596,12 @@ void BaselineJIT::generate_ThrowException()
void BaselineJIT::generate_GetException() { as->getException(); }
void BaselineJIT::generate_SetException() { as->setException(); }
-static void createCallContextHelper(Value *stack, CppStackFrame *frame)
-{
- stack[CallData::Context] = ExecutionContext::newCallContext(frame);
-}
-
void BaselineJIT::generate_CreateCallContext()
{
- as->prepareCallWithArgCount(2);
- as->passCppFrameAsArg(1);
- as->passRegAsArg(0, 0);
- JIT_GENERATE_RUNTIME_CALL(createCallContextHelper, Assembler::IgnoreResult);
+ as->prepareCallWithArgCount(1);
+ as->passCppFrameAsArg(0);
+ JIT_GENERATE_RUNTIME_CALL(ExecutionContext::newCallContext, Assembler::IgnoreResult); // keeps result in return value register
+ as->storeHeapObject(CallData::Context);
}
void BaselineJIT::generate_PushCatchContext(int name, int reg) { as->pushCatchContext(name, reg); }
@@ -951,6 +972,11 @@ void BaselineJIT::collectLabelsInBytecode()
{
MOTH_JUMP_TABLE;
+ const auto addLabel = [&](int offset) {
+ Q_ASSERT(offset >= 0 && offset < static_cast<int>(function->compiledFunction->codeSize));
+ labels.push_back(offset);
+ };
+
const char *code = reinterpret_cast<const char *>(function->codeData);
const char *start = code;
const char *end = code + function->compiledFunction->codeSize;
@@ -1087,8 +1113,14 @@ void BaselineJIT::collectLabelsInBytecode()
MOTH_BEGIN_INSTR(CallGlobalLookup)
MOTH_END_INSTR(CallGlobalLookup)
+ MOTH_BEGIN_INSTR(CallScopeObjectProperty)
+ MOTH_END_INSTR(CallScopeObjectProperty)
+
+ MOTH_BEGIN_INSTR(CallContextObjectProperty)
+ MOTH_END_INSTR(CallContextObjectProperty)
+
MOTH_BEGIN_INSTR(SetExceptionHandler)
- labels.push_back(code - start + offset);
+ addLabel(code - start + offset);
MOTH_END_INSTR(SetExceptionHandler)
MOTH_BEGIN_INSTR(ThrowException)
@@ -1155,15 +1187,15 @@ void BaselineJIT::collectLabelsInBytecode()
MOTH_END_INSTR(Construct)
MOTH_BEGIN_INSTR(Jump)
- labels.push_back(code - start + offset);
+ addLabel(code - start + offset);
MOTH_END_INSTR(Jump)
MOTH_BEGIN_INSTR(JumpTrue)
- labels.push_back(code - start + offset);
+ addLabel(code - start + offset);
MOTH_END_INSTR(JumpTrue)
MOTH_BEGIN_INSTR(JumpFalse)
- labels.push_back(code - start + offset);
+ addLabel(code - start + offset);
MOTH_END_INSTR(JumpFalse)
MOTH_BEGIN_INSTR(CmpEqNull)
@@ -1209,11 +1241,11 @@ void BaselineJIT::collectLabelsInBytecode()
MOTH_END_INSTR(CmpInstanceOf)
MOTH_BEGIN_INSTR(JumpStrictEqualStackSlotInt)
- labels.push_back(code - start + offset);
+ addLabel(code - start + offset);
MOTH_END_INSTR(JumpStrictEqualStackSlotInt)
MOTH_BEGIN_INSTR(JumpStrictNotEqualStackSlotInt)
- labels.push_back(code - start + offset);
+ addLabel(code - start + offset);
MOTH_END_INSTR(JumpStrictNotEqualStackSlotInt)
MOTH_BEGIN_INSTR(UNot)
@@ -1288,10 +1320,8 @@ void BaselineJIT::collectLabelsInBytecode()
MOTH_BEGIN_INSTR(Ret)
MOTH_END_INSTR(Ret)
-#ifndef QT_NO_QML_DEBUGGER
MOTH_BEGIN_INSTR(Debug)
MOTH_END_INSTR(Debug)
-#endif // QT_NO_QML_DEBUGGER
MOTH_BEGIN_INSTR(LoadQmlContext)
MOTH_END_INSTR(LoadQmlContext)
diff --git a/src/qml/jit/qv4jit_p.h b/src/qml/jit/qv4jit_p.h
index c7ec1700c3..c17ab4ff6e 100644
--- a/src/qml/jit/qv4jit_p.h
+++ b/src/qml/jit/qv4jit_p.h
@@ -119,129 +119,131 @@ public:
void generate();
- void generate_Ret() Q_DECL_OVERRIDE;
- void generate_Debug() Q_DECL_OVERRIDE;
- void generate_LoadConst(int index) Q_DECL_OVERRIDE;
- void generate_LoadZero() Q_DECL_OVERRIDE;
- void generate_LoadTrue() Q_DECL_OVERRIDE;
- void generate_LoadFalse() Q_DECL_OVERRIDE;
- void generate_LoadNull() Q_DECL_OVERRIDE;
- void generate_LoadUndefined() Q_DECL_OVERRIDE;
- void generate_LoadInt(int value) Q_DECL_OVERRIDE;
- void generate_MoveConst(int constIndex, int destTemp) Q_DECL_OVERRIDE;
- void generate_LoadReg(int reg) Q_DECL_OVERRIDE;
- void generate_StoreReg(int reg) Q_DECL_OVERRIDE;
- void generate_MoveReg(int srcReg, int destReg) Q_DECL_OVERRIDE;
- void generate_LoadLocal(int index) Q_DECL_OVERRIDE;
- void generate_StoreLocal(int index) Q_DECL_OVERRIDE;
- void generate_LoadScopedLocal(int scope, int index) Q_DECL_OVERRIDE;
- void generate_StoreScopedLocal(int scope, int index) Q_DECL_OVERRIDE;
- void generate_LoadRuntimeString(int stringId) Q_DECL_OVERRIDE;
- void generate_MoveRegExp(int regExpId, int destReg) Q_DECL_OVERRIDE;
- void generate_LoadClosure(int value) Q_DECL_OVERRIDE;
- void generate_LoadName(int name) Q_DECL_OVERRIDE;
- void generate_LoadGlobalLookup(int index) Q_DECL_OVERRIDE;
- void generate_StoreNameSloppy(int name) Q_DECL_OVERRIDE;
- void generate_StoreNameStrict(int name) Q_DECL_OVERRIDE;
- void generate_LoadElement(int base, int index) Q_DECL_OVERRIDE;
- void generate_LoadElementA(int base) Q_DECL_OVERRIDE;
- void generate_StoreElement(int base, int index) Q_DECL_OVERRIDE;
- void generate_LoadProperty(int name, int base) Q_DECL_OVERRIDE;
- void generate_LoadPropertyA(int name) Q_DECL_OVERRIDE;
- void generate_GetLookup(int index, int base) Q_DECL_OVERRIDE;
- void generate_GetLookupA(int index) Q_DECL_OVERRIDE;
- void generate_StoreProperty(int name, int base) Q_DECL_OVERRIDE;
- void generate_SetLookup(int index, int base) Q_DECL_OVERRIDE;
+ void generate_Ret() override;
+ void generate_Debug() override;
+ void generate_LoadConst(int index) override;
+ void generate_LoadZero() override;
+ void generate_LoadTrue() override;
+ void generate_LoadFalse() override;
+ void generate_LoadNull() override;
+ void generate_LoadUndefined() override;
+ void generate_LoadInt(int value) override;
+ void generate_MoveConst(int constIndex, int destTemp) override;
+ void generate_LoadReg(int reg) override;
+ void generate_StoreReg(int reg) override;
+ void generate_MoveReg(int srcReg, int destReg) override;
+ void generate_LoadLocal(int index) override;
+ void generate_StoreLocal(int index) override;
+ void generate_LoadScopedLocal(int scope, int index) override;
+ void generate_StoreScopedLocal(int scope, int index) override;
+ void generate_LoadRuntimeString(int stringId) override;
+ void generate_MoveRegExp(int regExpId, int destReg) override;
+ void generate_LoadClosure(int value) override;
+ void generate_LoadName(int name) override;
+ void generate_LoadGlobalLookup(int index) override;
+ void generate_StoreNameSloppy(int name) override;
+ void generate_StoreNameStrict(int name) override;
+ void generate_LoadElement(int base, int index) override;
+ void generate_LoadElementA(int base) override;
+ void generate_StoreElement(int base, int index) override;
+ void generate_LoadProperty(int name, int base) override;
+ void generate_LoadPropertyA(int name) override;
+ void generate_GetLookup(int index, int base) override;
+ void generate_GetLookupA(int index) override;
+ void generate_StoreProperty(int name, int base) override;
+ void generate_SetLookup(int index, int base) override;
void generate_StoreScopeObjectProperty(int base,
- int propertyIndex) Q_DECL_OVERRIDE;
+ int propertyIndex) override;
void generate_StoreContextObjectProperty(int base,
- int propertyIndex) Q_DECL_OVERRIDE;
+ int propertyIndex) override;
void generate_LoadScopeObjectProperty(int propertyIndex, int base,
- int captureRequired) Q_DECL_OVERRIDE;
+ int captureRequired) override;
void generate_LoadContextObjectProperty(int propertyIndex, int base,
- int captureRequired) Q_DECL_OVERRIDE;
- void generate_LoadIdObject(int index, int base) Q_DECL_OVERRIDE;
- void generate_CallValue(int name, int argc, int argv) Q_DECL_OVERRIDE;
- void generate_CallProperty(int name, int base, int argc, int argv) Q_DECL_OVERRIDE;
- void generate_CallPropertyLookup(int lookupIndex, int base, int argc, int argv) Q_DECL_OVERRIDE;
- void generate_CallElement(int base, int index, int argc, int argv) Q_DECL_OVERRIDE;
- void generate_CallName(int name, int argc, int argv) Q_DECL_OVERRIDE;
- void generate_CallPossiblyDirectEval(int argc, int argv) Q_DECL_OVERRIDE;
- void generate_CallGlobalLookup(int index, int argc, int argv) Q_DECL_OVERRIDE;
- void generate_SetExceptionHandler(int offset) Q_DECL_OVERRIDE;
- void generate_ThrowException() Q_DECL_OVERRIDE;
- void generate_GetException() Q_DECL_OVERRIDE;
- void generate_SetException() Q_DECL_OVERRIDE;
- void generate_CreateCallContext() Q_DECL_OVERRIDE;
- void generate_PushCatchContext(int name, int reg) Q_DECL_OVERRIDE;
- void generate_PushWithContext(int reg) Q_DECL_OVERRIDE;
- void generate_PopContext(int reg) Q_DECL_OVERRIDE;
- void generate_ForeachIteratorObject() Q_DECL_OVERRIDE;
- void generate_ForeachNextPropertyName() Q_DECL_OVERRIDE;
- void generate_DeleteMember(int member, int base) Q_DECL_OVERRIDE;
- void generate_DeleteSubscript(int base, int index) Q_DECL_OVERRIDE;
- void generate_DeleteName(int name) Q_DECL_OVERRIDE;
- void generate_TypeofName(int name) Q_DECL_OVERRIDE;
- void generate_TypeofValue() Q_DECL_OVERRIDE;
- void generate_DeclareVar(int varName, int isDeletable) Q_DECL_OVERRIDE;
- void generate_DefineArray(int argc, int args) Q_DECL_OVERRIDE;
+ int captureRequired) override;
+ void generate_LoadIdObject(int index, int base) override;
+ void generate_CallValue(int name, int argc, int argv) override;
+ void generate_CallProperty(int name, int base, int argc, int argv) override;
+ void generate_CallPropertyLookup(int lookupIndex, int base, int argc, int argv) override;
+ void generate_CallElement(int base, int index, int argc, int argv) override;
+ void generate_CallName(int name, int argc, int argv) override;
+ void generate_CallPossiblyDirectEval(int argc, int argv) override;
+ void generate_CallGlobalLookup(int index, int argc, int argv) override;
+ void generate_CallScopeObjectProperty(int propIdx, int base, int argc, int argv) override;
+ void generate_CallContextObjectProperty(int propIdx, int base, int argc, int argv) override;
+ void generate_SetExceptionHandler(int offset) override;
+ void generate_ThrowException() override;
+ void generate_GetException() override;
+ void generate_SetException() override;
+ void generate_CreateCallContext() override;
+ void generate_PushCatchContext(int name, int reg) override;
+ void generate_PushWithContext(int reg) override;
+ void generate_PopContext(int reg) override;
+ void generate_ForeachIteratorObject() override;
+ void generate_ForeachNextPropertyName() override;
+ void generate_DeleteMember(int member, int base) override;
+ void generate_DeleteSubscript(int base, int index) override;
+ void generate_DeleteName(int name) override;
+ void generate_TypeofName(int name) override;
+ void generate_TypeofValue() override;
+ void generate_DeclareVar(int varName, int isDeletable) override;
+ void generate_DefineArray(int argc, int args) override;
void generate_DefineObjectLiteral(int internalClassId, int arrayValueCount,
int arrayGetterSetterCountAndFlags,
- int args) Q_DECL_OVERRIDE;
- void generate_CreateMappedArgumentsObject() Q_DECL_OVERRIDE;
- void generate_CreateUnmappedArgumentsObject() Q_DECL_OVERRIDE;
- void generate_ConvertThisToObject() Q_DECL_OVERRIDE;
- void generate_Construct(int func, int argc, int argv) Q_DECL_OVERRIDE;
- void generate_Jump(int offset) Q_DECL_OVERRIDE;
- void generate_JumpTrue(int offset) Q_DECL_OVERRIDE;
- void generate_JumpFalse(int offset) Q_DECL_OVERRIDE;
- void generate_CmpEqNull() Q_DECL_OVERRIDE;
- void generate_CmpNeNull() Q_DECL_OVERRIDE;
- void generate_CmpEqInt(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpNeInt(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpEq(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpNe(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpGt(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpGe(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpLt(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpLe(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpStrictEqual(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpStrictNotEqual(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpIn(int lhs) Q_DECL_OVERRIDE;
- void generate_CmpInstanceOf(int lhs) Q_DECL_OVERRIDE;
+ int args) override;
+ void generate_CreateMappedArgumentsObject() override;
+ void generate_CreateUnmappedArgumentsObject() override;
+ void generate_ConvertThisToObject() override;
+ void generate_Construct(int func, int argc, int argv) override;
+ void generate_Jump(int offset) override;
+ void generate_JumpTrue(int offset) override;
+ void generate_JumpFalse(int offset) override;
+ void generate_CmpEqNull() override;
+ void generate_CmpNeNull() override;
+ void generate_CmpEqInt(int lhs) override;
+ void generate_CmpNeInt(int lhs) override;
+ void generate_CmpEq(int lhs) override;
+ void generate_CmpNe(int lhs) override;
+ void generate_CmpGt(int lhs) override;
+ void generate_CmpGe(int lhs) override;
+ void generate_CmpLt(int lhs) override;
+ void generate_CmpLe(int lhs) override;
+ void generate_CmpStrictEqual(int lhs) override;
+ void generate_CmpStrictNotEqual(int lhs) override;
+ void generate_CmpIn(int lhs) override;
+ void generate_CmpInstanceOf(int lhs) override;
void generate_JumpStrictEqualStackSlotInt(int lhs, int rhs,
- int offset) Q_DECL_OVERRIDE;
+ int offset) override;
void generate_JumpStrictNotEqualStackSlotInt(int lhs, int rhs,
- int offset) Q_DECL_OVERRIDE;
- void generate_UNot() Q_DECL_OVERRIDE;
- void generate_UPlus() Q_DECL_OVERRIDE;
- void generate_UMinus() Q_DECL_OVERRIDE;
- void generate_UCompl() Q_DECL_OVERRIDE;
- void generate_Increment() Q_DECL_OVERRIDE;
- void generate_Decrement() Q_DECL_OVERRIDE;
- void generate_Add(int lhs) Q_DECL_OVERRIDE;
- void generate_BitAnd(int lhs) Q_DECL_OVERRIDE;
- void generate_BitOr(int lhs) Q_DECL_OVERRIDE;
- void generate_BitXor(int lhs) Q_DECL_OVERRIDE;
- void generate_UShr(int lhs) Q_DECL_OVERRIDE;
- void generate_Shr(int lhs) Q_DECL_OVERRIDE;
- void generate_Shl(int lhs) Q_DECL_OVERRIDE;
- void generate_BitAndConst(int rhs) Q_DECL_OVERRIDE;
- void generate_BitOrConst(int rhs) Q_DECL_OVERRIDE;
- void generate_BitXorConst(int rhs) Q_DECL_OVERRIDE;
- void generate_UShrConst(int rhs) Q_DECL_OVERRIDE;
- void generate_ShrConst(int rhs) Q_DECL_OVERRIDE;
- void generate_ShlConst(int rhs) Q_DECL_OVERRIDE;
- void generate_Mul(int lhs) Q_DECL_OVERRIDE;
- void generate_Div(int lhs) Q_DECL_OVERRIDE;
- void generate_Mod(int lhs) Q_DECL_OVERRIDE;
- void generate_Sub(int lhs) Q_DECL_OVERRIDE;
- void generate_LoadQmlContext(int result) Q_DECL_OVERRIDE;
- void generate_LoadQmlImportedScripts(int result) Q_DECL_OVERRIDE;
- void generate_LoadQmlSingleton(int name) Q_DECL_OVERRIDE;
+ int offset) override;
+ void generate_UNot() override;
+ void generate_UPlus() override;
+ void generate_UMinus() override;
+ void generate_UCompl() override;
+ void generate_Increment() override;
+ void generate_Decrement() override;
+ void generate_Add(int lhs) override;
+ void generate_BitAnd(int lhs) override;
+ void generate_BitOr(int lhs) override;
+ void generate_BitXor(int lhs) override;
+ void generate_UShr(int lhs) override;
+ void generate_Shr(int lhs) override;
+ void generate_Shl(int lhs) override;
+ void generate_BitAndConst(int rhs) override;
+ void generate_BitOrConst(int rhs) override;
+ void generate_BitXorConst(int rhs) override;
+ void generate_UShrConst(int rhs) override;
+ void generate_ShrConst(int rhs) override;
+ void generate_ShlConst(int rhs) override;
+ void generate_Mul(int lhs) override;
+ void generate_Div(int lhs) override;
+ void generate_Mod(int lhs) override;
+ void generate_Sub(int lhs) override;
+ void generate_LoadQmlContext(int result) override;
+ void generate_LoadQmlImportedScripts(int result) override;
+ void generate_LoadQmlSingleton(int name) override;
- void startInstruction(Moth::Instr::Type instr) Q_DECL_OVERRIDE;
- void endInstruction(Moth::Instr::Type instr) Q_DECL_OVERRIDE;
+ void startInstruction(Moth::Instr::Type instr) override;
+ void endInstruction(Moth::Instr::Type instr) override;
protected:
bool hasLabel() const
diff --git a/src/qml/jsapi/qjsengine.cpp b/src/qml/jsapi/qjsengine.cpp
index bca4057fbe..c483af638b 100644
--- a/src/qml/jsapi/qjsengine.cpp
+++ b/src/qml/jsapi/qjsengine.cpp
@@ -166,16 +166,30 @@ Q_DECLARE_METATYPE(QList<int>)
properties of the proxy object. No binding code is needed because it
is done dynamically using the Qt meta object system.
+ \snippet code/src_script_qjsengine.cpp 5
+
Use newQMetaObject() to wrap a QMetaObject; this gives you a
"script representation" of a QObject-based class. newQMetaObject()
returns a proxy script object; enum values of the class are available
as properties of the proxy object.
- Constructors exposed to the meta-object system ( using Q_INVOKABLE ) can be
+ Constructors exposed to the meta-object system (using Q_INVOKABLE) can be
called from the script to create a new QObject instance with
- JavaScriptOwnership.
+ JavaScriptOwnership. For example, given the following class definition:
- \snippet code/src_script_qjsengine.cpp 5
+ \snippet code/src_script_qjsengine.cpp 7
+
+ The \c staticMetaObject for the class can be exposed to JavaScript like so:
+
+ \snippet code/src_script_qjsengine.cpp 8
+
+ Instances of the class can then be created in JavaScript:
+
+ \snippet code/src_script_qjsengine.cpp 9
+
+ \note Currently only classes using the Q_OBJECT macro are supported; it is
+ not possible to expose the \c staticMetaObject of a Q_GADGET class to
+ JavaScript.
\section2 Dynamic QObject Properties
@@ -290,8 +304,9 @@ QJSEngine::QJSEngine()
QJSEngine::QJSEngine(QObject *parent)
: QObject(*new QJSEnginePrivate, parent)
- , d(new QV8Engine(this))
+ , m_v4Engine(new QV4::ExecutionEngine)
{
+ m_v4Engine->v8Engine = new QV8Engine(this, m_v4Engine);
checkForApplicationInstance();
QJSEnginePrivate::addToDebugServer(this);
@@ -302,8 +317,9 @@ QJSEngine::QJSEngine(QObject *parent)
*/
QJSEngine::QJSEngine(QJSEnginePrivate &dd, QObject *parent)
: QObject(dd, parent)
- , d(new QV8Engine(this))
+ , m_v4Engine(new QV4::ExecutionEngine)
{
+ m_v4Engine->v8Engine = new QV8Engine(this, m_v4Engine);
checkForApplicationInstance();
}
@@ -317,11 +333,12 @@ QJSEngine::QJSEngine(QJSEnginePrivate &dd, QObject *parent)
QJSEngine::~QJSEngine()
{
QJSEnginePrivate::removeFromDebugServer(this);
- delete d;
+ delete m_v4Engine->v8Engine;
+ delete m_v4Engine;
}
/*!
- \fn QV8Engine *QJSEngine::handle() const
+ \fn QV4::ExecutionEngine *QJSEngine::handle() const
\internal
*/
@@ -338,7 +355,7 @@ QJSEngine::~QJSEngine()
*/
void QJSEngine::collectGarbage()
{
- d->m_v4Engine->memoryManager->runGC();
+ m_v4Engine->memoryManager->runGC();
}
#if QT_DEPRECATED_SINCE(5, 6)
@@ -395,12 +412,12 @@ void QJSEngine::installTranslatorFunctions(const QJSValue &object)
void QJSEngine::installExtensions(QJSEngine::Extensions extensions, const QJSValue &object)
{
QV4::ExecutionEngine *otherEngine = QJSValuePrivate::engine(&object);
- if (otherEngine && otherEngine != d->m_v4Engine) {
+ if (otherEngine && otherEngine != m_v4Engine) {
qWarning("QJSEngine: Trying to install extensions from a different engine");
return;
}
- QV4::Scope scope(d->m_v4Engine);
+ QV4::Scope scope(m_v4Engine);
QV4::ScopedObject obj(scope);
QV4::Value *val = QJSValuePrivate::getValue(&object);
if (val)
@@ -441,11 +458,11 @@ void QJSEngine::installExtensions(QJSEngine::Extensions extensions, const QJSVal
*/
QJSValue QJSEngine::evaluate(const QString& program, const QString& fileName, int lineNumber)
{
- QV4::ExecutionEngine *v4 = d->m_v4Engine;
+ QV4::ExecutionEngine *v4 = m_v4Engine;
QV4::Scope scope(v4);
QV4::ScopedValue result(scope);
- QV4::Script script(v4->rootContext(), QV4::Compiler::EvalCode, program, fileName, lineNumber);
+ QV4::Script script(v4->rootContext(), QV4::Compiler::GlobalCode, program, fileName, lineNumber);
script.strictMode = false;
if (v4->currentStackFrame)
script.strictMode = v4->currentStackFrame->v4Function->isStrict();
@@ -473,9 +490,9 @@ QJSValue QJSEngine::evaluate(const QString& program, const QString& fileName, in
*/
QJSValue QJSEngine::newObject()
{
- QV4::Scope scope(d->m_v4Engine);
- QV4::ScopedValue v(scope, d->m_v4Engine->newObject());
- return QJSValue(d->m_v4Engine, v->asReturnedValue());
+ QV4::Scope scope(m_v4Engine);
+ QV4::ScopedValue v(scope, m_v4Engine->newObject());
+ return QJSValue(m_v4Engine, v->asReturnedValue());
}
/*!
@@ -485,12 +502,12 @@ QJSValue QJSEngine::newObject()
*/
QJSValue QJSEngine::newArray(uint length)
{
- QV4::Scope scope(d->m_v4Engine);
- QV4::ScopedArrayObject array(scope, d->m_v4Engine->newArrayObject());
+ QV4::Scope scope(m_v4Engine);
+ QV4::ScopedArrayObject array(scope, m_v4Engine->newArrayObject());
if (length < 0x1000)
array->arrayReserve(length);
array->setArrayLengthUnchecked(length);
- return QJSValue(d->m_v4Engine, array.asReturnedValue());
+ return QJSValue(m_v4Engine, array.asReturnedValue());
}
/*!
@@ -516,7 +533,7 @@ QJSValue QJSEngine::newArray(uint length)
QJSValue QJSEngine::newQObject(QObject *object)
{
Q_D(QJSEngine);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(d);
+ QV4::ExecutionEngine *v4 = m_v4Engine;
QV4::Scope scope(v4);
if (object) {
QQmlData *ddata = QQmlData::get(object, true);
@@ -538,24 +555,24 @@ QJSValue QJSEngine::newQObject(QObject *object)
When called as a constructor, a new instance of the class will be created.
Only constructors exposed by Q_INVOKABLE will be visible from the script engine.
- \sa newQObject()
+ \sa newQObject(), {QObject Integration}
*/
QJSValue QJSEngine::newQMetaObject(const QMetaObject* metaObject) {
Q_D(QJSEngine);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(d);
+ QV4::ExecutionEngine *v4 = m_v4Engine;
QV4::Scope scope(v4);
QV4::ScopedValue v(scope, QV4::QMetaObjectWrapper::create(v4, metaObject));
return QJSValue(v4, v->asReturnedValue());
}
-/*! \fn QJSValue QJSEngine::newQMetaObject<T>()
+/*! \fn template <typename T> QJSValue QJSEngine::newQMetaObject()
\since 5.8
Creates a JavaScript object that wraps the static QMetaObject associated
with class \c{T}.
- \sa newQObject()
+ \sa newQObject(), {QObject Integration}
*/
@@ -571,10 +588,9 @@ QJSValue QJSEngine::newQMetaObject(const QMetaObject* metaObject) {
*/
QJSValue QJSEngine::globalObject() const
{
- Q_D(const QJSEngine);
- QV4::Scope scope(d->m_v4Engine);
- QV4::ScopedValue v(scope, d->m_v4Engine->globalObject);
- return QJSValue(d->m_v4Engine, v->asReturnedValue());
+ QV4::Scope scope(m_v4Engine);
+ QV4::ScopedValue v(scope, m_v4Engine->globalObject);
+ return QJSValue(m_v4Engine, v->asReturnedValue());
}
/*!
@@ -583,10 +599,9 @@ QJSValue QJSEngine::globalObject() const
*/
QJSValue QJSEngine::create(int type, const void *ptr)
{
- Q_D(QJSEngine);
- QV4::Scope scope(d->m_v4Engine);
+ QV4::Scope scope(m_v4Engine);
QV4::ScopedValue v(scope, scope.engine->metaTypeToJS(type, ptr));
- return QJSValue(d->m_v4Engine, v->asReturnedValue());
+ return QJSValue(m_v4Engine, v->asReturnedValue());
}
/*!
@@ -709,14 +724,14 @@ bool QJSEngine::convertV2(const QJSValue &value, int type, void *ptr)
}
}
-/*! \fn QJSValue QJSEngine::toScriptValue(const T &value)
+/*! \fn template <typename T> QJSValue QJSEngine::toScriptValue(const T &value)
Creates a QJSValue with the given \a value.
\sa fromScriptValue()
*/
-/*! \fn T QJSEngine::fromScriptValue(const QJSValue &value)
+/*! \fn template <typename T> T QJSEngine::fromScriptValue(const QJSValue &value)
Returns the given \a value converted to the template type \c{T}.
@@ -726,7 +741,7 @@ bool QJSEngine::convertV2(const QJSValue &value, int type, void *ptr)
QJSEnginePrivate *QJSEnginePrivate::get(QV4::ExecutionEngine *e)
{
- return e->v8Engine->publicEngine()->d_func();
+ return e->jsEngine()->d_func();
}
QJSEnginePrivate::~QJSEnginePrivate()
@@ -768,7 +783,7 @@ QJSEngine *qjsEngine(const QObject *object)
{
QQmlData *data = QQmlData::get(object, false);
if (!data || data->jsWrapper.isNullOrUndefined())
- return 0;
+ return nullptr;
return data->jsWrapper.engine()->jsEngine();
}
diff --git a/src/qml/jsapi/qjsengine.h b/src/qml/jsapi/qjsengine.h
index 913757107f..3ba2b52e89 100644
--- a/src/qml/jsapi/qjsengine.h
+++ b/src/qml/jsapi/qjsengine.h
@@ -52,8 +52,6 @@
QT_BEGIN_NAMESPACE
-class QV8Engine;
-
template <typename T>
inline T qjsvalue_cast(const QJSValue &);
@@ -65,7 +63,7 @@ class Q_QML_EXPORT QJSEngine
public:
QJSEngine();
explicit QJSEngine(QObject *parent);
- virtual ~QJSEngine();
+ ~QJSEngine() override;
QJSValue globalObject() const;
@@ -111,7 +109,7 @@ public:
void installExtensions(Extensions extensions, const QJSValue &object = QJSValue());
- QV8Engine *handle() const { return d; }
+ QV4::ExecutionEngine *handle() const { return m_v4Engine; }
private:
QJSValue create(int type, const void *ptr);
@@ -124,10 +122,9 @@ protected:
QJSEngine(QJSEnginePrivate &dd, QObject *parent = nullptr);
private:
- QV8Engine *d;
+ QV4::ExecutionEngine *m_v4Engine;
Q_DISABLE_COPY(QJSEngine)
Q_DECLARE_PRIVATE(QJSEngine)
- friend class QV8Engine;
};
Q_DECLARE_OPERATORS_FOR_FLAGS(QJSEngine::Extensions)
diff --git a/src/qml/jsapi/qjsengine_p.h b/src/qml/jsapi/qjsengine_p.h
index cbfe0f14a3..360c9df075 100644
--- a/src/qml/jsapi/qjsengine_p.h
+++ b/src/qml/jsapi/qjsengine_p.h
@@ -75,7 +75,7 @@ public:
static QJSEnginePrivate* get(QV4::ExecutionEngine *e);
QJSEnginePrivate() : mutex(QMutex::Recursive) {}
- ~QJSEnginePrivate();
+ ~QJSEnginePrivate() override;
static void addToDebugServer(QJSEngine *q);
static void removeFromDebugServer(QJSEngine *q);
@@ -163,7 +163,7 @@ QQmlPropertyCache until the QQmlEngine is destroyed.
QQmlPropertyCache *QJSEnginePrivate::cache(QObject *obj)
{
if (!obj || QObjectPrivate::get(obj)->metaObject || QObjectPrivate::get(obj)->wasDeleted)
- return 0;
+ return nullptr;
Locker locker(this);
const QMetaObject *mo = obj->metaObject();
diff --git a/src/qml/jsapi/qjsvalue.cpp b/src/qml/jsapi/qjsvalue.cpp
index c1a135c835..b97468ab7b 100644
--- a/src/qml/jsapi/qjsvalue.cpp
+++ b/src/qml/jsapi/qjsvalue.cpp
@@ -67,7 +67,7 @@
QJSValue supports the types defined in the \l{ECMA-262}
standard: The primitive types, which are Undefined, Null, Boolean,
- Number, and String; and the Object type. Additionally, built-in
+ Number, and String; and the Object and Array types. Additionally, built-in
support is provided for Qt/C++ types such as QVariant and QObject.
For the object-based types (including Date and RegExp), use the
@@ -108,6 +108,38 @@
script code, or QJSValueIterator in C++.
\sa QJSEngine, QJSValueIterator
+
+ \section1 Working With Arrays
+
+ To create an array using QJSValue, use \l QJSEngine::newArray():
+
+ \code
+ // Assumes that this class was declared in QML.
+ QJSValue jsArray = engine->newArray(3);
+ \endcode
+
+ To set individual elements in the array, use
+ the \l {QJSValue::}{setProperty(quint32 arrayIndex, const QJSValue &value)}
+ overload. For example, to fill the array above with integers:
+
+ \code
+ for (int i = 0; i < 3; ++i) {
+ jsArray.setProperty(i, QRandomGenerator::global().generate());
+ }
+ \endcode
+
+ To determine the length of the array, access the \c "length" property.
+ To access array elements, use the
+ \l {QJSValue::}{property(quint32 arrayIndex)} overload. The following code
+ reads the array we created above back into a list:
+
+ \code
+ QVector<int> integers;
+ const int length = jsArray.property("length").toInt();
+ for (int i = 0; i < length; ++i) {
+ integers.append(jsArray.property(i).toInt());
+ }
+ \endcode
*/
/*!
@@ -232,7 +264,7 @@ QJSValue::QJSValue(const QJSValue& other)
*/
/*!
- \fn QJSValue &operator=(QJSValue && other)
+ \fn QJSValue &QJSValue::operator=(QJSValue && other)
Move-assigns \a other to this QJSValue object.
*/
@@ -630,7 +662,7 @@ QVariant QJSValue::toVariant() const
return QVariant(val->asDouble());
}
if (val->isNull())
- return QVariant(QMetaType::Nullptr, 0);
+ return QVariant(QMetaType::Nullptr, nullptr);
Q_ASSERT(val->isUndefined());
return QVariant();
}
@@ -799,7 +831,7 @@ QJSEngine* QJSValue::engine() const
QV4::ExecutionEngine *engine = QJSValuePrivate::engine(this);
if (engine)
return engine->jsEngine();
- return 0;
+ return nullptr;
}
#endif // QT_DEPRECATED
@@ -852,7 +884,7 @@ void QJSValue::setPrototype(const QJSValue& prototype)
if (!val)
return;
if (val->isNull()) {
- o->setPrototype(0);
+ o->setPrototype(nullptr);
return;
}
@@ -1008,6 +1040,10 @@ bool QJSValue::strictlyEquals(const QJSValue& other) const
occurred, property() returns the value that was thrown (typically
an \c{Error} object).
+ To access array elements, use the
+ \l {QJSValue::}{setProperty(quint32 arrayIndex, const QJSValue &value)}
+ overload instead.
+
\sa setProperty(), hasProperty(), QJSValueIterator
*/
QJSValue QJSValue::property(const QString& name) const
@@ -1039,8 +1075,25 @@ QJSValue QJSValue::property(const QString& name) const
Returns the property at the given \a arrayIndex.
- This function is provided for convenience and performance when
- working with array objects.
+ It is possible to access elements in an array in two ways. The first is to
+ use the array index as the property name:
+
+ \code
+ qDebug() << jsValueArray.property(QLatin1String("4")).toString();
+ \endcode
+
+ The second is to use the overload that takes an index:
+
+ \code
+ qDebug() << jsValueArray.property(4).toString();
+ \endcode
+
+ Both of these approaches achieve the same result, except that the latter:
+
+ \list
+ \li Is easier to use (can use an integer directly)
+ \li Is faster (no conversion to integer)
+ \endlist
If this QJSValue is not an Array object, this function behaves
as if property() was called with the string representation of \a
@@ -1072,6 +1125,10 @@ QJSValue QJSValue::property(quint32 arrayIndex) const
If this QJSValue does not already have a property with name \a name,
a new property is created.
+ To modify array elements, use the
+ \l {QJSValue::}{setProperty(quint32 arrayIndex, const QJSValue &value)}
+ overload instead.
+
\sa property(), deleteProperty()
*/
void QJSValue::setProperty(const QString& name, const QJSValue& value)
@@ -1109,12 +1166,31 @@ void QJSValue::setProperty(const QString& name, const QJSValue& value)
Sets the property at the given \a arrayIndex to the given \a value.
- This function is provided for convenience and performance when
- working with array objects.
+ It is possible to modify elements in an array in two ways. The first is to
+ use the array index as the property name:
+
+ \code
+ jsValueArray.setProperty(QLatin1String("4"), value);
+ \endcode
+
+ The second is to use the overload that takes an index:
+
+ \code
+ jsValueArray.setProperty(4, value);
+ \endcode
+
+ Both of these approaches achieve the same result, except that the latter:
+
+ \list
+ \li Is easier to use (can use an integer directly)
+ \li Is faster (no conversion to integer)
+ \endlist
If this QJSValue is not an Array object, this function behaves
as if setProperty() was called with the string representation of \a
arrayIndex.
+
+ \sa {QJSValue::}{property(quint32 arrayIndex)}, {Working With Arrays}
*/
void QJSValue::setProperty(quint32 arrayIndex, const QJSValue& value)
{
@@ -1232,11 +1308,11 @@ QObject *QJSValue::toQObject() const
{
QV4::ExecutionEngine *engine = QJSValuePrivate::engine(this);
if (!engine)
- return 0;
+ return nullptr;
QV4::Scope scope(engine);
QV4::Scoped<QV4::QObjectWrapper> wrapper(scope, QJSValuePrivate::getValue(this));
if (!wrapper)
- return 0;
+ return nullptr;
return wrapper->object();
}
@@ -1253,11 +1329,11 @@ const QMetaObject *QJSValue::toQMetaObject() const
{
QV4::ExecutionEngine *engine = QJSValuePrivate::engine(this);
if (!engine)
- return 0;
+ return nullptr;
QV4::Scope scope(engine);
QV4::Scoped<QV4::QMetaObjectWrapper> wrapper(scope, QJSValuePrivate::getValue(this));
if (!wrapper)
- return 0;
+ return nullptr;
return wrapper->metaObject();
}
@@ -1313,7 +1389,7 @@ bool QJSValue::isRegExp() const
bool QJSValue::isQObject() const
{
QV4::Value *val = QJSValuePrivate::getValue(this);
- return val && val->as<QV4::QObjectWrapper>() != 0;
+ return val && val->as<QV4::QObjectWrapper>() != nullptr;
}
/*!
@@ -1327,7 +1403,7 @@ bool QJSValue::isQObject() const
bool QJSValue::isQMetaObject() const
{
QV4::Value *val = QJSValuePrivate::getValue(this);
- return val && val->as<QV4::QMetaObjectWrapper>() != 0;
+ return val && val->as<QV4::QMetaObjectWrapper>() != nullptr;
}
QT_END_NAMESPACE
diff --git a/src/qml/jsapi/qjsvalue_p.h b/src/qml/jsapi/qjsvalue_p.h
index c4761ad6ea..62e09f72be 100644
--- a/src/qml/jsapi/qjsvalue_p.h
+++ b/src/qml/jsapi/qjsvalue_p.h
@@ -68,7 +68,7 @@ public:
static inline QV4::Value *getValue(const QJSValue *jsval)
{
if (jsval->d & 3)
- return 0;
+ return nullptr;
return reinterpret_cast<QV4::Value *>(jsval->d);
}
@@ -76,7 +76,7 @@ public:
{
if (jsval->d & 1)
return reinterpret_cast<QVariant *>(jsval->d & ~3);
- return 0;
+ return nullptr;
}
static inline void setVariant(QJSValue *jsval, const QVariant &v) {
@@ -153,14 +153,14 @@ public:
*v = QV4::Encode(variant->toUInt());
break;
default:
- return 0;
+ return nullptr;
}
return v;
}
static QV4::ExecutionEngine *engine(const QJSValue *jsval) {
QV4::Value *v = getValue(jsval);
- return v ? QV4::PersistentValueStorage::getEngine(v) : 0;
+ return v ? QV4::PersistentValueStorage::getEngine(v) : nullptr;
}
static inline bool checkEngine(QV4::ExecutionEngine *e, const QJSValue &jsval) {
diff --git a/src/qml/jsruntime/jsruntime.pri b/src/qml/jsruntime/jsruntime.pri
index 519c87d0c4..4bc877bd9d 100644
--- a/src/qml/jsruntime/jsruntime.pri
+++ b/src/qml/jsruntime/jsruntime.pri
@@ -41,7 +41,8 @@ SOURCES += \
$$PWD/qv4qobjectwrapper.cpp \
$$PWD/qv4arraybuffer.cpp \
$$PWD/qv4typedarray.cpp \
- $$PWD/qv4dataview.cpp
+ $$PWD/qv4dataview.cpp \
+ $$PWD/qv4vme_moth.cpp
qtConfig(qml-debug): SOURCES += $$PWD/qv4profiling.cpp
@@ -94,14 +95,8 @@ HEADERS += \
$$PWD/qv4profiling_p.h \
$$PWD/qv4arraybuffer_p.h \
$$PWD/qv4typedarray_p.h \
- $$PWD/qv4dataview_p.h
-
-qtConfig(qml-interpreter) {
- HEADERS += \
- $$PWD/qv4vme_moth_p.h
- SOURCES += \
- $$PWD/qv4vme_moth.cpp
-}
+ $$PWD/qv4dataview_p.h \
+ $$PWD/qv4vme_moth_p.h
}
diff --git a/src/qml/jsruntime/qv4arraybuffer.cpp b/src/qml/jsruntime/qv4arraybuffer.cpp
index f7b9e8acef..c4eddb6b2a 100644
--- a/src/qml/jsruntime/qv4arraybuffer.cpp
+++ b/src/qml/jsruntime/qv4arraybuffer.cpp
@@ -96,7 +96,7 @@ void Heap::ArrayBuffer::init(size_t length)
Object::init();
data = QTypedArrayData<char>::allocate(length + 1);
if (!data) {
- data = 0;
+ data = nullptr;
internalClass->engine->throwRangeError(QStringLiteral("ArrayBuffer: out of memory"));
return;
}
@@ -152,7 +152,7 @@ void ArrayBufferPrototype::init(ExecutionEngine *engine, Object *ctor)
ctor->defineReadonlyProperty(engine->id_prototype(), (o = this));
ctor->defineDefaultProperty(QStringLiteral("isView"), ArrayBufferCtor::method_isView, 1);
defineDefaultProperty(engine->id_constructor(), (o = ctor));
- defineAccessorProperty(QStringLiteral("byteLength"), method_get_byteLength, 0);
+ defineAccessorProperty(QStringLiteral("byteLength"), method_get_byteLength, nullptr);
defineDefaultProperty(QStringLiteral("slice"), method_slice, 2);
defineDefaultProperty(QStringLiteral("toString"), method_toString, 0);
}
diff --git a/src/qml/jsruntime/qv4arraybuffer_p.h b/src/qml/jsruntime/qv4arraybuffer_p.h
index e236a23d1f..59e78ee85f 100644
--- a/src/qml/jsruntime/qv4arraybuffer_p.h
+++ b/src/qml/jsruntime/qv4arraybuffer_p.h
@@ -93,8 +93,8 @@ struct Q_QML_PRIVATE_EXPORT ArrayBuffer : Object
QByteArray asByteArray() const;
uint byteLength() const { return d()->byteLength(); }
- char *data() { detach(); return d()->data ? d()->data->data() : 0; }
- const char *constData() { detach(); return d()->data ? d()->data->data() : 0; }
+ char *data() { detach(); return d()->data ? d()->data->data() : nullptr; }
+ const char *constData() { detach(); return d()->data ? d()->data->data() : nullptr; }
private:
void detach();
diff --git a/src/qml/jsruntime/qv4arraydata.cpp b/src/qml/jsruntime/qv4arraydata.cpp
index 390840fb1e..30c8527f21 100644
--- a/src/qml/jsruntime/qv4arraydata.cpp
+++ b/src/qml/jsruntime/qv4arraydata.cpp
@@ -50,7 +50,7 @@ using namespace QV4;
QT_WARNING_SUPPRESS_GCC_TAUTOLOGICAL_COMPARE_ON
const QV4::VTable QV4::ArrayData::static_vtbl = {
- 0,
+ nullptr,
0,
0,
QV4::ArrayData::IsExecutionContext,
@@ -69,7 +69,7 @@ const QV4::VTable QV4::ArrayData::static_vtbl = {
const ArrayVTable SimpleArrayData::static_vtbl =
{
- DEFINE_MANAGED_VTABLE_INT(SimpleArrayData, 0),
+ DEFINE_MANAGED_VTABLE_INT(SimpleArrayData, nullptr),
Heap::ArrayData::Simple,
SimpleArrayData::reallocate,
SimpleArrayData::get,
@@ -85,7 +85,7 @@ const ArrayVTable SimpleArrayData::static_vtbl =
const ArrayVTable SparseArrayData::static_vtbl =
{
- DEFINE_MANAGED_VTABLE_INT(SparseArrayData, 0),
+ DEFINE_MANAGED_VTABLE_INT(SparseArrayData, nullptr),
Heap::ArrayData::Sparse,
SparseArrayData::reallocate,
SparseArrayData::get,
@@ -170,7 +170,7 @@ void ArrayData::realloc(Object *o, Type newType, uint requested, bool enforceAtt
newData->setType(newType);
if (d)
newData->d()->needsMark = d->d()->needsMark;
- newData->setAttrs(enforceAttributes ? reinterpret_cast<PropertyAttributes *>(newData->d()->values.values + alloc) : 0);
+ newData->setAttrs(enforceAttributes ? reinterpret_cast<PropertyAttributes *>(newData->d()->values.values + alloc) : nullptr);
o->setArrayData(newData);
if (d) {
@@ -203,12 +203,11 @@ void ArrayData::realloc(Object *o, Type newType, uint requested, bool enforceAtt
if (d && d->type() == Heap::ArrayData::Sparse) {
Heap::SparseArrayData *old = static_cast<Heap::SparseArrayData *>(d->d());
sparse->sparse = old->sparse;
- old->sparse = 0;
- sparse->freeList = old->freeList;
- lastFree = &sparse->freeList;
+ old->sparse = nullptr;
+ lastFree = &sparse->sparse->freeList;
} else {
sparse->sparse = new SparseArray;
- lastFree = &sparse->freeList;
+ lastFree = &sparse->sparse->freeList;
storeValue(lastFree, 0);
for (uint i = 0; i < toCopy; ++i) {
if (!sparse->values[i].isEmpty()) {
@@ -228,10 +227,10 @@ void ArrayData::realloc(Object *o, Type newType, uint requested, bool enforceAtt
sparse->values.values[i].setEmpty();
lastFree = &sparse->values.values[i].rawValueRef();
}
- storeValue(lastFree, UINT_MAX);
}
+ storeValue(lastFree, UINT_MAX);
- Q_ASSERT(Value::fromReturnedValue(sparse->freeList).isEmpty());
+ Q_ASSERT(Value::fromReturnedValue(sparse->sparse->freeList).isEmpty());
// ### Could explicitly free the old data
}
@@ -373,12 +372,12 @@ void SparseArrayData::free(Heap::ArrayData *d, uint idx)
Value *v = d->values.values + idx;
if (d->attrs && d->attrs[idx].isAccessor()) {
// double slot, free both. Order is important, so we have a double slot for allocation again afterwards.
- v[1].setEmpty(Value::fromReturnedValue(d->freeList).emptyValue());
+ v[1].setEmpty(Value::fromReturnedValue(d->sparse->freeList).emptyValue());
v[0].setEmpty(idx + 1);
} else {
- v->setEmpty(Value::fromReturnedValue(d->freeList).emptyValue());
+ v->setEmpty(Value::fromReturnedValue(d->sparse->freeList).emptyValue());
}
- d->freeList = Primitive::emptyValue(idx).asReturnedValue();
+ d->sparse->freeList = Primitive::emptyValue(idx).asReturnedValue();
if (d->attrs)
d->attrs[idx].clear();
}
@@ -395,12 +394,12 @@ uint SparseArrayData::allocate(Object *o, bool doubleSlot)
Q_ASSERT(o->d()->arrayData->type == Heap::ArrayData::Sparse);
Heap::SimpleArrayData *dd = o->d()->arrayData.cast<Heap::SimpleArrayData>();
if (doubleSlot) {
- ReturnedValue *last = &dd->freeList;
+ ReturnedValue *last = &dd->sparse->freeList;
while (1) {
if (Value::fromReturnedValue(*last).value() == UINT_MAX) {
reallocate(o, dd->values.alloc + 2, true);
dd = o->d()->arrayData.cast<Heap::SimpleArrayData>();
- last = &dd->freeList;
+ last = &dd->sparse->freeList;
Q_ASSERT(Value::fromReturnedValue(*last).value() != UINT_MAX);
}
@@ -417,14 +416,14 @@ uint SparseArrayData::allocate(Object *o, bool doubleSlot)
last = &dd->values.values[Value::fromReturnedValue(*last).value()].rawValueRef();
}
} else {
- if (Value::fromReturnedValue(dd->freeList).value() == UINT_MAX) {
+ if (Value::fromReturnedValue(dd->sparse->freeList).value() == UINT_MAX) {
reallocate(o, dd->values.alloc + 1, false);
dd = o->d()->arrayData.cast<Heap::SimpleArrayData>();
}
- uint idx = Value::fromReturnedValue(dd->freeList).value();
+ uint idx = Value::fromReturnedValue(dd->sparse->freeList).value();
Q_ASSERT(idx != UINT_MAX);
- dd->freeList = dd->values[idx].asReturnedValue();
- Q_ASSERT(Value::fromReturnedValue(dd->freeList).isEmpty());
+ dd->sparse->freeList = dd->values[idx].asReturnedValue();
+ Q_ASSERT(Value::fromReturnedValue(dd->sparse->freeList).isEmpty());
if (dd->attrs)
dd->attrs[idx] = Attr_Data;
return idx;
@@ -479,14 +478,14 @@ bool SparseArrayData::del(Object *o, uint index)
if (isAccessor) {
// free up both indices
- dd->values.values[pidx + 1].setEmpty(Value::fromReturnedValue(dd->freeList).emptyValue());
+ dd->values.values[pidx + 1].setEmpty(Value::fromReturnedValue(dd->sparse->freeList).emptyValue());
dd->values.values[pidx].setEmpty(pidx + 1);
} else {
Q_ASSERT(dd->type == Heap::ArrayData::Sparse);
- dd->values.values[pidx].setEmpty(Value::fromReturnedValue(dd->freeList).emptyValue());
+ dd->values.values[pidx].setEmpty(Value::fromReturnedValue(dd->sparse->freeList).emptyValue());
}
- dd->freeList = Primitive::emptyValue(pidx).asReturnedValue();
+ dd->sparse->freeList = Primitive::emptyValue(pidx).asReturnedValue();
dd->sparse->erase(n);
return true;
}
@@ -780,7 +779,7 @@ void ArrayData::sort(ExecutionEngine *engine, Object *thisObject, const Value &c
if (!sparse->sparse()->nEntries())
return;
- thisObject->setArrayData(0);
+ thisObject->setArrayData(nullptr);
ArrayData::realloc(thisObject, Heap::ArrayData::Simple, sparse->sparse()->nEntries(), sparse->attrs() ? true : false);
Heap::SimpleArrayData *d = thisObject->d()->arrayData.cast<Heap::SimpleArrayData>();
diff --git a/src/qml/jsruntime/qv4arraydata_p.h b/src/qml/jsruntime/qv4arraydata_p.h
index db9db5a220..9356670b6d 100644
--- a/src/qml/jsruntime/qv4arraydata_p.h
+++ b/src/qml/jsruntime/qv4arraydata_p.h
@@ -95,7 +95,6 @@ namespace Heap {
Member(class, NoMark, ushort, needsMark) \
Member(class, NoMark, uint, offset) \
Member(class, NoMark, PropertyAttributes *, attrs) \
- Member(class, NoMark, ReturnedValue, freeList) \
Member(class, NoMark, SparseArray *, sparse) \
Member(class, ValueArray, ValueArray, values)
@@ -142,7 +141,7 @@ DECLARE_HEAP_OBJECT(ArrayData, Base) {
uint mappedIndex(uint index) const;
};
-V4_ASSERT_IS_TRIVIAL(ArrayData)
+Q_STATIC_ASSERT(std::is_trivial< ArrayData >::value);
struct SimpleArrayData : public ArrayData {
uint mappedIndex(uint index) const { index += offset; if (index >= values.alloc) index -= values.alloc; return index; }
@@ -157,7 +156,7 @@ struct SimpleArrayData : public ArrayData {
return attrs ? attrs[i] : Attr_Data;
}
};
-V4_ASSERT_IS_TRIVIAL(SimpleArrayData)
+Q_STATIC_ASSERT(std::is_trivial< SimpleArrayData >::value);
struct SparseArrayData : public ArrayData {
void destroy() {
@@ -264,8 +263,6 @@ struct Q_QML_EXPORT SparseArrayData : public ArrayData
V4_INTERNALCLASS(SparseArrayData)
V4_NEEDS_DESTROY
- ReturnedValue &freeList() { return d()->freeList; }
- ReturnedValue freeList() const { return d()->freeList; }
SparseArray *sparse() const { return d()->sparse; }
void setSparse(SparseArray *s) { d()->sparse = s; }
@@ -334,7 +331,7 @@ ArrayData::Index ArrayData::getValueOrSetter(uint index, PropertyAttributes *att
uint idx = mappedIndex(index);
if (idx == UINT_MAX) {
*attrs = Attr_Invalid;
- return { 0, 0 };
+ return { nullptr, 0 };
}
*attrs = attributes(index);
diff --git a/src/qml/jsruntime/qv4context.cpp b/src/qml/jsruntime/qv4context.cpp
index 00d816fe91..020e519e74 100644
--- a/src/qml/jsruntime/qv4context.cpp
+++ b/src/qml/jsruntime/qv4context.cpp
@@ -302,7 +302,7 @@ ReturnedValue ExecutionContext::getProperty(String *name)
ReturnedValue ExecutionContext::getPropertyAndBase(String *name, Value *base)
{
- base->setM(0);
+ base->setM(nullptr);
name->makeIdentifier();
Heap::ExecutionContext *ctx = d();
diff --git a/src/qml/jsruntime/qv4context_p.h b/src/qml/jsruntime/qv4context_p.h
index 4efd0bc899..512bfa06d8 100644
--- a/src/qml/jsruntime/qv4context_p.h
+++ b/src/qml/jsruntime/qv4context_p.h
@@ -143,7 +143,7 @@ DECLARE_HEAP_OBJECT(ExecutionContext, Base) {
quint8 padding_[4];
#endif
};
-V4_ASSERT_IS_TRIVIAL(ExecutionContext)
+Q_STATIC_ASSERT(std::is_trivial< ExecutionContext >::value);
Q_STATIC_ASSERT(sizeof(ExecutionContext) == sizeof(Base) + sizeof(ExecutionContextData) + QT_POINTER_SIZE);
Q_STATIC_ASSERT(std::is_standard_layout<ExecutionContextData>::value);
@@ -170,7 +170,7 @@ DECLARE_HEAP_OBJECT(CallContext, ExecutionContext) {
}
void setArg(uint index, Value v);
};
-V4_ASSERT_IS_TRIVIAL(CallContext)
+Q_STATIC_ASSERT(std::is_trivial< CallContext >::value);
Q_STATIC_ASSERT(std::is_standard_layout<CallContextData>::value);
Q_STATIC_ASSERT(offsetof(CallContextData, function) == 0);
//### The following size check fails on Win8. With the ValueArray at the end of the
@@ -190,7 +190,7 @@ DECLARE_HEAP_OBJECT(CatchContext, ExecutionContext) {
void init(ExecutionContext *outerContext, String *exceptionVarName, const Value &exceptionValue);
};
-V4_ASSERT_IS_TRIVIAL(CatchContext)
+Q_STATIC_ASSERT(std::is_trivial< CatchContext >::value);
}
@@ -246,12 +246,12 @@ struct CatchContext : public ExecutionContext
inline CallContext *ExecutionContext::asCallContext()
{
- return d()->type == Heap::ExecutionContext::Type_CallContext ? static_cast<CallContext *>(this) : 0;
+ return d()->type == Heap::ExecutionContext::Type_CallContext ? static_cast<CallContext *>(this) : nullptr;
}
inline const CallContext *ExecutionContext::asCallContext() const
{
- return d()->type == Heap::ExecutionContext::Type_CallContext ? static_cast<const CallContext *>(this) : 0;
+ return d()->type == Heap::ExecutionContext::Type_CallContext ? static_cast<const CallContext *>(this) : nullptr;
}
} // namespace QV4
diff --git a/src/qml/jsruntime/qv4dataview.cpp b/src/qml/jsruntime/qv4dataview.cpp
index 397ef1cfec..d894d909ff 100644
--- a/src/qml/jsruntime/qv4dataview.cpp
+++ b/src/qml/jsruntime/qv4dataview.cpp
@@ -88,9 +88,9 @@ void DataViewPrototype::init(ExecutionEngine *engine, Object *ctor)
ctor->defineReadonlyProperty(engine->id_length(), Primitive::fromInt32(3));
ctor->defineReadonlyProperty(engine->id_prototype(), (o = this));
defineDefaultProperty(engine->id_constructor(), (o = ctor));
- defineAccessorProperty(QStringLiteral("buffer"), method_get_buffer, 0);
- defineAccessorProperty(QStringLiteral("byteLength"), method_get_byteLength, 0);
- defineAccessorProperty(QStringLiteral("byteOffset"), method_get_byteOffset, 0);
+ defineAccessorProperty(QStringLiteral("buffer"), method_get_buffer, nullptr);
+ defineAccessorProperty(QStringLiteral("byteLength"), method_get_byteLength, nullptr);
+ defineAccessorProperty(QStringLiteral("byteOffset"), method_get_byteOffset, nullptr);
defineDefaultProperty(QStringLiteral("getInt8"), method_getChar<signed char>, 0);
defineDefaultProperty(QStringLiteral("getUint8"), method_getChar<unsigned char>, 0);
diff --git a/src/qml/jsruntime/qv4dateobject.cpp b/src/qml/jsruntime/qv4dateobject.cpp
index b8392d27e9..bc9b3013d1 100644
--- a/src/qml/jsruntime/qv4dateobject.cpp
+++ b/src/qml/jsruntime/qv4dateobject.cpp
@@ -328,7 +328,7 @@ static inline double DaylightSavingTA(double t) // t is a UTC time
static inline double DaylightSavingTA(double t)
{
struct tm tmtm;
-#if defined(_MSC_VER) && _MSC_VER >= 1400
+#if defined(Q_CC_MSVC)
__time64_t tt = (__time64_t)(t / msPerSecond);
// _localtime_64_s returns non-zero on failure
if (_localtime64_s(&tmtm, &tt) != 0)
@@ -854,7 +854,7 @@ void DatePrototype::init(ExecutionEngine *engine, Object *ctor)
ScopedString us(scope, engine->newIdentifier(toUtcString));
ScopedString gs(scope, engine->newIdentifier(toGmtString));
ExecutionContext *global = engine->rootContext();
- ScopedFunctionObject toUtcGmtStringFn(scope, BuiltinFunction::create(global, us, method_toUTCString));
+ ScopedFunctionObject toUtcGmtStringFn(scope, FunctionObject::createBuiltinFunction(global, us, method_toUTCString));
toUtcGmtStringFn->defineReadonlyConfigurableProperty(engine->id_length(), Primitive::fromInt32(0));
defineDefaultProperty(us, toUtcGmtStringFn);
defineDefaultProperty(gs, toUtcGmtStringFn);
diff --git a/src/qml/jsruntime/qv4dateobject_p.h b/src/qml/jsruntime/qv4dateobject_p.h
index a4ab0a27ed..2b9a580288 100644
--- a/src/qml/jsruntime/qv4dateobject_p.h
+++ b/src/qml/jsruntime/qv4dateobject_p.h
@@ -101,7 +101,7 @@ struct DateObject: Object {
template<>
inline const DateObject *Value::as() const {
- return isManaged() && m()->vtable()->type == Managed::Type_DateObject ? static_cast<const DateObject *>(this) : 0;
+ return isManaged() && m()->vtable()->type == Managed::Type_DateObject ? static_cast<const DateObject *>(this) : nullptr;
}
struct DateCtor: FunctionObject
diff --git a/src/qml/jsruntime/qv4debugging_p.h b/src/qml/jsruntime/qv4debugging_p.h
index 61a55964ab..9b41bb6e7a 100644
--- a/src/qml/jsruntime/qv4debugging_p.h
+++ b/src/qml/jsruntime/qv4debugging_p.h
@@ -78,7 +78,7 @@ class Q_QML_EXPORT Debugger : public QObject
Q_OBJECT
public:
- virtual ~Debugger() {}
+ ~Debugger() override {}
virtual bool pauseAtNextOpportunity() const = 0;
virtual void maybeBreakAtInstruction() = 0;
virtual void enteringFunction() = 0;
diff --git a/src/qml/jsruntime/qv4engine.cpp b/src/qml/jsruntime/qv4engine.cpp
index c57f39f61c..5f59e1e809 100644
--- a/src/qml/jsruntime/qv4engine.cpp
+++ b/src/qml/jsruntime/qv4engine.cpp
@@ -101,7 +101,7 @@ using namespace QV4;
static QBasicAtomicInt engineSerial = Q_BASIC_ATOMIC_INITIALIZER(1);
-ReturnedValue throwTypeError(const BuiltinFunction *b, CallData *)
+ReturnedValue throwTypeError(const FunctionObject *b, const QV4::Value *, const QV4::Value *, int)
{
return b->engine()->throwTypeError();
}
@@ -127,13 +127,16 @@ ExecutionEngine::ExecutionEngine()
, bumperPointerAllocator(new WTF::BumpPointerAllocator)
, jsStack(new WTF::PageAllocation)
, gcStack(new WTF::PageAllocation)
- , globalCode(0)
- , v8Engine(0)
- , argumentsAccessors(0)
+ , globalCode(nullptr)
+ , v8Engine(nullptr)
+ , argumentsAccessors(nullptr)
, nArgumentsAccessors(0)
, m_engineId(engineSerial.fetchAndAddOrdered(1))
- , regExpCache(0)
- , m_multiplyWrappedQObjects(0)
+ , regExpCache(nullptr)
+ , m_multiplyWrappedQObjects(nullptr)
+#if defined(V4_ENABLE_JIT) && !defined(V4_BOOTSTRAP)
+ , m_canAllocateExecutableMemory(OSAllocator::canAllocateExecutableMemory())
+#endif
{
memoryManager = new QV4::MemoryManager(this);
@@ -168,6 +171,15 @@ ExecutionEngine::ExecutionEngine()
/* writable */ true, /* executable */ false,
/* includesGuardPages */ true);
+ {
+ bool ok = false;
+ jitCallCountThreshold = qEnvironmentVariableIntValue("QV4_JIT_CALL_THRESHOLD", &ok);
+ if (!ok)
+ jitCallCountThreshold = 3;
+ if (qEnvironmentVariableIsSet("QV4_FORCE_INTERPRETER"))
+ jitCallCountThreshold = std::numeric_limits<int>::max();
+ }
+
exceptionValue = jsAlloca(1);
globalObject = static_cast<Object *>(jsAlloca(1));
jsObjects = jsAlloca(NJSObjects);
@@ -188,6 +200,7 @@ ExecutionEngine::ExecutionEngine()
internalClasses[Class_SimpleArrayData] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::SimpleArrayData::staticVTable());
internalClasses[Class_SparseArrayData] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::SparseArrayData::staticVTable());
internalClasses[Class_ExecutionContext] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::ExecutionContext::staticVTable());
+ internalClasses[Class_QmlContext] = internalClasses[EngineBase::Class_ExecutionContext]->changeVTable(QV4::QmlContext::staticVTable());
internalClasses[Class_CallContext] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::CallContext::staticVTable());
jsStrings[String_Empty] = newIdentifier(QString());
@@ -230,6 +243,7 @@ ExecutionEngine::ExecutionEngine()
InternalClass *ic = internalClasses[Class_Empty]->changeVTable(QV4::Object::staticVTable());
jsObjects[ObjectProto] = memoryManager->allocObject<ObjectPrototype>(ic);
internalClasses[Class_Object] = ic->changePrototype(objectPrototype()->d());
+ internalClasses[EngineBase::Class_QmlContextWrapper] = internalClasses[Class_Object]->changeVTable(QV4::QQmlContextWrapper::staticVTable());
ic = newInternalClass(ArrayPrototype::staticVTable(), objectPrototype());
Q_ASSERT(ic->prototype);
@@ -275,8 +289,6 @@ ExecutionEngine::ExecutionEngine()
ic = ic->changeVTable(ScriptFunction::staticVTable());
internalClasses[EngineBase::Class_ScriptFunction] = ic->addMember(id_length(), Attr_ReadOnly, &index);
Q_ASSERT(index == Heap::ScriptFunction::Index_Length);
- internalClasses[EngineBase::Class_BuiltinFunction] = ic->changeVTable(BuiltinFunction::staticVTable());
- Q_ASSERT(index == Heap::ScriptFunction::Index_Length);
internalClasses[EngineBase::Class_ObjectProto] = internalClasses[Class_Object]->addMember(id_constructor(), Attr_NotEnumerable, &index);
Q_ASSERT(index == Heap::FunctionObject::Index_ProtoConstructor);
@@ -302,7 +314,7 @@ ExecutionEngine::ExecutionEngine()
internalClasses[EngineBase::Class_RegExpExecArray] = ic->addMember(id_input(), Attr_Data, &index);
Q_ASSERT(index == RegExpObject::Index_ArrayInput);
- ic = newInternalClass(ErrorObject::staticVTable(), 0);
+ ic = newInternalClass(ErrorObject::staticVTable(), nullptr);
ic = ic->addMember((str = newIdentifier(QStringLiteral("stack"))), Attr_Accessor|Attr_NotConfigurable|Attr_NotEnumerable, &index);
Q_ASSERT(index == ErrorObject::Index_Stack);
ic = ic->addMember((str = newIdentifier(QStringLiteral("fileName"))), Attr_Data|Attr_NotEnumerable, &index);
@@ -320,7 +332,7 @@ ExecutionEngine::ExecutionEngine()
internalClasses[EngineBase::Class_ErrorProto] = ic->addMember(id_name(), Attr_Data|Attr_NotEnumerable, &index);
Q_ASSERT(index == ErrorPrototype::Index_Name);
- jsObjects[GetStack_Function] = BuiltinFunction::create(rootContext(), str = newIdentifier(QStringLiteral("stack")), ErrorObject::method_get_stack);
+ jsObjects[GetStack_Function] = FunctionObject::createBuiltinFunction(rootContext(), str = newIdentifier(QStringLiteral("stack")), ErrorObject::method_get_stack);
getStackFunction()->defineReadonlyProperty(id_length(), Primitive::fromInt32(0));
jsObjects[ErrorProto] = memoryManager->allocObject<ErrorPrototype>(internalClasses[EngineBase::Class_ErrorProto], objectPrototype());
@@ -384,8 +396,8 @@ ExecutionEngine::ExecutionEngine()
jsObjects[DataView_Ctor] = memoryManager->allocObject<DataViewCtor>(global);
jsObjects[DataViewProto] = memoryManager->allocObject<DataViewPrototype>();
static_cast<DataViewPrototype *>(dataViewPrototype())->init(this, dataViewCtor());
- jsObjects[ValueTypeProto] = (Heap::Base *) 0;
- jsObjects[SignalHandlerProto] = (Heap::Base *) 0;
+ jsObjects[ValueTypeProto] = (Heap::Base *) nullptr;
+ jsObjects[SignalHandlerProto] = (Heap::Base *) nullptr;
for (int i = 0; i < Heap::TypedArray::NTypes; ++i) {
static_cast<Value &>(typedArrayCtors[i]) = memoryManager->allocObject<TypedArrayCtor>(global, Heap::TypedArray::Type(i));
@@ -442,8 +454,8 @@ ExecutionEngine::ExecutionEngine()
ScopedString pi(scope, newIdentifier(piString));
ScopedString pf(scope, newIdentifier(pfString));
ExecutionContext *global = rootContext();
- ScopedFunctionObject parseIntFn(scope, BuiltinFunction::create(global, pi, GlobalFunctions::method_parseInt));
- ScopedFunctionObject parseFloatFn(scope, BuiltinFunction::create(global, pf, GlobalFunctions::method_parseFloat));
+ ScopedFunctionObject parseIntFn(scope, FunctionObject::createBuiltinFunction(global, pi, GlobalFunctions::method_parseInt));
+ ScopedFunctionObject parseFloatFn(scope, FunctionObject::createBuiltinFunction(global, pf, GlobalFunctions::method_parseFloat));
parseIntFn->defineReadonlyConfigurableProperty(id_length(), Primitive::fromInt32(2));
parseFloatFn->defineReadonlyConfigurableProperty(id_length(), Primitive::fromInt32(1));
globalObject->defineDefaultProperty(piString, parseIntFn);
@@ -462,13 +474,13 @@ ExecutionEngine::ExecutionEngine()
globalObject->defineDefaultProperty(QStringLiteral("unescape"), GlobalFunctions::method_unescape, 1);
ScopedString name(scope, newString(QStringLiteral("thrower")));
- jsObjects[ThrowerObject] = BuiltinFunction::create(global, name, ::throwTypeError);
+ jsObjects[ThrowerObject] = FunctionObject::createBuiltinFunction(global, name, ::throwTypeError);
}
ExecutionEngine::~ExecutionEngine()
{
delete m_multiplyWrappedQObjects;
- m_multiplyWrappedQObjects = 0;
+ m_multiplyWrappedQObjects = nullptr;
delete identifierTable;
delete memoryManager;
@@ -519,7 +531,7 @@ InternalClass *ExecutionEngine::newClass(const InternalClass &other)
InternalClass *ExecutionEngine::newInternalClass(const VTable *vtable, Object *prototype)
{
- return internalClasses[EngineBase::Class_Empty]->changeVTable(vtable)->changePrototype(prototype ? prototype->d() : 0);
+ return internalClasses[EngineBase::Class_Empty]->changeVTable(vtable)->changePrototype(prototype ? prototype->d() : nullptr);
}
Heap::Object *ExecutionEngine::newObject()
@@ -721,18 +733,18 @@ Heap::Object *ExecutionEngine::newForEachIteratorObject(Object *o)
Heap::QmlContext *ExecutionEngine::qmlContext() const
{
if (!currentStackFrame)
- return 0;
+ return nullptr;
Heap::ExecutionContext *ctx = currentContext()->d();
if (ctx->type != Heap::ExecutionContext::Type_QmlContext && !ctx->outer)
- return 0;
+ return nullptr;
while (ctx->outer && ctx->outer->type != Heap::ExecutionContext::Type_GlobalContext)
ctx = ctx->outer;
Q_ASSERT(ctx);
if (ctx->type != Heap::ExecutionContext::Type_QmlContext)
- return 0;
+ return nullptr;
return static_cast<Heap::QmlContext *>(ctx);
}
@@ -741,7 +753,7 @@ QObject *ExecutionEngine::qmlScopeObject() const
{
Heap::QmlContext *ctx = qmlContext();
if (!ctx)
- return 0;
+ return nullptr;
return ctx->qml()->scopeObject;
}
@@ -771,7 +783,7 @@ QQmlContextData *ExecutionEngine::callingQmlContext() const
{
Heap::QmlContext *ctx = qmlContext();
if (!ctx)
- return 0;
+ return nullptr;
return ctx->qml()->context->contextData();
}
@@ -868,14 +880,14 @@ QUrl ExecutionEngine::resolvedUrl(const QString &file)
CppStackFrame *f = currentStackFrame;
while (f) {
if (f->v4Function) {
- base.setUrl(f->v4Function->sourceFile());
+ base = f->v4Function->finalUrl();
break;
}
f = f->parent;
}
if (base.isEmpty() && globalCode)
- base.setUrl(globalCode->sourceFile());
+ base = globalCode->finalUrl();
if (base.isEmpty())
return src;
@@ -898,7 +910,7 @@ void ExecutionEngine::requireArgumentsAccessors(int n)
nArgumentsAccessors = qMax(8, n);
argumentsAccessors = new Property[nArgumentsAccessors];
if (oldAccessors) {
- memcpy(argumentsAccessors, oldAccessors, oldSize*sizeof(Property));
+ memcpy(static_cast<void *>(argumentsAccessors), static_cast<const void *>(oldAccessors), oldSize*sizeof(Property));
delete [] oldAccessors;
}
ExecutionContext *global = rootContext();
@@ -1079,7 +1091,7 @@ QQmlError ExecutionEngine::catchExceptionAsQmlError()
typedef QSet<QV4::Heap::Object *> V4ObjectSet;
static QVariant toVariant(QV4::ExecutionEngine *e, const QV4::Value &value, int typeHint, bool createJSValueForObjects, V4ObjectSet *visitedObjects);
static QObject *qtObjectFromJS(QV4::ExecutionEngine *engine, const QV4::Value &value);
-static QVariant objectToVariant(QV4::ExecutionEngine *e, const QV4::Object *o, V4ObjectSet *visitedObjects = 0);
+static QVariant objectToVariant(QV4::ExecutionEngine *e, const QV4::Object *o, V4ObjectSet *visitedObjects = nullptr);
static bool convertToNativeQObject(QV4::ExecutionEngine *e, const QV4::Value &value,
const QByteArray &targetType,
void **result);
@@ -1093,7 +1105,7 @@ static QV4::ReturnedValue variantToJS(QV4::ExecutionEngine *v4, const QVariant &
QVariant ExecutionEngine::toVariant(const Value &value, int typeHint, bool createJSValueForObjects)
{
- return ::toVariant(this, value, typeHint, createJSValueForObjects, 0);
+ return ::toVariant(this, value, typeHint, createJSValueForObjects, nullptr);
}
@@ -1457,7 +1469,7 @@ static QV4::ReturnedValue variantMapToJS(QV4::ExecutionEngine *v4, const QVarian
// Returns the value if conversion succeeded, an empty handle otherwise.
QV4::ReturnedValue ExecutionEngine::metaTypeToJS(int type, const void *data)
{
- Q_ASSERT(data != 0);
+ Q_ASSERT(data != nullptr);
// check if it's one of the types we know
switch (QMetaType::Type(type)) {
@@ -1545,13 +1557,9 @@ QV4::ReturnedValue ExecutionEngine::metaTypeToJS(int type, const void *data)
return 0;
}
-bool ExecutionEngine::canJIT()
+ReturnedValue ExecutionEngine::global()
{
-#ifdef V4_ENABLE_JIT
- return true;
-#else
- return false;
-#endif
+ return globalObject->asReturnedValue();
}
// Converts a JS value to a meta-type.
@@ -1734,7 +1742,7 @@ bool ExecutionEngine::metaTypeFromJS(const Value *value, int type, void *data)
QByteArray className = name.left(name.size()-1);
QV4::ScopedObject p(scope, proto.getPointer());
if (QObject *qobject = qtObjectFromJS(this, p))
- canCast = qobject->qt_metacast(className) != 0;
+ canCast = qobject->qt_metacast(className) != nullptr;
}
if (canCast) {
QByteArray varTypeName = QMetaType::typeName(var.userType());
@@ -1748,7 +1756,7 @@ bool ExecutionEngine::metaTypeFromJS(const Value *value, int type, void *data)
}
}
} else if (value->isNull() && name.endsWith('*')) {
- *reinterpret_cast<void* *>(data) = 0;
+ *reinterpret_cast<void* *>(data) = nullptr;
return true;
} else if (type == qMetaTypeId<QJSValue>()) {
*reinterpret_cast<QJSValue*>(data) = QJSValue(this, value->asReturnedValue());
@@ -1776,7 +1784,7 @@ static bool convertToNativeQObject(QV4::ExecutionEngine *e, const QV4::Value &va
static QObject *qtObjectFromJS(QV4::ExecutionEngine *engine, const QV4::Value &value)
{
if (!value.isObject())
- return 0;
+ return nullptr;
QV4::Scope scope(engine);
QV4::Scoped<QV4::VariantObject> v(scope, value);
@@ -1789,7 +1797,7 @@ static QObject *qtObjectFromJS(QV4::ExecutionEngine *engine, const QV4::Value &v
}
QV4::Scoped<QV4::QObjectWrapper> wrapper(scope, value);
if (!wrapper)
- return 0;
+ return nullptr;
return wrapper->object();
}
diff --git a/src/qml/jsruntime/qv4engine_p.h b/src/qml/jsruntime/qv4engine_p.h
index 346f290feb..5edf89f720 100644
--- a/src/qml/jsruntime/qv4engine_p.h
+++ b/src/qml/jsruntime/qv4engine_p.h
@@ -56,7 +56,9 @@
#include <private/qintrusivelist_p.h>
#include "qv4enginebase_p.h"
+
#ifndef V4_BOOTSTRAP
+# include "qv4function_p.h"
# include <private/qv8engine_p.h>
# include <private/qv4compileddata_p.h>
#endif
@@ -85,6 +87,7 @@ namespace CompiledData {
struct CompilationUnit;
}
+struct Function;
struct InternalClass;
struct InternalClassPool;
@@ -365,6 +368,9 @@ public:
// but any time a QObject is wrapped a second time in another engine, we have to do
// bookkeeping.
MultiplyWrappedQObjectMap *m_multiplyWrappedQObjects;
+#if defined(V4_ENABLE_JIT) && !defined(V4_BOOTSTRAP)
+ const bool m_canAllocateExecutableMemory;
+#endif
int internalClassIdCount = 0;
@@ -453,7 +459,7 @@ public:
StackTrace exceptionStackTrace;
ReturnedValue throwError(const Value &value);
- ReturnedValue catchException(StackTrace *trace = 0);
+ ReturnedValue catchException(StackTrace *trace = nullptr);
ReturnedValue throwError(const QString &message);
ReturnedValue throwSyntaxError(const QString &message);
@@ -481,13 +487,28 @@ public:
bool checkStackLimits();
- static bool canJIT();
+ bool canJIT(Function *f = nullptr)
+ {
+#if defined(V4_ENABLE_JIT) && !defined(V4_BOOTSTRAP)
+ if (!m_canAllocateExecutableMemory)
+ return false;
+ if (f)
+ return f->interpreterCallCount >= jitCallCountThreshold;
+ return true;
+#else
+ Q_UNUSED(f);
+ return false;
+#endif
+ }
+
+ QV4::ReturnedValue global();
private:
#if QT_CONFIG(qml_debug)
QScopedPointer<QV4::Debugging::Debugger> m_debugger;
QScopedPointer<QV4::Profiling::Profiler> m_profiler;
#endif
+ int jitCallCountThreshold;
};
// This is a trick to tell the code generators that functions taking a NoThrowContext won't
diff --git a/src/qml/jsruntime/qv4enginebase_p.h b/src/qml/jsruntime/qv4enginebase_p.h
index e0f5f3ffb1..59fb4a564a 100644
--- a/src/qml/jsruntime/qv4enginebase_p.h
+++ b/src/qml/jsruntime/qv4enginebase_p.h
@@ -101,7 +101,6 @@ struct Q_QML_EXPORT EngineBase {
Class_FunctionObject,
Class_StringObject,
Class_ScriptFunction,
- Class_BuiltinFunction,
Class_ObjectProto,
Class_RegExp,
Class_RegExpObject,
@@ -111,6 +110,8 @@ struct Q_QML_EXPORT EngineBase {
Class_ErrorObject,
Class_ErrorObjectWithMessage,
Class_ErrorProto,
+ Class_QmlContextWrapper,
+ Class_QmlContext,
NClasses
};
InternalClass *internalClasses[NClasses];
diff --git a/src/qml/jsruntime/qv4errorobject_p.h b/src/qml/jsruntime/qv4errorobject_p.h
index a5ee0eb886..6b578e8c38 100644
--- a/src/qml/jsruntime/qv4errorobject_p.h
+++ b/src/qml/jsruntime/qv4errorobject_p.h
@@ -180,7 +180,7 @@ struct ErrorObject: Object {
template<>
inline const ErrorObject *Value::as() const {
- return isManaged() && m()->vtable()->isErrorObject ? reinterpret_cast<const ErrorObject *>(this) : 0;
+ return isManaged() && m()->vtable()->isErrorObject ? reinterpret_cast<const ErrorObject *>(this) : nullptr;
}
struct EvalErrorObject: ErrorObject {
@@ -322,7 +322,7 @@ struct URIErrorPrototype : ErrorObject
inline SyntaxErrorObject *ErrorObject::asSyntaxError()
{
- return d()->errorType == QV4::Heap::ErrorObject::SyntaxError ? static_cast<SyntaxErrorObject *>(this) : 0;
+ return d()->errorType == QV4::Heap::ErrorObject::SyntaxError ? static_cast<SyntaxErrorObject *>(this) : nullptr;
}
diff --git a/src/qml/jsruntime/qv4executableallocator.cpp b/src/qml/jsruntime/qv4executableallocator.cpp
index 64ac1267ce..6f04a712e6 100644
--- a/src/qml/jsruntime/qv4executableallocator.cpp
+++ b/src/qml/jsruntime/qv4executableallocator.cpp
@@ -159,7 +159,7 @@ ExecutableAllocator::~ExecutableAllocator()
ExecutableAllocator::Allocation *ExecutableAllocator::allocate(size_t size)
{
QMutexLocker locker(&mutex);
- Allocation *allocation = 0;
+ Allocation *allocation = nullptr;
// Code is best aligned to 16-byte boundaries.
size = WTF::roundUpToMultipleOf(16, size);
@@ -217,7 +217,7 @@ void ExecutableAllocator::free(Allocation *allocation)
if (!merged)
freeAllocations.insert(allocation->size, allocation);
- allocation = 0;
+ allocation = nullptr;
if (!chunk->firstAllocation->next) {
freeAllocations.remove(chunk->firstAllocation->size, chunk->firstAllocation);
@@ -235,7 +235,7 @@ ExecutableAllocator::ChunkOfPages *ExecutableAllocator::chunkForAllocation(Alloc
if (it != chunks.begin())
--it;
if (it == chunks.end())
- return 0;
+ return nullptr;
return *it;
}
diff --git a/src/qml/jsruntime/qv4executableallocator_p.h b/src/qml/jsruntime/qv4executableallocator_p.h
index dad02d9560..19eaed8723 100644
--- a/src/qml/jsruntime/qv4executableallocator_p.h
+++ b/src/qml/jsruntime/qv4executableallocator_p.h
@@ -82,11 +82,8 @@ public:
struct Allocation
{
Allocation()
- : addr(0)
- , size(0)
+ : size(0)
, free(true)
- , next(0)
- , prev(0)
{}
void *start() const;
@@ -103,16 +100,16 @@ public:
bool mergeNext(ExecutableAllocator *allocator);
bool mergePrevious(ExecutableAllocator *allocator);
- quintptr addr;
#ifndef QT_NO_BITFIELDS
+ quintptr addr = 0;
uint size : 31; // More than 2GB of function code? nah :)
uint free : 1;
#else
uint size = 31; // More than 2GB of function code? nah :)
uint free = 1;
#endif
- Allocation *next;
- Allocation *prev;
+ Allocation *next = nullptr;
+ Allocation *prev = nullptr;
};
// for debugging / unit-testing
@@ -122,13 +119,12 @@ public:
struct ChunkOfPages
{
ChunkOfPages()
- : pages(0)
- , firstAllocation(0)
+
{}
~ChunkOfPages();
- WTF::PageAllocation *pages;
- Allocation *firstAllocation;
+ WTF::PageAllocation *pages = nullptr;
+ Allocation *firstAllocation = nullptr;
bool contains(Allocation *alloc) const;
};
diff --git a/src/qml/jsruntime/qv4function_p.h b/src/qml/jsruntime/qv4function_p.h
index 0e61be5115..4c8c790ca7 100644
--- a/src/qml/jsruntime/qv4function_p.h
+++ b/src/qml/jsruntime/qv4function_p.h
@@ -83,6 +83,7 @@ struct Q_QML_EXPORT Function {
// first nArguments names in internalClass are the actual arguments
InternalClass *internalClass;
uint nFormals;
+ int interpreterCallCount = 0;
bool hasQmlDependencies;
Function(ExecutionEngine *engine, CompiledData::CompilationUnit *unit, const CompiledData::Function *function, Code codePtr);
@@ -95,6 +96,7 @@ struct Q_QML_EXPORT Function {
return compilationUnit->runtimeStrings[compiledFunction->nameIndex];
}
inline QString sourceFile() const { return compilationUnit->fileName(); }
+ inline QUrl finalUrl() const { return compilationUnit->finalUrl(); }
inline bool usesArgumentsObject() const { return compiledFunction->flags & CompiledData::Function::UsesArgumentsObject; }
inline bool isStrict() const { return compiledFunction->flags & CompiledData::Function::IsStrict; }
diff --git a/src/qml/jsruntime/qv4functionobject.cpp b/src/qml/jsruntime/qv4functionobject.cpp
index 4293d43791..a8c1640767 100644
--- a/src/qml/jsruntime/qv4functionobject.cpp
+++ b/src/qml/jsruntime/qv4functionobject.cpp
@@ -232,7 +232,7 @@ ReturnedValue FunctionCtor::callAsConstructor(const FunctionObject *f, const Val
if (!fe)
return scope.engine->throwSyntaxError(QLatin1String("Parse error"));
- Compiler::Module module(scope.engine->debugger() != 0);
+ Compiler::Module module(scope.engine->debugger() != nullptr);
Compiler::JSUnitGenerator jsGenerator(&module);
RuntimeCodegen cg(scope.engine, &jsGenerator, false);
@@ -351,7 +351,7 @@ ReturnedValue FunctionPrototype::method_bind(const FunctionObject *b, const Valu
return scope.engine->throwTypeError();
ScopedValue boundThis(scope, argc ? argv[0] : Primitive::undefinedValue());
- Scoped<MemberData> boundArgs(scope, (Heap::MemberData *)0);
+ Scoped<MemberData> boundArgs(scope, (Heap::MemberData *)nullptr);
if (argc > 1) {
boundArgs = MemberData::allocate(scope.engine, argc - 1);
boundArgs->d()->values.size = argc - 1;
@@ -430,27 +430,6 @@ InternalClass *ScriptFunction::classForConstructor() const
return ic;
}
-DEFINE_OBJECT_VTABLE(BuiltinFunction);
-
-void Heap::BuiltinFunction::init(QV4::ExecutionContext *scope, QV4::String *name, ReturnedValue (*code)(const QV4::BuiltinFunction *, CallData *))
-{
- Heap::FunctionObject::init(scope, name);
- this->code = code;
-}
-
-ReturnedValue BuiltinFunction::callAsConstructor(const QV4::FunctionObject *f, const Value *, int)
-{
- return f->engine()->throwTypeError();
-}
-
-ReturnedValue BuiltinFunction::call(const FunctionObject *fo, const Value *thisObject, const Value *argv, int argc)
-{
- const BuiltinFunction *f = static_cast<const BuiltinFunction *>(fo);
- Scope scope(f->engine());
- JSCallData callData(scope, argc, argv, thisObject);
- return f->d()->code(f, callData.callData());
-}
-
DEFINE_OBJECT_VTABLE(IndexedBuiltinFunction);
DEFINE_OBJECT_VTABLE(BoundFunction);
@@ -461,7 +440,7 @@ void Heap::BoundFunction::init(QV4::ExecutionContext *scope, QV4::FunctionObject
Scope s(scope);
Heap::FunctionObject::init(scope, QStringLiteral("__bound function__"));
this->target.set(s.engine, target->d());
- this->boundArgs.set(s.engine, boundArgs ? boundArgs->d() : 0);
+ this->boundArgs.set(s.engine, boundArgs ? boundArgs->d() : nullptr);
this->boundThis.set(scope->engine(), boundThis);
ScopedObject f(s, this);
diff --git a/src/qml/jsruntime/qv4functionobject_p.h b/src/qml/jsruntime/qv4functionobject_p.h
index d61006a6b0..d6066ec648 100644
--- a/src/qml/jsruntime/qv4functionobject_p.h
+++ b/src/qml/jsruntime/qv4functionobject_p.h
@@ -61,7 +61,6 @@ struct QQmlSourceLocation;
namespace QV4 {
-struct BuiltinFunction;
struct IndexedBuiltinFunction;
struct JSCallData;
@@ -84,8 +83,8 @@ DECLARE_HEAP_OBJECT(FunctionObject, Object) {
Index_ProtoConstructor = 0
};
- void init(QV4::ExecutionContext *scope, QV4::String *name, ReturnedValue (*code)(const QV4::FunctionObject *, const Value *thisObject, const Value *argv, int argc));
- void init(QV4::ExecutionContext *scope, QV4::String *name = 0, bool createProto = false);
+ Q_QML_PRIVATE_EXPORT void init(QV4::ExecutionContext *scope, QV4::String *name, ReturnedValue (*code)(const QV4::FunctionObject *, const Value *thisObject, const Value *argv, int argc));
+ void init(QV4::ExecutionContext *scope, QV4::String *name = nullptr, bool createProto = false);
void init(QV4::ExecutionContext *scope, QV4::Function *function, bool createProto = false);
void init(QV4::ExecutionContext *scope, const QString &name, bool createProto = false);
void init();
@@ -105,13 +104,8 @@ struct FunctionPrototype : FunctionObject {
void init();
};
-struct Q_QML_EXPORT BuiltinFunction : FunctionObject {
- void init(QV4::ExecutionContext *scope, QV4::String *name, ReturnedValue (*code)(const QV4::BuiltinFunction *, CallData *));
- ReturnedValue (*code)(const QV4::BuiltinFunction *, CallData *);
-};
-
-struct IndexedBuiltinFunction : BuiltinFunction {
- inline void init(QV4::ExecutionContext *scope, uint index, ReturnedValue (*code)(const QV4::BuiltinFunction *, CallData *));
+struct IndexedBuiltinFunction : FunctionObject {
+ inline void init(QV4::ExecutionContext *scope, uint index, ReturnedValue (*code)(const QV4::FunctionObject *, const Value *, const Value *, int));
uint index;
};
@@ -170,6 +164,11 @@ struct Q_QML_EXPORT FunctionObject: Object {
static ReturnedValue call(const FunctionObject *f, const Value *thisObject, const Value *argv, int argc);
static Heap::FunctionObject *createScriptFunction(ExecutionContext *scope, Function *function);
+ static Heap::FunctionObject *createBuiltinFunction(ExecutionContext *scope, String *name,
+ ReturnedValue (*code)(const FunctionObject *, const Value *thisObject, const Value *argv, int argc))
+ {
+ return scope->engine()->memoryManager->allocObject<FunctionObject>(scope, name, code);
+ }
bool strictMode() const { return d()->function ? d()->function->isStrict() : false; }
bool isBinding() const;
@@ -180,7 +179,7 @@ struct Q_QML_EXPORT FunctionObject: Object {
template<>
inline const FunctionObject *Value::as() const {
- return isManaged() && m()->vtable()->isFunctionObject ? reinterpret_cast<const FunctionObject *>(this) : 0;
+ return isManaged() && m()->vtable()->isFunctionObject ? reinterpret_cast<const FunctionObject *>(this) : nullptr;
}
@@ -204,34 +203,16 @@ struct FunctionPrototype: FunctionObject
static ReturnedValue method_bind(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
};
-struct Q_QML_EXPORT BuiltinFunction : FunctionObject {
- V4_OBJECT2(BuiltinFunction, FunctionObject)
- V4_INTERNALCLASS(BuiltinFunction)
-
- static Heap::BuiltinFunction *create(ExecutionContext *scope, String *name, ReturnedValue (*code)(const BuiltinFunction *, CallData *))
- {
- return scope->engine()->memoryManager->allocObject<BuiltinFunction>(scope, name, code);
- }
-
- static Heap::FunctionObject *create(ExecutionContext *scope, String *name, ReturnedValue (*code)(const FunctionObject *, const Value *thisObject, const Value *argv, int argc))
- {
- return scope->engine()->memoryManager->allocObject<FunctionObject>(scope, name, code);
- }
-
- static ReturnedValue callAsConstructor(const FunctionObject *, const Value *argv, int argc);
- static ReturnedValue call(const FunctionObject *f, const Value *thisObject, const Value *argv, int argc);
-};
-
-struct IndexedBuiltinFunction: BuiltinFunction
+struct IndexedBuiltinFunction : FunctionObject
{
- V4_OBJECT2(IndexedBuiltinFunction, BuiltinFunction)
+ V4_OBJECT2(IndexedBuiltinFunction, FunctionObject)
};
void Heap::IndexedBuiltinFunction::init(QV4::ExecutionContext *scope, uint index,
- ReturnedValue (*code)(const QV4::BuiltinFunction *, CallData *))
+ ReturnedValue (*code)(const QV4::FunctionObject *, const Value *thisObject, const Value *argv, int argc))
{
Heap::FunctionObject::init(scope);
- this->code = code;
+ this->jsCall = code;
this->index = index;
}
diff --git a/src/qml/jsruntime/qv4global_p.h b/src/qml/jsruntime/qv4global_p.h
index 29eddc864d..382dd9b7e1 100644
--- a/src/qml/jsruntime/qv4global_p.h
+++ b/src/qml/jsruntime/qv4global_p.h
@@ -76,9 +76,6 @@ namespace std {
inline bool isinf(double d) { return !_finite(d) && !_isnan(d); }
inline bool isnan(double d) { return !!_isnan(d); }
inline bool isfinite(double d) { return _finite(d); }
-#if _MSC_VER < 1800
-inline bool signbit(double d) { return _copysign(1.0, d) < 0; }
-#endif
} // namespace std
@@ -95,7 +92,7 @@ inline double trunc(double d) { return d > 0 ? floor(d) : ceil(d); }
&& (defined(Q_OS_WIN) || defined(Q_OS_LINUX) || defined(Q_OS_QNX) || defined(Q_OS_FREEBSD))
# define V4_ENABLE_JIT
#elif defined(Q_PROCESSOR_X86_64) && (QT_POINTER_SIZE == 8) \
- && (defined(Q_OS_WIN) || defined(Q_OS_LINUX) || defined(Q_OS_MAC) || defined(Q_OS_FREEBSD))
+ && (defined(Q_OS_WIN) || defined(Q_OS_LINUX) || defined(Q_OS_QNX) || defined(Q_OS_MAC) || defined(Q_OS_FREEBSD))
# define V4_ENABLE_JIT
#elif defined(Q_PROCESSOR_ARM_32) && (QT_POINTER_SIZE == 4)
# if defined(thumb2) || defined(__thumb2__) || ((defined(__thumb) || defined(__thumb__)) && __TARGET_ARCH_THUMB-0 == 4)
@@ -104,7 +101,7 @@ inline double trunc(double d) { return d > 0 ? floor(d) : ceil(d); }
# define V4_ENABLE_JIT
# endif
#elif defined(Q_PROCESSOR_ARM_64) && (QT_POINTER_SIZE == 8)
-# if defined(Q_OS_LINUX)
+# if defined(Q_OS_LINUX) || defined(Q_OS_QNX)
# define V4_ENABLE_JIT
# endif
//#elif defined(Q_PROCESSOR_MIPS_32) && defined(Q_OS_LINUX)
@@ -211,7 +208,6 @@ struct StringObject;
struct ArrayObject;
struct DateObject;
struct FunctionObject;
-struct BuiltinFunction;
struct ErrorObject;
struct ArgumentsObject;
struct Managed;
diff --git a/src/qml/jsruntime/qv4globalobject.cpp b/src/qml/jsruntime/qv4globalobject.cpp
index 3214a716e8..f419ab53fe 100644
--- a/src/qml/jsruntime/qv4globalobject.cpp
+++ b/src/qml/jsruntime/qv4globalobject.cpp
@@ -375,12 +375,12 @@ ReturnedValue EvalFunction::evalCall(const Value *, const Value *argv, int argc,
if (function->isStrict() || isStrict) {
ScopedFunctionObject e(scope, FunctionObject::createScriptFunction(ctx, function));
ScopedValue thisObject(scope, directCall ? scope.engine->currentStackFrame->thisObject() : scope.engine->globalObject->asReturnedValue());
- return e->call(thisObject, 0, 0);
+ return e->call(thisObject, nullptr, 0);
}
ScopedValue thisObject(scope, scope.engine->currentStackFrame->thisObject());
- return function->call(thisObject, 0, 0, ctx);
+ return function->call(thisObject, nullptr, 0, ctx);
}
@@ -507,7 +507,7 @@ ReturnedValue GlobalFunctions::method_parseFloat(const FunctionObject *b, const
QByteArray ba = trimmed.toLatin1();
bool ok;
const char *begin = ba.constData();
- const char *end = 0;
+ const char *end = nullptr;
double d = qstrtod(begin, &end, &ok);
if (end - begin == 0)
RETURN_RESULT(Encode(std::numeric_limits<double>::quiet_NaN())); // 3
diff --git a/src/qml/jsruntime/qv4identifier.cpp b/src/qml/jsruntime/qv4identifier.cpp
index e35f72b820..c122bcb51a 100644
--- a/src/qml/jsruntime/qv4identifier.cpp
+++ b/src/qml/jsruntime/qv4identifier.cpp
@@ -75,13 +75,13 @@ IdentifierHashData::IdentifierHashData(IdentifierHashData *other)
memcpy(entries, other->entries, alloc*sizeof(IdentifierHashEntry));
}
-IdentifierHashBase::IdentifierHashBase(ExecutionEngine *engine)
+IdentifierHash::IdentifierHash(ExecutionEngine *engine)
{
d = new IdentifierHashData(3);
d->identifierTable = engine->identifierTable;
}
-void IdentifierHashBase::detach()
+void IdentifierHash::detach()
{
if (!d || d->refCount == 1)
return;
@@ -92,7 +92,7 @@ void IdentifierHashBase::detach()
}
-IdentifierHashEntry *IdentifierHashBase::addEntry(const Identifier *identifier)
+IdentifierHashEntry *IdentifierHash::addEntry(const Identifier *identifier)
{
// fill up to max 50%
bool grow = (d->alloc <= d->size*2);
@@ -129,16 +129,16 @@ IdentifierHashEntry *IdentifierHashBase::addEntry(const Identifier *identifier)
return d->entries + idx;
}
-const IdentifierHashEntry *IdentifierHashBase::lookup(const Identifier *identifier) const
+const IdentifierHashEntry *IdentifierHash::lookup(const Identifier *identifier) const
{
if (!d)
- return 0;
+ return nullptr;
Q_ASSERT(d->entries);
uint idx = identifier->hashValue % d->alloc;
while (1) {
if (!d->entries[idx].identifier)
- return 0;
+ return nullptr;
if (d->entries[idx].identifier == identifier)
return d->entries + idx;
++idx;
@@ -146,17 +146,17 @@ const IdentifierHashEntry *IdentifierHashBase::lookup(const Identifier *identifi
}
}
-const IdentifierHashEntry *IdentifierHashBase::lookup(const QString &str) const
+const IdentifierHashEntry *IdentifierHash::lookup(const QString &str) const
{
if (!d)
- return 0;
+ return nullptr;
Q_ASSERT(d->entries);
uint hash = String::createHashValue(str.constData(), str.length(), nullptr);
uint idx = hash % d->alloc;
while (1) {
if (!d->entries[idx].identifier)
- return 0;
+ return nullptr;
if (d->entries[idx].identifier->string == str)
return d->entries + idx;
++idx;
@@ -164,22 +164,22 @@ const IdentifierHashEntry *IdentifierHashBase::lookup(const QString &str) const
}
}
-const IdentifierHashEntry *IdentifierHashBase::lookup(String *str) const
+const IdentifierHashEntry *IdentifierHash::lookup(String *str) const
{
if (!d)
- return 0;
+ return nullptr;
if (str->d()->identifier)
return lookup(str->d()->identifier);
return lookup(str->toQString());
}
-const Identifier *IdentifierHashBase::toIdentifier(const QString &str) const
+const Identifier *IdentifierHash::toIdentifier(const QString &str) const
{
Q_ASSERT(d);
return d->identifierTable->identifier(str);
}
-const Identifier *IdentifierHashBase::toIdentifier(Heap::String *str) const
+const Identifier *IdentifierHash::toIdentifier(Heap::String *str) const
{
Q_ASSERT(d);
return d->identifierTable->identifier(str);
diff --git a/src/qml/jsruntime/qv4identifier_p.h b/src/qml/jsruntime/qv4identifier_p.h
index 2695bbc875..82346d5f68 100644
--- a/src/qml/jsruntime/qv4identifier_p.h
+++ b/src/qml/jsruntime/qv4identifier_p.h
@@ -73,13 +73,7 @@ struct Identifier
struct IdentifierHashEntry {
const Identifier *identifier;
- union {
- int value;
- void *pointer;
- };
- static int get(const IdentifierHashEntry *This, int *) { return This ? This->value : -1; }
- static bool get(const IdentifierHashEntry *This, bool *) { return This != 0; }
- static void *get(const IdentifierHashEntry *This, void **) { return This ? This->pointer : 0; }
+ int value;
};
struct IdentifierHashData
@@ -98,26 +92,30 @@ struct IdentifierHashData
IdentifierHashEntry *entries;
};
-struct IdentifierHashBase
+struct IdentifierHash
{
- IdentifierHashData *d;
+ IdentifierHashData *d = nullptr;
- IdentifierHashBase() : d(0) {}
- IdentifierHashBase(ExecutionEngine *engine);
- inline IdentifierHashBase(const IdentifierHashBase &other);
- inline ~IdentifierHashBase();
- inline IdentifierHashBase &operator=(const IdentifierHashBase &other);
+ IdentifierHash() {}
+ IdentifierHash(ExecutionEngine *engine);
+ inline IdentifierHash(const IdentifierHash &other);
+ inline ~IdentifierHash();
+ inline IdentifierHash &operator=(const IdentifierHash &other);
bool isEmpty() const { return !d; }
inline int count() const;
- bool contains(const Identifier *i) const;
- bool contains(const QString &str) const;
- bool contains(String *str) const;
void detach();
+ void add(const QString &str, int value);
+ void add(Heap::String *str, int value);
+
+ inline int value(const QString &str) const;
+ inline int value(String *str) const;
+ QString findId(int value) const;
+
protected:
IdentifierHashEntry *addEntry(const Identifier *i);
const IdentifierHashEntry *lookup(const Identifier *identifier) const;
@@ -128,43 +126,20 @@ protected:
};
-template<typename T>
-struct IdentifierHash : public IdentifierHashBase
-{
- IdentifierHash()
- : IdentifierHashBase() {}
- IdentifierHash(ExecutionEngine *engine)
- : IdentifierHashBase(engine) {}
- inline IdentifierHash(const IdentifierHash<T> &other)
- : IdentifierHashBase(other) {}
- inline ~IdentifierHash() {}
- inline IdentifierHash &operator=(const IdentifierHash<T> &other) {
- IdentifierHashBase::operator =(other);
- return *this;
- }
-
- void add(const QString &str, const T &value);
- void add(Heap::String *str, const T &value);
-
- inline T value(const QString &str) const;
- inline T value(String *str) const;
- QString findId(T value) const;
-};
-
-inline IdentifierHashBase::IdentifierHashBase(const IdentifierHashBase &other)
+inline IdentifierHash::IdentifierHash(const IdentifierHash &other)
{
d = other.d;
if (d)
d->refCount.ref();
}
-inline IdentifierHashBase::~IdentifierHashBase()
+inline IdentifierHash::~IdentifierHash()
{
if (d && !d->refCount.deref())
delete d;
}
-IdentifierHashBase &IdentifierHashBase::operator=(const IdentifierHashBase &other)
+IdentifierHash &IdentifierHash::operator=(const IdentifierHash &other)
{
if (other.d)
other.d->refCount.ref();
@@ -174,60 +149,45 @@ IdentifierHashBase &IdentifierHashBase::operator=(const IdentifierHashBase &othe
return *this;
}
-inline int IdentifierHashBase::count() const
+inline int IdentifierHash::count() const
{
return d ? d->size : 0;
}
-inline bool IdentifierHashBase::contains(const Identifier *i) const
-{
- return lookup(i) != 0;
-}
-
-inline bool IdentifierHashBase::contains(const QString &str) const
-{
- return lookup(str) != 0;
-}
-
-inline bool IdentifierHashBase::contains(String *str) const
-{
- return lookup(str) != 0;
-}
-
-template<typename T>
-void IdentifierHash<T>::add(const QString &str, const T &value)
+inline
+void IdentifierHash::add(const QString &str, int value)
{
IdentifierHashEntry *e = addEntry(toIdentifier(str));
e->value = value;
}
-template<typename T>
-void IdentifierHash<T>::add(Heap::String *str, const T &value)
+inline
+void IdentifierHash::add(Heap::String *str, int value)
{
IdentifierHashEntry *e = addEntry(toIdentifier(str));
e->value = value;
}
-template<typename T>
-inline T IdentifierHash<T>::value(const QString &str) const
+inline int IdentifierHash::value(const QString &str) const
{
- return IdentifierHashEntry::get(lookup(str), (T*)0);
+ const IdentifierHashEntry *e = lookup(str);
+ return e ? e->value : -1;
}
-template<typename T>
-inline T IdentifierHash<T>::value(String *str) const
+inline int IdentifierHash::value(String *str) const
{
- return IdentifierHashEntry::get(lookup(str), (T*)0);
+ const IdentifierHashEntry *e = lookup(str);
+ return e ? e->value : -1;
}
-template<typename T>
-QString IdentifierHash<T>::findId(T value) const
+inline
+QString IdentifierHash::findId(int value) const
{
IdentifierHashEntry *e = d->entries;
IdentifierHashEntry *end = e + d->alloc;
while (e < end) {
- if (e->identifier && IdentifierHashEntry::get(e, (T*)0) == value)
+ if (e->identifier && e->value == value)
return e->identifier->string;
++e;
}
diff --git a/src/qml/jsruntime/qv4identifiertable.cpp b/src/qml/jsruntime/qv4identifiertable.cpp
index 3def6defbf..b77f9478d3 100644
--- a/src/qml/jsruntime/qv4identifiertable.cpp
+++ b/src/qml/jsruntime/qv4identifiertable.cpp
@@ -142,7 +142,7 @@ Identifier *IdentifierTable::identifierImpl(const Heap::String *str)
return str->identifier;
uint hash = str->hashValue();
if (str->subtype == Heap::String::StringType_ArrayIndex)
- return 0;
+ return nullptr;
uint idx = hash % alloc;
while (Heap::String *e = entries[idx]) {
@@ -161,7 +161,7 @@ Identifier *IdentifierTable::identifierImpl(const Heap::String *str)
Heap::String *IdentifierTable::stringFromIdentifier(Identifier *i)
{
if (!i)
- return 0;
+ return nullptr;
uint idx = i->hashValue % alloc;
while (1) {
diff --git a/src/qml/jsruntime/qv4include.cpp b/src/qml/jsruntime/qv4include.cpp
index 3e04ed63df..aaf5e3b857 100644
--- a/src/qml/jsruntime/qv4include.cpp
+++ b/src/qml/jsruntime/qv4include.cpp
@@ -61,7 +61,7 @@ QV4Include::QV4Include(const QUrl &url, QV4::ExecutionEngine *engine,
QV4::QmlContext *qmlContext, const QV4::Value &callback)
: v4(engine), m_url(url)
#if QT_CONFIG(qml_network)
- , m_redirectCount(0), m_network(0) , m_reply(0)
+ , m_redirectCount(0), m_network(nullptr) , m_reply(nullptr)
#endif
{
if (qmlContext)
@@ -88,7 +88,7 @@ QV4Include::~QV4Include()
{
#if QT_CONFIG(qml_network)
delete m_reply;
- m_reply = 0;
+ m_reply = nullptr;
#endif
}
@@ -196,10 +196,10 @@ void QV4Include::finished()
/*
Documented in qv8engine.cpp
*/
-QV4::ReturnedValue QV4Include::method_include(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QV4Include::method_include(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- if (!callData->argc())
+ if (!argc)
RETURN_UNDEFINED();
QQmlContextData *context = scope.engine->callingQmlContext();
@@ -208,11 +208,11 @@ QV4::ReturnedValue QV4Include::method_include(const QV4::BuiltinFunction *b, QV4
RETURN_RESULT(scope.engine->throwError(QString::fromUtf8("Qt.include(): Can only be called from JavaScript files")));
QV4::ScopedValue callbackFunction(scope, QV4::Primitive::undefinedValue());
- if (callData->argc() >= 2 && callData->args[1].as<QV4::FunctionObject>())
- callbackFunction = callData->args[1];
+ if (argc >= 2 && argv[1].as<QV4::FunctionObject>())
+ callbackFunction = argv[1];
#if QT_CONFIG(qml_network)
- QUrl url(scope.engine->resolvedUrl(callData->args[0].toQStringNoThrow()));
+ QUrl url(scope.engine->resolvedUrl(argv[0].toQStringNoThrow()));
if (scope.engine->qmlEngine() && scope.engine->qmlEngine()->urlInterceptor())
url = scope.engine->qmlEngine()->urlInterceptor()->intercept(url, QQmlAbstractUrlInterceptor::JavaScriptFile);
@@ -227,21 +227,7 @@ QV4::ReturnedValue QV4Include::method_include(const QV4::BuiltinFunction *b, QV4
} else {
QScopedPointer<QV4::Script> script;
-
- if (const QQmlPrivate::CachedQmlUnit *cachedUnit = QQmlMetaType::findCachedCompilationUnit(url)) {
- QV4::CompiledData::CompilationUnit *jsUnit = cachedUnit->createCompilationUnit();
- script.reset(new QV4::Script(scope.engine, qmlcontext, jsUnit));
- } else {
- QFile f(localFile);
-
- if (f.open(QIODevice::ReadOnly)) {
- QByteArray data = f.readAll();
- QString code = QString::fromUtf8(data);
- QmlIR::Document::removeScriptPragmas(code);
-
- script.reset(new QV4::Script(scope.engine, qmlcontext, code, url.toString()));
- }
- }
+ script.reset(QV4::Script::createFromFileOrCache(scope.engine, qmlcontext, localFile, url));
if (!script.isNull()) {
script->parse();
diff --git a/src/qml/jsruntime/qv4include_p.h b/src/qml/jsruntime/qv4include_p.h
index 68537ba2e8..8015722afc 100644
--- a/src/qml/jsruntime/qv4include_p.h
+++ b/src/qml/jsruntime/qv4include_p.h
@@ -77,7 +77,7 @@ public:
Exception = 3
};
- static QV4::ReturnedValue method_include(const QV4::BuiltinFunction *, QV4::CallData *callData);
+ static QV4::ReturnedValue method_include(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
private Q_SLOTS:
void finished();
diff --git a/src/qml/jsruntime/qv4internalclass.cpp b/src/qml/jsruntime/qv4internalclass.cpp
index d439884ca2..9da854e7d7 100644
--- a/src/qml/jsruntime/qv4internalclass.cpp
+++ b/src/qml/jsruntime/qv4internalclass.cpp
@@ -105,10 +105,10 @@ void PropertyHash::addEntry(const PropertyHash::Entry &entry, int classSize)
InternalClass::InternalClass(ExecutionEngine *engine)
: engine(engine)
- , vtable(0)
- , prototype(0)
- , m_sealed(0)
- , m_frozen(0)
+ , vtable(nullptr)
+ , prototype(nullptr)
+ , m_sealed(nullptr)
+ , m_frozen(nullptr)
, size(0)
, extensible(true)
{
@@ -124,8 +124,8 @@ InternalClass::InternalClass(const QV4::InternalClass &other)
, propertyTable(other.propertyTable)
, nameMap(other.nameMap)
, propertyData(other.propertyData)
- , m_sealed(0)
- , m_frozen(0)
+ , m_sealed(nullptr)
+ , m_frozen(nullptr)
, size(other.size)
, extensible(other.extensible)
, isUsedAsProto(other.isUsedAsProto)
@@ -149,6 +149,9 @@ static void removeFromPropertyData(Object *object, int idx, bool accessor = fals
int size = o->internalClass->size;
for (int i = idx; i < size; ++i)
o->setProperty(v4, i, *o->propertyData(i + (accessor ? 2 : 1)));
+ o->setProperty(v4, size, Primitive::undefinedValue());
+ if (accessor)
+ o->setProperty(v4, size + 1, Primitive::undefinedValue());
}
void InternalClass::changeMember(Object *object, String *string, PropertyAttributes data, uint *index)
@@ -220,7 +223,7 @@ InternalClass *InternalClass::changePrototypeImpl(Heap::Object *proto)
Q_ASSERT(prototype != proto);
Q_ASSERT(!proto || proto->internalClass->isUsedAsProto);
- Transition temp = { { nullptr }, 0, Transition::PrototypeChange };
+ Transition temp = { { nullptr }, nullptr, Transition::PrototypeChange };
temp.prototype = proto;
Transition &t = lookupOrInsertTransition(temp);
@@ -484,7 +487,7 @@ void InternalClass::destroy()
destroyStack.pop_back();
if (!next->engine)
continue;
- next->engine = 0;
+ next->engine = nullptr;
next->propertyTable.~PropertyHash();
next->nameMap.~SharedInternalClassData<Identifier *>();
next->propertyData.~SharedInternalClassData<PropertyAttributes>();
diff --git a/src/qml/jsruntime/qv4internalclass_p.h b/src/qml/jsruntime/qv4internalclass_p.h
index 546073dcf5..b689272006 100644
--- a/src/qml/jsruntime/qv4internalclass_p.h
+++ b/src/qml/jsruntime/qv4internalclass_p.h
@@ -277,10 +277,10 @@ struct InternalClass : public QQmlJS::Managed {
}
static void addMember(Object *object, String *string, PropertyAttributes data, uint *index);
- Q_REQUIRED_RESULT InternalClass *addMember(String *string, PropertyAttributes data, uint *index = 0);
- Q_REQUIRED_RESULT InternalClass *addMember(Identifier *identifier, PropertyAttributes data, uint *index = 0);
- Q_REQUIRED_RESULT InternalClass *changeMember(Identifier *identifier, PropertyAttributes data, uint *index = 0);
- static void changeMember(Object *object, String *string, PropertyAttributes data, uint *index = 0);
+ Q_REQUIRED_RESULT InternalClass *addMember(String *string, PropertyAttributes data, uint *index = nullptr);
+ Q_REQUIRED_RESULT InternalClass *addMember(Identifier *identifier, PropertyAttributes data, uint *index = nullptr);
+ Q_REQUIRED_RESULT InternalClass *changeMember(Identifier *identifier, PropertyAttributes data, uint *index = nullptr);
+ static void changeMember(Object *object, String *string, PropertyAttributes data, uint *index = nullptr);
static void removeMember(Object *object, Identifier *id);
uint find(const String *string);
uint find(const Identifier *id)
diff --git a/src/qml/jsruntime/qv4jscall_p.h b/src/qml/jsruntime/qv4jscall_p.h
index 6d641bf9c5..c676b57c51 100644
--- a/src/qml/jsruntime/qv4jscall_p.h
+++ b/src/qml/jsruntime/qv4jscall_p.h
@@ -61,7 +61,7 @@ QT_BEGIN_NAMESPACE
namespace QV4 {
struct JSCallData {
- JSCallData(const Scope &scope, int argc = 0, const Value *argv = 0, const Value *thisObject = 0)
+ JSCallData(const Scope &scope, int argc = 0, const Value *argv = nullptr, const Value *thisObject = nullptr)
: scope(scope), argc(argc)
{
if (thisObject)
@@ -124,7 +124,7 @@ struct ScopedStackFrame {
return;
frame.jsFrame = reinterpret_cast<CallData *>(scope.alloc(sizeof(CallData)/sizeof(Value)));
frame.jsFrame->context = context;
- frame.v4Function = frame.parent ? frame.parent->v4Function : 0;
+ frame.v4Function = frame.parent ? frame.parent->v4Function : nullptr;
scope.engine->currentStackFrame = &frame;
}
~ScopedStackFrame() {
diff --git a/src/qml/jsruntime/qv4jsonobject.cpp b/src/qml/jsruntime/qv4jsonobject.cpp
index 5e580b8b4d..99666806be 100644
--- a/src/qml/jsruntime/qv4jsonobject.cpp
+++ b/src/qml/jsruntime/qv4jsonobject.cpp
@@ -634,7 +634,7 @@ struct Stringify
return false;
}
- Stringify(ExecutionEngine *e) : v4(e), replacerFunction(0), propertyList(0), propertyListSize(0) {}
+ Stringify(ExecutionEngine *e) : v4(e), replacerFunction(nullptr), propertyList(nullptr), propertyListSize(0) {}
QString Str(const QString &key, const Value &v);
QString JA(ArrayObject *a);
@@ -884,12 +884,12 @@ void Heap::JsonObject::init()
}
-ReturnedValue JsonObject::method_parse(const BuiltinFunction *b, CallData *callData)
+ReturnedValue JsonObject::method_parse(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
ExecutionEngine *v4 = b->engine();
QString jtext;
- if (callData->argc() > 0)
- jtext = callData->args[0].toQString();
+ if (argc > 0)
+ jtext = argv[0].toQString();
DEBUG << "parsing source = " << jtext;
JsonParser parser(v4, jtext.constData(), jtext.length());
@@ -903,12 +903,12 @@ ReturnedValue JsonObject::method_parse(const BuiltinFunction *b, CallData *callD
return result;
}
-ReturnedValue JsonObject::method_stringify(const BuiltinFunction *b, CallData *callData)
+ReturnedValue JsonObject::method_stringify(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
Scope scope(b);
Stringify stringify(scope.engine);
- ScopedObject o(scope, callData->argument(1));
+ ScopedObject o(scope, argc > 1 ? argv[1] : Primitive::undefinedValue());
if (o) {
stringify.replacerFunction = o->as<FunctionObject>();
if (o->isArrayObject()) {
@@ -920,11 +920,11 @@ ReturnedValue JsonObject::method_stringify(const BuiltinFunction *b, CallData *c
if (v->as<NumberObject>() || v->as<StringObject>() || v->isNumber())
*v = v->toString(scope.engine);
if (!v->isString()) {
- v->setM(0);
+ v->setM(nullptr);
} else {
for (uint j = 0; j <i; ++j) {
if (stringify.propertyList[j].m() == v->m()) {
- v->setM(0);
+ v->setM(nullptr);
break;
}
}
@@ -933,7 +933,7 @@ ReturnedValue JsonObject::method_stringify(const BuiltinFunction *b, CallData *c
}
}
- ScopedValue s(scope, callData->argument(2));
+ ScopedValue s(scope, argc > 2 ? argv[2] : Primitive::undefinedValue());
if (NumberObject *n = s->as<NumberObject>())
s = Encode(n->value());
else if (StringObject *so = s->as<StringObject>())
@@ -946,7 +946,7 @@ ReturnedValue JsonObject::method_stringify(const BuiltinFunction *b, CallData *c
}
- ScopedValue arg0(scope, callData->argument(0));
+ ScopedValue arg0(scope, argc ? argv[0] : Primitive::undefinedValue());
QString result = stringify.Str(QString(), arg0);
if (result.isEmpty() || scope.engine->hasException)
RETURN_UNDEFINED();
diff --git a/src/qml/jsruntime/qv4jsonobject_p.h b/src/qml/jsruntime/qv4jsonobject_p.h
index 19dba14aef..7d9f204910 100644
--- a/src/qml/jsruntime/qv4jsonobject_p.h
+++ b/src/qml/jsruntime/qv4jsonobject_p.h
@@ -88,8 +88,8 @@ private:
typedef QSet<ObjectItem> V4ObjectSet;
public:
- static ReturnedValue method_parse(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_stringify(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_parse(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_stringify(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
static ReturnedValue fromJsonValue(ExecutionEngine *engine, const QJsonValue &value);
static ReturnedValue fromJsonObject(ExecutionEngine *engine, const QJsonObject &object);
diff --git a/src/qml/jsruntime/qv4managed.cpp b/src/qml/jsruntime/qv4managed.cpp
index 200380eda0..b50e5f0355 100644
--- a/src/qml/jsruntime/qv4managed.cpp
+++ b/src/qml/jsruntime/qv4managed.cpp
@@ -46,7 +46,7 @@ using namespace QV4;
const VTable Managed::static_vtbl =
{
- 0,
+ nullptr,
0,
0,
Managed::IsExecutionContext,
@@ -58,15 +58,15 @@ const VTable Managed::static_vtbl =
0,
Managed::MyType,
"Managed",
- 0,
- 0 /*markObjects*/,
+ nullptr,
+ nullptr /*markObjects*/,
isEqualTo
};
QString Managed::className() const
{
- const char *s = 0;
+ const char *s = nullptr;
switch (Type(d()->vtable()->type)) {
case Type_Invalid:
case Type_String:
diff --git a/src/qml/jsruntime/qv4managed_p.h b/src/qml/jsruntime/qv4managed_p.h
index f81dcf9479..092c61b81c 100644
--- a/src/qml/jsruntime/qv4managed_p.h
+++ b/src/qml/jsruntime/qv4managed_p.h
@@ -93,7 +93,7 @@ inline void qYouForgotTheQ_MANAGED_Macro(T1, T2) {}
dptr->_checkIsInitialized(); \
return dptr; \
} \
- V4_ASSERT_IS_TRIVIAL(QV4::Heap::DataClass)
+ Q_STATIC_ASSERT(std::is_trivial< QV4::Heap::DataClass >::value);
#define V4_MANAGED(DataClass, superClass) \
private: \
diff --git a/src/qml/jsruntime/qv4mathobject.cpp b/src/qml/jsruntime/qv4mathobject.cpp
index 252ec345d9..0c18d908de 100644
--- a/src/qml/jsruntime/qv4mathobject.cpp
+++ b/src/qml/jsruntime/qv4mathobject.cpp
@@ -277,7 +277,7 @@ ReturnedValue MathObject::method_pow(const FunctionObject *, const Value *, cons
ReturnedValue MathObject::method_random(const FunctionObject *, const Value *, const Value *, int)
{
- RETURN_RESULT(Encode(QRandomGenerator::getReal()));
+ RETURN_RESULT(Encode(QRandomGenerator::global()->generateDouble()));
}
ReturnedValue MathObject::method_round(const FunctionObject *, const Value *, const Value *argv, int argc)
diff --git a/src/qml/jsruntime/qv4memberdata_p.h b/src/qml/jsruntime/qv4memberdata_p.h
index 3e231d693b..ac9671254d 100644
--- a/src/qml/jsruntime/qv4memberdata_p.h
+++ b/src/qml/jsruntime/qv4memberdata_p.h
@@ -65,7 +65,7 @@ namespace Heap {
DECLARE_HEAP_OBJECT(MemberData, Base) {
DECLARE_MARKOBJECTS(MemberData);
};
-V4_ASSERT_IS_TRIVIAL(MemberData)
+Q_STATIC_ASSERT(std::is_trivial< MemberData >::value);
}
@@ -79,7 +79,7 @@ struct MemberData : Managed
Value *slot;
void set(EngineBase *e, Value newVal) {
- WriteBarrier::write(e, base, slot, newVal);
+ WriteBarrier::write(e, base, slot->data_ptr(), newVal.asReturnedValue());
}
const Value *operator->() const { return slot; }
const Value &operator*() const { return *slot; }
@@ -93,7 +93,7 @@ struct MemberData : Managed
inline uint size() const { return d()->values.size; }
- static Heap::MemberData *allocate(QV4::ExecutionEngine *e, uint n, Heap::MemberData *old = 0);
+ static Heap::MemberData *allocate(QV4::ExecutionEngine *e, uint n, Heap::MemberData *old = nullptr);
};
}
diff --git a/src/qml/jsruntime/qv4object.cpp b/src/qml/jsruntime/qv4object.cpp
index b4034fd196..8e9bf794a9 100644
--- a/src/qml/jsruntime/qv4object.cpp
+++ b/src/qml/jsruntime/qv4object.cpp
@@ -94,7 +94,7 @@ void Heap::Object::setUsedAsProto()
bool Object::setPrototype(Object *proto)
{
- Heap::Object *p = proto ? proto->d() : 0;
+ Heap::Object *p = proto ? proto->d() : nullptr;
Heap::Object *pp = p;
while (pp) {
if (pp == d())
@@ -156,34 +156,13 @@ void Object::defineDefaultProperty(const QString &name, const Value &value)
defineDefaultProperty(s, value);
}
-void Object::defineDefaultProperty(const QString &name, ReturnedValue (*code)(const BuiltinFunction *, CallData *), int argumentCount)
-{
- ExecutionEngine *e = engine();
- Scope scope(e);
- ScopedString s(scope, e->newIdentifier(name));
- ExecutionContext *global = e->rootContext();
- ScopedFunctionObject function(scope, BuiltinFunction::create(global, s, code));
- function->defineReadonlyConfigurableProperty(e->id_length(), Primitive::fromInt32(argumentCount));
- defineDefaultProperty(s, function);
-}
-
-void Object::defineDefaultProperty(String *name, ReturnedValue (*code)(const BuiltinFunction *, CallData *), int argumentCount)
-{
- ExecutionEngine *e = engine();
- Scope scope(e);
- ExecutionContext *global = e->rootContext();
- ScopedFunctionObject function(scope, BuiltinFunction::create(global, name, code));
- function->defineReadonlyConfigurableProperty(e->id_length(), Primitive::fromInt32(argumentCount));
- defineDefaultProperty(name, function);
-}
-
void Object::defineDefaultProperty(const QString &name, ReturnedValue (*code)(const FunctionObject *, const Value *thisObject, const Value *argv, int argc), int argumentCount)
{
ExecutionEngine *e = engine();
Scope scope(e);
ScopedString s(scope, e->newIdentifier(name));
ExecutionContext *global = e->rootContext();
- ScopedFunctionObject function(scope, BuiltinFunction::create(global, s, code));
+ ScopedFunctionObject function(scope, FunctionObject::createBuiltinFunction(global, s, code));
function->defineReadonlyConfigurableProperty(e->id_length(), Primitive::fromInt32(argumentCount));
defineDefaultProperty(s, function);
}
@@ -193,32 +172,11 @@ void Object::defineDefaultProperty(String *name, ReturnedValue (*code)(const Fun
ExecutionEngine *e = engine();
Scope scope(e);
ExecutionContext *global = e->rootContext();
- ScopedFunctionObject function(scope, BuiltinFunction::create(global, name, code));
+ ScopedFunctionObject function(scope, FunctionObject::createBuiltinFunction(global, name, code));
function->defineReadonlyConfigurableProperty(e->id_length(), Primitive::fromInt32(argumentCount));
defineDefaultProperty(name, function);
}
-void Object::defineAccessorProperty(const QString &name, ReturnedValue (*getter)(const BuiltinFunction *, CallData *),
- ReturnedValue (*setter)(const BuiltinFunction *, CallData *))
-{
- ExecutionEngine *e = engine();
- Scope scope(e);
- ScopedString s(scope, e->newIdentifier(name));
- defineAccessorProperty(s, getter, setter);
-}
-
-void Object::defineAccessorProperty(String *name, ReturnedValue (*getter)(const BuiltinFunction *, CallData *),
- ReturnedValue (*setter)(const BuiltinFunction *, CallData *))
-{
- ExecutionEngine *v4 = engine();
- QV4::Scope scope(v4);
- ScopedProperty p(scope);
- ExecutionContext *global = v4->rootContext();
- p->setGetter(ScopedFunctionObject(scope, (getter ? BuiltinFunction::create(global, name, getter) : 0)));
- p->setSetter(ScopedFunctionObject(scope, (setter ? BuiltinFunction::create(global, name, setter) : 0)));
- insertMember(name, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
-}
-
void Object::defineAccessorProperty(const QString &name, ReturnedValue (*getter)(const FunctionObject *, const Value *, const Value *, int),
ReturnedValue (*setter)(const FunctionObject *, const Value *, const Value *, int))
{
@@ -235,8 +193,8 @@ void Object::defineAccessorProperty(String *name, ReturnedValue (*getter)(const
QV4::Scope scope(v4);
ScopedProperty p(scope);
ExecutionContext *global = v4->rootContext();
- p->setGetter(ScopedFunctionObject(scope, (getter ? BuiltinFunction::create(global, name, getter) : 0)));
- p->setSetter(ScopedFunctionObject(scope, (setter ? BuiltinFunction::create(global, name, setter) : 0)));
+ p->setGetter(ScopedFunctionObject(scope, (getter ? FunctionObject::createBuiltinFunction(global, name, getter) : nullptr)));
+ p->setSetter(ScopedFunctionObject(scope, (setter ? FunctionObject::createBuiltinFunction(global, name, setter) : nullptr)));
insertMember(name, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
}
@@ -268,11 +226,6 @@ void Object::defineReadonlyConfigurableProperty(String *name, const Value &value
insertMember(name, value, Attr_ReadOnly_ButConfigurable);
}
-void Object::markObjects(Heap::Base *base, MarkStack *stack)
-{
- Heap::Object::markObjects(base, stack);
-}
-
void Heap::Object::markObjects(Heap::Base *b, MarkStack *stack)
{
Object *o = static_cast<Object *>(b);
@@ -368,7 +321,7 @@ MemberData::Index Object::getValueOrSetter(String *name, PropertyAttributes *att
o = o->prototype();
}
*attrs = Attr_Invalid;
- return { 0, 0 };
+ return { nullptr, nullptr };
}
ArrayData::Index Object::getValueOrSetter(uint index, PropertyAttributes *attrs)
@@ -393,7 +346,7 @@ ArrayData::Index Object::getValueOrSetter(uint index, PropertyAttributes *attrs)
o = o->prototype();
}
*attrs = Attr_Invalid;
- return { 0, 0 };
+ return { nullptr, 0 };
}
bool Object::hasProperty(String *name) const
@@ -531,7 +484,7 @@ bool Object::deleteIndexedProperty(Managed *m, uint index)
void Object::advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint *index, Property *pd, PropertyAttributes *attrs)
{
Object *o = static_cast<Object *>(m);
- name->setM(0);
+ name->setM(nullptr);
*index = UINT_MAX;
if (o->arrayData()) {
@@ -555,7 +508,7 @@ void Object::advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint *
return;
}
}
- it->arrayNode = 0;
+ it->arrayNode = nullptr;
it->arrayIndex = UINT_MAX;
}
// dense arrays
@@ -675,7 +628,7 @@ bool Object::internalPut(String *name, const Value &value)
name->makeIdentifier();
Identifier *id = name->identifier();
- MemberData::Index memberIndex{0, 0};
+ MemberData::Index memberIndex{nullptr, nullptr};
uint member = internalClass()->find(id);
PropertyAttributes attrs;
if (member < UINT_MAX) {
@@ -751,7 +704,7 @@ bool Object::internalPutIndexed(uint index, const Value &value)
PropertyAttributes attrs;
- ArrayData::Index arrayIndex = arrayData() ? arrayData()->getValueOrSetter(index, &attrs) : ArrayData::Index{ 0, 0 };
+ ArrayData::Index arrayIndex = arrayData() ? arrayData()->getValueOrSetter(index, &attrs) : ArrayData::Index{ nullptr, 0 };
if (arrayIndex.isNull() && isStringObject()) {
if (index < static_cast<StringObject *>(this)->length())
@@ -945,7 +898,7 @@ bool Object::defineOwnProperty2(ExecutionEngine *engine, uint index, const Prope
return true;
}
- return __defineOwnProperty__(engine, index, 0, p, attrs);
+ return __defineOwnProperty__(engine, index, nullptr, p, attrs);
}
bool Object::__defineOwnProperty__(ExecutionEngine *engine, uint index, String *member, const Property *p, PropertyAttributes attrs)
@@ -996,8 +949,8 @@ bool Object::__defineOwnProperty__(ExecutionEngine *engine, uint index, String *
Q_ASSERT(arrayData());
setArrayAttributes(index, cattrs);
}
- current->setGetter(0);
- current->setSetter(0);
+ current->setGetter(nullptr);
+ current->setSetter(nullptr);
} else {
// 9c
cattrs.setType(PropertyAttributes::Data);
@@ -1069,7 +1022,6 @@ void Object::copyArrayData(Object *other)
Heap::ArrayData *od = other->d()->arrayData;
Heap::ArrayData *dd = d()->arrayData;
dd->sparse = new SparseArray(*od->sparse);
- dd->freeList = od->freeList;
} else {
Heap::ArrayData *dd = d()->arrayData;
dd->values.size = other->d()->arrayData->values.size;
diff --git a/src/qml/jsruntime/qv4object_p.h b/src/qml/jsruntime/qv4object_p.h
index 66177617f7..1731ae3c76 100644
--- a/src/qml/jsruntime/qv4object_p.h
+++ b/src/qml/jsruntime/qv4object_p.h
@@ -64,8 +64,6 @@ QT_BEGIN_NAMESPACE
namespace QV4 {
-struct BuiltinFunction;
-
namespace Heap {
#define ObjectMembers(class, Member) \
@@ -87,12 +85,12 @@ DECLARE_EXPORTED_HEAP_OBJECT(Object, Base) {
void setInlineProperty(ExecutionEngine *e, uint index, Value v) {
Q_ASSERT(index < vtable()->nInlineProperties);
Value *prop = reinterpret_cast<Value *>(this) + vtable()->inlinePropertyOffset + index;
- WriteBarrier::write(e, this, prop, v);
+ WriteBarrier::write(e, this, prop->data_ptr(), v.asReturnedValue());
}
void setInlineProperty(ExecutionEngine *e, uint index, Heap::Base *b) {
Q_ASSERT(index < vtable()->nInlineProperties);
Value *prop = reinterpret_cast<Value *>(this) + vtable()->inlinePropertyOffset + index;
- WriteBarrier::write(e, this, prop, b);
+ WriteBarrier::write(e, this, prop->data_ptr(), b->asReturnedValue());
}
QV4::MemberData::Index writablePropertyData(uint index) {
@@ -153,7 +151,7 @@ DECLARE_EXPORTED_HEAP_OBJECT(Object, Base) {
dptr->_checkIsInitialized(); \
return dptr; \
} \
- V4_ASSERT_IS_TRIVIAL(QV4::Heap::DataClass);
+ Q_STATIC_ASSERT(std::is_trivial< QV4::Heap::DataClass >::value);
#define V4_PROTOTYPE(p) \
static QV4::Object *defaultPrototype(QV4::ExecutionEngine *e) \
@@ -238,8 +236,8 @@ struct Q_QML_EXPORT Object: Managed {
Heap::Object *prototype() const { return d()->prototype(); }
bool setPrototype(Object *proto);
- void getOwnProperty(String *name, PropertyAttributes *attrs, Property *p = 0);
- void getOwnProperty(uint index, PropertyAttributes *attrs, Property *p = 0);
+ void getOwnProperty(String *name, PropertyAttributes *attrs, Property *p = nullptr);
+ void getOwnProperty(uint index, PropertyAttributes *attrs, Property *p = nullptr);
MemberData::Index getValueOrSetter(String *name, PropertyAttributes *attrs);
ArrayData::Index getValueOrSetter(uint index, PropertyAttributes *attrs);
@@ -273,16 +271,8 @@ struct Q_QML_EXPORT Object: Managed {
insertMember(name, value, Attr_Data|Attr_NotEnumerable);
}
void defineDefaultProperty(const QString &name, const Value &value);
- // old calling convention
- void defineDefaultProperty(const QString &name, ReturnedValue (*code)(const BuiltinFunction *, CallData *), int argumentCount = 0);
- void defineDefaultProperty(String *name, ReturnedValue (*code)(const BuiltinFunction *, CallData *), int argumentCount = 0);
- // new calling convention
void defineDefaultProperty(const QString &name, ReturnedValue (*code)(const FunctionObject *, const Value *thisObject, const Value *argv, int argc), int argumentCount = 0);
void defineDefaultProperty(String *name, ReturnedValue (*code)(const FunctionObject *, const Value *thisObject, const Value *argv, int argc), int argumentCount = 0);
- void defineAccessorProperty(const QString &name, ReturnedValue (*getter)(const BuiltinFunction *, CallData *),
- ReturnedValue (*setter)(const BuiltinFunction *, CallData *));
- void defineAccessorProperty(String *name, ReturnedValue (*getter)(const BuiltinFunction *, CallData *),
- ReturnedValue (*setter)(const BuiltinFunction *, CallData *));
void defineAccessorProperty(const QString &name, ReturnedValue (*getter)(const FunctionObject *, const Value *, const Value *, int),
ReturnedValue (*setter)(const FunctionObject *, const Value *, const Value *, int));
void defineAccessorProperty(String *name, ReturnedValue (*getter)(const FunctionObject *, const Value *, const Value *, int),
@@ -308,8 +298,6 @@ struct Q_QML_EXPORT Object: Managed {
// Array handling
public:
- static void markObjects(Heap::Base *base, MarkStack *stack);
-
void copyArrayData(Object *other);
bool setArrayLength(uint newLen);
@@ -358,8 +346,8 @@ public:
}
void initSparseArray();
- SparseArrayNode *sparseBegin() { return arrayType() == Heap::ArrayData::Sparse ? d()->arrayData->sparse->begin() : 0; }
- SparseArrayNode *sparseEnd() { return arrayType() == Heap::ArrayData::Sparse ? d()->arrayData->sparse->end() : 0; }
+ SparseArrayNode *sparseBegin() { return arrayType() == Heap::ArrayData::Sparse ? d()->arrayData->sparse->begin() : nullptr; }
+ SparseArrayNode *sparseEnd() { return arrayType() == Heap::ArrayData::Sparse ? d()->arrayData->sparse->end() : nullptr; }
inline bool protoHasArray() {
Scope scope(engine());
@@ -372,9 +360,9 @@ public:
return false;
}
- inline ReturnedValue get(String *name, bool *hasProperty = 0) const
+ inline ReturnedValue get(String *name, bool *hasProperty = nullptr) const
{ return vtable()->get(this, name, hasProperty); }
- inline ReturnedValue getIndexed(uint idx, bool *hasProperty = 0) const
+ inline ReturnedValue getIndexed(uint idx, bool *hasProperty = nullptr) const
{ return vtable()->getIndexed(this, idx, hasProperty); }
// use the set variants instead, to customize throw behavior
@@ -563,7 +551,7 @@ inline void Object::arraySet(uint index, const Value &value)
template<>
inline const ArrayObject *Value::as() const {
- return isManaged() && m()->vtable()->type == Managed::Type_ArrayObject ? static_cast<const ArrayObject *>(this) : 0;
+ return isManaged() && m()->vtable()->type == Managed::Type_ArrayObject ? static_cast<const ArrayObject *>(this) : nullptr;
}
#ifndef V4_BOOTSTRAP
diff --git a/src/qml/jsruntime/qv4objectiterator.cpp b/src/qml/jsruntime/qv4objectiterator.cpp
index 0394c704f9..7bf7e1aa04 100644
--- a/src/qml/jsruntime/qv4objectiterator.cpp
+++ b/src/qml/jsruntime/qv4objectiterator.cpp
@@ -47,8 +47,8 @@ using namespace QV4;
void ObjectIterator::init(const Object *o)
{
- object->setM(o ? o->m() : 0);
- current->setM(o ? o->m() : 0);
+ object->setM(o ? o->m() : nullptr);
+ current->setM(o ? o->m() : nullptr);
if (object->as<ArgumentsObject>()) {
Scope scope(engine);
@@ -58,7 +58,7 @@ void ObjectIterator::init(const Object *o)
void ObjectIterator::next(Value *name, uint *index, Property *pd, PropertyAttributes *attrs)
{
- name->setM(0);
+ name->setM(nullptr);
*index = UINT_MAX;
if (!object->as<Object>()) {
@@ -100,7 +100,7 @@ void ObjectIterator::next(Value *name, uint *index, Property *pd, PropertyAttrib
if (flags & WithProtoChain)
current->setM(co->prototype());
else
- current->setM(0);
+ current->setM(nullptr);
arrayIndex = 0;
memberIndex = 0;
diff --git a/src/qml/jsruntime/qv4objectiterator_p.h b/src/qml/jsruntime/qv4objectiterator_p.h
index 30a6ad3025..744d16301a 100644
--- a/src/qml/jsruntime/qv4objectiterator_p.h
+++ b/src/qml/jsruntime/qv4objectiterator_p.h
@@ -73,7 +73,7 @@ struct Q_QML_EXPORT ObjectIteratorData
uint memberIndex;
uint flags;
};
-V4_ASSERT_IS_TRIVIAL(ObjectIteratorData)
+Q_STATIC_ASSERT(std::is_trivial< ObjectIteratorData >::value);
struct Q_QML_EXPORT ObjectIterator: ObjectIteratorData
{
@@ -101,7 +101,7 @@ struct Q_QML_EXPORT ObjectIterator: ObjectIteratorData
init(o);
}
- void next(Value *name, uint *index, Property *pd, PropertyAttributes *attributes = 0);
+ void next(Value *name, uint *index, Property *pd, PropertyAttributes *attributes = nullptr);
ReturnedValue nextPropertyName(Value *value);
ReturnedValue nextPropertyNameAsString(Value *value);
ReturnedValue nextPropertyNameAsString();
diff --git a/src/qml/jsruntime/qv4objectproto.cpp b/src/qml/jsruntime/qv4objectproto.cpp
index 5eef757ce9..b998b78520 100644
--- a/src/qml/jsruntime/qv4objectproto.cpp
+++ b/src/qml/jsruntime/qv4objectproto.cpp
@@ -121,8 +121,8 @@ void ObjectPrototype::init(ExecutionEngine *v4, Object *ctor)
ExecutionContext *global = v4->rootContext();
ScopedProperty p(scope);
- p->value = BuiltinFunction::create(global, v4->id___proto__(), method_get_proto);
- p->set = BuiltinFunction::create(global, v4->id___proto__(), method_set_proto);
+ p->value = FunctionObject::createBuiltinFunction(global, v4->id___proto__(), method_get_proto);
+ p->set = FunctionObject::createBuiltinFunction(global, v4->id___proto__(), method_set_proto);
insertMember(v4->id___proto__(), p, Attr_Accessor|Attr_NotEnumerable);
}
@@ -638,7 +638,7 @@ ReturnedValue ObjectPrototype::method_set_proto(const FunctionObject *b, const V
THROW_TYPE_ERROR();
if (argv[0].isNull()) {
- o->setPrototype(0);
+ o->setPrototype(nullptr);
RETURN_UNDEFINED();
}
diff --git a/src/qml/jsruntime/qv4persistent.cpp b/src/qml/jsruntime/qv4persistent.cpp
index 0b31c971f9..7fc74173e3 100644
--- a/src/qml/jsruntime/qv4persistent.cpp
+++ b/src/qml/jsruntime/qv4persistent.cpp
@@ -68,6 +68,22 @@ Page *getPage(Value *val) {
return reinterpret_cast<Page *>(reinterpret_cast<quintptr>(val) & ~((quintptr)(WTF::pageSize() - 1)));
}
+QML_NEARLY_ALWAYS_INLINE void insertInFront(PersistentValueStorage *storage, Page *p)
+{
+ p->header.next = reinterpret_cast<Page *>(storage->firstPage);
+ p->header.prev = reinterpret_cast<Page **>(&storage->firstPage);
+ if (p->header.next)
+ p->header.next->header.prev = &p->header.next;
+ storage->firstPage = p;
+}
+
+QML_NEARLY_ALWAYS_INLINE void unlink(Page *p)
+{
+ if (p->header.prev)
+ *p->header.prev = p->header.next;
+ if (p->header.next)
+ p->header.next->header.prev = p->header.prev;
+}
Page *allocatePage(PersistentValueStorage *storage)
{
@@ -78,19 +94,14 @@ Page *allocatePage(PersistentValueStorage *storage)
p->header.engine = storage->engine;
p->header.alloc = page;
- p->header.next = reinterpret_cast<Page *>(storage->firstPage);
- p->header.prev = reinterpret_cast<Page **>(&storage->firstPage);
p->header.refCount = 0;
p->header.freeList = 0;
- if (p->header.next)
- p->header.next->header.prev = &p->header.next;
+ insertInFront(storage, p);
for (int i = 0; i < kEntriesPerPage - 1; ++i) {
p->values[i].setEmpty(i + 1);
}
p->values[kEntriesPerPage - 1].setEmpty(-1);
- storage->firstPage = p;
-
return p;
}
@@ -161,7 +172,7 @@ Value &PersistentValueStorage::Iterator::operator *()
PersistentValueStorage::PersistentValueStorage(ExecutionEngine *engine)
: engine(engine),
- firstPage(0)
+ firstPage(nullptr)
{
}
@@ -174,9 +185,9 @@ PersistentValueStorage::~PersistentValueStorage()
p->values[i] = Encode::undefined();
}
Page *n = p->header.next;
- p->header.engine = 0;
- p->header.prev = 0;
- p->header.next = 0;
+ p->header.engine = nullptr;
+ p->header.prev = nullptr;
+ p->header.next = nullptr;
Q_ASSERT(p->header.refCount);
p = n;
}
@@ -195,6 +206,12 @@ Value *PersistentValueStorage::allocate()
Value *v = p->values + p->header.freeList;
p->header.freeList = v->int_32();
+
+ if (p->header.freeList != -1 && p != firstPage) {
+ unlink(p);
+ insertInFront(this, p);
+ }
+
++p->header.refCount;
v->setRawValue(Encode::undefined());
@@ -237,16 +254,13 @@ ExecutionEngine *PersistentValueStorage::getEngine(Value *v)
void PersistentValueStorage::freePage(void *page)
{
Page *p = static_cast<Page *>(page);
- if (p->header.prev)
- *p->header.prev = p->header.next;
- if (p->header.next)
- p->header.next->header.prev = p->header.prev;
+ unlink(p);
p->header.alloc.deallocate();
}
PersistentValue::PersistentValue(const PersistentValue &other)
- : val(0)
+ : val(nullptr)
{
if (other.val) {
val = other.engine()->memoryManager->m_persistentValues->allocate();
@@ -267,7 +281,7 @@ PersistentValue::PersistentValue(ExecutionEngine *engine, ReturnedValue value)
}
PersistentValue::PersistentValue(ExecutionEngine *engine, Object *object)
- : val(0)
+ : val(nullptr)
{
if (!object)
return;
@@ -344,7 +358,7 @@ void PersistentValue::set(ExecutionEngine *engine, Heap::Base *obj)
}
WeakValue::WeakValue(const WeakValue &other)
- : val(0)
+ : val(nullptr)
{
if (other.val) {
allocVal(other.engine());
@@ -404,6 +418,6 @@ void WeakValue::free()
PersistentValueStorage::free(val);
}
- val = 0;
+ val = nullptr;
}
diff --git a/src/qml/jsruntime/qv4persistent_p.h b/src/qml/jsruntime/qv4persistent_p.h
index 1f838f5531..55e8eefcb7 100644
--- a/src/qml/jsruntime/qv4persistent_p.h
+++ b/src/qml/jsruntime/qv4persistent_p.h
@@ -81,7 +81,7 @@ struct Q_QML_EXPORT PersistentValueStorage
Value &operator *();
};
Iterator begin() { return Iterator(firstPage, 0); }
- Iterator end() { return Iterator(0, 0); }
+ Iterator end() { return Iterator(nullptr, 0); }
static ExecutionEngine *getEngine(Value *v);
@@ -94,7 +94,7 @@ private:
class Q_QML_EXPORT PersistentValue
{
public:
- PersistentValue() : val(0) {}
+ PersistentValue() {}
PersistentValue(const PersistentValue &other);
PersistentValue &operator=(const PersistentValue &other);
PersistentValue &operator=(const WeakValue &other);
@@ -117,19 +117,19 @@ public:
}
Managed *asManaged() const {
if (!val)
- return 0;
+ return nullptr;
return val->managed();
}
template<typename T>
T *as() const {
if (!val)
- return 0;
+ return nullptr;
return val->as<T>();
}
ExecutionEngine *engine() const {
if (!val)
- return 0;
+ return nullptr;
return PersistentValueStorage::getEngine(val);
}
@@ -137,18 +137,18 @@ public:
bool isNullOrUndefined() const { return !val || val->isNullOrUndefined(); }
void clear() {
PersistentValueStorage::free(val);
- val = 0;
+ val = nullptr;
}
bool isEmpty() { return !val; }
private:
- Value *val;
+ Value *val = nullptr;
};
class Q_QML_EXPORT WeakValue
{
public:
- WeakValue() : val(0) {}
+ WeakValue() {}
WeakValue(const WeakValue &other);
WeakValue(ExecutionEngine *engine, const Value &value);
WeakValue &operator=(const WeakValue &other);
@@ -183,19 +183,19 @@ public:
}
Managed *asManaged() const {
if (!val)
- return 0;
+ return nullptr;
return val->managed();
}
template <typename T>
T *as() const {
if (!val)
- return 0;
+ return nullptr;
return val->as<T>();
}
ExecutionEngine *engine() const {
if (!val)
- return 0;
+ return nullptr;
return PersistentValueStorage::getEngine(val);
}
@@ -206,7 +206,7 @@ public:
void markOnce(MarkStack *markStack);
private:
- Value *val;
+ Value *val = nullptr;
private:
Q_NEVER_INLINE void allocVal(ExecutionEngine *engine);
diff --git a/src/qml/jsruntime/qv4profiling.cpp b/src/qml/jsruntime/qv4profiling.cpp
index bedcb5b164..5fd200efc1 100644
--- a/src/qml/jsruntime/qv4profiling.cpp
+++ b/src/qml/jsruntime/qv4profiling.cpp
@@ -120,7 +120,8 @@ void Profiler::startProfiling(quint64 features)
if (features & (1 << FeatureMemoryAllocation)) {
qint64 timestamp = m_timer.nsecsElapsed();
MemoryAllocationProperties heap = {timestamp,
- (qint64)m_engine->memoryManager->getAllocatedMem(),
+ (qint64)m_engine->memoryManager->getAllocatedMem() -
+ (qint64)m_engine->memoryManager->getLargeItemsMem(),
HeapPage};
m_memory_data.append(heap);
MemoryAllocationProperties small = {timestamp,
diff --git a/src/qml/jsruntime/qv4profiling_p.h b/src/qml/jsruntime/qv4profiling_p.h
index 8a24c71815..e8c154e4e7 100644
--- a/src/qml/jsruntime/qv4profiling_p.h
+++ b/src/qml/jsruntime/qv4profiling_p.h
@@ -59,12 +59,18 @@
#if !QT_CONFIG(qml_debug)
+#define Q_V4_PROFILE_ALLOC(engine, size, type) (!engine)
+#define Q_V4_PROFILE_DEALLOC(engine, size, type) (!engine)
QT_BEGIN_NAMESPACE
namespace QV4 {
namespace Profiling {
class Profiler {};
+class FunctionCallProfiler {
+public:
+ FunctionCallProfiler(ExecutionEngine *, Function *) {}
+};
}
}
@@ -72,6 +78,16 @@ QT_END_NAMESPACE
#else
+#define Q_V4_PROFILE_ALLOC(engine, size, type)\
+ (engine->profiler() &&\
+ (engine->profiler()->featuresEnabled & (1 << Profiling::FeatureMemoryAllocation)) ?\
+ engine->profiler()->trackAlloc(size, type) : false)
+
+#define Q_V4_PROFILE_DEALLOC(engine, size, type) \
+ (engine->profiler() &&\
+ (engine->profiler()->featuresEnabled & (1 << Profiling::FeatureMemoryAllocation)) ?\
+ engine->profiler()->trackDealloc(size, type) : false)
+
QT_BEGIN_NAMESPACE
namespace QV4 {
@@ -123,7 +139,7 @@ struct MemoryAllocationProperties {
class FunctionCall {
public:
- FunctionCall() : m_function(0), m_start(0), m_end(0)
+ FunctionCall() : m_function(nullptr), m_start(0), m_end(0)
{ Q_ASSERT_X(false, Q_FUNC_INFO, "Cannot construct a function call without function"); }
FunctionCall(Function *function, qint64 start, qint64 end) :
@@ -211,16 +227,24 @@ public:
bool trackAlloc(size_t size, MemoryType type)
{
- MemoryAllocationProperties allocation = {m_timer.nsecsElapsed(), (qint64)size, type};
- m_memory_data.append(allocation);
- return true;
+ if (size) {
+ MemoryAllocationProperties allocation = {m_timer.nsecsElapsed(), (qint64)size, type};
+ m_memory_data.append(allocation);
+ return true;
+ } else {
+ return false;
+ }
}
bool trackDealloc(size_t size, MemoryType type)
{
- MemoryAllocationProperties allocation = {m_timer.nsecsElapsed(), -(qint64)size, type};
- m_memory_data.append(allocation);
- return true;
+ if (size) {
+ MemoryAllocationProperties allocation = {m_timer.nsecsElapsed(), -(qint64)size, type};
+ m_memory_data.append(allocation);
+ return true;
+ } else {
+ return false;
+ }
}
quint64 featuresEnabled;
@@ -252,7 +276,7 @@ public:
// It's enough to ref() the function in the destructor as it will probably not disappear while
// it's executing ...
FunctionCallProfiler(ExecutionEngine *engine, Function *f)
- : profiler(0)
+ : profiler(nullptr)
{
Profiler *p = engine->profiler();
if (Q_UNLIKELY(p) && (p->featuresEnabled & (1 << Profiling::FeatureFunctionCall))) {
diff --git a/src/qml/jsruntime/qv4property_p.h b/src/qml/jsruntime/qv4property_p.h
index 2a5b6f7f74..7cb106c424 100644
--- a/src/qml/jsruntime/qv4property_p.h
+++ b/src/qml/jsruntime/qv4property_p.h
@@ -84,7 +84,7 @@ struct Property {
inline Heap::FunctionObject *getter() const { return reinterpret_cast<Heap::FunctionObject *>(value.heapObject()); }
inline Heap::FunctionObject *setter() const { return reinterpret_cast<Heap::FunctionObject *>(set.heapObject()); }
inline void setGetter(FunctionObject *g) { value = reinterpret_cast<Managed *>(g); }
- inline void setSetter(FunctionObject *s) { set = (s ? reinterpret_cast<Managed *>(s) : 0); }
+ inline void setSetter(FunctionObject *s) { set = (s ? reinterpret_cast<Managed *>(s) : nullptr); }
void copy(const Property *other, PropertyAttributes attrs) {
value = other->value;
@@ -92,7 +92,7 @@ struct Property {
set = other->set;
}
- explicit Property() { value = Encode::undefined(); set = Value::fromHeapObject(0); }
+ explicit Property() { value = Encode::undefined(); set = Value::fromHeapObject(nullptr); }
Property(Heap::FunctionObject *getter, Heap::FunctionObject *setter) {
value.setM(reinterpret_cast<Heap::Base *>(getter));
set.setM(reinterpret_cast<Heap::Base *>(setter));
diff --git a/src/qml/jsruntime/qv4qmlcontext.cpp b/src/qml/jsruntime/qv4qmlcontext.cpp
index 5a165b2309..040f060476 100644
--- a/src/qml/jsruntime/qv4qmlcontext.cpp
+++ b/src/qml/jsruntime/qv4qmlcontext.cpp
@@ -108,8 +108,8 @@ ReturnedValue QQmlContextWrapper::get(const Managed *m, String *name, bool *hasP
return result->asReturnedValue();
}
- // Its possible we could delay the calculation of the "actual" context (in the case
- // of sub contexts) until it is definately needed.
+ // It's possible we could delay the calculation of the "actual" context (in the case
+ // of sub contexts) until it is definitely needed.
QQmlContextData *context = resource->getContext();
QQmlContextData *expressionContext = context;
@@ -138,7 +138,9 @@ ReturnedValue QQmlContextWrapper::get(const Managed *m, String *name, bool *hasP
*hasProperty = true;
if (r.scriptIndex != -1) {
QV4::ScopedObject scripts(scope, context->importedScripts.valueRef());
- return scripts->getIndexed(r.scriptIndex);
+ if (scripts)
+ return scripts->getIndexed(r.scriptIndex);
+ return QV4::Encode::null();
} else if (r.type.isValid()) {
return QQmlTypeWrapper::create(v4, scopeObject, r.type);
} else if (r.importNamespace) {
@@ -154,7 +156,7 @@ ReturnedValue QQmlContextWrapper::get(const Managed *m, String *name, bool *hasP
while (context) {
// Search context properties
- const QV4::IdentifierHash<int> &properties = context->propertyNames();
+ const QV4::IdentifierHash &properties = context->propertyNames();
if (properties.count()) {
int propertyIdx = properties.value(name);
@@ -200,7 +202,7 @@ ReturnedValue QQmlContextWrapper::get(const Managed *m, String *name, bool *hasP
return result->asReturnedValue();
}
}
- scopeObject = 0;
+ scopeObject = nullptr;
// Search context object
@@ -248,8 +250,8 @@ bool QQmlContextWrapper::put(Managed *m, String *name, const Value &value)
return Object::put(m, name, value);
}
- // Its possible we could delay the calculation of the "actual" context (in the case
- // of sub contexts) until it is definately needed.
+ // It's possible we could delay the calculation of the "actual" context (in the case
+ // of sub contexts) until it is definitely needed.
QQmlContextData *context = wrapper->getContext();
QQmlContextData *expressionContext = context;
@@ -261,7 +263,7 @@ bool QQmlContextWrapper::put(Managed *m, String *name, const Value &value)
QObject *scopeObject = wrapper->getScopeObject();
while (context) {
- const QV4::IdentifierHash<int> &properties = context->propertyNames();
+ const QV4::IdentifierHash &properties = context->propertyNames();
// Search context properties
if (properties.count() && properties.value(name) != -1)
return false;
@@ -270,7 +272,7 @@ bool QQmlContextWrapper::put(Managed *m, String *name, const Value &value)
if (scopeObject &&
QV4::QObjectWrapper::setQmlProperty(v4, context, scopeObject, name, QV4::QObjectWrapper::CheckRevision, value))
return true;
- scopeObject = 0;
+ scopeObject = nullptr;
// Search context object
if (context->contextObject &&
@@ -310,7 +312,7 @@ Heap::QmlContext *QmlContext::createWorkerContext(ExecutionContext *parent, cons
context->isInternal = true;
context->isJSContext = true;
- Scoped<QQmlContextWrapper> qml(scope, scope.engine->memoryManager->allocObject<QQmlContextWrapper>(context, (QObject*)0));
+ Scoped<QQmlContextWrapper> qml(scope, scope.engine->memoryManager->allocObject<QQmlContextWrapper>(context, (QObject*)nullptr));
qml->d()->isNullWrapper = true;
qml->setReadOnly(false);
diff --git a/src/qml/jsruntime/qv4qmlcontext_p.h b/src/qml/jsruntime/qv4qmlcontext_p.h
index a1df5cb95f..647bef7fc1 100644
--- a/src/qml/jsruntime/qv4qmlcontext_p.h
+++ b/src/qml/jsruntime/qv4qmlcontext_p.h
@@ -91,6 +91,7 @@ struct Q_QML_EXPORT QQmlContextWrapper : Object
{
V4_OBJECT2(QQmlContextWrapper, Object)
V4_NEEDS_DESTROY
+ V4_INTERNALCLASS(QmlContextWrapper)
inline QObject *getScopeObject() const { return d()->scopeObject; }
inline QQmlContextData *getContext() const { return *d()->context; }
@@ -104,6 +105,7 @@ struct Q_QML_EXPORT QQmlContextWrapper : Object
struct Q_QML_EXPORT QmlContext : public ExecutionContext
{
V4_MANAGED(QmlContext, ExecutionContext)
+ V4_INTERNALCLASS(QmlContext)
static Heap::QmlContext *createWorkerContext(QV4::ExecutionContext *parent, const QUrl &source, Value *sendFunction);
static Heap::QmlContext *create(QV4::ExecutionContext *parent, QQmlContextData *context, QObject *scopeObject);
diff --git a/src/qml/jsruntime/qv4qobjectwrapper.cpp b/src/qml/jsruntime/qv4qobjectwrapper.cpp
index 6d7d929b61..c1bbe2a330 100644
--- a/src/qml/jsruntime/qv4qobjectwrapper.cpp
+++ b/src/qml/jsruntime/qv4qobjectwrapper.cpp
@@ -99,7 +99,7 @@ QPair<QObject *, int> QObjectMethod::extractQtMethod(const QV4::FunctionObject *
return qMakePair(method->object(), method->methodIndex());
}
- return qMakePair((QObject *)0, -1);
+ return qMakePair((QObject *)nullptr, -1);
}
static QPair<QObject *, int> extractQtSignal(const Value &value)
@@ -116,7 +116,7 @@ static QPair<QObject *, int> extractQtSignal(const Value &value)
return qMakePair(handler->object(), handler->signalIndex());
}
- return qMakePair((QObject *)0, -1);
+ return qMakePair((QObject *)nullptr, -1);
}
static QV4::ReturnedValue loadProperty(QV4::ExecutionEngine *v4, QObject *object,
@@ -126,7 +126,7 @@ static QV4::ReturnedValue loadProperty(QV4::ExecutionEngine *v4, QObject *object
QV4::Scope scope(v4);
if (property.isQObject()) {
- QObject *rv = 0;
+ QObject *rv = nullptr;
property.readProperty(object, &rv);
return QV4::QObjectWrapper::wrap(v4, rv);
} else if (property.isQList()) {
@@ -194,7 +194,7 @@ static QV4::ReturnedValue loadProperty(QV4::ExecutionEngine *v4, QObject *object
"'%s::%s'", p.typeName(), object->metaObject()->className(), p.name());
return QV4::Encode::undefined();
} else {
- QVariant v(property.propType(), (void *)0);
+ QVariant v(property.propType(), (void *)nullptr);
property.readProperty(object, v.data());
return scope.engine->fromVariant(v);
}
@@ -217,7 +217,7 @@ QQmlPropertyData *QObjectWrapper::findProperty(ExecutionEngine *engine, QObject
Q_UNUSED(revisionMode);
QQmlData *ddata = QQmlData::get(o, false);
- QQmlPropertyData *result = 0;
+ QQmlPropertyData *result = nullptr;
if (ddata && ddata->propertyCache)
result = ddata->propertyCache->property(name, o, qmlContext);
else
@@ -249,7 +249,7 @@ ReturnedValue QObjectWrapper::getProperty(ExecutionEngine *engine, QObject *obje
}
}
- QQmlEnginePrivate *ep = engine->qmlEngine() ? QQmlEnginePrivate::get(engine->qmlEngine()) : 0;
+ QQmlEnginePrivate *ep = engine->qmlEngine() ? QQmlEnginePrivate::get(engine->qmlEngine()) : nullptr;
if (captureRequired && ep && ep->propertyCapture && !property->isConstant())
ep->propertyCapture->captureProperty(object, property->coreIndex(), property->notifyIndex());
@@ -335,6 +335,11 @@ ReturnedValue QObjectWrapper::getProperty(ExecutionEngine *engine, QObject *obje
if (!ddata)
return QV4::Encode::undefined();
+ if (Q_UNLIKELY(!ddata->propertyCache)) {
+ ddata->propertyCache = QQmlEnginePrivate::get(engine)->cache(object->metaObject());
+ ddata->propertyCache->addref();
+ }
+
QQmlPropertyCache *cache = ddata->propertyCache;
Q_ASSERT(cache);
QQmlPropertyData *property = cache->property(propertyIndex);
@@ -434,7 +439,7 @@ void QObjectWrapper::setProperty(ExecutionEngine *engine, QObject *object, QQmlP
return;
}
- QQmlBinding *newBinding = 0;
+ QQmlBinding *newBinding = nullptr;
QV4::Scope scope(engine);
QV4::ScopedFunctionObject f(scope, value);
if (f) {
@@ -496,9 +501,9 @@ void QObjectWrapper::setProperty(ExecutionEngine *engine, QObject *object, QQmlP
QMetaObject::metacall(object, QMetaObject::WriteProperty, property->coreIndex(), argv);
if (value.isNull() && property->isQObject()) {
- PROPERTY_STORE(QObject*, 0);
+ PROPERTY_STORE(QObject*, nullptr);
} else if (value.isUndefined() && property->isResettable()) {
- void *a[] = { 0 };
+ void *a[] = { nullptr };
QMetaObject::metacall(object, QMetaObject::ResetProperty, property->coreIndex(), a);
} else if (value.isUndefined() && property->propType() == qMetaTypeId<QVariant>()) {
PROPERTY_STORE(QVariant, QVariant());
@@ -531,7 +536,7 @@ void QObjectWrapper::setProperty(ExecutionEngine *engine, QObject *object, QQmlP
Q_ASSERT(vmemo);
vmemo->setVMEProperty(property->coreIndex(), value);
} else if (property->propType() == qMetaTypeId<QQmlScriptString>() && (value.isUndefined() || value.isPrimitive())) {
- QQmlScriptString ss(value.toQStringNoThrow(), 0 /* context */, object);
+ QQmlScriptString ss(value.toQStringNoThrow(), nullptr /* context */, object);
if (value.isNumber()) {
ss.d->numberValue = value.toNumber();
ss.d->isNumberLiteral = true;
@@ -549,7 +554,7 @@ void QObjectWrapper::setProperty(ExecutionEngine *engine, QObject *object, QQmlP
QQmlContextData *callingQmlContext = scope.engine->callingQmlContext();
if (!QQmlPropertyPrivate::write(object, *property, v, callingQmlContext)) {
- const char *valueType = 0;
+ const char *valueType = nullptr;
if (v.userType() == QVariant::Invalid) valueType = "null";
else valueType = QMetaType::typeName(v.userType());
@@ -590,7 +595,7 @@ ReturnedValue QObjectWrapper::wrap_slowPath(ExecutionEngine *engine, QObject *ob
} else {
// If this object is tainted, we have to check to see if it is in our
// tainted object list
- ScopedObject alternateWrapper(scope, (Object *)0);
+ ScopedObject alternateWrapper(scope, (Object *)nullptr);
if (engine->m_multiplyWrappedQObjects && ddata->hasTaintedV4Object)
alternateWrapper = engine->m_multiplyWrappedQObjects->value(object);
@@ -715,6 +720,10 @@ bool QObjectWrapper::put(Managed *m, String *name, const Value &value)
PropertyAttributes QObjectWrapper::query(const Managed *m, String *name)
{
const QObjectWrapper *that = static_cast<const QObjectWrapper*>(m);
+ const QObject *thatObject = that->d()->object();
+ if (QQmlData::wasDeleted(thatObject))
+ return QV4::Object::query(m, name);
+
ExecutionEngine *engine = that->engine();
QQmlContextData *qmlContext = engine->callingQmlContext();
QQmlPropertyData local;
@@ -732,7 +741,7 @@ void QObjectWrapper::advanceIterator(Managed *m, ObjectIterator *it, Value *name
static const int destroyedIdx2 = QObject::staticMetaObject.indexOfSignal("destroyed()");
static const int deleteLaterIdx = QObject::staticMetaObject.indexOfSlot("deleteLater()");
- name->setM(0);
+ name->setM(nullptr);
*index = UINT_MAX;
QObjectWrapper *that = static_cast<QObjectWrapper*>(m);
@@ -809,7 +818,7 @@ struct QObjectSlotDispatcher : public QtPrivate::QSlotObjectBase
break;
QQmlMetaObject::ArgTypeStorage storage;
- int *argsTypes = QQmlMetaObject(r).methodParameterTypes(This->signalIndex, &storage, 0);
+ int *argsTypes = QQmlMetaObject(r).methodParameterTypes(This->signalIndex, &storage, nullptr);
int argCount = argsTypes ? argsTypes[0]:0;
@@ -838,7 +847,7 @@ struct QObjectSlotDispatcher : public QtPrivate::QSlotObjectBase
QQmlEnginePrivate::get(qmlEngine)->warning(error);
} else {
QMessageLogger(error.url().toString().toLatin1().constData(),
- error.line(), 0).warning().noquote()
+ error.line(), nullptr).warning().noquote()
<< error.toString();
}
}
@@ -900,14 +909,14 @@ struct QObjectSlotDispatcher : public QtPrivate::QSlotObjectBase
} // namespace QV4
-ReturnedValue QObjectWrapper::method_connect(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QObjectWrapper::method_connect(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() == 0)
+ if (argc == 0)
THROW_GENERIC_ERROR("Function.prototype.connect: no arguments given");
- QPair<QObject *, int> signalInfo = extractQtSignal(callData->thisObject);
+ QPair<QObject *, int> signalInfo = extractQtSignal(*thisObject);
QObject *signalObject = signalInfo.first;
int signalIndex = signalInfo.second; // in method range, not signal range!
@@ -921,25 +930,25 @@ ReturnedValue QObjectWrapper::method_connect(const BuiltinFunction *b, CallData
THROW_GENERIC_ERROR("Function.prototype.connect: this object is not a signal");
QV4::ScopedFunctionObject f(scope);
- QV4::ScopedValue thisObject (scope, QV4::Encode::undefined());
+ QV4::ScopedValue object (scope, QV4::Encode::undefined());
- if (callData->argc() == 1) {
- f = callData->args[0];
- } else if (callData->argc() >= 2) {
- thisObject = callData->args[0];
- f = callData->args[1];
+ if (argc == 1) {
+ f = argv[0];
+ } else if (argc >= 2) {
+ object = argv[0];
+ f = argv[1];
}
if (!f)
THROW_GENERIC_ERROR("Function.prototype.connect: target is not a function");
- if (!thisObject->isUndefined() && !thisObject->isObject())
+ if (!object->isUndefined() && !object->isObject())
THROW_GENERIC_ERROR("Function.prototype.connect: target this is not an object");
QV4::QObjectSlotDispatcher *slot = new QV4::QObjectSlotDispatcher;
slot->signalIndex = signalIndex;
- slot->thisObject.set(scope.engine, thisObject);
+ slot->thisObject.set(scope.engine, object);
slot->function.set(scope.engine, f);
if (QQmlData *ddata = QQmlData::get(signalObject)) {
@@ -952,14 +961,14 @@ ReturnedValue QObjectWrapper::method_connect(const BuiltinFunction *b, CallData
RETURN_UNDEFINED();
}
-ReturnedValue QObjectWrapper::method_disconnect(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QObjectWrapper::method_disconnect(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() == 0)
+ if (argc == 0)
THROW_GENERIC_ERROR("Function.prototype.disconnect: no arguments given");
- QPair<QObject *, int> signalInfo = extractQtSignal(callData->thisObject);
+ QPair<QObject *, int> signalInfo = extractQtSignal(*thisObject);
QObject *signalObject = signalInfo.first;
int signalIndex = signalInfo.second;
@@ -975,11 +984,11 @@ ReturnedValue QObjectWrapper::method_disconnect(const BuiltinFunction *b, CallDa
QV4::ScopedFunctionObject functionValue(scope);
QV4::ScopedValue functionThisValue(scope, QV4::Encode::undefined());
- if (callData->argc() == 1) {
- functionValue = callData->args[0];
- } else if (callData->argc() >= 2) {
- functionThisValue = callData->args[0];
- functionValue = callData->args[1];
+ if (argc == 1) {
+ functionValue = argv[0];
+ } else if (argc >= 2) {
+ functionThisValue = argv[0];
+ functionValue = argv[1];
}
if (!functionValue)
@@ -1048,8 +1057,8 @@ void QObjectWrapper::destroyObject(bool lastCall)
if (ddata && ddata->ownContext) {
Q_ASSERT(ddata->ownContext == ddata->context);
ddata->ownContext->emitDestruction();
- ddata->ownContext = 0;
- ddata->context = 0;
+ ddata->ownContext = nullptr;
+ ddata->context = nullptr;
}
// This object is notionally destroyed now
ddata->isQueuedForDeletion = true;
@@ -1177,14 +1186,14 @@ static QV4::ReturnedValue CallMethod(const QQmlObjectOrGadget &object, int index
} else {
- void *args[] = { 0 };
+ void *args[] = { nullptr };
object.metacall(callType, index, args);
return Encode::undefined();
}
}
-/*!
+/*
Returns the match score for converting \a actual to be of type \a conversionType. A
zero score means "perfect match" whereas a higher score is worse.
@@ -1341,7 +1350,7 @@ static inline int QMetaObject_methods(const QMetaObject *metaObject)
return reinterpret_cast<const Private *>(metaObject->d.data)->methodCount;
}
-/*!
+/*
Returns the next related method, if one, or 0.
*/
static const QQmlPropertyData * RelatedMethod(const QQmlObjectOrGadget &object,
@@ -1350,7 +1359,7 @@ static const QQmlPropertyData * RelatedMethod(const QQmlObjectOrGadget &object,
const QQmlPropertyCache *propertyCache)
{
if (!current->isOverload())
- return 0;
+ return nullptr;
Q_ASSERT(!current->overrideIndexIsProperty());
@@ -1368,7 +1377,7 @@ static const QQmlPropertyData * RelatedMethod(const QQmlObjectOrGadget &object,
// If we've been called before with the same override index, then
// we can't go any further...
if (&dummy == current && dummy.coreIndex() == current->overrideIndex())
- return 0;
+ return nullptr;
QMetaMethod method = mo->method(current->overrideIndex());
dummy.load(method);
@@ -1403,7 +1412,7 @@ static QV4::ReturnedValue CallPrecise(const QQmlObjectOrGadget &object, const QQ
if (data.hasArguments()) {
- int *args = 0;
+ int *args = nullptr;
QQmlMetaObject::ArgTypeStorage storage;
if (data.isConstructor())
@@ -1426,12 +1435,12 @@ static QV4::ReturnedValue CallPrecise(const QQmlObjectOrGadget &object, const QQ
} else {
- return CallMethod(object, data.coreIndex(), returnType, 0, 0, engine, callArgs, callType);
+ return CallMethod(object, data.coreIndex(), returnType, 0, nullptr, engine, callArgs, callType);
}
}
-/*!
+/*
Resolve the overloaded method to call. The algorithm works conceptually like this:
1. Resolve the set of overloads it is *possible* to call.
Impossible overloads include those that have too many parameters or have parameters
@@ -1463,9 +1472,9 @@ static QV4::ReturnedValue CallOverloaded(const QQmlObjectOrGadget &object, const
do {
QQmlMetaObject::ArgTypeStorage storage;
int methodArgumentCount = 0;
- int *methodArgTypes = 0;
+ int *methodArgTypes = nullptr;
if (attempt->hasArguments()) {
- int *args = object.methodParameterTypes(attempt->coreIndex(), &storage, 0);
+ int *args = object.methodParameterTypes(attempt->coreIndex(), &storage, nullptr);
if (!args) // Must be an unknown argument
continue;
@@ -1493,7 +1502,7 @@ static QV4::ReturnedValue CallOverloaded(const QQmlObjectOrGadget &object, const
if (bestParameterScore == 0 && bestMatchScore == 0)
break; // We can't get better than that
- } while ((attempt = RelatedMethod(object, attempt, dummy, propertyCache)) != 0);
+ } while ((attempt = RelatedMethod(object, attempt, dummy, propertyCache)) != nullptr);
if (best.isValid()) {
return CallPrecise(object, best, engine, callArgs, callType);
@@ -1560,7 +1569,7 @@ void *CallArgument::dataPtr()
return stdVectorQModelIndexPtr;
else if (type != 0)
return (void *)&allocData;
- return 0;
+ return nullptr;
}
void CallArgument::initAsType(int callType)
@@ -1578,7 +1587,7 @@ void CallArgument::initAsType(int callType)
callType == QMetaType::Float) {
type = callType;
} else if (callType == QMetaType::QObjectStar) {
- qobjectPtr = 0;
+ qobjectPtr = nullptr;
type = callType;
} else if (callType == QMetaType::QString) {
qstringPtr = new (&allocData) QString();
@@ -1603,7 +1612,7 @@ void CallArgument::initAsType(int callType)
jsonValuePtr = new (&allocData) QJsonValue();
} else {
type = -1;
- qvariantPtr = new (&allocData) QVariant(callType, (void *)0);
+ qvariantPtr = new (&allocData) QVariant(callType, (void *)nullptr);
}
}
@@ -1655,7 +1664,7 @@ void CallArgument::fromValue(int callType, QV4::ExecutionEngine *engine, const Q
qstringPtr = new (&allocData) QString(value.toQStringNoThrow());
type = callType;
} else if (callType == QMetaType::QObjectStar) {
- qobjectPtr = 0;
+ qobjectPtr = nullptr;
if (const QV4::QObjectWrapper *qobjectWrapper = value.as<QV4::QObjectWrapper>())
qobjectPtr = qobjectWrapper->object();
else if (const QV4::QQmlTypeWrapper *qmlTypeWrapper = value.as<QV4::QQmlTypeWrapper>())
@@ -1672,14 +1681,14 @@ void CallArgument::fromValue(int callType, QV4::ExecutionEngine *engine, const Q
uint length = array->getLength();
for (uint ii = 0; ii < length; ++ii) {
- QObject *o = 0;
+ QObject *o = nullptr;
qobjectWrapper = array->getIndexed(ii);
if (!!qobjectWrapper)
o = qobjectWrapper->object();
qlistPtr->append(o);
}
} else {
- QObject *o = 0;
+ QObject *o = nullptr;
if (const QV4::QObjectWrapper *qobjectWrapper = value.as<QV4::QObjectWrapper>())
o = qobjectWrapper->object();
qlistPtr->append(o);
@@ -1736,7 +1745,7 @@ void CallArgument::fromValue(int callType, QV4::ExecutionEngine *engine, const Q
qvariantPtr = new (&allocData) QVariant();
type = -1;
- QQmlEnginePrivate *ep = engine->qmlEngine() ? QQmlEnginePrivate::get(engine->qmlEngine()) : 0;
+ QQmlEnginePrivate *ep = engine->qmlEngine() ? QQmlEnginePrivate::get(engine->qmlEngine()) : nullptr;
QVariant v = scope.engine->toVariant(value, callType);
if (v.userType() == callType) {
@@ -1749,12 +1758,12 @@ void CallArgument::fromValue(int callType, QV4::ExecutionEngine *engine, const Q
if (!mo.isNull()) {
QObject *obj = ep->toQObject(v);
- if (obj != 0 && !QQmlMetaObject::canConvert(obj, mo))
- obj = 0;
+ if (obj != nullptr && !QQmlMetaObject::canConvert(obj, mo))
+ obj = nullptr;
*qvariantPtr = QVariant(callType, &obj);
} else {
- *qvariantPtr = QVariant(callType, (void *)0);
+ *qvariantPtr = QVariant(callType, (void *)nullptr);
}
}
}
@@ -1953,7 +1962,7 @@ ReturnedValue QObjectMethod::callInternal(const Value *thisObject, const Value *
QQmlV4Function func(callData, rv, v4);
QQmlV4Function *funcptr = &func;
- void *args[] = { 0, &funcptr };
+ void *args[] = { nullptr, &funcptr };
object.metacall(QMetaObject::InvokeMetaMethod, method.coreIndex(), args);
return rv->asReturnedValue();
@@ -2083,11 +2092,11 @@ ReturnedValue QMetaObjectWrapper::callOverloadedConstructor(QV4::ExecutionEngine
for (int i = 0; i < numberOfConstructors; i++) {
const QQmlPropertyData & attempt = d()->constructors[i];
+ QQmlMetaObject::ArgTypeStorage storage;
int methodArgumentCount = 0;
- int *methodArgTypes = 0;
+ int *methodArgTypes = nullptr;
if (attempt.hasArguments()) {
- QQmlMetaObject::ArgTypeStorage storage;
- int *args = object.constructorParameterTypes(attempt.coreIndex(), &storage, 0);
+ int *args = object.constructorParameterTypes(attempt.coreIndex(), &storage, nullptr);
if (!args) // Must be an unknown argument
continue;
diff --git a/src/qml/jsruntime/qv4qobjectwrapper_p.h b/src/qml/jsruntime/qv4qobjectwrapper_p.h
index c00e82e4fa..1455acc1b3 100644
--- a/src/qml/jsruntime/qv4qobjectwrapper_p.h
+++ b/src/qml/jsruntime/qv4qobjectwrapper_p.h
@@ -166,8 +166,8 @@ struct Q_QML_EXPORT QObjectWrapper : public Object
QObject *object() const { return d()->object(); }
- ReturnedValue getQmlProperty(QQmlContextData *qmlContext, String *name, RevisionMode revisionMode, bool *hasProperty = 0, bool includeImports = false) const;
- static ReturnedValue getQmlProperty(ExecutionEngine *engine, QQmlContextData *qmlContext, QObject *object, String *name, RevisionMode revisionMode, bool *hasProperty = 0);
+ ReturnedValue getQmlProperty(QQmlContextData *qmlContext, String *name, RevisionMode revisionMode, bool *hasProperty = nullptr, bool includeImports = false) const;
+ static ReturnedValue getQmlProperty(ExecutionEngine *engine, QQmlContextData *qmlContext, QObject *object, String *name, RevisionMode revisionMode, bool *hasProperty = nullptr);
static bool setQmlProperty(ExecutionEngine *engine, QQmlContextData *qmlContext, QObject *object, String *name, RevisionMode revisionMode, const Value &value);
@@ -198,8 +198,8 @@ protected:
static PropertyAttributes query(const Managed *, String *name);
static void advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint *index, Property *p, PropertyAttributes *attributes);
- static ReturnedValue method_connect(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_disconnect(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_connect(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_disconnect(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
private:
Q_NEVER_INLINE static ReturnedValue wrap_slowPath(ExecutionEngine *engine, QObject *object);
diff --git a/src/qml/jsruntime/qv4regexp.cpp b/src/qml/jsruntime/qv4regexp.cpp
index fb49def317..d99536829b 100644
--- a/src/qml/jsruntime/qv4regexp.cpp
+++ b/src/qml/jsruntime/qv4regexp.cpp
@@ -48,7 +48,7 @@ RegExpCache::~RegExpCache()
{
for (RegExpCache::Iterator it = begin(), e = end(); it != e; ++it) {
if (RegExp *re = it.value().as<RegExp>())
- re->d()->cache = 0;
+ re->d()->cache = nullptr;
}
}
@@ -82,7 +82,7 @@ Heap::RegExp *RegExp::create(ExecutionEngine* engine, const QString& pattern, bo
return result->d();
Scope scope(engine);
- Scoped<RegExp> result(scope, engine->memoryManager->alloc<RegExp>(pattern, ignoreCase, multiline, global));
+ Scoped<RegExp> result(scope, engine->memoryManager->alloc<RegExp>(engine, pattern, ignoreCase, multiline, global));
result->d()->cache = cache;
cachedValue.set(engine, result);
@@ -90,7 +90,7 @@ Heap::RegExp *RegExp::create(ExecutionEngine* engine, const QString& pattern, bo
return result->d();
}
-void Heap::RegExp::init(const QString &pattern, bool ignoreCase, bool multiline, bool global)
+void Heap::RegExp::init(ExecutionEngine *engine, const QString &pattern, bool ignoreCase, bool multiline, bool global)
{
Base::init();
this->pattern = new QString(pattern);
@@ -100,13 +100,13 @@ void Heap::RegExp::init(const QString &pattern, bool ignoreCase, bool multiline,
valid = false;
- const char* error = 0;
+ const char* error = nullptr;
JSC::Yarr::YarrPattern yarrPattern(WTF::String(pattern), ignoreCase, multiLine, &error);
if (error)
return;
subPatternCount = yarrPattern.m_numSubpatterns;
#if ENABLE(YARR_JIT)
- if (!yarrPattern.m_containsBackreferences) {
+ if (!yarrPattern.m_containsBackreferences && engine->canJIT()) {
jitCode = new JSC::Yarr::YarrCodeBlock;
JSC::JSGlobalData dummy(internalClass->engine->regExpAllocator);
JSC::Yarr::jitCompile(yarrPattern, JSC::Yarr::Char16, &dummy, *jitCode);
diff --git a/src/qml/jsruntime/qv4regexp_p.h b/src/qml/jsruntime/qv4regexp_p.h
index 498468e165..56454f73d3 100644
--- a/src/qml/jsruntime/qv4regexp_p.h
+++ b/src/qml/jsruntime/qv4regexp_p.h
@@ -76,7 +76,7 @@ struct RegExpCacheKey;
namespace Heap {
struct RegExp : Base {
- void init(const QString& pattern, bool ignoreCase, bool multiline, bool global);
+ void init(ExecutionEngine *engine, const QString& pattern, bool ignoreCase, bool multiline, bool global);
void destroy();
QString *pattern;
@@ -100,7 +100,7 @@ struct RegExp : Base {
int captureCount() const { return subPatternCount + 1; }
};
-V4_ASSERT_IS_TRIVIAL(RegExp)
+Q_STATIC_ASSERT(std::is_trivial< RegExp >::value);
}
diff --git a/src/qml/jsruntime/qv4regexpobject.cpp b/src/qml/jsruntime/qv4regexpobject.cpp
index f95719b25f..000e2c3a7e 100644
--- a/src/qml/jsruntime/qv4regexpobject.cpp
+++ b/src/qml/jsruntime/qv4regexpobject.cpp
@@ -283,25 +283,25 @@ void RegExpPrototype::init(ExecutionEngine *engine, Object *constructor)
ctor->defineReadonlyProperty(engine->id_length(), Primitive::fromInt32(2));
// Properties deprecated in the spec but required by "the web" :(
- ctor->defineAccessorProperty(QStringLiteral("lastMatch"), method_get_lastMatch_n<0>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$&"), method_get_lastMatch_n<0>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$1"), method_get_lastMatch_n<1>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$2"), method_get_lastMatch_n<2>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$3"), method_get_lastMatch_n<3>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$4"), method_get_lastMatch_n<4>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$5"), method_get_lastMatch_n<5>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$6"), method_get_lastMatch_n<6>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$7"), method_get_lastMatch_n<7>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$8"), method_get_lastMatch_n<8>, 0);
- ctor->defineAccessorProperty(QStringLiteral("$9"), method_get_lastMatch_n<9>, 0);
- ctor->defineAccessorProperty(QStringLiteral("lastParen"), method_get_lastParen, 0);
- ctor->defineAccessorProperty(QStringLiteral("$+"), method_get_lastParen, 0);
- ctor->defineAccessorProperty(QStringLiteral("input"), method_get_input, 0);
- ctor->defineAccessorProperty(QStringLiteral("$_"), method_get_input, 0);
- ctor->defineAccessorProperty(QStringLiteral("leftContext"), method_get_leftContext, 0);
- ctor->defineAccessorProperty(QStringLiteral("$`"), method_get_leftContext, 0);
- ctor->defineAccessorProperty(QStringLiteral("rightContext"), method_get_rightContext, 0);
- ctor->defineAccessorProperty(QStringLiteral("$'"), method_get_rightContext, 0);
+ ctor->defineAccessorProperty(QStringLiteral("lastMatch"), method_get_lastMatch_n<0>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$&"), method_get_lastMatch_n<0>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$1"), method_get_lastMatch_n<1>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$2"), method_get_lastMatch_n<2>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$3"), method_get_lastMatch_n<3>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$4"), method_get_lastMatch_n<4>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$5"), method_get_lastMatch_n<5>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$6"), method_get_lastMatch_n<6>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$7"), method_get_lastMatch_n<7>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$8"), method_get_lastMatch_n<8>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$9"), method_get_lastMatch_n<9>, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("lastParen"), method_get_lastParen, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$+"), method_get_lastParen, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("input"), method_get_input, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$_"), method_get_input, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("leftContext"), method_get_leftContext, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$`"), method_get_leftContext, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("rightContext"), method_get_rightContext, nullptr);
+ ctor->defineAccessorProperty(QStringLiteral("$'"), method_get_rightContext, nullptr);
defineDefaultProperty(QStringLiteral("constructor"), (o = ctor));
defineDefaultProperty(QStringLiteral("exec"), method_exec, 1);
@@ -343,7 +343,7 @@ ReturnedValue RegExpPrototype::execFirstMatch(const FunctionObject *b, const Val
if (r->value()->captureCount()) {
int start = matchOffsets[0];
int end = matchOffsets[1];
- retVal = (start != -1) ? scope.engine->newString(s.mid(start, end - start))->asReturnedValue() : Encode::undefined();
+ retVal = (start != -1) ? scope.engine->memoryManager->alloc<ComplexString>(str->d(), start, end - start)->asReturnedValue() : Encode::undefined();
}
RegExpCtor::Data *dd = regExpCtor->d();
@@ -394,7 +394,7 @@ ReturnedValue RegExpPrototype::method_exec(const FunctionObject *b, const Value
for (int i = 0; i < len; ++i) {
int start = matchOffsets[i * 2];
int end = matchOffsets[i * 2 + 1];
- v = (start != -1) ? scope.engine->newString(s.mid(start, end - start))->asReturnedValue() : Encode::undefined();
+ v = (start != -1) ? scope.engine->memoryManager->alloc<ComplexString>(str->d(), start, end - start)->asReturnedValue() : Encode::undefined();
array->arrayPut(i, v);
}
array->setArrayLengthUnchecked(len);
diff --git a/src/qml/jsruntime/qv4runtime.cpp b/src/qml/jsruntime/qv4runtime.cpp
index 240fba7905..04cad8ddb7 100644
--- a/src/qml/jsruntime/qv4runtime.cpp
+++ b/src/qml/jsruntime/qv4runtime.cpp
@@ -382,11 +382,11 @@ double RuntimeHelpers::stringToNumber(const QString &string)
{
const QStringRef s = QStringRef(&string).trimmed();
if (s.startsWith(QLatin1String("0x")) || s.startsWith(QLatin1String("0X")))
- return s.toLong(0, 16);
+ return s.toLong(nullptr, 16);
bool ok;
QByteArray ba = s.toLatin1();
const char *begin = ba.constData();
- const char *end = 0;
+ const char *end = nullptr;
double d = qstrtod(begin, &end, &ok);
if (end - begin != ba.size()) {
if (ba == "Infinity" || ba == "+Infinity")
@@ -457,7 +457,7 @@ Heap::Object *RuntimeHelpers::convertToObject(ExecutionEngine *engine, const Val
case Value::Undefined_Type:
case Value::Null_Type:
engine->throwTypeError();
- return 0;
+ return nullptr;
case Value::Boolean_Type:
return engine->newBooleanObject(value.booleanValue());
case Value::Managed_Type:
@@ -532,7 +532,7 @@ QV4::ReturnedValue RuntimeHelpers::addHelper(ExecutionEngine *engine, const Valu
if (!sright->d()->length())
return sleft->asReturnedValue();
MemoryManager *mm = engine->memoryManager;
- return (mm->alloc<String>(sleft->d(), sright->d()))->asReturnedValue();
+ return (mm->alloc<ComplexString>(sleft->d(), sright->d()))->asReturnedValue();
}
double x = RuntimeHelpers::toNumber(pleft);
double y = RuntimeHelpers::toNumber(pright);
@@ -604,6 +604,14 @@ static Q_NEVER_INLINE ReturnedValue getElementFallback(ExecutionEngine *engine,
return o->get(name);
}
+/* load element:
+
+ Managed *m = object.heapObject();
+ if (m)
+ return m->internalClass->getIndexed(m, index);
+ return getIndexedFallback(object, index);
+*/
+
ReturnedValue Runtime::method_loadElement(ExecutionEngine *engine, const Value &object, const Value &index)
{
uint idx = 0;
@@ -672,7 +680,7 @@ bool Runtime::method_storeElement(ExecutionEngine *engine, const Value &object,
ReturnedValue Runtime::method_foreachIterator(ExecutionEngine *engine, const Value &in)
{
Scope scope(engine);
- ScopedObject o(scope, (Object *)0);
+ ScopedObject o(scope, (Object *)nullptr);
if (!in.isNullOrUndefined())
o = in.toObject(engine);
return engine->newForEachIteratorObject(o)->asReturnedValue();
@@ -1090,6 +1098,37 @@ ReturnedValue Runtime::method_callValue(ExecutionEngine *engine, const Value &fu
return static_cast<const FunctionObject &>(func).call(nullptr, argv, argc);
}
+ReturnedValue Runtime::method_callQmlScopeObjectProperty(ExecutionEngine *engine, Value *base,
+ int propertyIndex, Value *argv, int argc)
+{
+ Scope scope(engine);
+ ScopedFunctionObject fo(scope, method_loadQmlScopeObjectProperty(engine, *base, propertyIndex,
+ /*captureRequired*/true));
+ if (!fo) {
+ QString error = QStringLiteral("Property '%1' of scope object is not a function").arg(propertyIndex);
+ return engine->throwTypeError(error);
+ }
+
+ QObject *qmlScopeObj = static_cast<QmlContext *>(base)->d()->qml()->scopeObject;
+ ScopedValue qmlScopeValue(scope, QObjectWrapper::wrap(engine, qmlScopeObj));
+ return fo->call(qmlScopeValue, argv, argc);
+}
+
+ReturnedValue Runtime::method_callQmlContextObjectProperty(ExecutionEngine *engine, Value *base,
+ int propertyIndex, Value *argv, int argc)
+{
+ Scope scope(engine);
+ ScopedFunctionObject fo(scope, method_loadQmlContextObjectProperty(engine, *base, propertyIndex,
+ /*captureRequired*/true));
+ if (!fo) {
+ QString error = QStringLiteral("Property '%1' of context object is not a function").arg(propertyIndex);
+ return engine->throwTypeError(error);
+ }
+
+ QObject *qmlContextObj = static_cast<QmlContext *>(base)->d()->qml()->context->contextData()->contextObject;
+ ScopedValue qmlContextValue(scope, QObjectWrapper::wrap(engine, qmlContextObj));
+ return fo->call(qmlContextValue, argv, argc);
+}
ReturnedValue Runtime::method_construct(ExecutionEngine *engine, const Value &function, Value *argv, int argc)
{
@@ -1160,7 +1199,7 @@ ReturnedValue Runtime::method_createCatchContext(ExecutionContext *parent, int e
{
ExecutionEngine *e = parent->engine();
return parent->newCatchContext(e->currentStackFrame->v4Function->compilationUnit->runtimeStrings[exceptionVarNameIndex],
- e->catchException(0))->asReturnedValue();
+ e->catchException(nullptr))->asReturnedValue();
}
void Runtime::method_declareVar(ExecutionEngine *engine, bool deletable, int nameIndex)
@@ -1260,7 +1299,7 @@ ReturnedValue Runtime::method_loadQmlIdObject(ExecutionEngine *engine, const Val
if (!context || index >= (uint)context->idValueCount)
return Encode::undefined();
- QQmlEnginePrivate *ep = engine->qmlEngine() ? QQmlEnginePrivate::get(engine->qmlEngine()) : 0;
+ QQmlEnginePrivate *ep = engine->qmlEngine() ? QQmlEnginePrivate::get(engine->qmlEngine()) : nullptr;
if (ep && ep->propertyCapture)
ep->propertyCapture->captureProperty(&context->idValues[index].bindings);
diff --git a/src/qml/jsruntime/qv4runtimeapi_p.h b/src/qml/jsruntime/qv4runtimeapi_p.h
index ea31dfd08b..2956a4a463 100644
--- a/src/qml/jsruntime/qv4runtimeapi_p.h
+++ b/src/qml/jsruntime/qv4runtimeapi_p.h
@@ -188,6 +188,8 @@ struct ExceptionCheck<void (*)(QV4::NoThrowEngine *, A, B, C)> {
F(ReturnedValue, loadQmlScopeObjectProperty, (ExecutionEngine *engine, const Value &context, int propertyIndex, bool captureRequired)) \
F(ReturnedValue, loadQmlContextObjectProperty, (ExecutionEngine *engine, const Value &context, int propertyIndex, bool captureRequired)) \
F(ReturnedValue, loadQmlIdObject, (ExecutionEngine *engine, const Value &context, uint index)) \
+ F(ReturnedValue, callQmlScopeObjectProperty, (ExecutionEngine *engine, Value *base, int propertyIndex, Value *argv, int argc)) \
+ F(ReturnedValue, callQmlContextObjectProperty, (ExecutionEngine *engine, Value *base, int propertyIndex, Value *argv, int argc)) \
\
F(void, storeQmlScopeObjectProperty, (ExecutionEngine *engine, const Value &context, int propertyIndex, const Value &value)) \
F(void, storeQmlContextObjectProperty, (ExecutionEngine *engine, const Value &context, int propertyIndex, const Value &value)) \
diff --git a/src/qml/jsruntime/qv4runtimecodegen.cpp b/src/qml/jsruntime/qv4runtimecodegen.cpp
index 9c115099b5..fe18ddf9ed 100644
--- a/src/qml/jsruntime/qv4runtimecodegen.cpp
+++ b/src/qml/jsruntime/qv4runtimecodegen.cpp
@@ -49,15 +49,16 @@ void RuntimeCodegen::generateFromFunctionExpression(const QString &fileName,
{
_module = module;
_module->fileName = fileName;
- _context = 0;
+ _module->finalUrl = fileName;
+ _context = nullptr;
Compiler::ScanFunctions scan(this, sourceCode, Compiler::GlobalCode);
// fake a global environment
- scan.enterEnvironment(0, Compiler::FunctionCode);
+ scan.enterEnvironment(nullptr, Compiler::FunctionCode);
scan(ast);
scan.leaveEnvironment();
- int index = defineFunction(ast->name.toString(), ast, ast->formals, ast->body ? ast->body->elements : 0);
+ int index = defineFunction(ast->name.toString(), ast, ast->formals, ast->body ? ast->body->elements : nullptr);
_module->rootContext = _module->functions.at(index);
}
diff --git a/src/qml/jsruntime/qv4scopedvalue_p.h b/src/qml/jsruntime/qv4scopedvalue_p.h
index afb5c21d36..bb20f384b3 100644
--- a/src/qml/jsruntime/qv4scopedvalue_p.h
+++ b/src/qml/jsruntime/qv4scopedvalue_p.h
@@ -209,7 +209,7 @@ struct Scoped
enum ConvertType { Convert };
QML_NEARLY_ALWAYS_INLINE void setPointer(const Managed *p) {
- ptr->setM(p ? p->m() : 0);
+ ptr->setM(p ? p->m() : nullptr);
}
QML_NEARLY_ALWAYS_INLINE Scoped(const Scope &scope)
@@ -244,7 +244,7 @@ struct Scoped
QML_NEARLY_ALWAYS_INLINE Scoped(const Scope &scope, const Value *v)
{
ptr = scope.engine->jsAlloca(1);
- setPointer(v ? v->as<T>() : 0);
+ setPointer(v ? v->as<T>() : nullptr);
}
QML_NEARLY_ALWAYS_INLINE Scoped(const Scope &scope, T *t)
@@ -290,7 +290,7 @@ struct Scoped
return *this;
}
Scoped<T> &operator=(Value *v) {
- setPointer(v ? v->as<T>() : 0);
+ setPointer(v ? v->as<T>() : nullptr);
return *this;
}
diff --git a/src/qml/jsruntime/qv4script.cpp b/src/qml/jsruntime/qv4script.cpp
index 901f2574da..bb6608bec0 100644
--- a/src/qml/jsruntime/qv4script.cpp
+++ b/src/qml/jsruntime/qv4script.cpp
@@ -62,14 +62,14 @@ using namespace QV4;
Script::Script(ExecutionEngine *v4, QmlContext *qml, CompiledData::CompilationUnit *compilationUnit)
: line(1), column(0), context(v4->rootContext()), strictMode(false), inheritContext(true), parsed(false)
- , compilationUnit(compilationUnit), vmFunction(0), parseAsBinding(true)
+ , compilationUnit(compilationUnit), vmFunction(nullptr), parseAsBinding(true)
{
if (qml)
qmlContext.set(v4, *qml);
parsed = true;
- vmFunction = compilationUnit ? compilationUnit->linkToEngine(v4) : 0;
+ vmFunction = compilationUnit ? compilationUnit->linkToEngine(v4) : nullptr;
}
Script::~Script()
@@ -88,7 +88,7 @@ void Script::parse()
ExecutionEngine *v4 = context->engine();
Scope valueScope(v4);
- Module module(v4->debugger() != 0);
+ Module module(v4->debugger() != nullptr);
Engine ee, *engine = &ee;
Lexer lexer(engine);
@@ -121,7 +121,7 @@ void Script::parse()
RuntimeCodegen cg(v4, &jsGenerator, strictMode);
if (inheritContext)
cg.setUseFastLookups(false);
- cg.generateFromProgram(sourceFile, sourceCode, program, &module, compilationMode);
+ cg.generateFromProgram(sourceFile, sourceFile, sourceCode, program, &module, compilationMode);
if (v4->hasException)
return;
@@ -149,10 +149,10 @@ ReturnedValue Script::run()
if (qmlContext.isUndefined()) {
TemporaryAssignment<Function*> savedGlobalCode(engine->globalCode, vmFunction);
- return vmFunction->call(engine->globalObject, 0, 0, context);
+ return vmFunction->call(engine->globalObject, nullptr, 0, context);
} else {
Scoped<QmlContext> qml(valueScope, qmlContext.value());
- return vmFunction->call(0, 0, 0, qml);
+ return vmFunction->call(nullptr, nullptr, 0, qml);
}
}
@@ -164,8 +164,8 @@ Function *Script::function()
}
QQmlRefPointer<QV4::CompiledData::CompilationUnit> Script::precompile(QV4::Compiler::Module *module, Compiler::JSUnitGenerator *unitGenerator,
- const QUrl &url, const QString &source, QList<QQmlError> *reportedErrors,
- Directives *directivesCollector)
+ const QString &fileName, const QString &finalUrl, const QString &source,
+ QList<QQmlError> *reportedErrors, Directives *directivesCollector)
{
using namespace QV4::Compiler;
using namespace QQmlJS::AST;
@@ -184,12 +184,12 @@ QQmlRefPointer<QV4::CompiledData::CompilationUnit> Script::precompile(QV4::Compi
const auto diagnosticMessages = parser.diagnosticMessages();
for (const DiagnosticMessage &m : diagnosticMessages) {
if (m.isWarning()) {
- qWarning("%s:%d : %s", qPrintable(url.toString()), m.loc.startLine, qPrintable(m.message));
+ qWarning("%s:%d : %s", qPrintable(fileName), m.loc.startLine, qPrintable(m.message));
continue;
}
QQmlError error;
- error.setUrl(url);
+ error.setUrl(QUrl(fileName));
error.setDescription(m.message);
error.setLine(m.loc.startLine);
error.setColumn(m.loc.startColumn);
@@ -199,29 +199,50 @@ QQmlRefPointer<QV4::CompiledData::CompilationUnit> Script::precompile(QV4::Compi
if (!errors.isEmpty()) {
if (reportedErrors)
*reportedErrors << errors;
- return 0;
+ return nullptr;
}
Program *program = AST::cast<Program *>(parser.rootNode());
if (!program) {
// if parsing was successful, and we have no program, then
// we're done...:
- return 0;
+ return nullptr;
}
Codegen cg(unitGenerator, /*strict mode*/false);
cg.setUseFastLookups(false);
- cg.generateFromProgram(url.toString(), source, program, module, GlobalCode);
+ cg.generateFromProgram(fileName, finalUrl, source, program, module, GlobalCode);
errors = cg.qmlErrors();
if (!errors.isEmpty()) {
if (reportedErrors)
*reportedErrors << errors;
- return 0;
+ return nullptr;
}
return cg.generateCompilationUnit(/*generate unit data*/false);
}
+Script *Script::createFromFileOrCache(ExecutionEngine *engine, QmlContext *qmlContext, const QString &fileName, const QUrl &originalUrl)
+{
+ if (const QV4::CompiledData::Unit *cachedUnit = QQmlMetaType::findCachedCompilationUnit(originalUrl)) {
+ QQmlRefPointer<QV4::CompiledData::CompilationUnit> jsUnit;
+ jsUnit.adopt(new QV4::CompiledData::CompilationUnit(cachedUnit));
+ return new QV4::Script(engine, qmlContext, jsUnit);
+ }
+
+ QFile f(fileName);
+ if (!f.open(QIODevice::ReadOnly))
+ return nullptr;
+
+ QByteArray data = f.readAll();
+ QString sourceCode = QString::fromUtf8(data);
+ QmlIR::Document::removeScriptPragmas(sourceCode);
+
+ auto result = new QV4::Script(engine, qmlContext, sourceCode, originalUrl.toString());
+ result->parse();
+ return result;
+}
+
QV4::ReturnedValue Script::evaluate(ExecutionEngine *engine, const QString &script, QmlContext *qmlContext)
{
QV4::Scope scope(engine);
diff --git a/src/qml/jsruntime/qv4script_p.h b/src/qml/jsruntime/qv4script_p.h
index 158d21c69d..24291b9aa6 100644
--- a/src/qml/jsruntime/qv4script_p.h
+++ b/src/qml/jsruntime/qv4script_p.h
@@ -68,11 +68,11 @@ struct Q_QML_EXPORT Script {
Script(ExecutionContext *scope, QV4::Compiler::CompilationMode mode, const QString &sourceCode, const QString &source = QString(), int line = 1, int column = 0)
: sourceFile(source), line(line), column(column), sourceCode(sourceCode)
, context(scope), strictMode(false), inheritContext(false), parsed(false), compilationMode(mode)
- , vmFunction(0), parseAsBinding(false) {}
+ , vmFunction(nullptr), parseAsBinding(false) {}
Script(ExecutionEngine *engine, QmlContext *qml, const QString &sourceCode, const QString &source = QString(), int line = 1, int column = 0)
: sourceFile(source), line(line), column(column), sourceCode(sourceCode)
, context(engine->rootContext()), strictMode(false), inheritContext(true), parsed(false)
- , vmFunction(0), parseAsBinding(true) {
+ , vmFunction(nullptr), parseAsBinding(true) {
if (qml)
qmlContext.set(engine, *qml);
}
@@ -97,8 +97,11 @@ struct Q_QML_EXPORT Script {
Function *function();
- static QQmlRefPointer<CompiledData::CompilationUnit> precompile(QV4::Compiler::Module *module, Compiler::JSUnitGenerator *unitGenerator, const QUrl &url, const QString &source,
- QList<QQmlError> *reportedErrors = 0, QQmlJS::Directives *directivesCollector = 0);
+ static QQmlRefPointer<CompiledData::CompilationUnit> precompile(
+ QV4::Compiler::Module *module, Compiler::JSUnitGenerator *unitGenerator,
+ const QString &fileName, const QString &finalUrl, const QString &source,
+ QList<QQmlError> *reportedErrors = nullptr, QQmlJS::Directives *directivesCollector = nullptr);
+ static Script *createFromFileOrCache(ExecutionEngine *engine, QmlContext *qmlContext, const QString &fileName, const QUrl &originalUrl);
static ReturnedValue evaluate(ExecutionEngine *engine, const QString &script, QmlContext *qmlContext);
};
diff --git a/src/qml/jsruntime/qv4sequenceobject.cpp b/src/qml/jsruntime/qv4sequenceobject.cpp
index 78cd7529d8..7d29d0b517 100644
--- a/src/qml/jsruntime/qv4sequenceobject.cpp
+++ b/src/qml/jsruntime/qv4sequenceobject.cpp
@@ -340,7 +340,7 @@ public:
void containerAdvanceIterator(ObjectIterator *it, Value *name, uint *index, Property *p, PropertyAttributes *attrs)
{
- name->setM(0);
+ name->setM(nullptr);
*index = UINT_MAX;
if (d()->isReference) {
@@ -420,11 +420,10 @@ public:
ScopedFunctionObject compare(scope, m_compareFn);
if (!compare)
return m_v4->throwTypeError();
- JSCallData jsCallData(scope, 2);
- jsCallData->args[0] = convertElementToValue(m_v4, lhs);
- jsCallData->args[1] = convertElementToValue(m_v4, rhs);
- *jsCallData->thisObject = m_v4->globalObject;
- QV4::ScopedValue result(scope, compare->call(jsCallData));
+ Value *argv = scope.alloc(2);
+ argv[0] = convertElementToValue(m_v4, lhs);
+ argv[1] = convertElementToValue(m_v4, rhs);
+ QV4::ScopedValue result(scope, compare->call(m_v4->globalObject, argv, 2));
return result->toNumber() < 0;
}
@@ -433,7 +432,7 @@ public:
const QV4::Value *m_compareFn;
};
- void sort(const BuiltinFunction *, Scope &scope, CallData *callData)
+ void sort(const FunctionObject *f, const Value *, const Value *argv, int argc)
{
if (d()->isReference) {
if (!d()->object)
@@ -441,8 +440,8 @@ public:
loadReference();
}
- if (callData->argc() == 1 && callData->args[0].as<FunctionObject>()) {
- CompareFunctor cf(scope.engine, callData->args[0]);
+ if (argc == 1 && argv[0].as<FunctionObject>()) {
+ CompareFunctor cf(f->engine(), argv[0]);
std::sort(d()->container->begin(), d()->container->end(), cf);
} else {
DefaultCompareFunctor cf;
@@ -453,10 +452,10 @@ public:
storeReference();
}
- static QV4::ReturnedValue method_get_length(const BuiltinFunction *b, CallData *callData)
+ static QV4::ReturnedValue method_get_length(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQmlSequence<Container> > This(scope, callData->thisObject.as<QQmlSequence<Container> >());
+ QV4::Scoped<QQmlSequence<Container>> This(scope, thisObject->as<QQmlSequence<Container> >());
if (!This)
THROW_TYPE_ERROR();
@@ -468,14 +467,14 @@ public:
RETURN_RESULT(Encode(qint32(This->d()->container->size())));
}
- static QV4::ReturnedValue method_set_length(const BuiltinFunction *b, CallData *callData)
+ static QV4::ReturnedValue method_set_length(const FunctionObject *f, const Value *thisObject, const Value *argv, int argc)
{
- QV4::Scope scope(b);
- QV4::Scoped<QQmlSequence<Container> > This(scope, callData->thisObject.as<QQmlSequence<Container> >());
+ QV4::Scope scope(f);
+ QV4::Scoped<QQmlSequence<Container>> This(scope, thisObject->as<QQmlSequence<Container> >());
if (!This)
THROW_TYPE_ERROR();
- quint32 newLength = callData->args[0].toUInt32();
+ quint32 newLength = argc ? argv[0].toUInt32() : 0;
/* Qt containers have int (rather than uint) allowable indexes. */
if (newLength > INT_MAX) {
generateWarning(scope.engine, QLatin1String("Index out of range during length set"));
@@ -536,7 +535,7 @@ public:
{
Q_ASSERT(d()->object);
Q_ASSERT(d()->isReference);
- void *a[] = { d()->container, 0 };
+ void *a[] = { d()->container, nullptr };
QMetaObject::metacall(d()->object, QMetaObject::ReadProperty, d()->propertyIndex, a);
}
@@ -546,7 +545,7 @@ public:
Q_ASSERT(d()->isReference);
int status = -1;
QQmlPropertyData::WriteFlags flags = QQmlPropertyData::DontRemoveBinding;
- void *a[] = { d()->container, 0, &status, &flags };
+ void *a[] = { d()->container, nullptr, &status, &flags };
QMetaObject::metacall(d()->object, QMetaObject::WriteProperty, d()->propertyIndex, a);
}
@@ -652,24 +651,24 @@ void SequencePrototype::init()
}
#undef REGISTER_QML_SEQUENCE_METATYPE
-ReturnedValue SequencePrototype::method_valueOf(const BuiltinFunction *f, CallData *callData)
+ReturnedValue SequencePrototype::method_valueOf(const FunctionObject *f, const Value *thisObject, const Value *, int)
{
- return Encode(callData->thisObject.toString(f->engine()));
+ return Encode(thisObject->toString(f->engine()));
}
-ReturnedValue SequencePrototype::method_sort(const BuiltinFunction *b, CallData *callData)
+ReturnedValue SequencePrototype::method_sort(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- QV4::ScopedObject o(scope, callData->thisObject);
+ QV4::ScopedObject o(scope, thisObject);
if (!o || !o->isListType())
THROW_TYPE_ERROR();
- if (callData->argc() >= 2)
+ if (argc >= 2)
return o.asReturnedValue();
#define CALL_SORT(SequenceElementType, SequenceElementTypeName, SequenceType, DefaultValue) \
if (QQml##SequenceElementTypeName##List *s = o->as<QQml##SequenceElementTypeName##List>()) { \
- s->sort(b, scope, callData); \
+ s->sort(b, thisObject, argv, argc); \
} else
FOREACH_QML_SEQUENCE_TYPE(CALL_SORT)
diff --git a/src/qml/jsruntime/qv4sequenceobject_p.h b/src/qml/jsruntime/qv4sequenceobject_p.h
index 169a48c2f9..e9bef2f604 100644
--- a/src/qml/jsruntime/qv4sequenceobject_p.h
+++ b/src/qml/jsruntime/qv4sequenceobject_p.h
@@ -68,8 +68,8 @@ struct SequencePrototype : public QV4::Object
V4_PROTOTYPE(arrayPrototype)
void init();
- static ReturnedValue method_valueOf(const BuiltinFunction *f, CallData *callData);
- static ReturnedValue method_sort(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_valueOf(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_sort(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
static bool isSequenceType(int sequenceTypeId);
static ReturnedValue newSequence(QV4::ExecutionEngine *engine, int sequenceTypeId, QObject *object, int propertyIndex, bool *succeeded);
diff --git a/src/qml/jsruntime/qv4sparsearray.cpp b/src/qml/jsruntime/qv4sparsearray.cpp
index 8f6aa6723c..2a3e28bf63 100644
--- a/src/qml/jsruntime/qv4sparsearray.cpp
+++ b/src/qml/jsruntime/qv4sparsearray.cpp
@@ -89,20 +89,20 @@ const SparseArrayNode *SparseArrayNode::previousNode() const
SparseArrayNode *SparseArrayNode::copy(SparseArray *d) const
{
- SparseArrayNode *n = d->createNode(size_left, 0, false);
+ SparseArrayNode *n = d->createNode(size_left, nullptr, false);
n->value = value;
n->setColor(color());
if (left) {
n->left = left->copy(d);
n->left->setParent(n);
} else {
- n->left = 0;
+ n->left = nullptr;
}
if (right) {
n->right = right->copy(d);
n->right->setParent(n);
} else {
- n->right = 0;
+ n->right = nullptr;
}
return n;
}
@@ -119,7 +119,7 @@ void SparseArray::rotateLeft(SparseArrayNode *x)
SparseArrayNode *&root = header.left;
SparseArrayNode *y = x->right;
x->right = y->left;
- if (y->left != 0)
+ if (y->left != nullptr)
y->left->setParent(x);
y->setParent(x->parent());
if (x == root)
@@ -146,7 +146,7 @@ void SparseArray::rotateRight(SparseArrayNode *x)
SparseArrayNode *&root = header.left;
SparseArrayNode *y = x->left;
x->left = y->right;
- if (y->right != 0)
+ if (y->right != nullptr)
y->right->setParent(x);
y->setParent(x->parent());
if (x == root)
@@ -209,7 +209,7 @@ void SparseArray::deleteNode(SparseArrayNode *z)
SparseArrayNode *y = z;
SparseArrayNode *x;
SparseArrayNode *x_parent;
- if (y->left == 0) {
+ if (y->left == nullptr) {
x = y->right;
if (y == mostLeftNode) {
if (x)
@@ -217,11 +217,11 @@ void SparseArray::deleteNode(SparseArrayNode *z)
else
mostLeftNode = y->parent();
}
- } else if (y->right == 0) {
+ } else if (y->right == nullptr) {
x = y->left;
} else {
y = y->right;
- while (y->left != 0)
+ while (y->left != nullptr)
y = y->left;
x = y->right;
}
@@ -261,7 +261,7 @@ void SparseArray::deleteNode(SparseArrayNode *z)
y->size_left = 0;
}
if (y->color() != SparseArrayNode::Red) {
- while (x != root && (x == 0 || x->color() == SparseArrayNode::Black)) {
+ while (x != root && (x == nullptr || x->color() == SparseArrayNode::Black)) {
if (x == x_parent->left) {
SparseArrayNode *w = x_parent->right;
if (w->color() == SparseArrayNode::Red) {
@@ -270,13 +270,13 @@ void SparseArray::deleteNode(SparseArrayNode *z)
rotateLeft(x_parent);
w = x_parent->right;
}
- if ((w->left == 0 || w->left->color() == SparseArrayNode::Black) &&
- (w->right == 0 || w->right->color() == SparseArrayNode::Black)) {
+ if ((w->left == nullptr || w->left->color() == SparseArrayNode::Black) &&
+ (w->right == nullptr || w->right->color() == SparseArrayNode::Black)) {
w->setColor(SparseArrayNode::Red);
x = x_parent;
x_parent = x_parent->parent();
} else {
- if (w->right == 0 || w->right->color() == SparseArrayNode::Black) {
+ if (w->right == nullptr || w->right->color() == SparseArrayNode::Black) {
if (w->left)
w->left->setColor(SparseArrayNode::Black);
w->setColor(SparseArrayNode::Red);
@@ -298,13 +298,13 @@ void SparseArray::deleteNode(SparseArrayNode *z)
rotateRight(x_parent);
w = x_parent->left;
}
- if ((w->right == 0 || w->right->color() == SparseArrayNode::Black) &&
- (w->left == 0 || w->left->color() == SparseArrayNode::Black)) {
+ if ((w->right == nullptr || w->right->color() == SparseArrayNode::Black) &&
+ (w->left == nullptr || w->left->color() == SparseArrayNode::Black)) {
w->setColor(SparseArrayNode::Red);
x = x_parent;
x_parent = x_parent->parent();
} else {
- if (w->left == 0 || w->left->color() == SparseArrayNode::Black) {
+ if (w->left == nullptr || w->left->color() == SparseArrayNode::Black) {
if (w->right)
w->right->setColor(SparseArrayNode::Black);
w->setColor(SparseArrayNode::Red);
@@ -363,8 +363,8 @@ SparseArrayNode *SparseArray::createNode(uint sl, SparseArrayNode *parent, bool
Q_CHECK_PTR(node);
node->p = (quintptr)parent;
- node->left = 0;
- node->right = 0;
+ node->left = nullptr;
+ node->right = nullptr;
node->size_left = sl;
node->value = UINT_MAX;
++numEntries;
@@ -395,21 +395,23 @@ void SparseArray::freeTree(SparseArrayNode *root, int alignment)
SparseArray::SparseArray()
: numEntries(0)
{
+ freeList = Primitive::emptyValue(UINT_MAX).asReturnedValue();
header.p = 0;
- header.left = 0;
- header.right = 0;
+ header.left = nullptr;
+ header.right = nullptr;
mostLeftNode = &header;
}
SparseArray::SparseArray(const SparseArray &other)
{
header.p = 0;
- header.right = 0;
+ header.right = nullptr;
if (other.header.left) {
header.left = other.header.left->copy(this);
header.left->setParent(&header);
recalcMostLeftNode();
}
+ freeList = other.freeList;
}
SparseArrayNode *SparseArray::insert(uint akey)
diff --git a/src/qml/jsruntime/qv4sparsearray_p.h b/src/qml/jsruntime/qv4sparsearray_p.h
index 2e4ac883f2..51869b259f 100644
--- a/src/qml/jsruntime/qv4sparsearray_p.h
+++ b/src/qml/jsruntime/qv4sparsearray_p.h
@@ -109,7 +109,7 @@ struct SparseArrayNode
inline SparseArrayNode *SparseArrayNode::lowerBound(uint akey)
{
SparseArrayNode *n = this;
- SparseArrayNode *last = 0;
+ SparseArrayNode *last = nullptr;
while (n) {
if (akey <= n->size_left) {
last = n;
@@ -126,7 +126,7 @@ inline SparseArrayNode *SparseArrayNode::lowerBound(uint akey)
inline SparseArrayNode *SparseArrayNode::upperBound(uint akey)
{
SparseArrayNode *n = this;
- SparseArrayNode *last = 0;
+ SparseArrayNode *last = nullptr;
while (n) {
if (akey < n->size_left) {
last = n;
@@ -150,6 +150,8 @@ struct Q_QML_EXPORT SparseArray
}
SparseArray(const SparseArray &other);
+
+ ReturnedValue freeList;
private:
SparseArray &operator=(const SparseArray &other);
@@ -221,7 +223,7 @@ inline SparseArrayNode *SparseArray::findNode(uint akey) const
}
}
- return 0;
+ return nullptr;
}
inline uint SparseArray::pop_front()
diff --git a/src/qml/jsruntime/qv4string.cpp b/src/qml/jsruntime/qv4string.cpp
index b38b01c9f7..447992ebec 100644
--- a/src/qml/jsruntime/qv4string.cpp
+++ b/src/qml/jsruntime/qv4string.cpp
@@ -55,9 +55,16 @@ using namespace QV4;
void Heap::String::markObjects(Heap::Base *that, MarkStack *markStack)
{
String *s = static_cast<String *>(that);
- if (s->largestSubLength) {
- s->left->mark(markStack);
- s->right->mark(markStack);
+ if (s->subtype < StringType_Complex)
+ return;
+
+ ComplexString *cs = static_cast<ComplexString *>(s);
+ if (cs->subtype == StringType_AddedString) {
+ cs->left->mark(markStack);
+ cs->right->mark(markStack);
+ } else {
+ Q_ASSERT(cs->subtype == StringType_SubString);
+ cs->left->mark(markStack);
}
}
@@ -84,37 +91,45 @@ void Heap::String::init(const QString &t)
text = const_cast<QString &>(t).data_ptr();
text->ref.ref();
- identifier = 0;
- stringHash = UINT_MAX;
- largestSubLength = 0;
- len = text->size;
}
-void Heap::String::init(String *l, String *r)
+void Heap::ComplexString::init(String *l, String *r)
{
Base::init();
- subtype = String::StringType_Unknown;
+ subtype = String::StringType_AddedString;
left = l;
right = r;
- stringHash = UINT_MAX;
- largestSubLength = qMax(l->largestSubLength, r->largestSubLength);
- len = l->len + r->len;
- Q_ASSERT(largestSubLength <= len);
-
- if (!l->largestSubLength && l->len > largestSubLength)
- largestSubLength = l->len;
- if (!r->largestSubLength && r->len > largestSubLength)
- largestSubLength = r->len;
+ len = left->length() + right->length();
+ if (left->subtype >= StringType_Complex)
+ largestSubLength = static_cast<ComplexString *>(left)->largestSubLength;
+ else
+ largestSubLength = left->length();
+ if (right->subtype >= StringType_Complex)
+ largestSubLength = qMax(largestSubLength, static_cast<ComplexString *>(right)->largestSubLength);
+ else
+ largestSubLength = qMax(largestSubLength, right->length());
// make sure we don't get excessive depth in our strings
if (len > 256 && len >= 2*largestSubLength)
simplifyString();
}
+void Heap::ComplexString::init(Heap::String *ref, int from, int len)
+{
+ Q_ASSERT(ref->length() >= from + len);
+ Base::init();
+
+ subtype = String::StringType_SubString;
+
+ left = ref;
+ this->from = from;
+ this->len = len;
+}
+
void Heap::String::destroy() {
- if (!largestSubLength) {
+ if (text) {
internalClass->engine->memoryManager->changeUnmanagedHeapSizeUsage(qptrdiff(-text->size) * (int)sizeof(QChar));
if (!text->ref.deref())
QStringData::deallocate(text);
@@ -126,7 +141,7 @@ uint String::toUInt(bool *ok) const
{
*ok = true;
- if (subtype() == Heap::String::StringType_Unknown)
+ if (subtype() >= Heap::String::StringType_Unknown)
d()->createHashValue();
if (subtype() == Heap::String::StringType_ArrayIndex)
return d()->stringHash;
@@ -142,15 +157,15 @@ uint String::toUInt(bool *ok) const
void String::makeIdentifierImpl() const
{
- if (d()->largestSubLength)
+ if (!d()->text)
d()->simplifyString();
- Q_ASSERT(!d()->largestSubLength);
+ Q_ASSERT(d()->text);
engine()->identifierTable->identifier(this);
}
void Heap::String::simplifyString() const
{
- Q_ASSERT(largestSubLength);
+ Q_ASSERT(!text);
int l = length();
QString result(l, Qt::Uninitialized);
@@ -158,9 +173,33 @@ void Heap::String::simplifyString() const
append(this, ch);
text = result.data_ptr();
text->ref.ref();
- identifier = 0;
- largestSubLength = 0;
+ const ComplexString *cs = static_cast<const ComplexString *>(this);
+ identifier = nullptr;
+ cs->left = cs->right = nullptr;
+
internalClass->engine->memoryManager->changeUnmanagedHeapSizeUsage(qptrdiff(text->size) * (qptrdiff)sizeof(QChar));
+ subtype = StringType_Unknown;
+}
+
+bool Heap::String::startsWithUpper() const
+{
+ if (subtype == StringType_AddedString)
+ return static_cast<const Heap::ComplexString *>(this)->left->startsWithUpper();
+
+ const Heap::String *str = this;
+ int offset = 0;
+ if (subtype == StringType_SubString) {
+ const ComplexString *cs = static_cast<const Heap::ComplexString *>(this);
+ if (!cs->len)
+ return false;
+ // simplification here is not ideal, but hopefully not a common case.
+ if (cs->left->subtype >= Heap::String::StringType_Complex)
+ cs->left->simplifyString();
+ str = cs->left;
+ offset = cs->from;
+ }
+ Q_ASSERT(str->subtype < Heap::String::StringType_Complex);
+ return str->text->size > offset && QChar::isUpper(str->text->data()[offset]);
}
void Heap::String::append(const String *data, QChar *ch)
@@ -173,11 +212,16 @@ void Heap::String::append(const String *data, QChar *ch)
const String *item = worklist.back();
worklist.pop_back();
- if (item->largestSubLength) {
- worklist.push_back(item->right);
- worklist.push_back(item->left);
+ if (item->subtype == StringType_AddedString) {
+ const ComplexString *cs = static_cast<const ComplexString *>(item);
+ worklist.push_back(cs->right);
+ worklist.push_back(cs->left);
+ } else if (item->subtype == StringType_SubString) {
+ const ComplexString *cs = static_cast<const ComplexString *>(item);
+ memcpy(ch, cs->left->toQString().constData() + cs->from, cs->len*sizeof(QChar));
+ ch += cs->len;
} else {
- memcpy(ch, item->text->data(), item->text->size * sizeof(QChar));
+ memcpy(static_cast<void *>(ch), static_cast<const void *>(item->text->data()), item->text->size * sizeof(QChar));
ch += item->text->size;
}
}
@@ -185,9 +229,9 @@ void Heap::String::append(const String *data, QChar *ch)
void Heap::String::createHashValue() const
{
- if (largestSubLength)
+ if (!text)
simplifyString();
- Q_ASSERT(!largestSubLength);
+ Q_ASSERT(text);
const QChar *ch = reinterpret_cast<const QChar *>(text->data());
const QChar *end = ch + text->size;
stringHash = QV4::String::calculateHashValue(ch, end, &subtype);
diff --git a/src/qml/jsruntime/qv4string_p.h b/src/qml/jsruntime/qv4string_p.h
index 85345aca4d..5466cc274d 100644
--- a/src/qml/jsruntime/qv4string_p.h
+++ b/src/qml/jsruntime/qv4string_p.h
@@ -67,35 +67,32 @@ namespace Heap {
struct Q_QML_PRIVATE_EXPORT String : Base {
static void markObjects(Heap::Base *that, MarkStack *markStack);
enum StringType {
- StringType_Unknown,
StringType_Regular,
- StringType_ArrayIndex
+ StringType_ArrayIndex,
+ StringType_Unknown,
+ StringType_AddedString,
+ StringType_SubString,
+ StringType_Complex = StringType_AddedString
};
#ifndef V4_BOOTSTRAP
void init(const QString &text);
- void init(String *l, String *n);
void destroy();
void simplifyString() const;
- int length() const {
- Q_ASSERT((largestSubLength &&
- (len == left->len + right->len)) ||
- len == (uint)text->size);
- return len;
- }
+ int length() const;
std::size_t retainedTextSize() const {
- return largestSubLength ? 0 : (std::size_t(text->size) * sizeof(QChar));
+ return subtype >= StringType_Complex ? 0 : (std::size_t(text->size) * sizeof(QChar));
}
void createHashValue() const;
inline unsigned hashValue() const {
- if (subtype == StringType_Unknown)
+ if (subtype >= StringType_Unknown)
createHashValue();
- Q_ASSERT(!largestSubLength);
+ Q_ASSERT(subtype < StringType_Complex);
return stringHash;
}
inline QString toQString() const {
- if (largestSubLength)
+ if (subtype >= StringType_Complex)
simplifyString();
QStringDataPtr ptr = { text };
text->ref.ref();
@@ -106,7 +103,7 @@ struct Q_QML_PRIVATE_EXPORT String : Base {
return true;
if (hashValue() != other->hashValue())
return false;
- Q_ASSERT(!largestSubLength);
+ Q_ASSERT(subtype < StringType_Complex);
if (identifier && identifier == other->identifier)
return true;
if (subtype == Heap::String::StringType_ArrayIndex && other->subtype == Heap::String::StringType_ArrayIndex)
@@ -115,23 +112,37 @@ struct Q_QML_PRIVATE_EXPORT String : Base {
return toQString() == other->toQString();
}
- union {
- mutable QStringData *text;
- mutable String *left;
- };
- union {
- mutable Identifier *identifier;
- mutable String *right;
- };
+ bool startsWithUpper() const;
+
+ mutable QStringData *text;
+ mutable Identifier *identifier;
mutable uint subtype;
mutable uint stringHash;
- mutable uint largestSubLength;
- uint len;
private:
static void append(const String *data, QChar *ch);
#endif
};
-V4_ASSERT_IS_TRIVIAL(String)
+Q_STATIC_ASSERT(std::is_trivial< String >::value);
+
+#ifndef V4_BOOTSTRAP
+struct ComplexString : String {
+ void init(String *l, String *n);
+ void init(String *ref, int from, int len);
+ mutable String *left;
+ mutable String *right;
+ union {
+ mutable int largestSubLength;
+ int from;
+ };
+ int len;
+};
+Q_STATIC_ASSERT(std::is_trivial< ComplexString >::value);
+
+inline
+int String::length() const {
+ return text ? text->size : static_cast<const ComplexString *>(this)->len;
+}
+#endif
}
@@ -167,9 +178,9 @@ struct Q_QML_PRIVATE_EXPORT String : public Managed {
return d()->hashValue();
}
uint asArrayIndex() const {
- if (subtype() == Heap::String::StringType_Unknown)
+ if (subtype() >= Heap::String::StringType_Unknown)
d()->createHashValue();
- Q_ASSERT(!d()->largestSubLength);
+ Q_ASSERT(d()->subtype < Heap::String::StringType_Complex);
if (subtype() == Heap::String::StringType_ArrayIndex)
return d()->stringHash;
return UINT_MAX;
@@ -197,12 +208,7 @@ struct Q_QML_PRIVATE_EXPORT String : public Managed {
return calculateHashValue(ch, end, subtype);
}
- bool startsWithUpper() const {
- const String::Data *l = d();
- while (l->largestSubLength)
- l = l->left;
- return l->text->size && QChar::isUpper(l->text->data()[0]);
- }
+ bool startsWithUpper() const { return d()->startsWithUpper(); }
Identifier *identifier() const { return d()->identifier; }
@@ -216,7 +222,7 @@ public:
private:
static inline uint toUInt(const QChar *ch) { return ch->unicode(); }
- static inline uint toUInt(const char *ch) { return *ch; }
+ static inline uint toUInt(const char *ch) { return static_cast<unsigned char>(*ch); }
template <typename T>
static inline uint toArrayIndex(const T *ch, const T *end)
@@ -263,12 +269,22 @@ public:
}
};
+#ifndef V4_BOOTSTRAP
+struct ComplexString : String {
+ typedef QV4::Heap::ComplexString Data;
+ QV4::Heap::ComplexString *d_unchecked() const { return static_cast<QV4::Heap::ComplexString *>(m()); }
+ QV4::Heap::ComplexString *d() const {
+ QV4::Heap::ComplexString *dptr = d_unchecked();
+ dptr->_checkIsInitialized();
+ return dptr;
+ }
+};
+
template<>
inline const String *Value::as() const {
- return isManaged() && m()->vtable()->isString ? static_cast<const String *>(this) : 0;
+ return isManaged() && m()->vtable()->isString ? static_cast<const String *>(this) : nullptr;
}
-#ifndef V4_BOOTSTRAP
template<>
inline ReturnedValue value_convert<String>(ExecutionEngine *e, const Value &v)
{
diff --git a/src/qml/jsruntime/qv4stringobject.cpp b/src/qml/jsruntime/qv4stringobject.cpp
index efab51ec53..e5a02fdc22 100644
--- a/src/qml/jsruntime/qv4stringobject.cpp
+++ b/src/qml/jsruntime/qv4stringobject.cpp
@@ -86,13 +86,13 @@ Heap::String *Heap::StringObject::getIndex(uint index) const
{
QString str = string->toQString();
if (index >= (uint)str.length())
- return 0;
+ return nullptr;
return internalClass->engine->newString(str.mid(index, 1));
}
uint Heap::StringObject::length() const
{
- return string->len;
+ return string->length();
}
bool StringObject::deleteIndexedProperty(Managed *m, uint index)
@@ -109,7 +109,7 @@ bool StringObject::deleteIndexedProperty(Managed *m, uint index)
void StringObject::advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint *index, Property *p, PropertyAttributes *attrs)
{
- name->setM(0);
+ name->setM(nullptr);
StringObject *s = static_cast<StringObject *>(m);
uint slen = s->d()->string->toQString().length();
if (it->arrayIndex <= slen) {
@@ -200,6 +200,15 @@ void StringPrototype::init(ExecutionEngine *engine, Object *ctor)
defineDefaultProperty(QStringLiteral("trim"), method_trim);
}
+static Heap::String *thisAsString(ExecutionEngine *v4, const Value *thisObject)
+{
+ if (String *s = thisObject->stringValue())
+ return s->d();
+ if (const StringObject *thisString = thisObject->as<StringObject>())
+ return thisString->d()->string;
+ return thisObject->toString(v4);
+}
+
static QString getThisString(ExecutionEngine *v4, const Value *thisObject)
{
if (String *s = thisObject->stringValue())
@@ -649,11 +658,13 @@ ReturnedValue StringPrototype::method_search(const FunctionObject *b, const Valu
ReturnedValue StringPrototype::method_slice(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
ExecutionEngine *v4 = b->engine();
- const QString text = getThisString(v4, thisObject);
+ Scope scope(v4);
+ ScopedString s(scope, thisAsString(v4, thisObject));
if (v4->hasException)
return QV4::Encode::undefined();
+ Q_ASSERT(s);
- const double length = text.length();
+ const double length = s->d()->length();
double start = argc ? argv[0].toInteger() : 0;
double end = (argc < 2 || argv[1].isUndefined())
@@ -673,7 +684,7 @@ ReturnedValue StringPrototype::method_slice(const FunctionObject *b, const Value
const int intEnd = int(end);
int count = qMax(0, intEnd - intStart);
- return Encode(v4->newString(text.mid(intStart, count)));
+ return Encode(v4->memoryManager->alloc<ComplexString>(s->d(), intStart, count));
}
ReturnedValue StringPrototype::method_split(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
@@ -706,7 +717,7 @@ ReturnedValue StringPrototype::method_split(const FunctionObject *b, const Value
Scoped<RegExpObject> re(scope, separatorValue);
if (re) {
if (re->value()->pattern->isEmpty()) {
- re = (RegExpObject *)0;
+ re = (RegExpObject *)nullptr;
separatorValue = scope.engine->newString();
}
}
diff --git a/src/qml/jsruntime/qv4typedarray.cpp b/src/qml/jsruntime/qv4typedarray.cpp
index 4ba31f9b6e..ea1532b8ce 100644
--- a/src/qml/jsruntime/qv4typedarray.cpp
+++ b/src/qml/jsruntime/qv4typedarray.cpp
@@ -399,10 +399,10 @@ void TypedArrayPrototype::init(ExecutionEngine *engine, TypedArrayCtor *ctor)
ctor->defineReadonlyProperty(engine->id_prototype(), (o = this));
ctor->defineReadonlyProperty(QStringLiteral("BYTES_PER_ELEMENT"), Primitive::fromInt32(operations[ctor->d()->type].bytesPerElement));
defineDefaultProperty(engine->id_constructor(), (o = ctor));
- defineAccessorProperty(QStringLiteral("buffer"), method_get_buffer, 0);
- defineAccessorProperty(QStringLiteral("byteLength"), method_get_byteLength, 0);
- defineAccessorProperty(QStringLiteral("byteOffset"), method_get_byteOffset, 0);
- defineAccessorProperty(QStringLiteral("length"), method_get_length, 0);
+ defineAccessorProperty(QStringLiteral("buffer"), method_get_buffer, nullptr);
+ defineAccessorProperty(QStringLiteral("byteLength"), method_get_byteLength, nullptr);
+ defineAccessorProperty(QStringLiteral("byteOffset"), method_get_byteOffset, nullptr);
+ defineAccessorProperty(QStringLiteral("length"), method_get_length, nullptr);
defineReadonlyProperty(QStringLiteral("BYTES_PER_ELEMENT"), Primitive::fromInt32(operations[ctor->d()->type].bytesPerElement));
defineDefaultProperty(QStringLiteral("set"), method_set, 1);
@@ -514,7 +514,7 @@ ReturnedValue TypedArrayPrototype::method_set(const FunctionObject *b, const Val
RETURN_UNDEFINED();
}
- char *srcCopy = 0;
+ char *srcCopy = nullptr;
if (buffer->d() == srcBuffer->d()) {
// same buffer, need to take a temporary copy, to not run into problems
srcCopy = new char[srcTypedArray->d()->byteLength];
diff --git a/src/qml/jsruntime/qv4value_p.h b/src/qml/jsruntime/qv4value_p.h
index 52d9f23afd..97ed13cd91 100644
--- a/src/qml/jsruntime/qv4value_p.h
+++ b/src/qml/jsruntime/qv4value_p.h
@@ -57,6 +57,8 @@
#include "qv4global_p.h"
#include <private/qv4heap_p.h>
+#include <private/qnumeric_p.h>
+
QT_BEGIN_NAMESPACE
namespace QV4 {
@@ -322,6 +324,8 @@ public:
return d;
}
QML_NEARLY_ALWAYS_INLINE void setDouble(double d) {
+ if (qt_is_nan(d))
+ d = qt_qnan();
memcpy(&_val, &d, 8);
_val ^= NaNEncodeMask;
Q_ASSERT(isDouble());
@@ -422,7 +426,7 @@ public:
template <typename T>
const T *as() const {
if (!isManaged())
- return 0;
+ return nullptr;
Q_ASSERT(m()->vtable());
#if !defined(QT_NO_QOBJECT_CHECK)
@@ -434,7 +438,7 @@ public:
return static_cast<const T *>(this);
vt = vt->parent;
}
- return 0;
+ return nullptr;
}
template <typename T>
T *as() {
@@ -457,6 +461,7 @@ public:
uint asArrayLength(bool *ok) const;
#endif
+ ReturnedValue *data_ptr() { return &_val; }
ReturnedValue asReturnedValue() const { return _val; }
static Value fromReturnedValue(ReturnedValue val) { Value v; v._val = val; return v; }
@@ -469,7 +474,7 @@ public:
Value &operator=(ReturnedValue v) { _val = v; return *this; }
Value &operator=(Managed *m) {
if (!m) {
- setM(0);
+ setM(nullptr);
} else {
_val = reinterpret_cast<Value *>(m)->_val;
}
@@ -483,7 +488,7 @@ public:
template<typename T>
Value &operator=(const Scoped<T> &t);
};
-V4_ASSERT_IS_TRIVIAL(Value)
+Q_STATIC_ASSERT(std::is_trivial< Value >::value);
inline void Value::mark(MarkStack *markStack)
{
@@ -792,6 +797,94 @@ inline double Value::toInteger() const
}
+template <size_t o>
+struct HeapValue : Value {
+ static Q_CONSTEXPR size_t offset = o;
+ Heap::Base *base() {
+ Heap::Base *base = reinterpret_cast<Heap::Base *>(this) - (offset/sizeof(Heap::Base));
+ Q_ASSERT(base->inUse());
+ return base;
+ }
+
+ void set(EngineBase *e, const Value &newVal) {
+ WriteBarrier::write(e, base(), data_ptr(), newVal.asReturnedValue());
+ }
+ void set(EngineBase *e, Heap::Base *b) {
+ WriteBarrier::write(e, base(), data_ptr(), b->asReturnedValue());
+ }
+};
+
+template <size_t o>
+struct ValueArray {
+ static Q_CONSTEXPR size_t offset = o;
+ uint size;
+ uint alloc;
+ Value values[1];
+
+ Heap::Base *base() {
+ Heap::Base *base = reinterpret_cast<Heap::Base *>(this) - (offset/sizeof(Heap::Base));
+ Q_ASSERT(base->inUse());
+ return base;
+ }
+
+ void set(EngineBase *e, uint index, Value v) {
+ WriteBarrier::write(e, base(), values[index].data_ptr(), v.asReturnedValue());
+ }
+ void set(EngineBase *e, uint index, Heap::Base *b) {
+ WriteBarrier::write(e, base(), values[index].data_ptr(), b->asReturnedValue());
+ }
+ inline const Value &operator[] (uint index) const {
+ Q_ASSERT(index < alloc);
+ return values[index];
+ }
+ inline const Value *data() const {
+ return values;
+ }
+
+ void insertData(EngineBase *e, uint index, Value v) {
+ for (uint i = size - 1; i > index; --i) {
+ values[i] = values[i - 1];
+ }
+ set(e, index, v);
+ }
+ void removeData(EngineBase *e, uint index, int n = 1) {
+ Q_UNUSED(e);
+ for (uint i = index; i < size - n; ++i) {
+ values[i] = values[i + n];
+ }
+ }
+
+ void mark(MarkStack *markStack) {
+ Value *v = values;
+ const Value *end = v + alloc;
+ if (alloc > 32*1024) {
+ // drain from time to time to avoid overflows in the js stack
+ Heap::Base **currentBase = markStack->top;
+ while (v < end) {
+ v->mark(markStack);
+ ++v;
+ if (markStack->top >= currentBase + 32*1024) {
+ Heap::Base **oldBase = markStack->base;
+ markStack->base = currentBase;
+ markStack->drain();
+ markStack->base = oldBase;
+ }
+ }
+ } else {
+ while (v < end) {
+ v->mark(markStack);
+ ++v;
+ }
+ }
+ }
+};
+
+// It's really important that the offset of values in this structure is
+// constant across all architecture, otherwise JIT cross-compiled code will
+// have wrong offsets between host and target.
+Q_STATIC_ASSERT(offsetof(ValueArray<0>, values) == 8);
+
+
}
QT_END_NAMESPACE
diff --git a/src/qml/jsruntime/qv4variantobject.cpp b/src/qml/jsruntime/qv4variantobject.cpp
index 00be90b3c2..bee17e0390 100644
--- a/src/qml/jsruntime/qv4variantobject.cpp
+++ b/src/qml/jsruntime/qv4variantobject.cpp
@@ -113,17 +113,17 @@ void VariantPrototype::init()
defineDefaultProperty(engine()->id_toString(), method_toString, 0);
}
-ReturnedValue VariantPrototype::method_preserve(const BuiltinFunction *, CallData *callData)
+ReturnedValue VariantPrototype::method_preserve(const FunctionObject *, const Value *thisObject, const Value *, int)
{
- VariantObject *o = callData->thisObject.as<QV4::VariantObject>();
+ const VariantObject *o = thisObject->as<QV4::VariantObject>();
if (o && o->d()->isScarce())
o->d()->addVmePropertyReference();
RETURN_UNDEFINED();
}
-ReturnedValue VariantPrototype::method_destroy(const BuiltinFunction *, CallData *callData)
+ReturnedValue VariantPrototype::method_destroy(const FunctionObject *, const Value *thisObject, const Value *, int)
{
- VariantObject *o = callData->thisObject.as<QV4::VariantObject>();
+ const VariantObject *o = thisObject->as<QV4::VariantObject>();
if (o) {
if (o->d()->isScarce())
o->d()->addVmePropertyReference();
@@ -132,10 +132,10 @@ ReturnedValue VariantPrototype::method_destroy(const BuiltinFunction *, CallData
RETURN_UNDEFINED();
}
-ReturnedValue VariantPrototype::method_toString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue VariantPrototype::method_toString(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
ExecutionEngine *v4 = b->engine();
- VariantObject *o = callData->thisObject.as<QV4::VariantObject>();
+ const VariantObject *o = thisObject->as<QV4::VariantObject>();
if (!o)
RETURN_UNDEFINED();
QString result = o->d()->data().toString();
@@ -147,9 +147,9 @@ ReturnedValue VariantPrototype::method_toString(const BuiltinFunction *b, CallDa
return Encode(v4->newString(result));
}
-ReturnedValue VariantPrototype::method_valueOf(const BuiltinFunction *b, CallData *callData)
+ReturnedValue VariantPrototype::method_valueOf(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
- VariantObject *o = callData->thisObject.as<QV4::VariantObject>();
+ const VariantObject *o = thisObject->as<QV4::VariantObject>();
if (o) {
QVariant v = o->d()->data();
switch (v.type()) {
@@ -170,7 +170,7 @@ ReturnedValue VariantPrototype::method_valueOf(const BuiltinFunction *b, CallDat
break;
}
}
- return callData->thisObject.asReturnedValue();
+ return thisObject->asReturnedValue();
}
QT_END_NAMESPACE
diff --git a/src/qml/jsruntime/qv4variantobject_p.h b/src/qml/jsruntime/qv4variantobject_p.h
index 07b3310e91..62fa7ff9a8 100644
--- a/src/qml/jsruntime/qv4variantobject_p.h
+++ b/src/qml/jsruntime/qv4variantobject_p.h
@@ -108,10 +108,10 @@ public:
V4_PROTOTYPE(objectPrototype)
void init();
- static ReturnedValue method_preserve(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_destroy(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_toString(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_valueOf(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_preserve(const FunctionObject *f, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_destroy(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_toString(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_valueOf(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
};
}
diff --git a/src/qml/jsruntime/qv4vme_moth.cpp b/src/qml/jsruntime/qv4vme_moth.cpp
index bc1cb8caa7..bd07473176 100644
--- a/src/qml/jsruntime/qv4vme_moth.cpp
+++ b/src/qml/jsruntime/qv4vme_moth.cpp
@@ -492,6 +492,7 @@ static bool compareEqualInt(Value &accumulator, Value lhs, int rhs)
if (val.isDouble()) \
d = val.doubleValue(); \
else { \
+ STORE_ACC(); \
d = val.toNumberImpl(); \
CHECK_EXCEPTION; \
} \
@@ -552,17 +553,17 @@ QV4::ReturnedValue VME::exec(const FunctionObject *fo, const Value *thisObject,
Profiling::FunctionCallProfiler profiler(engine, function); // start execution profiling
QV4::Debugging::Debugger *debugger = engine->debugger();
-
- const uchar *exceptionHandler = 0;
+ const uchar *exceptionHandler = nullptr;
QV4::Value &accumulator = frame.jsFrame->accumulator;
QV4::ReturnedValue acc = Encode::undefined();
#ifdef V4_ENABLE_JIT
- static const bool forceInterpreter = qEnvironmentVariableIsSet("QV4_FORCE_INTERPRETER");
- if (function->jittedCode == nullptr) {
- if (ExecutionEngine::canJIT() && debugger == nullptr && !forceInterpreter)
+ if (function->jittedCode == nullptr && debugger == nullptr) {
+ if (engine->canJIT(function))
QV4::JIT::BaselineJIT(function).generate();
+ else
+ ++function->interpreterCallCount;
}
#endif // V4_ENABLE_JIT
@@ -634,7 +635,7 @@ QV4::ReturnedValue VME::exec(const FunctionObject *fo, const Value *thisObject,
MOTH_BEGIN_INSTR(StoreLocal)
CHECK_EXCEPTION;
auto cc = static_cast<Heap::CallContext *>(stack[CallData::Context].m());
- QV4::WriteBarrier::write(engine, cc, cc->locals.values + index, ACC);
+ QV4::WriteBarrier::write(engine, cc, cc->locals.values[index].data_ptr(), acc);
MOTH_END_INSTR(StoreLocal)
MOTH_BEGIN_INSTR(LoadScopedLocal)
@@ -645,7 +646,7 @@ QV4::ReturnedValue VME::exec(const FunctionObject *fo, const Value *thisObject,
MOTH_BEGIN_INSTR(StoreScopedLocal)
CHECK_EXCEPTION;
auto cc = getScope(stack, scope);
- QV4::WriteBarrier::write(engine, cc, cc->locals.values + index, ACC);
+ QV4::WriteBarrier::write(engine, cc, cc->locals.values[index].data_ptr(), acc);
MOTH_END_INSTR(StoreScopedLocal)
MOTH_BEGIN_INSTR(LoadRuntimeString)
@@ -839,6 +840,18 @@ QV4::ReturnedValue VME::exec(const FunctionObject *fo, const Value *thisObject,
CHECK_EXCEPTION;
MOTH_END_INSTR(CallGlobalLookup)
+ MOTH_BEGIN_INSTR(CallScopeObjectProperty)
+ STORE_IP();
+ acc = Runtime::method_callQmlScopeObjectProperty(engine, stack + base, name, stack + argv, argc);
+ CHECK_EXCEPTION;
+ MOTH_END_INSTR(CallScopeObjectProperty)
+
+ MOTH_BEGIN_INSTR(CallContextObjectProperty)
+ STORE_IP();
+ acc = Runtime::method_callQmlContextObjectProperty(engine, stack + base, name, stack + argv, argc);
+ CHECK_EXCEPTION;
+ MOTH_END_INSTR(CallContextObjectProperty)
+
MOTH_BEGIN_INSTR(SetExceptionHandler)
exceptionHandler = offset ? code + offset : nullptr;
MOTH_END_INSTR(SetExceptionHandler)
@@ -1145,14 +1158,13 @@ QV4::ReturnedValue VME::exec(const FunctionObject *fo, const Value *thisObject,
MOTH_BEGIN_INSTR(CmpInstanceOf)
// 11.8.6, 5: rval must be an Object
- const Object *rhs = Primitive::fromReturnedValue(acc).as<Object>();
- if (Q_UNLIKELY(!rhs)) {
+ if (Q_UNLIKELY(!Primitive::fromReturnedValue(acc).isObject())) {
acc = engine->throwTypeError();
goto catchException;
}
// 11.8.6, 7: call "HasInstance", which we term instanceOf, and return the result.
- acc = rhs->instanceOf(STACK_VALUE(lhs));
+ acc = Primitive::fromReturnedValue(acc).objectValue()->instanceOf(STACK_VALUE(lhs));
CHECK_EXCEPTION;
MOTH_END_INSTR(CmpInstanceOf)
@@ -1294,9 +1306,9 @@ QV4::ReturnedValue VME::exec(const FunctionObject *fo, const Value *thisObject,
MOTH_END_INSTR(BitXor)
MOTH_BEGIN_INSTR(UShr)
- uint l = STACK_VALUE(lhs).toUInt32();
+ VALUE_TO_INT(l, STACK_VALUE(lhs));
VALUE_TO_INT(a, ACC);
- acc = Encode(l >> uint(a & 0x1f));
+ acc = Encode(static_cast<uint>(l) >> uint(a & 0x1f));
MOTH_END_INSTR(UShr)
MOTH_BEGIN_INSTR(Shr)
@@ -1345,12 +1357,12 @@ QV4::ReturnedValue VME::exec(const FunctionObject *fo, const Value *thisObject,
goto functionExit;
MOTH_END_INSTR(Ret)
-#if QT_CONFIG(qml_debug)
MOTH_BEGIN_INSTR(Debug)
+#if QT_CONFIG(qml_debug)
STORE_IP();
debug_slowPath(engine);
- MOTH_END_INSTR(Debug)
#endif // QT_CONFIG(qml_debug)
+ MOTH_END_INSTR(Debug)
MOTH_BEGIN_INSTR(LoadQmlContext)
STACK_VALUE(result) = Runtime::method_loadQmlContext(static_cast<QV4::NoThrowEngine*>(engine));
diff --git a/src/qml/jsruntime/qv4vme_moth_p.h b/src/qml/jsruntime/qv4vme_moth_p.h
index dbf9ed3550..3b7723ca7e 100644
--- a/src/qml/jsruntime/qv4vme_moth_p.h
+++ b/src/qml/jsruntime/qv4vme_moth_p.h
@@ -53,8 +53,6 @@
#include <private/qv4global_p.h>
-QT_REQUIRE_CONFIG(qml_interpreter);
-
QT_BEGIN_NAMESPACE
namespace QV4 {
diff --git a/src/qml/memory/qv4heap_p.h b/src/qml/memory/qv4heap_p.h
index d6cb661d19..63d6b0a609 100644
--- a/src/qml/memory/qv4heap_p.h
+++ b/src/qml/memory/qv4heap_p.h
@@ -53,6 +53,7 @@
#include <QtCore/QString>
#include <private/qv4global_p.h>
#include <private/qv4mmdefs_p.h>
+#include <private/qv4writebarrier_p.h>
#include <private/qv4internalclass_p.h>
#include <QSharedPointer>
@@ -60,12 +61,6 @@
// parent's init all up the inheritance chain), define QML_CHECK_INIT_DESTROY_CALLS below.
#undef QML_CHECK_INIT_DESTROY_CALLS
-#if defined(_MSC_VER) && (_MSC_VER < 1900) // broken compilers:
-# define V4_ASSERT_IS_TRIVIAL(x)
-#else // working compilers:
-# define V4_ASSERT_IS_TRIVIAL(x) Q_STATIC_ASSERT(std::is_trivial< x >::value);
-#endif
-
QT_BEGIN_NAMESPACE
namespace QV4 {
@@ -188,7 +183,7 @@ struct Q_QML_EXPORT Base {
Q_ALWAYS_INLINE void _setDestroyed() {}
#endif
};
-V4_ASSERT_IS_TRIVIAL(Base)
+Q_STATIC_ASSERT(std::is_trivial< Base >::value);
// This class needs to consist only of pointer sized members to allow
// for a size/offset translation when cross-compiling between 32- and
// 64-bit.
@@ -214,6 +209,39 @@ void Heap::Base::mark(QV4::MarkStack *markStack)
}
}
+namespace Heap {
+
+template <typename T, size_t o>
+struct Pointer {
+ static Q_CONSTEXPR size_t offset = o;
+ T operator->() const { return get(); }
+ operator T () const { return get(); }
+
+ Heap::Base *base() {
+ Heap::Base *base = reinterpret_cast<Heap::Base *>(this) - (offset/sizeof(Heap::Base));
+ Q_ASSERT(base->inUse());
+ return base;
+ }
+
+ void set(EngineBase *e, T newVal) {
+ WriteBarrier::write(e, base(), &ptr, reinterpret_cast<Heap::Base *>(newVal));
+ }
+
+ T get() const { return reinterpret_cast<T>(ptr); }
+
+ template <typename Type>
+ Type *cast() { return static_cast<Type *>(ptr); }
+
+ Heap::Base *heapObject() const { return ptr; }
+
+private:
+ Heap::Base *ptr;
+};
+typedef Pointer<char *, 0> V4PointerCheck;
+Q_STATIC_ASSERT(std::is_trivial< V4PointerCheck >::value);
+
+}
+
#ifdef QT_NO_QOBJECT
template <class T>
struct QQmlQPointer {
@@ -266,7 +294,7 @@ private:
QtSharedPointer::ExternalRefCountData *d;
QObject *qObject;
};
-V4_ASSERT_IS_TRIVIAL(QQmlQPointer<QObject>)
+Q_STATIC_ASSERT(std::is_trivial< QQmlQPointer<QObject> >::value);
#endif
}
diff --git a/src/qml/memory/qv4mm.cpp b/src/qml/memory/qv4mm.cpp
index 3ea7908e9d..4e83abebdf 100644
--- a/src/qml/memory/qv4mm.cpp
+++ b/src/qml/memory/qv4mm.cpp
@@ -44,6 +44,7 @@
#include "qv4qobjectwrapper_p.h"
#include <QtCore/qalgorithms.h>
#include <QtCore/private/qnumeric_p.h>
+#include <QtCore/qloggingcategory.h>
#include <qqmlengine.h>
#include "PageReservation.h"
#include "PageAllocation.h"
@@ -91,6 +92,11 @@
#define MIN_UNMANAGED_HEAPSIZE_GC_LIMIT std::size_t(128 * 1024)
+Q_LOGGING_CATEGORY(lcGcStats, "qt.qml.gc.statistics")
+Q_DECLARE_LOGGING_CATEGORY(lcGcStats)
+Q_LOGGING_CATEGORY(lcGcAllocatorStats, "qt.qml.gc.allocatorStats")
+Q_DECLARE_LOGGING_CATEGORY(lcGcAllocatorStats)
+
using namespace WTF;
QT_BEGIN_NAMESPACE
@@ -180,7 +186,7 @@ struct MemorySegment {
}
PageReservation pageReservation;
- Chunk *base = 0;
+ Chunk *base = nullptr;
quint64 allocatedMap = 0;
size_t availableBytes = 0;
uint nChunks = 0;
@@ -197,14 +203,14 @@ Chunk *MemorySegment::allocate(size_t size)
}
size_t requiredChunks = (size + sizeof(Chunk) - 1)/sizeof(Chunk);
uint sequence = 0;
- Chunk *candidate = 0;
+ Chunk *candidate = nullptr;
for (uint i = 0; i < nChunks; ++i) {
if (!testBit(i)) {
if (!candidate)
candidate = base + i;
++sequence;
} else {
- candidate = 0;
+ candidate = nullptr;
sequence = 0;
}
if (sequence == requiredChunks) {
@@ -215,7 +221,7 @@ Chunk *MemorySegment::allocate(size_t size)
return candidate;
}
}
- return 0;
+ return nullptr;
}
struct ChunkAllocator {
@@ -290,7 +296,8 @@ static void increaseFreedCountForClass(const char *className)
(*freedObjectStatsGlobal())[className]++;
}
-bool Chunk::sweep(ClassDestroyStatsCallback classCountPtr)
+//bool Chunk::sweep(ClassDestroyStatsCallback classCountPtr)
+bool Chunk::sweep(ExecutionEngine *engine)
{
bool hasUsedSlots = false;
SDUMP() << "sweeping chunk" << this;
@@ -329,13 +336,19 @@ bool Chunk::sweep(ClassDestroyStatsCallback classCountPtr)
HeapItem *itemToFree = o + index;
Heap::Base *b = *itemToFree;
const VTable *v = b->vtable();
- if (Q_UNLIKELY(classCountPtr))
- classCountPtr(v->className);
+// if (Q_UNLIKELY(classCountPtr))
+// classCountPtr(v->className);
if (v->destroy) {
v->destroy(b);
b->_checkIsDestroyed();
}
+#ifdef V4_USE_HEAPTRACK
+ heaptrack_report_free(itemToFree);
+#endif
}
+ Q_V4_PROFILE_DEALLOC(engine, qPopulationCount((objectBitmap[i] | extendsBitmap[i])
+ - (blackBitmap[i] | e)) * Chunk::SlotSize,
+ Profiling::SmallItem);
objectBitmap[i] = blackBitmap[i];
grayBitmap[i] = 0;
hasUsedSlots |= (blackBitmap[i] != 0);
@@ -350,7 +363,7 @@ bool Chunk::sweep(ClassDestroyStatsCallback classCountPtr)
return hasUsedSlots;
}
-void Chunk::freeAll()
+void Chunk::freeAll(ExecutionEngine *engine)
{
// DEBUG << "sweeping chunk" << this << (*freeList);
HeapItem *o = realBase();
@@ -380,7 +393,12 @@ void Chunk::freeAll()
b->vtable()->destroy(b);
b->_checkIsDestroyed();
}
+#ifdef V4_USE_HEAPTRACK
+ heaptrack_report_free(itemToFree);
+#endif
}
+ Q_V4_PROFILE_DEALLOC(engine, (qPopulationCount(objectBitmap[i]|extendsBitmap[i])
+ - qPopulationCount(e)) * Chunk::SlotSize, Profiling::SmallItem);
objectBitmap[i] = 0;
grayBitmap[i] = 0;
extendsBitmap[i] = e;
@@ -498,9 +516,9 @@ void Chunk::sortIntoBins(HeapItem **bins, uint nBins)
HeapItem *BlockAllocator::allocate(size_t size, bool forceAllocation) {
Q_ASSERT((size % Chunk::SlotSize) == 0);
size_t slotsRequired = size >> Chunk::SlotSizeShift;
-#if MM_DEBUG
- ++allocations[bin];
-#endif
+
+ if (allocationStats)
+ ++allocationStats[binForSlots(slotsRequired)];
HeapItem **last;
@@ -576,8 +594,9 @@ HeapItem *BlockAllocator::allocate(size_t size, bool forceAllocation) {
if (!m) {
if (!forceAllocation)
- return 0;
+ return nullptr;
Chunk *newChunk = chunkAllocator->allocate();
+ Q_V4_PROFILE_ALLOC(engine, Chunk::DataSize, Profiling::HeapPage);
chunks.push_back(newChunk);
nextFree = newChunk->first();
nFree = Chunk::AvailableSlots;
@@ -588,26 +607,31 @@ HeapItem *BlockAllocator::allocate(size_t size, bool forceAllocation) {
done:
m->setAllocatedSlots(slotsRequired);
+ Q_V4_PROFILE_ALLOC(engine, slotsRequired * Chunk::SlotSize, Profiling::SmallItem);
+#ifdef V4_USE_HEAPTRACK
+ heaptrack_report_alloc(m, slotsRequired * Chunk::SlotSize);
+#endif
// DEBUG << " " << hex << m->chunk() << m->chunk()->objectBitmap[0] << m->chunk()->extendsBitmap[0] << (m - m->chunk()->realBase());
return m;
}
-void BlockAllocator::sweep(ClassDestroyStatsCallback classCountPtr)
+void BlockAllocator::sweep()
{
- nextFree = 0;
+ nextFree = nullptr;
nFree = 0;
memset(freeBins, 0, sizeof(freeBins));
// qDebug() << "BlockAlloc: sweep";
usedSlotsAfterLastSweep = 0;
- auto isFree = [this, classCountPtr] (Chunk *c) {
- bool isUsed = c->sweep(classCountPtr);
+ auto isFree = [this] (Chunk *c) {
+ bool isUsed = c->sweep(engine);
if (isUsed) {
c->sortIntoBins(freeBins, NumBins);
usedSlotsAfterLastSweep += c->nUsedSlots();
} else {
+ Q_V4_PROFILE_DEALLOC(engine, Chunk::DataSize, Profiling::HeapPage);
chunkAllocator->free(c);
}
return !isUsed;
@@ -620,7 +644,8 @@ void BlockAllocator::sweep(ClassDestroyStatsCallback classCountPtr)
void BlockAllocator::freeAll()
{
for (auto c : chunks) {
- c->freeAll();
+ c->freeAll(engine);
+ Q_V4_PROFILE_DEALLOC(engine, Chunk::DataSize, Profiling::HeapPage);
chunkAllocator->free(c);
}
}
@@ -638,41 +663,27 @@ void BlockAllocator::collectGrayItems(MarkStack *markStack)
}
-#if MM_DEBUG
-void BlockAllocator::stats() {
- DEBUG << "MM stats:";
- QString s;
- for (int i = 0; i < 10; ++i) {
- uint c = 0;
- HeapItem *item = freeBins[i];
- while (item) {
- ++c;
- item = item->freeData.next;
- }
- s += QString::number(c) + QLatin1String(", ");
- }
- HeapItem *item = freeBins[NumBins - 1];
- uint c = 0;
- while (item) {
- ++c;
- item = item->freeData.next;
- }
- s += QLatin1String("..., ") + QString::number(c);
- DEBUG << "bins:" << s;
- QString a;
- for (int i = 0; i < 10; ++i)
- a += QString::number(allocations[i]) + QLatin1String(", ");
- a += QLatin1String("..., ") + QString::number(allocations[NumBins - 1]);
- DEBUG << "allocs:" << a;
- memset(allocations, 0, sizeof(allocations));
-}
-#endif
-
-
HeapItem *HugeItemAllocator::allocate(size_t size) {
- Chunk *c = chunkAllocator->allocate(size);
- chunks.push_back(HugeChunk{c, size});
+ MemorySegment *m = nullptr;
+ Chunk *c = nullptr;
+ if (size >= MemorySegment::SegmentSize/2) {
+ // too large to handle through the ChunkAllocator, let's get our own memory segement
+ size_t segmentSize = size + Chunk::HeaderSize; // space required for the Chunk header
+ size_t pageSize = WTF::pageSize();
+ segmentSize = (segmentSize + pageSize - 1) & ~(pageSize - 1); // align to page sizes
+ m = new MemorySegment(segmentSize);
+ size = (size + pageSize - 1) & ~(pageSize - 1); // align to page sizes
+ c = m->allocate(size);
+ } else {
+ c = chunkAllocator->allocate(size);
+ }
+ Q_ASSERT(c);
+ chunks.push_back(HugeChunk{m, c, size});
Chunk::setBit(c->objectBitmap, c->first() - c->realBase());
+ Q_V4_PROFILE_ALLOC(engine, size, Profiling::LargeItem);
+#ifdef V4_USE_HEAPTRACK
+ heaptrack_report_alloc(c, size);
+#endif
return c->first();
}
@@ -688,15 +699,27 @@ static void freeHugeChunk(ChunkAllocator *chunkAllocator, const HugeItemAllocato
v->destroy(b);
b->_checkIsDestroyed();
}
- chunkAllocator->free(c.chunk, c.size);
+ if (c.segment) {
+ // own memory segment
+ c.segment->free(c.chunk, c.size);
+ delete c.segment;
+ } else {
+ chunkAllocator->free(c.chunk, c.size);
+ }
+#ifdef V4_USE_HEAPTRACK
+ heaptrack_report_free(c.chunk);
+#endif
}
void HugeItemAllocator::sweep(ClassDestroyStatsCallback classCountPtr)
{
auto isBlack = [this, classCountPtr] (const HugeChunk &c) {
bool b = c.chunk->first()->isBlack();
- if (!b)
+ Chunk::clearBit(c.chunk->blackBitmap, c.chunk->first() - c.chunk->realBase());
+ if (!b) {
+ Q_V4_PROFILE_DEALLOC(engine, c.size, Profiling::LargeItem);
freeHugeChunk(chunkAllocator, c, classCountPtr);
+ }
return !b;
};
@@ -725,6 +748,7 @@ void HugeItemAllocator::collectGrayItems(MarkStack *markStack)
void HugeItemAllocator::freeAll()
{
for (auto &c : chunks) {
+ Q_V4_PROFILE_DEALLOC(engine, c.size, Profiling::LargeItem);
freeHugeChunk(chunkAllocator, c, nullptr);
}
}
@@ -733,17 +757,21 @@ void HugeItemAllocator::freeAll()
MemoryManager::MemoryManager(ExecutionEngine *engine)
: engine(engine)
, chunkAllocator(new ChunkAllocator)
- , blockAllocator(chunkAllocator)
- , hugeItemAllocator(chunkAllocator)
+ , blockAllocator(chunkAllocator, engine)
+ , hugeItemAllocator(chunkAllocator, engine)
, m_persistentValues(new PersistentValueStorage(engine))
, m_weakValues(new PersistentValueStorage(engine))
, unmanagedHeapSizeGCLimit(MIN_UNMANAGED_HEAPSIZE_GC_LIMIT)
, aggressiveGC(!qEnvironmentVariableIsEmpty("QV4_MM_AGGRESSIVE_GC"))
- , gcStats(!qEnvironmentVariableIsEmpty(QV4_MM_STATS))
+ , gcStats(lcGcStats().isDebugEnabled())
+ , gcCollectorStats(lcGcAllocatorStats().isDebugEnabled())
{
#ifdef V4_USE_VALGRIND
VALGRIND_CREATE_MEMPOOL(this, 0, true);
#endif
+ memset(statistics.allocations, 0, sizeof(statistics.allocations));
+ if (gcStats)
+ blockAllocator.allocationStats = statistics.allocations;
}
#ifdef MM_STATS
@@ -803,9 +831,6 @@ Heap::Base *MemoryManager::allocData(std::size_t size)
runGC();
didRunGC = true;
}
-#ifdef DETAILED_MM_STATS
- willAllocate(size);
-#endif // DETAILED_MM_STATS
Q_ASSERT(size >= Chunk::SlotSize);
Q_ASSERT(size % Chunk::SlotSize == 0);
@@ -992,7 +1017,7 @@ void MemoryManager::sweep(bool lastSweep, ClassDestroyStatsCallback classCountPt
}
}
- blockAllocator.sweep(classCountPtr);
+ blockAllocator.sweep();
hugeItemAllocator.sweep(classCountPtr);
}
@@ -1006,9 +1031,10 @@ bool MemoryManager::shouldRunGC() const
size_t dumpBins(BlockAllocator *b, bool printOutput = true)
{
+ const QLoggingCategory &stats = lcGcAllocatorStats();
size_t totalSlotMem = 0;
if (printOutput)
- qDebug() << "Slot map:";
+ qDebug(stats) << "Slot map:";
for (uint i = 0; i < BlockAllocator::NumBins; ++i) {
uint nEntries = 0;
HeapItem *h = b->freeBins[i];
@@ -1018,7 +1044,7 @@ size_t dumpBins(BlockAllocator *b, bool printOutput = true)
h = h->freeData.next;
}
if (printOutput)
- qDebug() << " number of entries in slot" << i << ":" << nEntries;
+ qDebug(stats) << " number of entries in slot" << i << ":" << nEntries;
}
SDUMP() << " large slot map";
HeapItem *h = b->freeBins[BlockAllocator::NumBins - 1];
@@ -1028,7 +1054,7 @@ size_t dumpBins(BlockAllocator *b, bool printOutput = true)
}
if (printOutput)
- qDebug() << " total mem in bins" << totalSlotMem*Chunk::SlotSize;
+ qDebug(stats) << " total mem in bins" << totalSlotMem*Chunk::SlotSize;
return totalSlotMem*Chunk::SlotSize;
}
@@ -1042,27 +1068,32 @@ void MemoryManager::runGC()
QScopedValueRollback<bool> gcBlocker(gcBlocked, true);
// qDebug() << "runGC";
- if (!gcStats) {
-// uint oldUsed = allocator.usedMem();
+ if (gcStats) {
+ statistics.maxReservedMem = qMax(statistics.maxReservedMem, getAllocatedMem());
+ statistics.maxAllocatedMem = qMax(statistics.maxAllocatedMem, getUsedMem() + getLargeItemsMem());
+ }
+
+ if (!gcCollectorStats) {
mark();
sweep();
-// DEBUG << "RUN GC: allocated:" << allocator.allocatedMem() << "used before" << oldUsed << "used now" << allocator.usedMem();
} else {
bool triggeredByUnmanagedHeap = (unmanagedHeapSize > unmanagedHeapSizeGCLimit);
size_t oldUnmanagedSize = unmanagedHeapSize;
+
const size_t totalMem = getAllocatedMem();
const size_t usedBefore = getUsedMem();
const size_t largeItemsBefore = getLargeItemsMem();
- qDebug() << "========== GC ==========";
+ const QLoggingCategory &stats = lcGcAllocatorStats();
+ qDebug(stats) << "========== GC ==========";
#ifdef MM_STATS
- qDebug() << " Triggered by alloc request of" << lastAllocRequestedSlots << "slots.";
- qDebug() << " Allocations since last GC" << allocationCount;
+ qDebug(stats) << " Triggered by alloc request of" << lastAllocRequestedSlots << "slots.";
+ qDebug(stats) << " Allocations since last GC" << allocationCount;
allocationCount = 0;
#endif
size_t oldChunks = blockAllocator.chunks.size();
- qDebug() << "Allocated" << totalMem << "bytes in" << oldChunks << "chunks";
- qDebug() << "Fragmented memory before GC" << (totalMem - usedBefore);
+ qDebug(stats) << "Allocated" << totalMem << "bytes in" << oldChunks << "chunks";
+ qDebug(stats) << "Fragmented memory before GC" << (totalMem - usedBefore);
dumpBins(&blockAllocator);
#ifdef MM_STATS
@@ -1080,15 +1111,15 @@ void MemoryManager::runGC()
qint64 sweepTime = t.nsecsElapsed()/1000;
if (triggeredByUnmanagedHeap) {
- qDebug() << "triggered by unmanaged heap:";
- qDebug() << " old unmanaged heap size:" << oldUnmanagedSize;
- qDebug() << " new unmanaged heap:" << unmanagedHeapSize;
- qDebug() << " unmanaged heap limit:" << unmanagedHeapSizeGCLimit;
+ qDebug(stats) << "triggered by unmanaged heap:";
+ qDebug(stats) << " old unmanaged heap size:" << oldUnmanagedSize;
+ qDebug(stats) << " new unmanaged heap:" << unmanagedHeapSize;
+ qDebug(stats) << " unmanaged heap limit:" << unmanagedHeapSizeGCLimit;
}
size_t memInBins = dumpBins(&blockAllocator);
- qDebug() << "Marked object in" << markTime << "us.";
- qDebug() << " " << markStackSize << "objects marked";
- qDebug() << "Sweeped object in" << sweepTime << "us.";
+ qDebug(stats) << "Marked object in" << markTime << "us.";
+ qDebug(stats) << " " << markStackSize << "objects marked";
+ qDebug(stats) << "Sweeped object in" << sweepTime << "us.";
// sort our object types by number of freed instances
MMStatsHash freedObjectStats;
@@ -1103,26 +1134,29 @@ void MemoryManager::runGC()
return a.second > b.second && strcmp(a.first, b.first) < 0;
});
- qDebug() << "Used memory before GC:" << usedBefore;
- qDebug() << "Used memory after GC:" << usedAfter;
- qDebug() << "Freed up bytes :" << (usedBefore - usedAfter);
- qDebug() << "Freed up chunks :" << (oldChunks - blockAllocator.chunks.size());
+ qDebug(stats) << "Used memory before GC:" << usedBefore;
+ qDebug(stats) << "Used memory after GC:" << usedAfter;
+ qDebug(stats) << "Freed up bytes :" << (usedBefore - usedAfter);
+ qDebug(stats) << "Freed up chunks :" << (oldChunks - blockAllocator.chunks.size());
size_t lost = blockAllocator.allocatedMem() - memInBins - usedAfter;
if (lost)
- qDebug() << "!!!!!!!!!!!!!!!!!!!!! LOST MEM:" << lost << "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!";
+ qDebug(stats) << "!!!!!!!!!!!!!!!!!!!!! LOST MEM:" << lost << "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!";
if (largeItemsBefore || largeItemsAfter) {
- qDebug() << "Large item memory before GC:" << largeItemsBefore;
- qDebug() << "Large item memory after GC:" << largeItemsAfter;
- qDebug() << "Large item memory freed up:" << (largeItemsBefore - largeItemsAfter);
+ qDebug(stats) << "Large item memory before GC:" << largeItemsBefore;
+ qDebug(stats) << "Large item memory after GC:" << largeItemsAfter;
+ qDebug(stats) << "Large item memory freed up:" << (largeItemsBefore - largeItemsAfter);
}
for (auto it = freedObjectsSorted.cbegin(); it != freedObjectsSorted.cend(); ++it) {
- qDebug().noquote() << QString::fromLatin1("Freed JS type: %1 (%2 instances)").arg(QString::fromLatin1(it->first), QString::number(it->second));
+ qDebug(stats).noquote() << QString::fromLatin1("Freed JS type: %1 (%2 instances)").arg(QString::fromLatin1(it->first), QString::number(it->second));
}
- qDebug() << "======== End GC ========";
+ qDebug(stats) << "======== End GC ========";
}
+ if (gcStats)
+ statistics.maxUsedMem = qMax(statistics.maxUsedMem, getUsedMem() + getLargeItemsMem());
+
if (aggressiveGC) {
// ensure we don't 'loose' any memory
Q_ASSERT(blockAllocator.allocatedMem() == getUsedMem() + dumpBins(&blockAllocator, false));
@@ -1154,6 +1188,8 @@ MemoryManager::~MemoryManager()
{
delete m_persistentValues;
+ dumpStats();
+
sweep(/*lastSweep*/true);
blockAllocator.freeAll();
hugeItemAllocator.freeAll();
@@ -1168,30 +1204,20 @@ MemoryManager::~MemoryManager()
void MemoryManager::dumpStats() const
{
-#ifdef DETAILED_MM_STATS
- std::cerr << "=================" << std::endl;
- std::cerr << "Allocation stats:" << std::endl;
- std::cerr << "Requests for each chunk size:" << std::endl;
- for (int i = 0; i < allocSizeCounters.size(); ++i) {
- if (unsigned count = allocSizeCounters[i]) {
- std::cerr << "\t" << (i << 4) << " bytes chunks: " << count << std::endl;
- }
- }
-#endif // DETAILED_MM_STATS
-}
+ if (!gcStats)
+ return;
-#ifdef DETAILED_MM_STATS
-void MemoryManager::willAllocate(std::size_t size)
-{
- unsigned alignedSize = (size + 15) >> 4;
- QVector<unsigned> &counters = allocSizeCounters;
- if ((unsigned) counters.size() < alignedSize + 1)
- counters.resize(alignedSize + 1);
- counters[alignedSize]++;
+ const QLoggingCategory &stats = lcGcStats();
+ qDebug(stats) << "Qml GC memory allocation statistics:";
+ qDebug(stats) << "Total memory allocated:" << statistics.maxReservedMem;
+ qDebug(stats) << "Max memory used before a GC run:" << statistics.maxAllocatedMem;
+ qDebug(stats) << "Max memory used after a GC run:" << statistics.maxUsedMem;
+ qDebug(stats) << "Requests for different item sizes:";
+ for (int i = 1; i < BlockAllocator::NumBins - 1; ++i)
+ qDebug(stats) << " <" << (i << Chunk::SlotSizeShift) << " bytes: " << statistics.allocations[i];
+ qDebug(stats) << " >=" << ((BlockAllocator::NumBins - 1) << Chunk::SlotSizeShift) << " bytes: " << statistics.allocations[BlockAllocator::NumBins - 1];
}
-#endif // DETAILED_MM_STATS
-
void MemoryManager::collectFromJSStack(MarkStack *markStack) const
{
Value *v = engine->jsStackBase;
diff --git a/src/qml/memory/qv4mm_p.h b/src/qml/memory/qv4mm_p.h
index 921fea3956..40670bcdc7 100644
--- a/src/qml/memory/qv4mm_p.h
+++ b/src/qml/memory/qv4mm_p.h
@@ -58,8 +58,6 @@
#include <private/qv4mmdefs_p.h>
#include <QVector>
-//#define DETAILED_MM_STATS
-
#define QV4_MM_MAXBLOCK_SHIFT "QV4_MM_MAXBLOCK_SHIFT"
#define QV4_MM_MAX_CHUNK_SIZE "QV4_MM_MAX_CHUNK_SIZE"
#define QV4_MM_STATS "QV4_MM_STATS"
@@ -71,15 +69,13 @@ QT_BEGIN_NAMESPACE
namespace QV4 {
struct ChunkAllocator;
+struct MemorySegment;
struct BlockAllocator {
- BlockAllocator(ChunkAllocator *chunkAllocator)
- : chunkAllocator(chunkAllocator)
+ BlockAllocator(ChunkAllocator *chunkAllocator, ExecutionEngine *engine)
+ : chunkAllocator(chunkAllocator), engine(engine)
{
memset(freeBins, 0, sizeof(freeBins));
-#if MM_DEBUG
- memset(allocations, 0, sizeof(allocations));
-#endif
}
enum { NumBins = 8 };
@@ -88,10 +84,6 @@ struct BlockAllocator {
return nSlots >= NumBins ? NumBins - 1 : nSlots;
}
-#if MM_DEBUG
- void stats();
-#endif
-
HeapItem *allocate(size_t size, bool forceAllocation = false);
size_t totalSlots() const {
@@ -108,26 +100,25 @@ struct BlockAllocator {
return used;
}
- void sweep(ClassDestroyStatsCallback classCountPtr);
+ void sweep();
void freeAll();
void resetBlackBits();
void collectGrayItems(MarkStack *markStack);
// bump allocations
- HeapItem *nextFree = 0;
+ HeapItem *nextFree = nullptr;
size_t nFree = 0;
size_t usedSlotsAfterLastSweep = 0;
HeapItem *freeBins[NumBins];
ChunkAllocator *chunkAllocator;
+ ExecutionEngine *engine;
std::vector<Chunk *> chunks;
-#if MM_DEBUG
- uint allocations[NumBins];
-#endif
+ uint *allocationStats = nullptr;
};
struct HugeItemAllocator {
- HugeItemAllocator(ChunkAllocator *chunkAllocator)
- : chunkAllocator(chunkAllocator)
+ HugeItemAllocator(ChunkAllocator *chunkAllocator, ExecutionEngine *engine)
+ : chunkAllocator(chunkAllocator), engine(engine)
{}
HeapItem *allocate(size_t size);
@@ -144,7 +135,9 @@ struct HugeItemAllocator {
}
ChunkAllocator *chunkAllocator;
+ ExecutionEngine *engine;
struct HugeChunk {
+ MemorySegment *segment;
Chunk *chunk;
size_t size;
};
@@ -169,7 +162,7 @@ public:
template<typename ManagedType>
inline typename ManagedType::Data *allocManaged(std::size_t size)
{
- V4_ASSERT_IS_TRIVIAL(typename ManagedType::Data)
+ Q_STATIC_ASSERT(std::is_trivial< typename ManagedType::Data >::value);
size = align(size);
Heap::Base *o = allocData(size);
InternalClass *ic = ManagedType::defaultInternalClass(engine);
@@ -182,7 +175,7 @@ public:
template<typename ManagedType>
inline typename ManagedType::Data *allocManaged(std::size_t size, InternalClass *ic)
{
- V4_ASSERT_IS_TRIVIAL(typename ManagedType::Data)
+ Q_STATIC_ASSERT(std::is_trivial< typename ManagedType::Data >::value);
size = align(size);
Heap::Base *o = allocData(size);
o->internalClass = ic;
@@ -238,7 +231,7 @@ public:
{
Scope scope(engine);
Scoped<ObjectType> t(scope, allocateObject<ObjectType>(ic));
- Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : 0));
+ Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : nullptr));
Q_UNUSED(prototype);
t->d_unchecked()->init();
return t->d();
@@ -249,7 +242,7 @@ public:
{
Scope scope(engine);
Scoped<ObjectType> t(scope, allocateObject<ObjectType>(ic));
- Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : 0));
+ Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : nullptr));
Q_UNUSED(prototype);
t->d_unchecked()->init(arg1);
return t->d();
@@ -260,7 +253,7 @@ public:
{
Scope scope(engine);
Scoped<ObjectType> t(scope, allocateObject<ObjectType>(ic));
- Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : 0));
+ Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : nullptr));
Q_UNUSED(prototype);
t->d_unchecked()->init(arg1, arg2);
return t->d();
@@ -271,7 +264,7 @@ public:
{
Scope scope(engine);
Scoped<ObjectType> t(scope, allocateObject<ObjectType>(ic));
- Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : 0));
+ Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : nullptr));
Q_UNUSED(prototype);
t->d_unchecked()->init(arg1, arg2, arg3);
return t->d();
@@ -282,7 +275,7 @@ public:
{
Scope scope(engine);
Scoped<ObjectType> t(scope, allocateObject<ObjectType>(ic));
- Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : 0));
+ Q_ASSERT(t->internalClass()->prototype == (prototype ? prototype->d() : nullptr));
Q_UNUSED(prototype);
t->d_unchecked()->init(arg1, arg2, arg3, arg4);
return t->d();
@@ -405,10 +398,6 @@ protected:
Heap::Base *allocData(std::size_t size);
Heap::Object *allocObjectWithMemberData(const QV4::VTable *vtable, uint nMembers);
-#ifdef DETAILED_MM_STATS
- void willAllocate(std::size_t size);
-#endif // DETAILED_MM_STATS
-
private:
void collectFromJSStack(MarkStack *markStack) const;
void mark();
@@ -432,6 +421,14 @@ public:
bool gcBlocked = false;
bool aggressiveGC = false;
bool gcStats = false;
+ bool gcCollectorStats = false;
+
+ struct {
+ size_t maxReservedMem = 0;
+ size_t maxAllocatedMem = 0;
+ size_t maxUsedMem = 0;
+ uint allocations[BlockAllocator::NumBins];
+ } statistics;
};
}
diff --git a/src/qml/memory/qv4mmdefs_p.h b/src/qml/memory/qv4mmdefs_p.h
index 6d911e69f6..3e2bae46c2 100644
--- a/src/qml/memory/qv4mmdefs_p.h
+++ b/src/qml/memory/qv4mmdefs_p.h
@@ -187,9 +187,10 @@ struct Chunk {
}
bool sweep(ClassDestroyStatsCallback classCountPtr);
- void freeAll();
void resetBlackBits();
void collectGrayItems(QV4::MarkStack *markStack);
+ bool sweep(ExecutionEngine *engine);
+ void freeAll(ExecutionEngine *engine);
void sortIntoBins(HeapItem **bins, uint nBins);
};
@@ -271,9 +272,9 @@ Q_STATIC_ASSERT((1 << Chunk::BitShift) == Chunk::Bits);
struct MarkStack {
MarkStack(ExecutionEngine *engine);
- Heap::Base **top = 0;
- Heap::Base **base = 0;
- Heap::Base **limit = 0;
+ Heap::Base **top = nullptr;
+ Heap::Base **base = nullptr;
+ Heap::Base **limit = nullptr;
ExecutionEngine *engine;
void push(Heap::Base *m) {
*top = m;
diff --git a/src/qml/memory/qv4writebarrier_p.h b/src/qml/memory/qv4writebarrier_p.h
index c0f4b0b29a..8b04aa6cb1 100644
--- a/src/qml/memory/qv4writebarrier_p.h
+++ b/src/qml/memory/qv4writebarrier_p.h
@@ -51,7 +51,7 @@
//
#include <private/qv4global_p.h>
-#include <private/qv4value_p.h>
+#include <private/qv4enginebase_p.h>
QT_BEGIN_NAMESPACE
@@ -84,14 +84,7 @@ static Q_CONSTEXPR inline bool isRequired() {
return false;
}
-inline void write(EngineBase *engine, Heap::Base *base, Value *slot, Value value)
-{
- Q_UNUSED(engine);
- Q_UNUSED(base);
- *slot = value;
-}
-
-inline void write(EngineBase *engine, Heap::Base *base, Value *slot, Heap::Base *value)
+inline void write(EngineBase *engine, Heap::Base *base, ReturnedValue *slot, ReturnedValue value)
{
Q_UNUSED(engine);
Q_UNUSED(base);
@@ -109,126 +102,6 @@ inline void write(EngineBase *engine, Heap::Base *base, Heap::Base **slot, Heap:
}
-namespace Heap {
-
-template <typename T, size_t o>
-struct Pointer {
- static Q_CONSTEXPR size_t offset = o;
- T operator->() const { return get(); }
- operator T () const { return get(); }
-
- Heap::Base *base() {
- Heap::Base *base = reinterpret_cast<Heap::Base *>(this) - (offset/sizeof(Heap::Base));
- Q_ASSERT(base->inUse());
- return base;
- }
-
- void set(EngineBase *e, T newVal) {
- WriteBarrier::write(e, base(), &ptr, reinterpret_cast<Heap::Base *>(newVal));
- }
-
- T get() const { return reinterpret_cast<T>(ptr); }
-
- template <typename Type>
- Type *cast() { return static_cast<Type *>(ptr); }
-
- Heap::Base *heapObject() const { return ptr; }
-
-private:
- Heap::Base *ptr;
-};
-typedef Pointer<char *, 0> V4PointerCheck;
-V4_ASSERT_IS_TRIVIAL(V4PointerCheck)
-
-}
-
-template <size_t o>
-struct HeapValue : Value {
- static Q_CONSTEXPR size_t offset = o;
- Heap::Base *base() {
- Heap::Base *base = reinterpret_cast<Heap::Base *>(this) - (offset/sizeof(Heap::Base));
- Q_ASSERT(base->inUse());
- return base;
- }
-
- void set(EngineBase *e, const Value &newVal) {
- WriteBarrier::write(e, base(), this, newVal);
- }
- void set(EngineBase *e, Heap::Base *b) {
- WriteBarrier::write(e, base(), this, b);
- }
-};
-
-template <size_t o>
-struct ValueArray {
- static Q_CONSTEXPR size_t offset = o;
- uint size;
- uint alloc;
- Value values[1];
-
- Heap::Base *base() {
- Heap::Base *base = reinterpret_cast<Heap::Base *>(this) - (offset/sizeof(Heap::Base));
- Q_ASSERT(base->inUse());
- return base;
- }
-
- void set(EngineBase *e, uint index, Value v) {
- WriteBarrier::write(e, base(), values + index, v);
- }
- void set(EngineBase *e, uint index, Heap::Base *b) {
- WriteBarrier::write(e, base(), values + index, b);
- }
- inline const Value &operator[] (uint index) const {
- Q_ASSERT(index < alloc);
- return values[index];
- }
- inline const Value *data() const {
- return values;
- }
-
- void insertData(EngineBase *e, uint index, Value v) {
- for (uint i = size - 1; i > index; --i) {
- values[i] = values[i - 1];
- }
- set(e, index, v);
- }
- void removeData(EngineBase *e, uint index, int n = 1) {
- Q_UNUSED(e);
- for (uint i = index; i < size - n; ++i) {
- values[i] = values[i + n];
- }
- }
-
- void mark(MarkStack *markStack) {
- Value *v = values;
- const Value *end = v + alloc;
- if (alloc > 32*1024) {
- // drain from time to time to avoid overflows in the js stack
- Heap::Base **currentBase = markStack->top;
- while (v < end) {
- v->mark(markStack);
- ++v;
- if (markStack->top >= currentBase + 32*1024) {
- Heap::Base **oldBase = markStack->base;
- markStack->base = currentBase;
- markStack->drain();
- markStack->base = oldBase;
- }
- }
- } else {
- while (v < end) {
- v->mark(markStack);
- ++v;
- }
- }
- }
-};
-
-// It's really important that the offset of values in this structure is
-// constant across all architecture, otherwise JIT cross-compiled code will
-// have wrong offsets between host and target.
-Q_STATIC_ASSERT(offsetof(ValueArray<0>, values) == 8);
-
}
QT_END_NAMESPACE
diff --git a/src/qml/parser/qqmljsast.cpp b/src/qml/parser/qqmljsast.cpp
index 2433522f42..34657a7d48 100644
--- a/src/qml/parser/qqmljsast.cpp
+++ b/src/qml/parser/qqmljsast.cpp
@@ -61,22 +61,22 @@ void Node::accept(Node *node, Visitor *visitor)
ExpressionNode *Node::expressionCast()
{
- return 0;
+ return nullptr;
}
BinaryExpression *Node::binaryExpressionCast()
{
- return 0;
+ return nullptr;
}
Statement *Node::statementCast()
{
- return 0;
+ return nullptr;
}
UiObjectMember *Node::uiObjectMemberCast()
{
- return 0;
+ return nullptr;
}
ExpressionNode *ExpressionNode::expressionCast()
diff --git a/src/qml/parser/qqmljsast_p.h b/src/qml/parser/qqmljsast_p.h
index 7291cf0d3d..ed3c83badf 100644
--- a/src/qml/parser/qqmljsast_p.h
+++ b/src/qml/parser/qqmljsast_p.h
@@ -224,8 +224,7 @@ public:
Kind_UiEnumMemberList
};
- inline Node()
- : kind(Kind_Undefined) {}
+ inline Node() {}
// NOTE: node destructors are never called,
// instead we block free the memory
@@ -248,7 +247,7 @@ public:
virtual SourceLocation lastSourceLocation() const = 0;
// attributes
- int kind;
+ int kind = Kind_Undefined;
};
class QML_PARSER_EXPORT ExpressionNode: public Node
@@ -457,11 +456,11 @@ public:
QQMLJS_DECLARE_AST_NODE(ArrayLiteral)
ArrayLiteral(Elision *e):
- elements (0), elision (e)
+ elements (nullptr), elision (e)
{ kind = K; }
ArrayLiteral(ElementList *elts):
- elements (elts), elision (0)
+ elements (elts), elision (nullptr)
{ kind = K; }
ArrayLiteral(ElementList *elts, Elision *e):
@@ -489,8 +488,8 @@ class QML_PARSER_EXPORT ObjectLiteral: public ExpressionNode
public:
QQMLJS_DECLARE_AST_NODE(ObjectLiteral)
- ObjectLiteral():
- properties (0) { kind = K; }
+ ObjectLiteral()
+ { kind = K; }
ObjectLiteral(PropertyAssignmentList *plist):
properties (plist) { kind = K; }
@@ -504,7 +503,7 @@ public:
{ return rbraceToken; }
// attributes
- PropertyAssignmentList *properties;
+ PropertyAssignmentList *properties = nullptr;
SourceLocation lbraceToken;
SourceLocation rbraceToken;
};
@@ -535,7 +534,7 @@ public:
inline Elision *finish ()
{
Elision *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -564,7 +563,7 @@ public:
inline ElementList *finish ()
{
ElementList *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -641,7 +640,7 @@ public:
inline PropertyAssignmentList *finish ()
{
PropertyAssignmentList *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -693,7 +692,7 @@ public:
};
PropertyGetterSetter(PropertyName *n, FunctionBody *b)
- : PropertyAssignment(n), type(Getter), formals(0), functionBody (b)
+ : PropertyAssignment(n), type(Getter), formals(nullptr), functionBody (b)
{ kind = K; }
PropertyGetterSetter(PropertyName *n, FormalParameterList *f, FunctionBody *b)
@@ -917,7 +916,7 @@ public:
inline ArgumentList *finish ()
{
ArgumentList *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -1281,7 +1280,7 @@ public:
inline StatementList *finish ()
{
StatementList *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -1377,9 +1376,9 @@ public:
inline VariableDeclarationList *finish(VariableDeclaration::VariableScope s)
{
VariableDeclarationList *front = next;
- next = 0;
+ next = nullptr;
VariableDeclarationList *vdl;
- for (vdl = front; vdl != 0; vdl = vdl->next) {
+ for (vdl = front; vdl != nullptr; vdl = vdl->next) {
vdl->declaration->scope = s;
}
return front;
@@ -1436,7 +1435,7 @@ class QML_PARSER_EXPORT IfStatement: public Statement
public:
QQMLJS_DECLARE_AST_NODE(IfStatement)
- IfStatement(ExpressionNode *e, Statement *t, Statement *f = 0):
+ IfStatement(ExpressionNode *e, Statement *t, Statement *f = nullptr):
expression (e), ok (t), ko (f)
{ kind = K; }
@@ -1727,7 +1726,7 @@ class QML_PARSER_EXPORT CaseBlock: public Node
public:
QQMLJS_DECLARE_AST_NODE(CaseBlock)
- CaseBlock(CaseClauses *c, DefaultClause *d = 0, CaseClauses *r = 0):
+ CaseBlock(CaseClauses *c, DefaultClause *d = nullptr, CaseClauses *r = nullptr):
clauses (c), defaultClause (d), moreClauses (r)
{ kind = K; }
@@ -1824,7 +1823,7 @@ public:
inline CaseClauses *finish ()
{
CaseClauses *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -1960,11 +1959,11 @@ public:
{ kind = K; }
TryStatement(Statement *stmt, Finally *f):
- statement (stmt), catchExpression (0), finallyExpression (f)
+ statement (stmt), catchExpression (nullptr), finallyExpression (f)
{ kind = K; }
TryStatement(Statement *stmt, Catch *c):
- statement (stmt), catchExpression (c), finallyExpression (0)
+ statement (stmt), catchExpression (c), finallyExpression (nullptr)
{ kind = K; }
void accept0(Visitor *visitor) override;
@@ -2058,7 +2057,7 @@ public:
inline FormalParameterList *finish ()
{
FormalParameterList *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -2106,7 +2105,7 @@ public:
inline SourceElements *finish ()
{
SourceElements *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -2240,7 +2239,7 @@ public:
UiQualifiedId *finish()
{
UiQualifiedId *head = next;
- next = 0;
+ next = nullptr;
return head;
}
@@ -2264,7 +2263,7 @@ public:
QQMLJS_DECLARE_AST_NODE(UiImport)
UiImport(const QStringRef &fileName)
- : fileName(fileName), importUri(0)
+ : fileName(fileName), importUri(nullptr)
{ kind = K; }
UiImport(UiQualifiedId *uri)
@@ -2328,7 +2327,7 @@ public:
UiObjectMemberList *finish()
{
UiObjectMemberList *head = next;
- next = 0;
+ next = nullptr;
return head;
}
@@ -2357,7 +2356,7 @@ public:
UiQualifiedPragmaId *finish()
{
UiQualifiedPragmaId *head = next;
- next = 0;
+ next = nullptr;
return head;
}
@@ -2430,7 +2429,7 @@ public:
UiHeaderItemList *finish()
{
UiHeaderItemList *head = next;
- next = 0;
+ next = nullptr;
return head;
}
@@ -2509,7 +2508,7 @@ public:
UiArrayMemberList *finish()
{
UiArrayMemberList *head = next;
- next = 0;
+ next = nullptr;
return head;
}
@@ -2570,7 +2569,7 @@ public:
inline UiParameterList *finish ()
{
UiParameterList *front = next;
- next = 0;
+ next = nullptr;
return front;
}
@@ -2590,13 +2589,13 @@ public:
UiPublicMember(UiQualifiedId *memberType,
const QStringRef &name)
- : type(Property), memberType(memberType), name(name), statement(0), binding(0), isDefaultMember(false), isReadonlyMember(false), parameters(0)
+ : type(Property), memberType(memberType), name(name), statement(nullptr), binding(nullptr), isDefaultMember(false), isReadonlyMember(false), parameters(nullptr)
{ kind = K; }
UiPublicMember(UiQualifiedId *memberType,
const QStringRef &name,
Statement *statement)
- : type(Property), memberType(memberType), name(name), statement(statement), binding(0), isDefaultMember(false), isReadonlyMember(false), parameters(0)
+ : type(Property), memberType(memberType), name(name), statement(statement), binding(nullptr), isDefaultMember(false), isReadonlyMember(false), parameters(nullptr)
{ kind = K; }
void accept0(Visitor *visitor) override;
@@ -2825,7 +2824,7 @@ public:
UiEnumMemberList *finish()
{
UiEnumMemberList *head = next;
- next = 0;
+ next = nullptr;
return head;
}
diff --git a/src/qml/parser/qqmljsengine_p.cpp b/src/qml/parser/qqmljsengine_p.cpp
index 7a6d9c3826..b4f0debf85 100644
--- a/src/qml/parser/qqmljsengine_p.cpp
+++ b/src/qml/parser/qqmljsengine_p.cpp
@@ -120,7 +120,7 @@ double integerFromString(const QString &str, int radix)
Engine::Engine()
- : _lexer(0), _directives(0)
+ : _lexer(nullptr), _directives(nullptr)
{ }
Engine::~Engine()
diff --git a/src/qml/parser/qqmljsengine_p.h b/src/qml/parser/qqmljsengine_p.h
index 8cbe69a0ba..af26bac0ff 100644
--- a/src/qml/parser/qqmljsengine_p.h
+++ b/src/qml/parser/qqmljsengine_p.h
@@ -71,8 +71,7 @@ class QML_PARSER_EXPORT DiagnosticMessage
public:
enum Kind { Warning, Error };
- DiagnosticMessage()
- : kind(Error) {}
+ DiagnosticMessage() {}
DiagnosticMessage(Kind kind, const AST::SourceLocation &loc, const QString &message)
: kind(kind), loc(loc), message(message) {}
@@ -83,7 +82,7 @@ public:
bool isError() const
{ return kind == Error; }
- Kind kind;
+ Kind kind = Error;
AST::SourceLocation loc;
QString message;
};
diff --git a/src/qml/parser/qqmljsgrammar.cpp b/src/qml/parser/qqmljsgrammar.cpp
index f345990ff9..2aaeb385e3 100644
--- a/src/qml/parser/qqmljsgrammar.cpp
+++ b/src/qml/parser/qqmljsgrammar.cpp
@@ -49,11 +49,11 @@ const char *const QQmlJSGrammar::spell [] = {
"if", "in", "instanceof", "{", "[", "<=", "(", "<", "<<", "<<=",
"-", "-=", "--", "new", "!", "!=", "!==", "numeric literal", "|", "|=",
"||", "+", "+=", "++", "?", "}", "]", "%", "%=", "return",
- ")", ";", 0, "*", "*=", "string literal", "property", "signal", "readonly", "switch",
+ ")", ";", nullptr, "*", "*=", "string literal", "property", "signal", "readonly", "switch",
"this", "throw", "~", "try", "typeof", "var", "void", "while", "with", "^",
"^=", "null", "true", "false", "const", "let", "debugger", "reserved word", "multiline string literal", "comment",
- 0, "enum", "public", "import", "pragma", "as", "on", "get", "set", 0,
- 0, 0, 0, 0, 0, 0, 0, 0
+ nullptr, "enum", "public", "import", "pragma", "as", "on", "get", "set", nullptr,
+ nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr
};
const short QQmlJSGrammar::lhs [] = {
diff --git a/src/qml/parser/qqmljslexer.cpp b/src/qml/parser/qqmljslexer.cpp
index 78ed5e3b2c..aab9025a08 100644
--- a/src/qml/parser/qqmljslexer.cpp
+++ b/src/qml/parser/qqmljslexer.cpp
@@ -85,11 +85,11 @@ static inline QChar convertUnicode(QChar c1, QChar c2, QChar c3, QChar c4)
Lexer::Lexer(Engine *engine)
: _engine(engine)
- , _codePtr(0)
- , _endPtr(0)
- , _lastLinePtr(0)
- , _tokenLinePtr(0)
- , _tokenStartPtr(0)
+ , _codePtr(nullptr)
+ , _endPtr(nullptr)
+ , _lastLinePtr(nullptr)
+ , _tokenLinePtr(nullptr)
+ , _tokenStartPtr(nullptr)
, _char(QLatin1Char('\n'))
, _errorCode(NoError)
, _currentLineNumber(0)
@@ -589,7 +589,7 @@ again:
chars.append('\0');
const char *begin = chars.constData();
- const char *end = 0;
+ const char *end = nullptr;
bool ok = false;
_tokenValue = qstrtod(begin, &end, &ok);
@@ -773,7 +773,7 @@ again:
u = QLatin1Char('\0');
break;
}
- // fall through
+ Q_FALLTHROUGH();
case '1':
case '2':
case '3':
@@ -915,7 +915,7 @@ int Lexer::scanNumber(QChar ch)
scanChar();
}
buf.append('\0');
- _tokenValue = strtod(buf.constData(), 0);
+ _tokenValue = strtod(buf.constData(), nullptr);
return T_NUMERIC_LITERAL;
}
} else if (_char.isDigit() && !qmlMode()) {
@@ -1010,7 +1010,7 @@ int Lexer::scanNumber(QChar ch)
chars.append('\0');
const char *begin = chars.constData();
- const char *end = 0;
+ const char *end = nullptr;
bool ok = false;
_tokenValue = qstrtod(begin, &end, &ok);
diff --git a/src/qml/parser/qqmljsmemorypool_p.h b/src/qml/parser/qqmljsmemorypool_p.h
index 536f5d4239..ef443d96bc 100644
--- a/src/qml/parser/qqmljsmemorypool_p.h
+++ b/src/qml/parser/qqmljsmemorypool_p.h
@@ -71,13 +71,7 @@ class QML_PARSER_EXPORT MemoryPool : public QSharedData
void operator =(const MemoryPool &other);
public:
- MemoryPool()
- : _blocks(0),
- _allocatedBlocks(0),
- _blockCount(-1),
- _ptr(0),
- _end(0)
- { }
+ MemoryPool() {}
~MemoryPool()
{
@@ -105,7 +99,7 @@ public:
void reset()
{
_blockCount = -1;
- _ptr = _end = 0;
+ _ptr = _end = nullptr;
}
template <typename Tp> Tp *New() { return new (this->allocate(sizeof(Tp))) Tp(); }
@@ -125,7 +119,7 @@ private:
Q_CHECK_PTR(_blocks);
for (int index = _blockCount; index < _allocatedBlocks; ++index)
- _blocks[index] = 0;
+ _blocks[index] = nullptr;
}
char *&block = _blocks[_blockCount];
@@ -144,11 +138,11 @@ private:
}
private:
- char **_blocks;
- int _allocatedBlocks;
- int _blockCount;
- char *_ptr;
- char *_end;
+ char **_blocks = nullptr;
+ int _allocatedBlocks = 0;
+ int _blockCount = -1;
+ char *_ptr = nullptr;
+ char *_end = nullptr;
enum
{
diff --git a/src/qml/parser/qqmljsparser.cpp b/src/qml/parser/qqmljsparser.cpp
index df16a24bcc..24b04b02f9 100644
--- a/src/qml/parser/qqmljsparser.cpp
+++ b/src/qml/parser/qqmljsparser.cpp
@@ -79,7 +79,7 @@ void Parser::reallocateStack()
sym_stack = reinterpret_cast<Value*> (realloc(sym_stack, stack_size * sizeof(Value)));
state_stack = reinterpret_cast<int*> (realloc(state_stack, stack_size * sizeof(int)));
location_stack = reinterpret_cast<AST::SourceLocation*> (realloc(location_stack, stack_size * sizeof(AST::SourceLocation)));
- string_stack = reinterpret_cast<QStringRef*> (realloc(string_stack, stack_size * sizeof(QStringRef)));
+ string_stack = reinterpret_cast<QStringRef*> (realloc(static_cast<void *>(string_stack), stack_size * sizeof(QStringRef)));
}
Parser::Parser(Engine *engine):
@@ -87,14 +87,14 @@ Parser::Parser(Engine *engine):
pool(engine->pool()),
tos(0),
stack_size(0),
- sym_stack(0),
- state_stack(0),
- location_stack(0),
- string_stack(0),
- program(0),
+ sym_stack(nullptr),
+ state_stack(nullptr),
+ location_stack(nullptr),
+ string_stack(nullptr),
+ program(nullptr),
yylval(0),
- first_token(0),
- last_token(0)
+ first_token(nullptr),
+ last_token(nullptr)
{
}
@@ -143,7 +143,7 @@ AST::UiQualifiedId *Parser::reparseAsQualifiedId(AST::ExpressionNode *expr)
return currentId->finish();
}
- return 0;
+ return nullptr;
}
AST::UiQualifiedPragmaId *Parser::reparseAsQualifiedPragmaId(AST::ExpressionNode *expr)
@@ -155,7 +155,7 @@ AST::UiQualifiedPragmaId *Parser::reparseAsQualifiedPragmaId(AST::ExpressionNode
return q->finish();
}
- return 0;
+ return nullptr;
}
@@ -188,7 +188,7 @@ bool Parser::parse(int startToken)
}
tos = -1;
- program = 0;
+ program = nullptr;
do {
if (++tos == stack_size)
@@ -315,7 +315,7 @@ case 24: {
} break;
case 25: {
- AST::UiPragma *node = 0;
+ AST::UiPragma *node = nullptr;
if (AST::UiQualifiedPragmaId *qualifiedId = reparseAsQualifiedPragmaId(sym(2).Expression)) {
node = new (pool) AST::UiPragma(qualifiedId);
@@ -334,7 +334,7 @@ case 25: {
} break;
case 26: {
- AST::UiImport *node = 0;
+ AST::UiImport *node = nullptr;
if (AST::StringLiteral *importIdLiteral = AST::cast<AST::StringLiteral *>(sym(2).Expression)) {
node = new (pool) AST::UiImport(importIdLiteral->value);
@@ -357,7 +357,7 @@ case 26: {
} break;
case 27: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 28: {
@@ -386,7 +386,7 @@ case 32: {
} break;
case 33: {
- AST::UiObjectInitializer *node = new (pool) AST::UiObjectInitializer((AST::UiObjectMemberList*)0);
+ AST::UiObjectInitializer *node = new (pool) AST::UiObjectInitializer((AST::UiObjectMemberList*)nullptr);
node->lbraceToken = loc(1);
node->rbraceToken = loc(2);
sym(1).Node = node;
@@ -462,7 +462,7 @@ case 51: {
} break;
case 52: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 53: {
@@ -594,7 +594,7 @@ case 71: {
AST::UiQualifiedId *propertyName = new (pool) AST::UiQualifiedId(stringRef(6));
propertyName->identifierToken = loc(6);
- propertyName->next = 0;
+ propertyName->next = nullptr;
AST::UiArrayBinding *binding = new (pool) AST::UiArrayBinding(
propertyName, sym(9).UiArrayMemberList->finish());
@@ -616,7 +616,7 @@ case 72: {
AST::UiQualifiedId *propertyName = new (pool) AST::UiQualifiedId(stringRef(3));
propertyName->identifierToken = loc(3);
- propertyName->next = 0;
+ propertyName->next = nullptr;
AST::UiObjectBinding *binding = new (pool) AST::UiObjectBinding(
propertyName, sym(5).UiQualifiedId, sym(6).UiObjectInitializer);
@@ -638,7 +638,7 @@ case 73: {
AST::UiQualifiedId *propertyName = new (pool) AST::UiQualifiedId(stringRef(4));
propertyName->identifierToken = loc(4);
- propertyName->next = 0;
+ propertyName->next = nullptr;
AST::UiObjectBinding *binding = new (pool) AST::UiObjectBinding(
propertyName, sym(6).UiQualifiedId, sym(7).UiObjectInitializer);
@@ -770,7 +770,7 @@ case 97: {
} break;
case 98: {
- AST::ArrayLiteral *node = new (pool) AST::ArrayLiteral((AST::Elision *) 0);
+ AST::ArrayLiteral *node = new (pool) AST::ArrayLiteral((AST::Elision *) nullptr);
node->lbracketToken = loc(1);
node->rbracketToken = loc(2);
sym(1).Node = node;
@@ -792,7 +792,7 @@ case 100: {
case 101: {
AST::ArrayLiteral *node = new (pool) AST::ArrayLiteral(sym(2).ElementList->finish (),
- (AST::Elision *) 0);
+ (AST::Elision *) nullptr);
node->lbracketToken = loc(1);
node->commaToken = loc(3);
node->rbracketToken = loc(4);
@@ -809,7 +809,7 @@ case 102: {
} break;
case 103: {
- AST::ObjectLiteral *node = 0;
+ AST::ObjectLiteral *node = nullptr;
if (sym(2).Node)
node = new (pool) AST::ObjectLiteral(
sym(2).PropertyAssignmentList->finish ());
@@ -846,7 +846,7 @@ case 106: {
if (AST::UiQualifiedId *qualifiedId = reparseAsQualifiedId(sym(1).Expression)) {
sym(1).UiQualifiedId = qualifiedId;
} else {
- sym(1).UiQualifiedId = 0;
+ sym(1).UiQualifiedId = nullptr;
diagnostic_messages.append(DiagnosticMessage(DiagnosticMessage::Error, loc(1),
QLatin1String("Expected a qualified name id")));
@@ -856,7 +856,7 @@ case 106: {
} break;
case 107: {
- sym(1).Node = new (pool) AST::ElementList((AST::Elision *) 0, sym(1).Expression);
+ sym(1).Node = new (pool) AST::ElementList((AST::Elision *) nullptr, sym(1).Expression);
} break;
case 108: {
@@ -865,7 +865,7 @@ case 108: {
case 109: {
AST::ElementList *node = new (pool) AST::ElementList(sym(1).ElementList,
- (AST::Elision *) 0, sym(3).Expression);
+ (AST::Elision *) nullptr, sym(3).Expression);
node->commaToken = loc(2);
sym(1).Node = node;
} break;
@@ -1010,7 +1010,7 @@ case 167: {
} break;
case 168: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 169: {
@@ -1437,7 +1437,7 @@ case 262: {
} break;
case 263: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 266: {
@@ -1447,7 +1447,7 @@ case 266: {
} break;
case 267: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 284: {
@@ -1466,7 +1466,7 @@ case 286: {
} break;
case 287: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 288: {
@@ -1537,7 +1537,7 @@ case 300: {
} break;
case 301: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 303: {
@@ -1546,7 +1546,7 @@ case 303: {
} break;
case 304: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 306: {
@@ -1718,7 +1718,7 @@ case 334: {
} break;
case 335: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 336: {
@@ -1840,7 +1840,7 @@ case 354: {
} break;
case 355: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 356: {
@@ -1848,7 +1848,7 @@ case 356: {
} break;
case 357: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
case 359: {
@@ -1876,7 +1876,7 @@ case 365: {
} break;
case 366: {
- sym(1).Node = 0;
+ sym(1).Node = nullptr;
} break;
} // switch
diff --git a/src/qml/parser/qqmljsparser_p.h b/src/qml/parser/qqmljsparser_p.h
index 9dfee70f3a..b4aecd2f08 100644
--- a/src/qml/parser/qqmljsparser_p.h
+++ b/src/qml/parser/qqmljsparser_p.h
@@ -146,7 +146,7 @@ public:
AST::Statement *statement() const
{
if (! program)
- return 0;
+ return nullptr;
return program->statementCast();
}
@@ -154,7 +154,7 @@ public:
AST::ExpressionNode *expression() const
{
if (! program)
- return 0;
+ return nullptr;
return program->expressionCast();
}
@@ -162,7 +162,7 @@ public:
AST::UiObjectMember *uiObjectMember() const
{
if (! program)
- return 0;
+ return nullptr;
return program->uiObjectMemberCast();
}
diff --git a/src/qml/qml.pro b/src/qml/qml.pro
index c13227d8fe..f75bfa0313 100644
--- a/src/qml/qml.pro
+++ b/src/qml/qml.pro
@@ -6,7 +6,7 @@ qtConfig(qml-network): \
DEFINES += QT_NO_URL_CAST_FROM_STRING QT_NO_INTEGER_EVENT_COORDINATES
-win32-msvc*|win32-icc:QMAKE_LFLAGS += /BASE:0x66000000
+msvc:equals(QT_ARCH, i386): QMAKE_LFLAGS += /BASE:0x66000000
win32-msvc*:DEFINES *= _CRT_SECURE_NO_WARNINGS
win32:!winrt:LIBS += -lshell32
solaris-cc*:QMAKE_CXXFLAGS_RELEASE -= -O2
@@ -16,17 +16,28 @@ gcc:isEqual(QT_ARCH, "mips"): QMAKE_CXXFLAGS += -fno-reorder-blocks
DEFINES += QT_NO_FOREACH
-tagFile=$$PWD/../../.tag
-tag=
-exists($$tagFile) {
- tag=$$cat($$tagFile, singleline)
- QMAKE_INTERNAL_INCLUDED_FILES += $$tagFile
-}
-!equals(tag, "$${LITERAL_DOLLAR}Format:%H$${LITERAL_DOLLAR}") {
- DEFINES += QML_COMPILE_HASH="$$tag"
-} else:exists($$PWD/../../.git) {
- commit=$$system(git describe --tags --always --long --dirty)
- DEFINES += QML_COMPILE_HASH="$$commit"
+!build_pass {
+ # Create a header containing a hash that describes this library. For a
+ # released version of Qt, we'll use the .tag file that is updated by git
+ # archive with the commit hash. For unreleased versions, we'll ask git
+ # describe. Note that it won't update unless qmake is run again, even if
+ # the commit change also changed something in this library.
+ tagFile = $$PWD/../../.tag
+ tag =
+ exists($$tagFile) {
+ tag = $$cat($$tagFile, singleline)
+ QMAKE_INTERNAL_INCLUDED_FILES += $$tagFile
+ }
+ !equals(tag, "$${LITERAL_DOLLAR}Format:%H$${LITERAL_DOLLAR}") {
+ QML_COMPILE_HASH = $$tag
+ } else:exists($$PWD/../../.git) {
+ commit = $$system(git describe --tags --always --long --dirty)
+ QML_COMPILE_HASH = $$commit
+ }
+ compile_hash_contents = \
+ "// Generated file, DO NOT EDIT" \
+ "$${LITERAL_HASH}define QML_COMPILE_HASH \"$$QML_COMPILE_HASH\""
+ write_file("$$OUT_PWD/qml_compile_hash_p.h", compile_hash_contents)|error()
}
exists("qqml_enable_gcov") {
diff --git a/src/qml/qml/ftw/qbitfield_p.h b/src/qml/qml/ftw/qbitfield_p.h
index 8f35842249..92017580d6 100644
--- a/src/qml/qml/ftw/qbitfield_p.h
+++ b/src/qml/qml/ftw/qbitfield_p.h
@@ -77,12 +77,12 @@ private:
};
QBitField::QBitField()
-: bits(0), ownData(0), data(0)
+: bits(0), ownData(nullptr), data(nullptr)
{
}
QBitField::QBitField(const quint32 *bitData, int bitCount)
-: bits((quint32)bitCount), ownData(0), data(bitData)
+: bits((quint32)bitCount), ownData(nullptr), data(bitData)
{
}
diff --git a/src/qml/qml/ftw/qfieldlist_p.h b/src/qml/qml/ftw/qfieldlist_p.h
index d83d708b5e..2bf07fb20d 100644
--- a/src/qml/qml/ftw/qfieldlist_p.h
+++ b/src/qml/qml/ftw/qfieldlist_p.h
@@ -141,7 +141,7 @@ N *QForwardFieldList<N, nextMember>::takeFirst()
N *value = *_first;
if (value) {
_first = next(value);
- value->*nextMember = 0;
+ value->*nextMember = nullptr;
}
return value;
}
@@ -149,7 +149,7 @@ N *QForwardFieldList<N, nextMember>::takeFirst()
template<class N, N *N::*nextMember>
void QForwardFieldList<N, nextMember>::prepend(N *v)
{
- Q_ASSERT(v->*nextMember == 0);
+ Q_ASSERT(v->*nextMember == nullptr);
v->*nextMember = *_first;
_first = v;
}
@@ -229,7 +229,7 @@ void QForwardFieldList<N, nextMember>::setFlag2Value(bool v)
template<class N, N *N::*nextMember>
QFieldList<N, nextMember>::QFieldList()
-: _first(0), _last(0), _flag(0), _count(0)
+: _first(nullptr), _last(nullptr), _flag(0), _count(0)
{
}
@@ -246,10 +246,10 @@ N *QFieldList<N, nextMember>::takeFirst()
if (value) {
_first = next(value);
if (_last == value) {
- Q_ASSERT(_first == 0);
- _last = 0;
+ Q_ASSERT(_first == nullptr);
+ _last = nullptr;
}
- value->*nextMember = 0;
+ value->*nextMember = nullptr;
--_count;
}
return value;
@@ -258,7 +258,7 @@ N *QFieldList<N, nextMember>::takeFirst()
template<class N, N *N::*nextMember>
void QFieldList<N, nextMember>::append(N *v)
{
- Q_ASSERT(v->*nextMember == 0);
+ Q_ASSERT(v->*nextMember == nullptr);
if (isEmpty()) {
_first = v;
_last = v;
@@ -272,7 +272,7 @@ void QFieldList<N, nextMember>::append(N *v)
template<class N, N *N::*nextMember>
void QFieldList<N, nextMember>::prepend(N *v)
{
- Q_ASSERT(v->*nextMember == 0);
+ Q_ASSERT(v->*nextMember == nullptr);
if (isEmpty()) {
_first = v;
_last = v;
@@ -375,7 +375,7 @@ void QFieldList<N, nextMember>::copyAndClear(QFieldList<N, nextMember> &o)
_first = o._first;
_last = o._last;
_count = o._count;
- o._first = o._last = 0;
+ o._first = o._last = nullptr;
o._count = 0;
}
@@ -391,8 +391,8 @@ void QFieldList<N, nextMember>::copyAndClearAppend(QForwardFieldList<N, nextMemb
template<class N, N *N::*nextMember>
void QFieldList<N, nextMember>::copyAndClearPrepend(QForwardFieldList<N, nextMember> &o)
{
- _first = 0;
- _last = 0;
+ _first = nullptr;
+ _last = nullptr;
_count = 0;
while (N *n = o.takeFirst()) prepend(n);
}
diff --git a/src/qml/qml/ftw/qfinitestack_p.h b/src/qml/qml/ftw/qfinitestack_p.h
index f1f1a551d5..9a74199137 100644
--- a/src/qml/qml/ftw/qfinitestack_p.h
+++ b/src/qml/qml/ftw/qfinitestack_p.h
@@ -81,7 +81,7 @@ private:
template<typename T>
QFiniteStack<T>::QFiniteStack()
-: _array(0), _alloc(0), _size(0)
+: _array(nullptr), _alloc(0), _size(0)
{
}
@@ -156,7 +156,7 @@ T &QFiniteStack<T>::operator[](int index)
template<typename T>
void QFiniteStack<T>::allocate(int size)
{
- Q_ASSERT(_array == 0);
+ Q_ASSERT(_array == nullptr);
Q_ASSERT(_alloc == 0);
Q_ASSERT(_size == 0);
@@ -177,7 +177,7 @@ void QFiniteStack<T>::deallocate()
free(_array);
- _array = 0;
+ _array = nullptr;
_alloc = 0;
_size = 0;
}
diff --git a/src/qml/qml/ftw/qflagpointer_p.h b/src/qml/qml/ftw/qflagpointer_p.h
index 6954a8f09c..91ce74bec9 100644
--- a/src/qml/qml/ftw/qflagpointer_p.h
+++ b/src/qml/qml/ftw/qflagpointer_p.h
@@ -83,7 +83,7 @@ public:
inline T *data() const;
private:
- quintptr ptr_value;
+ quintptr ptr_value = 0;
static const quintptr FlagBit = 0x1;
static const quintptr Flag2Bit = 0x2;
@@ -115,7 +115,7 @@ public:
inline T2 *asT2() const;
private:
- quintptr ptr_value;
+ quintptr ptr_value = 0;
static const quintptr FlagBit = 0x1;
static const quintptr Flag2Bit = 0x2;
@@ -124,7 +124,6 @@ private:
template<typename T>
QFlagPointer<T>::QFlagPointer()
-: ptr_value(0)
{
}
@@ -233,7 +232,6 @@ T *QFlagPointer<T>::data() const
template<typename T, typename T2>
QBiPointer<T, T2>::QBiPointer()
-: ptr_value(0)
{
}
diff --git a/src/qml/qml/ftw/qhashedstring_p.h b/src/qml/qml/ftw/qhashedstring_p.h
index 956805d696..2d6c25bdd3 100644
--- a/src/qml/qml/ftw/qhashedstring_p.h
+++ b/src/qml/qml/ftw/qhashedstring_p.h
@@ -94,7 +94,7 @@ private:
friend class QStringHashNode;
inline void computeHash() const;
- mutable quint32 m_hash;
+ mutable quint32 m_hash = 0;
};
class QHashedCStringRef;
@@ -142,9 +142,9 @@ private:
inline void computeHash() const;
- const QChar *m_data;
- int m_length;
- mutable quint32 m_hash;
+ const QChar *m_data = nullptr;
+ int m_length = 0;
+ mutable quint32 m_hash = 0;
};
class Q_AUTOTEST_EXPORT QHashedCStringRef
@@ -169,9 +169,9 @@ private:
inline void computeHash() const;
- const char *m_data;
- int m_length;
- mutable quint32 m_hash;
+ const char *m_data = nullptr;
+ int m_length = 0;
+ mutable quint32 m_hash = 0;
};
class QStringHashData;
@@ -179,7 +179,7 @@ class Q_AUTOTEST_EXPORT QStringHashNode
{
public:
QStringHashNode()
- : length(0), hash(0), symbolId(0), ckey(0)
+ : ckey(nullptr)
{
}
@@ -210,9 +210,9 @@ public:
QFlagPointer<QStringHashNode> next;
- qint32 length;
- quint32 hash;
- quint32 symbolId;
+ qint32 length = 0;
+ quint32 hash = 0;
+ quint32 symbolId = 0;
union {
const char *ckey;
@@ -276,25 +276,20 @@ public:
class Q_AUTOTEST_EXPORT QStringHashData
{
public:
- QStringHashData()
- : buckets(0), numBuckets(0), size(0), numBits(0)
-#ifdef QSTRINGHASH_LINK_DEBUG
- , linkCount(0)
-#endif
- {}
+ QStringHashData() {}
- QStringHashNode **buckets;
- int numBuckets;
- int size;
- short numBits;
+ QStringHashNode **buckets = nullptr;
+ int numBuckets = 0;
+ int size = 0;
+ short numBits = 0;
#ifdef QSTRINGHASH_LINK_DEBUG
- int linkCount;
+ int linkCount = 0;
#endif
struct IteratorData {
- IteratorData() : n(0), p(0) {}
- QStringHashNode *n;
- void *p;
+ IteratorData() {}
+ QStringHashNode *n = nullptr;
+ void *p = nullptr;
};
void rehashToBits(short);
void rehashToSize(int);
@@ -362,17 +357,17 @@ public:
T value;
};
struct NewedNode : public Node {
- NewedNode(const QHashedString &key, const T &value) : Node(key, value), nextNewed(0) {}
- NewedNode(const QHashedCStringRef &key, const T &value) : Node(key, value), nextNewed(0) {}
- NewedNode(const Node &o) : Node(o), nextNewed(0) {}
+ NewedNode(const QHashedString &key, const T &value) : Node(key, value), nextNewed(nullptr) {}
+ NewedNode(const QHashedCStringRef &key, const T &value) : Node(key, value), nextNewed(nullptr) {}
+ NewedNode(const Node &o) : Node(o), nextNewed(nullptr) {}
NewedNode *nextNewed;
};
struct ReservedNodePool
{
- ReservedNodePool() : count(0), used(0), nodes(0) {}
+ ReservedNodePool() : nodes(nullptr) {}
~ReservedNodePool() { delete [] nodes; }
- int count;
- int used;
+ int count = 0;
+ int used = 0;
Node *nodes;
};
@@ -475,13 +470,13 @@ public:
template<class T>
QStringHash<T>::QStringHash()
-: newedNodes(0), nodePool(0), link(0)
+: newedNodes(nullptr), nodePool(nullptr), link(nullptr)
{
}
template<class T>
QStringHash<T>::QStringHash(const QStringHash<T> &other)
-: newedNodes(0), nodePool(0), link(0)
+: newedNodes(nullptr), nodePool(nullptr), link(nullptr)
{
data.numBits = other.data.numBits;
data.size = other.data.size;
@@ -579,14 +574,14 @@ void QStringHash<T>::clear()
if (nodePool) delete nodePool;
delete [] data.buckets;
- data.buckets = 0;
+ data.buckets = nullptr;
data.numBuckets = 0;
data.numBits = 0;
data.size = 0;
- newedNodes = 0;
- nodePool = 0;
- link = 0;
+ newedNodes = nullptr;
+ nodePool = nullptr;
+ link = nullptr;
}
template<class T>
@@ -716,16 +711,16 @@ QStringHash<T>::iterateNext(const QStringHashData::IteratorData &d)
node < (This->nodePool->nodes + This->nodePool->used)) {
node--;
if (node < This->nodePool->nodes)
- node = 0;
+ node = nullptr;
} else {
NewedNode *nn = (NewedNode *)node;
node = nn->nextNewed;
- if (node == 0 && This->nodePool && This->nodePool->used)
+ if (node == nullptr && This->nodePool && This->nodePool->used)
node = This->nodePool->nodes + This->nodePool->used - 1;
}
- if (node == 0 && This->link)
+ if (node == nullptr && This->link)
return This->link->iterateFirst();
QStringHashData::IteratorData rv;
@@ -737,13 +732,13 @@ QStringHash<T>::iterateNext(const QStringHashData::IteratorData &d)
template<class T>
QStringHashData::IteratorData QStringHash<T>::iterateFirst() const
{
- Node *n = 0;
+ Node *n = nullptr;
if (newedNodes)
n = newedNodes;
else if (nodePool && nodePool->used)
n = nodePool->nodes + nodePool->used - 1;
- if (n == 0 && link)
+ if (n == nullptr && link)
return link->iterateFirst();
QStringHashData::IteratorData rv;
@@ -822,7 +817,7 @@ void QStringHash<T>::insert(const K &key, const T &value)
{
// If this is a linked hash, we can't rely on owning the node, so we always
// create a new one.
- Node *n = link?0:findNode(key);
+ Node *n = link?nullptr:findNode(key);
if (n) n->value = value;
else createNode(key, value);
}
@@ -837,7 +832,7 @@ template<class T>
template<class K>
typename QStringHash<T>::Node *QStringHash<T>::findNode(const K &key) const
{
- QStringHashNode *node = data.numBuckets?data.buckets[hashOf(key) % data.numBuckets]:0;
+ QStringHashNode *node = data.numBuckets?data.buckets[hashOf(key) % data.numBuckets]:nullptr;
typename HashedForm<K>::Type hashedKey(hashedString(key));
while (node && !node->equals(hashedKey))
@@ -851,7 +846,7 @@ template<class K>
T *QStringHash<T>::value(const K &key) const
{
Node *n = findNode(key);
- return n?&n->value:0;
+ return n?&n->value:nullptr;
}
template<class T>
@@ -865,14 +860,14 @@ template<class T>
T *QStringHash<T>::value(const QV4::String *string) const
{
Node *n = findNode(string);
- return n?&n->value:0;
+ return n?&n->value:nullptr;
}
template<class T>
template<class K>
bool QStringHash<T>::contains(const K &key) const
{
- return 0 != value(key);
+ return nullptr != value(key);
}
template<class T>
@@ -1038,7 +1033,7 @@ inline uint qHash(const QHashedStringRef &string)
}
QHashedString::QHashedString()
-: QString(), m_hash(0)
+: QString()
{
}
@@ -1089,7 +1084,6 @@ quint32 QHashedString::existingHash() const
}
QHashedStringRef::QHashedStringRef()
-: m_data(0), m_length(0), m_hash(0)
{
}
@@ -1236,7 +1230,6 @@ quint32 QHashedStringRef::hash() const
}
QHashedCStringRef::QHashedCStringRef()
-: m_data(0), m_length(0), m_hash(0)
{
}
diff --git a/src/qml/qml/ftw/qintrusivelist_p.h b/src/qml/qml/ftw/qintrusivelist_p.h
index 3d749e697e..8992be9f93 100644
--- a/src/qml/qml/ftw/qintrusivelist_p.h
+++ b/src/qml/qml/ftw/qintrusivelist_p.h
@@ -95,7 +95,7 @@ public:
private:
static inline N *nodeToN(QIntrusiveListNode *node);
- QIntrusiveListNode *__first;
+ QIntrusiveListNode *__first = nullptr;
};
class QIntrusiveListNode
@@ -107,13 +107,13 @@ public:
inline void remove();
inline bool isInList() const;
- QIntrusiveListNode *_next;
- QIntrusiveListNode**_prev;
+ QIntrusiveListNode *_next = nullptr;
+ QIntrusiveListNode**_prev = nullptr;
};
template<class N, QIntrusiveListNode N::*member>
QIntrusiveList<N, member>::iterator::iterator()
-: _value(0)
+: _value(nullptr)
{
}
@@ -165,7 +165,7 @@ typename QIntrusiveList<N, member>::iterator &QIntrusiveList<N, member>::iterato
template<class N, QIntrusiveListNode N::*member>
QIntrusiveList<N, member>::QIntrusiveList()
-: __first(0)
+
{
}
@@ -178,7 +178,7 @@ QIntrusiveList<N, member>::~QIntrusiveList()
template<class N, QIntrusiveListNode N::*member>
bool QIntrusiveList<N, member>::isEmpty() const
{
- return __first == 0;
+ return __first == nullptr;
}
template<class N, QIntrusiveListNode N::*member>
@@ -215,14 +215,14 @@ bool QIntrusiveList<N, member>::contains(N *n) const
template<class N, QIntrusiveListNode N::*member>
N *QIntrusiveList<N, member>::first() const
{
- return __first?nodeToN(__first):0;
+ return __first?nodeToN(__first):nullptr;
}
template<class N, QIntrusiveListNode N::*member>
N *QIntrusiveList<N, member>::next(N *current)
{
QIntrusiveListNode *nextnode = (current->*member)._next;
- N *nextstruct = nextnode?nodeToN(nextnode):0;
+ N *nextstruct = nextnode?nodeToN(nextnode):nullptr;
return nextstruct;
}
@@ -241,11 +241,10 @@ typename QIntrusiveList<N, member>::iterator QIntrusiveList<N, member>::end()
template<class N, QIntrusiveListNode N::*member>
N *QIntrusiveList<N, member>::nodeToN(QIntrusiveListNode *node)
{
- return (N *)((char *)node - ((char *)&(((N *)0)->*member) - (char *)0));
+ return (N *)((char *)node - ((char *)&(((N *)nullptr)->*member) - (char *)nullptr));
}
QIntrusiveListNode::QIntrusiveListNode()
-: _next(0), _prev(0)
{
}
@@ -258,13 +257,13 @@ void QIntrusiveListNode::remove()
{
if (_prev) *_prev = _next;
if (_next) _next->_prev = _prev;
- _prev = 0;
- _next = 0;
+ _prev = nullptr;
+ _next = nullptr;
}
bool QIntrusiveListNode::isInList() const
{
- return _prev != 0;
+ return _prev != nullptr;
}
QT_END_NAMESPACE
diff --git a/src/qml/qml/ftw/qpodvector_p.h b/src/qml/qml/ftw/qpodvector_p.h
index cafe3367de..b2fb481793 100644
--- a/src/qml/qml/ftw/qpodvector_p.h
+++ b/src/qml/qml/ftw/qpodvector_p.h
@@ -61,7 +61,7 @@ class QPODVector
{
public:
QPODVector()
- : m_count(0), m_capacity(0), m_data(0) {}
+ : m_count(0), m_capacity(0), m_data(nullptr) {}
~QPODVector() { if (m_data) ::free(m_data); }
const T &at(int idx) const {
@@ -87,11 +87,11 @@ public:
void insert(int idx, const T &v) {
if (m_count == m_capacity) {
m_capacity += Increment;
- m_data = (T *)realloc(m_data, m_capacity * sizeof(T));
+ m_data = (T *)realloc(static_cast<void *>(m_data), m_capacity * sizeof(T));
}
int moveCount = m_count - idx;
if (moveCount)
- ::memmove(m_data + idx + 1, m_data + idx, moveCount * sizeof(T));
+ ::memmove(static_cast<void *>(m_data + idx + 1), static_cast<const void *>(m_data + idx), moveCount * sizeof(T));
m_count++;
m_data[idx] = v;
}
@@ -99,7 +99,7 @@ public:
void reserve(int count) {
if (count >= m_capacity) {
m_capacity = (count + (Increment-1)) & (0xFFFFFFFF - Increment + 1);
- m_data = (T *)realloc(m_data, m_capacity * sizeof(T));
+ m_data = (T *)realloc(static_cast<void *>(m_data), m_capacity * sizeof(T));
}
}
@@ -108,7 +108,7 @@ public:
reserve(newSize);
int moveCount = m_count - idx;
if (moveCount)
- ::memmove(m_data + idx + count, m_data + idx,
+ ::memmove(static_cast<void *>(m_data + idx + count), static_cast<const void *>(m_data + idx),
moveCount * sizeof(T));
m_count = newSize;
}
@@ -116,7 +116,7 @@ public:
void remove(int idx, int count = 1) {
int moveCount = m_count - (idx + count);
if (moveCount)
- ::memmove(m_data + idx, m_data + idx + count,
+ ::memmove(static_cast<void *>(m_data + idx), static_cast<const void *>(m_data + idx + count),
moveCount * sizeof(T));
m_count -= count;
}
@@ -154,7 +154,7 @@ public:
other.m_data = m_data;
m_count = 0;
m_capacity = 0;
- m_data = 0;
+ m_data = nullptr;
}
QPODVector<T,Increment> &operator<<(const T &v) { append(v); return *this; }
diff --git a/src/qml/qml/ftw/qqmlnullablevalue_p.h b/src/qml/qml/ftw/qqmlnullablevalue_p.h
index 7a9e4d7b8a..5b3d2fc456 100644
--- a/src/qml/qml/ftw/qqmlnullablevalue_p.h
+++ b/src/qml/qml/ftw/qqmlnullablevalue_p.h
@@ -57,7 +57,7 @@ template<typename T>
struct QQmlNullableValue
{
QQmlNullableValue()
- : isNull(true), value(T()) {}
+ : value(T()) {}
QQmlNullableValue(const QQmlNullableValue<T> &o)
: isNull(o.isNull), value(o.value) {}
QQmlNullableValue(const T &t)
@@ -70,7 +70,7 @@ struct QQmlNullableValue
void invalidate() { isNull = true; }
bool isValid() const { return !isNull; }
- bool isNull;
+ bool isNull = true;
T value;
};
diff --git a/src/qml/qml/ftw/qqmlrefcount_p.h b/src/qml/qml/ftw/qqmlrefcount_p.h
index 225e18156c..3cfb345b30 100644
--- a/src/qml/qml/ftw/qqmlrefcount_p.h
+++ b/src/qml/qml/ftw/qqmlrefcount_p.h
@@ -137,7 +137,7 @@ void QQmlRefCount::destroy()
template<class T>
QQmlRefPointer<T>::QQmlRefPointer()
-: o(0)
+: o(nullptr)
{
}
diff --git a/src/qml/qml/ftw/qqmlthread.cpp b/src/qml/qml/ftw/qqmlthread.cpp
index bf62d7a99a..322d3281c7 100644
--- a/src/qml/qml/ftw/qqmlthread.cpp
+++ b/src/qml/qml/ftw/qqmlthread.cpp
@@ -129,7 +129,7 @@ bool QQmlThreadPrivate::MainObject::event(QEvent *e)
QQmlThreadPrivate::QQmlThreadPrivate(QQmlThread *q)
: q(q), m_threadProcessing(false), m_mainProcessing(false), m_shutdown(false),
- m_mainThreadWaiting(false), mainSync(0), m_mainObject(this)
+ m_mainThreadWaiting(false), mainSync(nullptr), m_mainObject(this)
{
setObjectName(QStringLiteral("QQmlThread"));
}
@@ -161,7 +161,7 @@ void QQmlThreadPrivate::mainEvent()
m_mainProcessing = true;
while (!mainList.isEmpty() || mainSync) {
- bool isSync = mainSync != 0;
+ bool isSync = mainSync != nullptr;
QQmlThread::Message *message = isSync?mainSync:mainList.takeFirst();
unlock();
@@ -171,7 +171,7 @@ void QQmlThreadPrivate::mainEvent()
lock();
if (isSync) {
- mainSync = 0;
+ mainSync = nullptr;
wakeOne();
}
}
@@ -339,7 +339,7 @@ void QQmlThread::internalCallMethodInThread(Message *message)
message->call(this);
delete message;
lock();
- d->mainSync = 0;
+ d->mainSync = nullptr;
wakeOne();
} else {
d->wait();
@@ -356,7 +356,7 @@ void QQmlThread::internalCallMethodInMain(Message *message)
d->lock();
- Q_ASSERT(d->mainSync == 0);
+ Q_ASSERT(d->mainSync == nullptr);
d->mainSync = message;
if (d->m_mainThreadWaiting) {
@@ -370,7 +370,7 @@ void QQmlThread::internalCallMethodInMain(Message *message)
while (d->mainSync) {
if (d->m_shutdown) {
delete d->mainSync;
- d->mainSync = 0;
+ d->mainSync = nullptr;
break;
}
d->wait();
@@ -418,7 +418,7 @@ void QQmlThread::waitForNextMessage()
message->call(this);
delete message;
lock();
- d->mainSync = 0;
+ d->mainSync = nullptr;
wakeOne();
} else {
d->wait();
diff --git a/src/qml/qml/ftw/qqmlthread_p.h b/src/qml/qml/ftw/qqmlthread_p.h
index 295235e255..0ed12a2972 100644
--- a/src/qml/qml/ftw/qqmlthread_p.h
+++ b/src/qml/qml/ftw/qqmlthread_p.h
@@ -124,7 +124,7 @@ private:
friend class QQmlThreadPrivate;
struct Message {
- Message() : next(0) {}
+ Message() : next(nullptr) {}
virtual ~Message() {}
Message *next;
virtual void call(QQmlThread *) = 0;
diff --git a/src/qml/qml/ftw/qrecursionwatcher_p.h b/src/qml/qml/ftw/qrecursionwatcher_p.h
index 99228b9583..56b714f922 100644
--- a/src/qml/qml/ftw/qrecursionwatcher_p.h
+++ b/src/qml/qml/ftw/qrecursionwatcher_p.h
@@ -74,7 +74,7 @@ private:
};
QRecursionNode::QRecursionNode()
-: _r(0)
+: _r(nullptr)
{
}
@@ -89,7 +89,7 @@ QRecursionWatcher<T, Node>::QRecursionWatcher(T *t)
template<class T, QRecursionNode T::*Node>
QRecursionWatcher<T, Node>::~QRecursionWatcher()
{
- if ((_t->*Node)._r == &_r) (_t->*Node)._r = 0;
+ if ((_t->*Node)._r == &_r) (_t->*Node)._r = nullptr;
}
template<class T, QRecursionNode T::*Node>
diff --git a/src/qml/qml/ftw/qrecyclepool_p.h b/src/qml/qml/ftw/qrecyclepool_p.h
index 42a2f13729..39f4f88512 100644
--- a/src/qml/qml/ftw/qrecyclepool_p.h
+++ b/src/qml/qml/ftw/qrecyclepool_p.h
@@ -61,7 +61,7 @@ class QRecyclePoolPrivate
public:
QRecyclePoolPrivate()
: recyclePoolHold(true), outstandingItems(0), cookie(QRECYCLEPOOLCOOKIE),
- currentPage(0), nextAllocated(0)
+ currentPage(nullptr), nextAllocated(nullptr)
{
}
@@ -178,7 +178,7 @@ void QRecyclePoolPrivate<T, Step>::releaseIfPossible()
template<typename T, int Step>
T *QRecyclePoolPrivate<T, Step>::allocate()
{
- PoolType *rv = 0;
+ PoolType *rv = nullptr;
if (nextAllocated) {
rv = nextAllocated;
nextAllocated = rv->nextAllocated;
diff --git a/src/qml/qml/qqml.h b/src/qml/qml/qqml.h
index 219df264be..213f23cd98 100644
--- a/src/qml/qml/qqml.h
+++ b/src/qml/qml/qqml.h
@@ -354,7 +354,7 @@ int qmlRegisterRevision(const char *uri, int versionMajor, int versionMinor)
sizeof(T), QQmlPrivate::createInto<T>,
QString(),
- uri, versionMajor, versionMinor, 0, &T::staticMetaObject,
+ uri, versionMajor, versionMinor, nullptr, &T::staticMetaObject,
QQmlPrivate::attachedPropertiesFunc<T>(),
QQmlPrivate::attachedPropertiesMetaObject<T>(),
diff --git a/src/qml/qml/qqmlabstractbinding.cpp b/src/qml/qml/qqmlabstractbinding.cpp
index b1c320afd4..42891c1a8e 100644
--- a/src/qml/qml/qqmlabstractbinding.cpp
+++ b/src/qml/qml/qqmlabstractbinding.cpp
@@ -83,7 +83,7 @@ void QQmlAbstractBinding::addToObject()
// Value type
// Find the value type proxy (if there is one)
- QQmlValueTypeProxyBinding *proxy = 0;
+ QQmlValueTypeProxyBinding *proxy = nullptr;
if (data->hasBindingBit(coreIndex)) {
QQmlAbstractBinding *b = data->bindings;
while (b && (b->targetPropertyIndex().coreIndex() != coreIndex ||
@@ -137,7 +137,7 @@ void QQmlAbstractBinding::removeFromObject()
QQmlAbstractBinding::Ptr next;
next = nextBinding();
- setNextBinding(0);
+ setNextBinding(nullptr);
int coreIndex = targetPropertyIndex().coreIndex();
if (targetPropertyIndex().hasValueTypeIndex()) {
diff --git a/src/qml/qml/qqmlabstractbinding_p.h b/src/qml/qml/qqmlabstractbinding_p.h
index bea2d253e4..fc53be3e7b 100644
--- a/src/qml/qml/qqmlabstractbinding_p.h
+++ b/src/qml/qml/qqmlabstractbinding_p.h
@@ -95,8 +95,8 @@ public:
{ return m_nextBinding.flag2(); }
struct RefCount {
- RefCount() : refCount(0) {}
- int refCount;
+ RefCount() {}
+ int refCount = 0;
void ref() { ++refCount; }
int deref() { return --refCount; }
operator int() const { return refCount; }
diff --git a/src/qml/qml/qqmlapplicationengine.cpp b/src/qml/qml/qqmlapplicationengine.cpp
index faab8bf926..a0517e4558 100644
--- a/src/qml/qml/qqmlapplicationengine.cpp
+++ b/src/qml/qml/qqmlapplicationengine.cpp
@@ -128,7 +128,7 @@ void QQmlApplicationEnginePrivate::finishLoad(QQmlComponent *c)
case QQmlComponent::Error:
qWarning() << "QQmlApplicationEngine failed to load component";
qWarning() << qPrintable(c->errorString());
- q->objectCreated(0, c->url());
+ q->objectCreated(nullptr, c->url());
break;
case QQmlComponent::Ready: {
auto newObj = c->create();
diff --git a/src/qml/qml/qqmlapplicationengine.h b/src/qml/qml/qqmlapplicationengine.h
index d0f9e6d319..bb5d6b5d68 100644
--- a/src/qml/qml/qqmlapplicationengine.h
+++ b/src/qml/qml/qqmlapplicationengine.h
@@ -56,7 +56,7 @@ public:
QQmlApplicationEngine(QObject *parent = nullptr);
QQmlApplicationEngine(const QUrl &url, QObject *parent = nullptr);
QQmlApplicationEngine(const QString &filePath, QObject *parent = nullptr);
- ~QQmlApplicationEngine();
+ ~QQmlApplicationEngine() override;
#if QT_VERSION < QT_VERSION_CHECK(6, 0, 0)
QList<QObject*> rootObjects(); // ### Qt 6: remove
diff --git a/src/qml/qml/qqmlbinding.cpp b/src/qml/qml/qqmlbinding.cpp
index 56ab259229..ca3bff43a4 100644
--- a/src/qml/qml/qqmlbinding.cpp
+++ b/src/qml/qml/qqmlbinding.cpp
@@ -70,7 +70,7 @@ QQmlBinding *QQmlBinding::create(const QQmlPropertyData *property, const QQmlScr
return b;
QString url;
- QV4::Function *runtimeFunction = 0;
+ QV4::Function *runtimeFunction = nullptr;
QQmlContextData *ctxtdata = QQmlContextData::get(scriptPrivate->context);
QQmlEnginePrivate *engine = QQmlEnginePrivate::get(scriptPrivate->context->engine());
@@ -84,7 +84,7 @@ QQmlBinding *QQmlBinding::create(const QQmlPropertyData *property, const QQmlScr
b->QQmlJavaScriptExpression::setContext(QQmlContextData::get(ctxt ? ctxt : scriptPrivate->context));
b->setScopeObject(obj ? obj : scriptPrivate->scope);
- QV4::ExecutionEngine *v4 = QQmlEnginePrivate::get(b->context()->engine)->v4engine();
+ QV4::ExecutionEngine *v4 = b->context()->engine->handle();
if (runtimeFunction) {
QV4::Scope scope(v4);
QV4::Scoped<QV4::QmlContext> qmlContext(scope, QV4::QmlContext::create(v4->rootContext(), ctxtdata, b->scopeObject()));
@@ -150,7 +150,7 @@ void QQmlBinding::update(QQmlPropertyData::WriteFlags flags)
QQmlPropertyData vtd;
getPropertyData(&d, &vtd);
Q_ASSERT(d);
- QQmlProperty p = QQmlPropertyPrivate::restore(targetObject(), *d, &vtd, 0);
+ QQmlProperty p = QQmlPropertyPrivate::restore(targetObject(), *d, &vtd, nullptr);
QQmlAbstractBinding::printBindingLoopError(p);
return;
}
@@ -158,13 +158,13 @@ void QQmlBinding::update(QQmlPropertyData::WriteFlags flags)
DeleteWatcher watcher(this);
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(context()->engine);
- QV4::Scope scope(ep->v4engine());
+ QQmlEngine *engine = context()->engine;
+ QV4::Scope scope(engine->handle());
if (canUseAccessor())
flags.setFlag(QQmlPropertyData::BypassInterceptor);
- QQmlBindingProfiler prof(ep->profiler, function());
+ QQmlBindingProfiler prof(QQmlEnginePrivate::get(engine)->profiler, function());
doUpdate(watcher, flags, scope);
if (!watcher.wasDeleted())
@@ -306,7 +306,7 @@ public:
}
void doUpdate(const DeleteWatcher &watcher,
- QQmlPropertyData::WriteFlags flags, QV4::Scope &) override final
+ QQmlPropertyData::WriteFlags flags, QV4::Scope &scope) override final
{
if (watcher.wasDeleted())
return;
@@ -322,7 +322,12 @@ public:
QQmlPropertyData vpd;
getPropertyData(&pd, &vpd);
Q_ASSERT(pd);
- doStore(result, pd, flags);
+ if (pd->propType() == QMetaType::QString) {
+ doStore(result, pd, flags);
+ } else {
+ QV4::ScopedString value(scope, scope.engine->newString(result));
+ slowWrite(*pd, vpd, value, /*isUndefined*/false, flags);
+ }
}
private:
@@ -346,7 +351,7 @@ Q_NEVER_INLINE bool QQmlBinding::slowWrite(const QQmlPropertyData &core,
bool isUndefined, QQmlPropertyData::WriteFlags flags)
{
QQmlEngine *engine = context()->engine;
- QV8Engine *v8engine = QQmlEnginePrivate::getV8Engine(engine);
+ QV4::ExecutionEngine *v4engine = engine->handle();
int type = valueTypeData.isValid() ? valueTypeData.propType() : core.propType();
@@ -357,13 +362,13 @@ Q_NEVER_INLINE bool QQmlBinding::slowWrite(const QQmlPropertyData &core,
if (isUndefined) {
} else if (core.isQList()) {
- value = QV8Engine::getV4(v8engine)->toVariant(result, qMetaTypeId<QList<QObject *> >());
+ value = v4engine->toVariant(result, qMetaTypeId<QList<QObject *> >());
} else if (result.isNull() && core.isQObject()) {
- value = QVariant::fromValue((QObject *)0);
+ value = QVariant::fromValue((QObject *)nullptr);
} else if (core.propType() == qMetaTypeId<QList<QUrl> >()) {
- value = QQmlPropertyPrivate::resolvedUrlSequence(QV8Engine::getV4(v8engine)->toVariant(result, qMetaTypeId<QList<QUrl> >()), context());
+ value = QQmlPropertyPrivate::resolvedUrlSequence(v4engine->toVariant(result, qMetaTypeId<QList<QUrl> >()), context());
} else if (!isVarProperty && type != qMetaTypeId<QJSValue>()) {
- value = QV8Engine::getV4(v8engine)->toVariant(result, type);
+ value = v4engine->toVariant(result, type);
}
if (hasError()) {
@@ -381,7 +386,7 @@ Q_NEVER_INLINE bool QQmlBinding::slowWrite(const QQmlPropertyData &core,
Q_ASSERT(vmemo);
vmemo->setVMEProperty(core.coreIndex(), result);
} else if (isUndefined && core.isResettable()) {
- void *args[] = { 0 };
+ void *args[] = { nullptr };
QMetaObject::metacall(m_target.data(), QMetaObject::ResetProperty, core.coreIndex(), args);
} else if (isUndefined && type == qMetaTypeId<QVariant>()) {
QQmlPropertyPrivate::writeValueProperty(m_target.data(), core, valueTypeData, QVariant(), context(), flags);
@@ -392,7 +397,7 @@ Q_NEVER_INLINE bool QQmlBinding::slowWrite(const QQmlPropertyData &core,
return false;
}
QQmlPropertyPrivate::writeValueProperty(m_target.data(), core, valueTypeData, QVariant::fromValue(
- QJSValue(QV8Engine::getV4(v8engine), result.asReturnedValue())),
+ QJSValue(v4engine, result.asReturnedValue())),
context(), flags);
} else if (isUndefined) {
const QLatin1String typeName(QMetaType::typeName(type)
@@ -412,8 +417,8 @@ Q_NEVER_INLINE bool QQmlBinding::slowWrite(const QQmlPropertyData &core,
if (watcher.wasDeleted())
return true;
- const char *valueType = 0;
- const char *propertyType = 0;
+ const char *valueType = nullptr;
+ const char *propertyType = nullptr;
const int userType = value.userType();
if (userType == QMetaType::QObjectStar) {
@@ -450,12 +455,13 @@ Q_NEVER_INLINE bool QQmlBinding::slowWrite(const QQmlPropertyData &core,
QVariant QQmlBinding::evaluate()
{
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(context()->engine);
+ QQmlEngine *engine = context()->engine;
+ QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
ep->referenceScarceResources();
bool isUndefined = false;
- QV4::Scope scope(ep->v4engine());
+ QV4::Scope scope(engine->handle());
QV4::ScopedValue result(scope, QQmlJavaScriptExpression::evaluate(&isUndefined));
ep->dereferenceScarceResources();
@@ -524,7 +530,7 @@ void QQmlBinding::setTarget(QObject *object, const QQmlPropertyData &core, const
int aValueTypeIndex;
if (!vme->aliasTarget(coreIndex, &object, &coreIndex, &aValueTypeIndex)) {
- m_target = 0;
+ m_target = nullptr;
m_targetIndex = QQmlPropertyIndex();
return;
}
@@ -533,7 +539,7 @@ void QQmlBinding::setTarget(QObject *object, const QQmlPropertyData &core, const
QQmlData *data = QQmlData::get(object, false);
if (!data || !data->propertyCache) {
- m_target = 0;
+ m_target = nullptr;
m_targetIndex = QQmlPropertyIndex();
return;
}
diff --git a/src/qml/qml/qqmlbinding_p.h b/src/qml/qml/qqmlbinding_p.h
index 8bc9554a42..19ec3f5d4f 100644
--- a/src/qml/qml/qqmlbinding_p.h
+++ b/src/qml/qml/qqmlbinding_p.h
@@ -79,7 +79,7 @@ public:
QObject *obj, QQmlContextData *ctxt, QV4::ExecutionContext *scope);
static QQmlBinding *createTranslationBinding(QV4::CompiledData::CompilationUnit *unit, const QV4::CompiledData::Binding *binding,
QObject *obj, QQmlContextData *ctxt);
- ~QQmlBinding();
+ ~QQmlBinding() override;
void setTarget(const QQmlProperty &);
void setTarget(QObject *, const QQmlPropertyData &, const QQmlPropertyData *valueType);
diff --git a/src/qml/qml/qqmlboundsignal.cpp b/src/qml/qml/qqmlboundsignal.cpp
index 1d7a37fc99..060706ac50 100644
--- a/src/qml/qml/qqmlboundsignal.cpp
+++ b/src/qml/qml/qqmlboundsignal.cpp
@@ -74,8 +74,7 @@ QQmlBoundSignalExpression::QQmlBoundSignalExpression(QObject *target, int index,
{
init(ctxt, scope);
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine());
- QV4::ExecutionEngine *v4 = ep->v4engine();
+ QV4::ExecutionEngine *v4 = engine()->handle();
QString function;
@@ -123,7 +122,7 @@ QQmlBoundSignalExpression::QQmlBoundSignalExpression(QObject *target, int index,
// It's important to call init first, because m_index gets remapped in case of cloned signals.
init(ctxt, scope);
- QV4::ExecutionEngine *engine = QQmlEnginePrivate::getV4Engine(ctxt->engine);
+ QV4::ExecutionEngine *engine = ctxt->engine->handle();
QList<QByteArray> signalParameters = QMetaObjectPrivate::signal(m_target->metaObject(), m_index).parameterNames();
if (!signalParameters.isEmpty()) {
@@ -182,15 +181,17 @@ void QQmlBoundSignalExpression::evaluate(void **a)
if (!expressionFunctionValid())
return;
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine());
- QV4::Scope scope(ep->v4engine());
+ QQmlEngine *qmlengine = engine();
+ QQmlEnginePrivate *ep = QQmlEnginePrivate::get(qmlengine);
+ QV4::ExecutionEngine *v4 = qmlengine->handle();
+ QV4::Scope scope(v4);
ep->referenceScarceResources(); // "hold" scarce resources in memory during evaluation.
QQmlMetaObject::ArgTypeStorage storage;
//TODO: lookup via signal index rather than method index as an optimization
int methodIndex = QMetaObjectPrivate::signal(m_target->metaObject(), m_index).methodIndex();
- int *argsTypes = QQmlMetaObject(m_target).methodParameterTypes(methodIndex, &storage, 0);
+ int *argsTypes = QQmlMetaObject(m_target).methodParameterTypes(methodIndex, &storage, nullptr);
int argCount = argsTypes ? *argsTypes : 0;
QV4::JSCallData jsCall(scope, argCount);
@@ -215,13 +216,13 @@ void QQmlBoundSignalExpression::evaluate(void **a)
if (!*reinterpret_cast<void* const *>(a[ii + 1]))
jsCall->args[ii] = QV4::Primitive::nullValue();
else
- jsCall->args[ii] = QV4::QObjectWrapper::wrap(ep->v4engine(), *reinterpret_cast<QObject* const *>(a[ii + 1]));
+ jsCall->args[ii] = QV4::QObjectWrapper::wrap(v4, *reinterpret_cast<QObject* const *>(a[ii + 1]));
} else {
jsCall->args[ii] = scope.engine->fromVariant(QVariant(type, a[ii + 1]));
}
}
- QQmlJavaScriptExpression::evaluate(jsCall.callData(), 0);
+ QQmlJavaScriptExpression::evaluate(jsCall.callData(), nullptr);
ep->dereferenceScarceResources(); // "release" scarce resources if top-level expression evaluation is complete.
}
@@ -233,8 +234,9 @@ void QQmlBoundSignalExpression::evaluate(const QList<QVariant> &args)
if (!expressionFunctionValid())
return;
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine());
- QV4::Scope scope(ep->v4engine());
+ QQmlEngine *qmlengine = engine();
+ QQmlEnginePrivate *ep = QQmlEnginePrivate::get(qmlengine);
+ QV4::Scope scope(qmlengine->handle());
ep->referenceScarceResources(); // "hold" scarce resources in memory during evaluation.
@@ -243,7 +245,7 @@ void QQmlBoundSignalExpression::evaluate(const QList<QVariant> &args)
jsCall->args[ii] = scope.engine->fromVariant(args[ii]);
}
- QQmlJavaScriptExpression::evaluate(jsCall.callData(), 0);
+ QQmlJavaScriptExpression::evaluate(jsCall.callData(), nullptr);
ep->dereferenceScarceResources(); // "release" scarce resources if top-level expression evaluation is complete.
}
@@ -258,8 +260,8 @@ void QQmlBoundSignalExpression::evaluate(const QList<QVariant> &args)
QQmlBoundSignal::QQmlBoundSignal(QObject *target, int signal, QObject *owner,
QQmlEngine *engine)
: QQmlNotifierEndpoint(QQmlNotifierEndpoint::QQmlBoundSignal),
- m_prevSignal(0), m_nextSignal(0),
- m_enabled(true), m_expression(0)
+ m_prevSignal(nullptr), m_nextSignal(nullptr),
+ m_enabled(true), m_expression(nullptr)
{
addToObject(owner);
@@ -296,8 +298,8 @@ void QQmlBoundSignal::removeFromObject()
if (m_prevSignal) {
*m_prevSignal = m_nextSignal;
if (m_nextSignal) m_nextSignal->m_prevSignal = m_prevSignal;
- m_prevSignal = 0;
- m_nextSignal = 0;
+ m_prevSignal = nullptr;
+ m_nextSignal = nullptr;
}
}
diff --git a/src/qml/qml/qqmlboundsignal_p.h b/src/qml/qml/qqmlboundsignal_p.h
index 3a0b8aed59..01094a11f7 100644
--- a/src/qml/qml/qqmlboundsignal_p.h
+++ b/src/qml/qml/qqmlboundsignal_p.h
@@ -89,14 +89,14 @@ public:
QString expression() const;
QObject *target() const { return m_target; }
- QQmlEngine *engine() const { return context() ? context()->engine : 0; }
+ QQmlEngine *engine() const { return context() ? context()->engine : nullptr; }
private:
- ~QQmlBoundSignalExpression();
+ ~QQmlBoundSignalExpression() override;
void init(QQmlContextData *ctxt, QObject *scope);
- bool expressionFunctionValid() const { return function() != 0; }
+ bool expressionFunctionValid() const { return function() != nullptr; }
int m_index;
QObject *m_target;
diff --git a/src/qml/qml/qqmlboundsignalexpressionpointer_p.h b/src/qml/qml/qqmlboundsignalexpressionpointer_p.h
index de651315f8..eabe6666b4 100644
--- a/src/qml/qml/qqmlboundsignalexpressionpointer_p.h
+++ b/src/qml/qml/qqmlboundsignalexpressionpointer_p.h
@@ -58,7 +58,7 @@ class QQmlBoundSignalExpression;
class Q_QML_PRIVATE_EXPORT QQmlBoundSignalExpressionPointer
{
public:
- inline QQmlBoundSignalExpressionPointer() : o(0) {}
+ inline QQmlBoundSignalExpressionPointer() {}
QQmlBoundSignalExpressionPointer(QQmlBoundSignalExpression *);
QQmlBoundSignalExpressionPointer(const QQmlBoundSignalExpressionPointer &);
~QQmlBoundSignalExpressionPointer();
@@ -73,7 +73,7 @@ public:
QQmlBoundSignalExpressionPointer &take(QQmlBoundSignalExpression *);
private:
- QQmlBoundSignalExpression *o;
+ QQmlBoundSignalExpression *o = nullptr;
};
QT_END_NAMESPACE
diff --git a/src/qml/qml/qqmlcleanup.cpp b/src/qml/qml/qqmlcleanup.cpp
index 708537a303..0d57ef5fe8 100644
--- a/src/qml/qml/qqmlcleanup.cpp
+++ b/src/qml/qml/qqmlcleanup.cpp
@@ -58,7 +58,7 @@ called by QQmlEngine just before it destroys the context.
Create a QQmlCleanup that is not associated with any engine.
*/
QQmlCleanup::QQmlCleanup()
-: prev(0), next(0), engine(0)
+: prev(nullptr), next(nullptr), engine(nullptr)
{
}
@@ -66,7 +66,7 @@ QQmlCleanup::QQmlCleanup()
Create a QQmlCleanup for \a engine
*/
QQmlCleanup::QQmlCleanup(QQmlEngine *engine)
-: prev(0), next(0), engine(0)
+: prev(nullptr), next(nullptr), engine(nullptr)
{
if (!engine)
return;
@@ -109,8 +109,8 @@ QQmlCleanup::~QQmlCleanup()
if (prev) *prev = next;
if (next) next->prev = prev;
- prev = 0;
- next = 0;
+ prev = nullptr;
+ next = nullptr;
}
QT_END_NAMESPACE
diff --git a/src/qml/qml/qqmlcleanup_p.h b/src/qml/qml/qqmlcleanup_p.h
index a1db656477..0e15c28b9d 100644
--- a/src/qml/qml/qqmlcleanup_p.h
+++ b/src/qml/qml/qqmlcleanup_p.h
@@ -64,7 +64,7 @@ public:
QQmlCleanup(QQmlEngine *);
virtual ~QQmlCleanup();
- bool hasEngine() const { return prev != 0; }
+ bool hasEngine() const { return prev != nullptr; }
void addToEngine(QQmlEngine *);
protected:
virtual void clear() = 0;
diff --git a/src/qml/qml/qqmlcomponent.cpp b/src/qml/qml/qqmlcomponent.cpp
index 5a03f2dd93..3174bbecd3 100644
--- a/src/qml/qml/qqmlcomponent.cpp
+++ b/src/qml/qml/qqmlcomponent.cpp
@@ -241,6 +241,9 @@ V4_DEFINE_EXTENSION(QQmlComponentExtension, componentExtension);
\li main.qml
\li \snippet qml/component/main.qml 0
\endtable
+
+ It is important that the lifetime of the creation context outlive any created objects. See
+ \l{Maintaining Dynamically Created Objects} for more details.
*/
/*!
@@ -315,7 +318,7 @@ void QQmlComponentPrivate::typeDataReady(QQmlTypeData *)
Q_ASSERT(typeData);
fromTypeData(typeData);
- typeData = 0;
+ typeData = nullptr;
progress = 1.0;
emit q->statusChanged(q->status());
@@ -349,7 +352,7 @@ void QQmlComponentPrivate::clear()
if (typeData) {
typeData->unregisterCallback(this);
typeData->release();
- typeData = 0;
+ typeData = nullptr;
}
compilationUnit = nullptr;
@@ -497,8 +500,7 @@ QQmlComponent::QQmlComponent(QQmlEngine *engine, QObject *parent)
Create a QQmlComponent from the given \a url and give it the
specified \a parent and \a engine.
- Ensure that the URL provided is full and correct, in particular, use
- \l QUrl::fromLocalFile() when loading a file from the local filesystem.
+ \include qqmlcomponent.qdoc url-note
\sa loadUrl()
*/
@@ -512,8 +514,7 @@ QQmlComponent::QQmlComponent(QQmlEngine *engine, const QUrl &url, QObject *paren
specified \a parent and \a engine. If \a mode is \l Asynchronous,
the component will be loaded and compiled asynchronously.
- Ensure that the URL provided is full and correct, in particular, use
- \l QUrl::fromLocalFile() when loading a file from the local filesystem.
+ \include qqmlcomponent.qdoc url-note
\sa loadUrl()
*/
@@ -549,7 +550,7 @@ QQmlComponent::QQmlComponent(QQmlEngine *engine, const QString &fileName,
: QQmlComponent(engine, parent)
{
Q_D(QQmlComponent);
- const QUrl url = QDir::isAbsolutePath(fileName) ? QUrl::fromLocalFile(fileName) : d->engine->baseUrl().resolved(QUrl(fileName));
+ const QUrl url = QDir::isAbsolutePath(fileName) ? QUrl::fromLocalFile(fileName) : QUrl(fileName);
d->loadUrl(url, mode);
}
@@ -562,7 +563,7 @@ QQmlComponent::QQmlComponent(QQmlEngine *engine, QV4::CompiledData::CompilationU
Q_D(QQmlComponent);
d->compilationUnit = compilationUnit;
d->start = start;
- d->url = compilationUnit->url();
+ d->url = compilationUnit->finalUrl();
d->progress = 1.0;
}
@@ -609,8 +610,7 @@ QQmlContext *QQmlComponent::creationContext() const
/*!
Load the QQmlComponent from the provided \a url.
- Ensure that the URL provided is full and correct, in particular, use
- \l QUrl::fromLocalFile() when loading a file from the local filesystem.
+ \include qqmlcomponent.qdoc url-note
*/
void QQmlComponent::loadUrl(const QUrl &url)
{
@@ -622,8 +622,7 @@ void QQmlComponent::loadUrl(const QUrl &url)
Load the QQmlComponent from the provided \a url.
If \a mode is \l Asynchronous, the component will be loaded and compiled asynchronously.
- Ensure that the URL provided is full and correct, in particular, use
- \l QUrl::fromLocalFile() when loading a file from the local filesystem.
+ \include qqmlcomponent.qdoc url-note
*/
void QQmlComponent::loadUrl(const QUrl &url, QQmlComponent::CompilationMode mode)
{
@@ -636,11 +635,21 @@ void QQmlComponentPrivate::loadUrl(const QUrl &newUrl, QQmlComponent::Compilatio
Q_Q(QQmlComponent);
clear();
- if ((newUrl.isRelative() && !newUrl.isEmpty())
- || newUrl.scheme() == QLatin1String("file")) // Workaround QTBUG-11929
- url = engine->baseUrl().resolved(newUrl);
- else
+ if (newUrl.isRelative()) {
+ // The new URL is a relative URL like QUrl("main.qml").
+ url = engine->baseUrl().resolved(QUrl(newUrl.toString()));
+ } else if (engine->baseUrl().isLocalFile() && newUrl.isLocalFile() && !QDir::isAbsolutePath(newUrl.toLocalFile())) {
+ // The new URL is a file on disk but it's a relative path; e.g.:
+ // QUrl::fromLocalFile("main.qml") or QUrl("file:main.qml")
+ // We need to remove the scheme so that it becomes a relative URL with a relative path:
+ QUrl fixedUrl(newUrl);
+ fixedUrl.setScheme(QString());
+ // Then, turn it into an absolute URL with an absolute path by resolving it against the engine's baseUrl().
+ // This is a compatibility hack for QTBUG-58837.
+ url = engine->baseUrl().resolved(fixedUrl);
+ } else {
url = newUrl;
+ }
if (newUrl.isEmpty()) {
QQmlError error;
@@ -814,27 +823,27 @@ QQmlComponentPrivate::beginCreate(QQmlContextData *context)
Q_Q(QQmlComponent);
if (!context) {
qWarning("QQmlComponent: Cannot create a component in a null context");
- return 0;
+ return nullptr;
}
if (!context->isValid()) {
qWarning("QQmlComponent: Cannot create a component in an invalid context");
- return 0;
+ return nullptr;
}
if (context->engine != engine) {
qWarning("QQmlComponent: Must create component in context from the same QQmlEngine");
- return 0;
+ return nullptr;
}
if (state.completePending) {
qWarning("QQmlComponent: Cannot create new component instance before completing the previous");
- return 0;
+ return nullptr;
}
if (!q->isReady()) {
qWarning("QQmlComponent: Component is not ready");
- return 0;
+ return nullptr;
}
// Do not create infinite recursion in object creation
@@ -842,7 +851,7 @@ QQmlComponentPrivate::beginCreate(QQmlContextData *context)
if (++creationDepth.localData() >= maxCreationDepth) {
qWarning("QQmlComponent: Component creation is recursing - aborting");
--creationDepth.localData();
- return 0;
+ return nullptr;
}
Q_ASSERT(creationDepth.localData() >= 1);
depthIncreased = true;
@@ -854,7 +863,7 @@ QQmlComponentPrivate::beginCreate(QQmlContextData *context)
state.completePending = true;
enginePriv->referenceScarceResources();
- QObject *rv = 0;
+ QObject *rv = nullptr;
state.creator.reset(new QQmlObjectCreator(context, compilationUnit, creationContext));
rv = state.creator->create(start);
if (!rv)
@@ -959,7 +968,7 @@ void QQmlComponentPrivate::completeCreate()
}
QQmlComponentAttached::QQmlComponentAttached(QObject *parent)
-: QObject(parent), prev(0), next(0)
+: QObject(parent), prev(nullptr), next(nullptr)
{
}
@@ -967,8 +976,8 @@ QQmlComponentAttached::~QQmlComponentAttached()
{
if (prev) *prev = next;
if (next) next->prev = prev;
- prev = 0;
- next = 0;
+ prev = nullptr;
+ next = nullptr;
}
/*!
@@ -1074,7 +1083,6 @@ void QQmlComponentPrivate::incubateObject(
QQmlComponentPrivate *componentPriv = QQmlComponentPrivate::get(component);
incubatorPriv->compilationUnit = componentPriv->compilationUnit;
- incubatorPriv->compilationUnit->addref();
incubatorPriv->enginePriv = enginePriv;
incubatorPriv->creator.reset(new QQmlObjectCreator(context, componentPriv->compilationUnit, componentPriv->creationContext));
incubatorPriv->subComponentToCreate = componentPriv->start;
@@ -1111,11 +1119,11 @@ struct QmlIncubatorObject : public QV4::Object
V4_OBJECT2(QmlIncubatorObject, Object)
V4_NEEDS_DESTROY
- static ReturnedValue method_get_statusChanged(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_set_statusChanged(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_get_status(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_get_object(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_forceCompletion(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_get_statusChanged(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_set_statusChanged(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_status(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_object(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_forceCompletion(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
void statusChanged(QQmlIncubator::Status);
void setInitialState(QObject *);
@@ -1264,7 +1272,7 @@ void QQmlComponent::createObject(QQmlV4Function *args)
Q_ASSERT(d->engine);
Q_ASSERT(args);
- QObject *parent = 0;
+ QObject *parent = nullptr;
QV4::ExecutionEngine *v4 = args->v4engine();
QV4::Scope scope(v4);
QV4::ScopedValue valuemap(scope, QV4::Primitive::undefinedValue());
@@ -1381,7 +1389,7 @@ void QQmlComponent::incubateObject(QQmlV4Function *args)
QV4::ExecutionEngine *v4 = args->v4engine();
QV4::Scope scope(v4);
- QObject *parent = 0;
+ QObject *parent = nullptr;
QV4::ScopedValue valuemap(scope, QV4::Primitive::undefinedValue());
QQmlIncubator::IncubationMode mode = QQmlIncubator::Asynchronous;
@@ -1436,8 +1444,7 @@ void QQmlComponent::incubateObject(QQmlV4Function *args)
// XXX used by QSGLoader
void QQmlComponentPrivate::initializeObjectWithInitialProperties(QV4::QmlContext *qmlContext, const QV4::Value &valuemap, QObject *toCreate)
{
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
- QV4::ExecutionEngine *v4engine = QV8Engine::getV4(ep->v8engine());
+ QV4::ExecutionEngine *v4engine = engine->handle();
QV4::Scope scope(v4engine);
QV4::ScopedValue object(scope, QV4::QObjectWrapper::wrap(v4engine, toCreate));
@@ -1453,27 +1460,27 @@ QQmlComponentExtension::QQmlComponentExtension(QV4::ExecutionEngine *v4)
QV4::ScopedObject proto(scope, v4->newObject());
proto->defineAccessorProperty(QStringLiteral("onStatusChanged"),
QV4::QmlIncubatorObject::method_get_statusChanged, QV4::QmlIncubatorObject::method_set_statusChanged);
- proto->defineAccessorProperty(QStringLiteral("status"), QV4::QmlIncubatorObject::method_get_status, 0);
- proto->defineAccessorProperty(QStringLiteral("object"), QV4::QmlIncubatorObject::method_get_object, 0);
+ proto->defineAccessorProperty(QStringLiteral("status"), QV4::QmlIncubatorObject::method_get_status, nullptr);
+ proto->defineAccessorProperty(QStringLiteral("object"), QV4::QmlIncubatorObject::method_get_object, nullptr);
proto->defineDefaultProperty(QStringLiteral("forceCompletion"), QV4::QmlIncubatorObject::method_forceCompletion);
incubationProto.set(v4, proto);
}
-QV4::ReturnedValue QV4::QmlIncubatorObject::method_get_object(const BuiltinFunction *b, CallData *callData)
+QV4::ReturnedValue QV4::QmlIncubatorObject::method_get_object(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QmlIncubatorObject> o(scope, callData->thisObject.as<QmlIncubatorObject>());
+ QV4::Scoped<QmlIncubatorObject> o(scope, thisObject->as<QmlIncubatorObject>());
if (!o)
THROW_TYPE_ERROR();
return QV4::QObjectWrapper::wrap(scope.engine, o->d()->incubator->object());
}
-QV4::ReturnedValue QV4::QmlIncubatorObject::method_forceCompletion(const BuiltinFunction *b, CallData *callData)
+QV4::ReturnedValue QV4::QmlIncubatorObject::method_forceCompletion(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QmlIncubatorObject> o(scope, callData->thisObject.as<QmlIncubatorObject>());
+ QV4::Scoped<QmlIncubatorObject> o(scope, thisObject->as<QmlIncubatorObject>());
if (!o)
THROW_TYPE_ERROR();
@@ -1482,34 +1489,34 @@ QV4::ReturnedValue QV4::QmlIncubatorObject::method_forceCompletion(const Builtin
RETURN_UNDEFINED();
}
-QV4::ReturnedValue QV4::QmlIncubatorObject::method_get_status(const BuiltinFunction *b, CallData *callData)
+QV4::ReturnedValue QV4::QmlIncubatorObject::method_get_status(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QmlIncubatorObject> o(scope, callData->thisObject.as<QmlIncubatorObject>());
+ QV4::Scoped<QmlIncubatorObject> o(scope, thisObject->as<QmlIncubatorObject>());
if (!o)
THROW_TYPE_ERROR();
return QV4::Encode(o->d()->incubator->status());
}
-QV4::ReturnedValue QV4::QmlIncubatorObject::method_get_statusChanged(const BuiltinFunction *b, CallData *callData)
+QV4::ReturnedValue QV4::QmlIncubatorObject::method_get_statusChanged(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QmlIncubatorObject> o(scope, callData->thisObject.as<QmlIncubatorObject>());
+ QV4::Scoped<QmlIncubatorObject> o(scope, thisObject->as<QmlIncubatorObject>());
if (!o)
THROW_TYPE_ERROR();
return QV4::Encode(o->d()->statusChanged);
}
-QV4::ReturnedValue QV4::QmlIncubatorObject::method_set_statusChanged(const BuiltinFunction *b, CallData *callData)
+QV4::ReturnedValue QV4::QmlIncubatorObject::method_set_statusChanged(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QmlIncubatorObject> o(scope, callData->thisObject.as<QmlIncubatorObject>());
- if (!o || callData->argc() < 1)
+ QV4::Scoped<QmlIncubatorObject> o(scope, thisObject->as<QmlIncubatorObject>());
+ if (!o || argc < 1)
THROW_TYPE_ERROR();
- o->d()->statusChanged.set(scope.engine, callData->args[0]);
+ o->d()->statusChanged.set(scope.engine, argv[0]);
RETURN_UNDEFINED();
}
diff --git a/src/qml/qml/qqmlcomponent.h b/src/qml/qml/qqmlcomponent.h
index b8cc556e4a..444b3ec46c 100644
--- a/src/qml/qml/qqmlcomponent.h
+++ b/src/qml/qml/qqmlcomponent.h
@@ -83,7 +83,7 @@ public:
QQmlComponent(QQmlEngine *, const QString &fileName, CompilationMode mode, QObject *parent = nullptr);
QQmlComponent(QQmlEngine *, const QUrl &url, QObject *parent = nullptr);
QQmlComponent(QQmlEngine *, const QUrl &url, CompilationMode mode, QObject *parent = nullptr);
- virtual ~QQmlComponent();
+ ~QQmlComponent() override;
enum Status { Null, Ready, Loading, Error };
Q_ENUM(Status)
diff --git a/src/qml/qml/qqmlcomponent_p.h b/src/qml/qml/qqmlcomponent_p.h
index 8a58a1ada0..2a8d36f317 100644
--- a/src/qml/qml/qqmlcomponent_p.h
+++ b/src/qml/qml/qqmlcomponent_p.h
@@ -79,7 +79,7 @@ class Q_QML_PRIVATE_EXPORT QQmlComponentPrivate : public QObjectPrivate, public
public:
QQmlComponentPrivate()
- : typeData(0), progress(0.), start(-1), engine(0), creationContext(0), depthIncreased(false) {}
+ : typeData(nullptr), progress(0.), start(-1), engine(nullptr), creationContext(nullptr), depthIncreased(false) {}
void loadUrl(const QUrl &newUrl, QQmlComponent::CompilationMode mode = QQmlComponent::PreferSynchronous);
diff --git a/src/qml/qml/qqmlcomponentattached_p.h b/src/qml/qml/qqmlcomponentattached_p.h
index 8236aac1af..e3bca18857 100644
--- a/src/qml/qml/qqmlcomponentattached_p.h
+++ b/src/qml/qml/qqmlcomponentattached_p.h
@@ -62,7 +62,7 @@ class Q_QML_PRIVATE_EXPORT QQmlComponentAttached : public QObject
{
Q_OBJECT
public:
- QQmlComponentAttached(QObject *parent = 0);
+ QQmlComponentAttached(QObject *parent = nullptr);
~QQmlComponentAttached();
void add(QQmlComponentAttached **a) {
@@ -72,7 +72,7 @@ public:
void rem() {
if (next) next->prev = prev;
*prev = next;
- next = 0; prev = 0;
+ next = nullptr; prev = nullptr;
}
QQmlComponentAttached **prev;
QQmlComponentAttached *next;
diff --git a/src/qml/qml/qqmlcontext.cpp b/src/qml/qml/qqmlcontext.cpp
index 37cb328b36..6e43bc735f 100644
--- a/src/qml/qml/qqmlcontext.cpp
+++ b/src/qml/qml/qqmlcontext.cpp
@@ -56,7 +56,7 @@
QT_BEGIN_NAMESPACE
QQmlContextPrivate::QQmlContextPrivate()
-: data(0), notifyIndex(-1)
+: data(nullptr), notifyIndex(-1)
{
}
@@ -177,7 +177,7 @@ QQmlContext::QQmlContext(QQmlEngine *engine, QObject *parent)
d->data = new QQmlContextData(this);
++d->data->refCount;
- d->data->setParent(engine?QQmlContextData::get(engine->rootContext()):0);
+ d->data->setParent(engine?QQmlContextData::get(engine->rootContext()):nullptr);
}
/*!
@@ -191,14 +191,14 @@ QQmlContext::QQmlContext(QQmlContext *parentContext, QObject *parent)
d->data = new QQmlContextData(this);
++d->data->refCount;
- d->data->setParent(parentContext?QQmlContextData::get(parentContext):0);
+ d->data->setParent(parentContext?QQmlContextData::get(parentContext):nullptr);
}
/*!
\internal
*/
QQmlContext::QQmlContext(QQmlContextData *data)
-: QObject(*(new QQmlContextPrivate), 0)
+: QObject(*(new QQmlContextPrivate), nullptr)
{
Q_D(QQmlContext);
d->data = data;
@@ -216,7 +216,7 @@ QQmlContext::~QQmlContext()
{
Q_D(QQmlContext);
- d->data->publicContext = 0;
+ d->data->publicContext = nullptr;
if (!--d->data->refCount)
d->data->destroy();
}
@@ -250,7 +250,7 @@ QQmlEngine *QQmlContext::engine() const
QQmlContext *QQmlContext::parentContext() const
{
Q_D(const QQmlContext);
- return d->data->parent?d->data->parent->asQQmlContext():0;
+ return d->data->parent?d->data->parent->asQQmlContext():nullptr;
}
/*!
@@ -306,16 +306,7 @@ void QQmlContext::setContextProperty(const QString &name, const QVariant &value)
return;
}
- if (data->engine) {
- bool ok;
- QObject *o = QQmlEnginePrivate::get(data->engine)->toQObject(value, &ok);
- if (ok) {
- setContextProperty(name, o);
- return;
- }
- }
-
- QV4::IdentifierHash<int> &properties = data->detachedPropertyNames();
+ QV4::IdentifierHash &properties = data->detachedPropertyNames();
int idx = properties.value(name);
if (idx == -1) {
properties.add(name, data->idValueCount + d->propertyValues.count());
@@ -324,7 +315,7 @@ void QQmlContext::setContextProperty(const QString &name, const QVariant &value)
data->refreshExpressions();
} else {
d->propertyValues[idx] = value;
- QMetaObject::activate(this, d->notifyIndex, idx, 0);
+ QMetaObject::activate(this, d->notifyIndex, idx, nullptr);
}
}
@@ -335,37 +326,54 @@ void QQmlContext::setContextProperty(const QString &name, const QVariant &value)
*/
void QQmlContext::setContextProperty(const QString &name, QObject *value)
{
- Q_D(QQmlContext);
- if (d->notifyIndex == -1)
- d->notifyIndex = QMetaObjectPrivate::absoluteSignalCount(&QQmlContext::staticMetaObject);
+ setContextProperty(name, QVariant::fromValue(value));
+}
+
+/*!
+ \since 5.11
+
+ Set a batch of \a properties on this context.
+
+ Setting all properties in one batch avoids unnecessary
+ refreshing expressions, and is therefore recommended
+ instead of calling \l setContextProperty() for each individual property.
+
+ \sa QQmlContext::setContextProperty()
+*/
+void QQmlContext::setContextProperties(const QVector<PropertyPair> &properties)
+{
+ Q_D(const QQmlContext);
QQmlContextData *data = d->data;
- if (data->isInternal) {
- qWarning("QQmlContext: Cannot set property on internal context.");
- return;
- }
+ QQmlJavaScriptExpression *expressions = data->expressions;
+ QQmlContextData *childContexts = data->childContexts;
- if (!isValid()) {
- qWarning("QQmlContext: Cannot set property on invalid context.");
- return;
- }
+ data->expressions = nullptr;
+ data->childContexts = nullptr;
- QV4::IdentifierHash<int> &properties = data->detachedPropertyNames();
- int idx = properties.value(name);
+ for (auto property : properties)
+ setContextProperty(property.name, property.value);
- if (idx == -1) {
- properties.add(name, data->idValueCount + d->propertyValues.count());
- d->propertyValues.append(QVariant::fromValue(value));
+ data->expressions = expressions;
+ data->childContexts = childContexts;
- data->refreshExpressions();
- } else {
- d->propertyValues[idx] = QVariant::fromValue(value);
- QMetaObject::activate(this, d->notifyIndex, idx, 0);
- }
+ data->refreshExpressions();
}
/*!
+ \since 5.11
+
+ \class QQmlContext::PropertyPair
+ \inmodule QtQml
+
+ This struct contains a property name and a property value.
+ It is used as a parameter for the \c setContextProperties function.
+
+ \sa QQmlContext::setContextProperties()
+*/
+
+/*!
Returns the value of the \a name property for this context
as a QVariant.
*/
@@ -377,7 +385,7 @@ QVariant QQmlContext::contextProperty(const QString &name) const
QQmlContextData *data = d->data;
- const QV4::IdentifierHash<int> &properties = data->propertyNames();
+ const QV4::IdentifierHash &properties = data->propertyNames();
if (properties.count())
idx = properties.value(name);
@@ -513,7 +521,7 @@ QObject *QQmlContextPrivate::context_at(QQmlListProperty<QObject> *prop, int ind
int contextProperty = (int)(quintptr)prop->data;
if (d->propertyValues.at(contextProperty).userType() != qMetaTypeId<QList<QObject*> >()) {
- return 0;
+ return nullptr;
} else {
return ((const QList<QObject*> *)d->propertyValues.at(contextProperty).constData())->at(index);
}
@@ -526,12 +534,12 @@ QQmlContextData::QQmlContextData()
}
QQmlContextData::QQmlContextData(QQmlContext *ctxt)
- : engine(0), isInternal(false), isJSContext(false),
+ : engine(nullptr), isInternal(false), isJSContext(false),
isPragmaLibraryContext(false), unresolvedNames(false), hasEmittedDestruction(false), isRootObjectInCreation(false),
- publicContext(ctxt), incubator(0), componentObjectIndex(-1),
- contextObject(0), nextChild(0), prevChild(0),
- expressions(0), contextObjects(0), idValues(0), idValueCount(0),
- componentAttached(0)
+ publicContext(ctxt), incubator(nullptr), componentObjectIndex(-1),
+ contextObject(nullptr), nextChild(nullptr), prevChild(nullptr),
+ expressions(nullptr), contextObjects(nullptr), idValues(nullptr), idValueCount(0),
+ componentAttached(nullptr)
{
}
@@ -548,8 +556,8 @@ void QQmlContextData::emitDestruction()
componentAttached = a->next;
if (componentAttached) componentAttached->prev = &componentAttached;
- a->next = 0;
- a->prev = 0;
+ a->next = nullptr;
+ a->prev = nullptr;
emit a->destruction();
}
@@ -575,12 +583,14 @@ void QQmlContextData::invalidate()
if (prevChild) {
*prevChild = nextChild;
if (nextChild) nextChild->prevChild = prevChild;
- nextChild = 0;
- prevChild = 0;
+ nextChild = nullptr;
+ prevChild = nullptr;
}
- engine = 0;
- parent = 0;
+ importedScripts.clear();
+
+ engine = nullptr;
+ parent = nullptr;
}
void QQmlContextData::clearContext()
@@ -591,20 +601,20 @@ void QQmlContextData::clearContext()
while (expression) {
QQmlJavaScriptExpression *nextExpression = expression->m_nextExpression;
- expression->m_prevExpression = 0;
- expression->m_nextExpression = 0;
+ expression->m_prevExpression = nullptr;
+ expression->m_nextExpression = nullptr;
- expression->setContext(0);
+ expression->setContext(nullptr);
expression = nextExpression;
}
- expressions = 0;
+ expressions = nullptr;
}
void QQmlContextData::destroy()
{
Q_ASSERT(refCount == 0);
- linkedContext = 0;
+ linkedContext = nullptr;
// avoid recursion
++refCount;
@@ -619,26 +629,26 @@ void QQmlContextData::destroy()
QQmlData *co = contextObjects;
contextObjects = contextObjects->nextContextObject;
- co->context = 0;
- co->outerContext = 0;
- co->nextContextObject = 0;
- co->prevContextObject = 0;
+ co->context = nullptr;
+ co->outerContext = nullptr;
+ co->nextContextObject = nullptr;
+ co->prevContextObject = nullptr;
}
Q_ASSERT(refCount == 1);
QQmlGuardedContextData *contextGuard = contextGuards;
while (contextGuard) {
QQmlGuardedContextData *next = contextGuard->m_next;
- contextGuard->m_next = 0;
- contextGuard->m_prev = 0;
- contextGuard->m_contextData = 0;
+ contextGuard->m_next = nullptr;
+ contextGuard->m_prev = nullptr;
+ contextGuard->m_contextData = nullptr;
contextGuard = next;
}
- contextGuards = 0;
+ contextGuards = nullptr;
Q_ASSERT(refCount == 1);
delete [] idValues;
- idValues = 0;
+ idValues = nullptr;
Q_ASSERT(refCount == 1);
if (publicContext) {
@@ -736,7 +746,7 @@ void QQmlContextData::refreshExpressionsRecursive(bool isGlobal)
// *structure* (not values) changes.
void QQmlContextData::refreshExpressions()
{
- bool isGlobal = (parent == 0);
+ bool isGlobal = (parent == nullptr);
// For efficiency, we try and minimize the number of guards we have to create
if (expressions_to_run(this, isGlobal) && childContexts) {
@@ -762,7 +772,7 @@ void QQmlContextData::addObject(QObject *o)
{
QQmlData *data = QQmlData::get(o, true);
- Q_ASSERT(data->context == 0);
+ Q_ASSERT(data->context == nullptr);
data->context = this;
data->outerContext = this;
@@ -782,7 +792,7 @@ void QQmlContextData::setIdProperty(int idx, QObject *obj)
QString QQmlContextData::findObjectId(const QObject *obj) const
{
- const QV4::IdentifierHash<int> &properties = propertyNames();
+ const QV4::IdentifierHash &properties = propertyNames();
if (propertyNameCache.isEmpty())
return QString();
@@ -824,18 +834,18 @@ void QQmlContextData::initFromTypeCompilationUnit(const QQmlRefPointer<QV4::Comp
idValues = new ContextGuard[idValueCount];
}
-const QV4::IdentifierHash<int> &QQmlContextData::propertyNames() const
+const QV4::IdentifierHash &QQmlContextData::propertyNames() const
{
if (propertyNameCache.isEmpty()) {
if (typeCompilationUnit)
propertyNameCache = typeCompilationUnit->namedObjectsPerComponent(componentObjectIndex);
else
- propertyNameCache = QV4::IdentifierHash<int>(QV8Engine::getV4(engine));
+ propertyNameCache = QV4::IdentifierHash(engine->handle());
}
return propertyNameCache;
}
-QV4::IdentifierHash<int> &QQmlContextData::detachedPropertyNames()
+QV4::IdentifierHash &QQmlContextData::detachedPropertyNames()
{
propertyNames();
propertyNameCache.detach();
@@ -845,14 +855,14 @@ QV4::IdentifierHash<int> &QQmlContextData::detachedPropertyNames()
QUrl QQmlContextData::url() const
{
if (typeCompilationUnit)
- return typeCompilationUnit->url();
+ return typeCompilationUnit->finalUrl();
return baseUrl;
}
QString QQmlContextData::urlString() const
{
if (typeCompilationUnit)
- return typeCompilationUnit->fileName();
+ return typeCompilationUnit->finalUrlString();
return baseUrlString;
}
diff --git a/src/qml/qml/qqmlcontext.h b/src/qml/qml/qqmlcontext.h
index b2b95b7573..7ed70c7619 100644
--- a/src/qml/qml/qqmlcontext.h
+++ b/src/qml/qml/qqmlcontext.h
@@ -42,6 +42,8 @@
#include <QtCore/qurl.h>
#include <QtCore/qobject.h>
+#include <QtCore/qlist.h>
+#include <QtCore/qpair.h>
#include <QtQml/qjsvalue.h>
#include <QtCore/qmetatype.h>
#include <QtCore/qvariant.h>
@@ -62,9 +64,11 @@ class Q_QML_EXPORT QQmlContext : public QObject
Q_DECLARE_PRIVATE(QQmlContext)
public:
+ struct PropertyPair { QString name; QVariant value; };
+
QQmlContext(QQmlEngine *parent, QObject *objParent = nullptr);
QQmlContext(QQmlContext *parent, QObject *objParent = nullptr);
- virtual ~QQmlContext();
+ ~QQmlContext() override;
bool isValid() const;
@@ -77,6 +81,7 @@ public:
QVariant contextProperty(const QString &) const;
void setContextProperty(const QString &, QObject *);
void setContextProperty(const QString &, const QVariant &);
+ void setContextProperties(const QVector<PropertyPair> &properties);
// ### Qt 6: no need for a mutable object, this should become a const QObject pointer
QString nameForObject(QObject *) const;
diff --git a/src/qml/qml/qqmlcontext_p.h b/src/qml/qml/qqmlcontext_p.h
index d01820a430..ff36d6c9a8 100644
--- a/src/qml/qml/qqmlcontext_p.h
+++ b/src/qml/qml/qqmlcontext_p.h
@@ -158,9 +158,9 @@ public:
void initFromTypeCompilationUnit(const QQmlRefPointer<QV4::CompiledData::CompilationUnit> &unit, int subComponentIndex);
// flag indicates whether the context owns the cache (after mutation) or not.
- mutable QV4::IdentifierHash<int> propertyNameCache;
- const QV4::IdentifierHash<int> &propertyNames() const;
- QV4::IdentifierHash<int> &detachedPropertyNames();
+ mutable QV4::IdentifierHash propertyNameCache;
+ const QV4::IdentifierHash &propertyNames() const;
+ QV4::IdentifierHash &detachedPropertyNames();
// Context object
QObject *contextObject;
@@ -178,7 +178,7 @@ public:
QQmlRefPointer<QQmlTypeNameCache> imports;
// My children
- QQmlContextData *childContexts = 0;
+ QQmlContextData *childContexts = nullptr;
// My peers in parent's childContexts list
QQmlContextData *nextChild;
@@ -191,7 +191,7 @@ public:
QQmlData *contextObjects;
// Doubly-linked list of context guards (XXX merge with contextObjects)
- QQmlGuardedContextData *contextGuards = 0;
+ QQmlGuardedContextData *contextGuards = nullptr;
// id guards
struct ContextGuard : public QQmlGuard<QObject>
@@ -261,9 +261,9 @@ private:
inline void clear();
- QQmlContextData *m_contextData = 0;
- QQmlGuardedContextData *m_next = 0;
- QQmlGuardedContextData **m_prev = 0;
+ QQmlContextData *m_contextData = nullptr;
+ QQmlGuardedContextData *m_next = nullptr;
+ QQmlGuardedContextData **m_prev = nullptr;
};
@@ -287,14 +287,14 @@ void QQmlGuardedContextData::clear()
if (m_prev) {
*m_prev = m_next;
if (m_next) m_next->m_prev = m_prev;
- m_contextData = 0;
- m_next = 0;
- m_prev = 0;
+ m_contextData = nullptr;
+ m_next = nullptr;
+ m_prev = nullptr;
}
}
QQmlContextDataRef::QQmlContextDataRef()
- : m_contextData(0)
+ : m_contextData(nullptr)
{
}
@@ -338,7 +338,7 @@ void QQmlContextDataRef::clear()
{
if (m_contextData && !--m_contextData->refCount)
m_contextData->destroy();
- m_contextData = 0;
+ m_contextData = nullptr;
}
QQmlContextDataRef &
@@ -356,7 +356,7 @@ QQmlContextDataRef::operator=(const QQmlContextDataRef &other)
}
QQmlContextData::ContextGuard::ContextGuard()
-: context(0)
+: context(nullptr)
{
}
diff --git a/src/qml/qml/qqmlcustomparser.cpp b/src/qml/qml/qqmlcustomparser.cpp
index cc6e75a39c..5cf87f5264 100644
--- a/src/qml/qml/qqmlcustomparser.cpp
+++ b/src/qml/qml/qqmlcustomparser.cpp
@@ -138,7 +138,7 @@ int QQmlCustomParser::evaluateEnum(const QByteArray& script, bool *ok) const
QQmlType type;
if (imports.isT1()) {
- imports.asT1()->resolveType(scope, &type, 0, 0, 0);
+ imports.asT1()->resolveType(scope, &type, nullptr, nullptr, nullptr);
} else {
QQmlTypeNameCache::Result result = imports.asT2()->query(scope);
if (result.isValid())
@@ -178,7 +178,7 @@ const QMetaObject *QQmlCustomParser::resolveType(const QString& name) const
if (!imports.isT1())
return nullptr;
QQmlType qmltype;
- if (!imports.asT1()->resolveType(name, &qmltype, 0, 0, 0))
+ if (!imports.asT1()->resolveType(name, &qmltype, nullptr, nullptr, nullptr))
return nullptr;
return qmltype.metaObject();
}
diff --git a/src/qml/qml/qqmlcustomparser_p.h b/src/qml/qml/qqmlcustomparser_p.h
index 5eb409990d..2a0f805014 100644
--- a/src/qml/qml/qqmlcustomparser_p.h
+++ b/src/qml/qml/qqmlcustomparser_p.h
@@ -74,8 +74,8 @@ public:
};
Q_DECLARE_FLAGS(Flags, Flag)
- QQmlCustomParser() : engine(0), validator(0), m_flags(NoFlag) {}
- QQmlCustomParser(Flags f) : engine(0), validator(0), m_flags(f) {}
+ QQmlCustomParser() : engine(nullptr), validator(nullptr), m_flags(NoFlag) {}
+ QQmlCustomParser(Flags f) : engine(nullptr), validator(nullptr), m_flags(f) {}
virtual ~QQmlCustomParser() {}
void clearErrors();
diff --git a/src/qml/qml/qqmldata_p.h b/src/qml/qml/qqmldata_p.h
index d692feb975..20b96d2c4b 100644
--- a/src/qml/qml/qqmldata_p.h
+++ b/src/qml/qml/qqmldata_p.h
@@ -56,6 +56,7 @@
#include <private/qqmlpropertyindex_p.h>
#include <private/qv4value_p.h>
#include <private/qv4persistent_p.h>
+#include <private/qqmlrefcount_p.h>
#include <qjsengine.h>
#include <qvector.h>
@@ -76,6 +77,7 @@ class QQmlNotifierEndpoint;
namespace QV4 {
namespace CompiledData {
struct CompilationUnit;
+struct Binding;
}
}
@@ -115,6 +117,7 @@ class Q_QML_PRIVATE_EXPORT QQmlData : public QAbstractDeclarativeData
{
public:
QQmlData();
+ ~QQmlData();
static inline void init() {
static bool initialized = false;
@@ -155,18 +158,21 @@ public:
quint32 hasInterceptorMetaObject:1;
quint32 hasVMEMetaObject:1;
quint32 parentFrozen:1;
- quint32 dummy:22;
+ quint32 dummy:6;
// When bindingBitsSize < sizeof(ptr), we store the binding bit flags inside
// bindingBitsValue. When we need more than sizeof(ptr) bits, we allocated
// sufficient space and use bindingBits to point to it.
- int bindingBitsSize;
+ quint32 bindingBitsArraySize : 16;
typedef quintptr BindingBitsType;
+ enum {
+ BitsPerType = sizeof(BindingBitsType) * 8,
+ InlineBindingArraySize = 2
+ };
union {
BindingBitsType *bindingBits;
- BindingBitsType bindingBitsValue;
+ BindingBitsType bindingBitsValue[InlineBindingArraySize];
};
- enum { MaxInlineBits = sizeof(BindingBitsType) * 8 };
struct NotifyList {
quint64 connectionMask;
@@ -189,9 +195,9 @@ public:
void disconnectNotifiers();
// The context that created the C++ object
- QQmlContextData *context = 0;
+ QQmlContextData *context = nullptr;
// The outermost context in which this object lives
- QQmlContextData *outerContext = 0;
+ QQmlContextData *outerContext = nullptr;
QQmlContextDataRef ownContext;
QQmlAbstractBinding *bindings;
@@ -215,13 +221,18 @@ public:
quint32 jsEngineId; // id of the engine that created the jsWrapper
struct DeferredData {
+ DeferredData();
+ ~DeferredData();
unsigned int deferredIdx;
- QV4::CompiledData::CompilationUnit *compilationUnit;//Not always the same as the other compilation unit
+ QMultiHash<int, const QV4::CompiledData::Binding *> bindings;
+ QQmlRefPointer<QV4::CompiledData::CompilationUnit> compilationUnit;//Not always the same as the other compilation unit
QQmlContextData *context;//Could be either context or outerContext
+ Q_DISABLE_COPY(DeferredData);
};
- QV4::CompiledData::CompilationUnit *compilationUnit;
+ QQmlRefPointer<QV4::CompiledData::CompilationUnit> compilationUnit;
QVector<DeferredData *> deferredData;
+ void deferData(int objectIndex, QV4::CompiledData::CompilationUnit *, QQmlContextData *);
void releaseDeferredData();
QV4::WeakValue jsWrapper;
@@ -236,13 +247,13 @@ public:
// to be avoided because QObjectPrivate::currentChildBeingDeleted is in use.
if (priv->isDeletingChildren || priv->wasDeleted) {
Q_ASSERT(!create);
- return 0;
+ return nullptr;
} else if (priv->declarativeData) {
return static_cast<QQmlData *>(priv->declarativeData);
} else if (create) {
return createQQmlData(priv);
} else {
- return 0;
+ return nullptr;
}
}
@@ -253,10 +264,10 @@ public:
return false;
}
- bool hasExtendedData() const { return extendedData != 0; }
+ bool hasExtendedData() const { return extendedData != nullptr; }
QHash<int, QObject *> *attachedProperties() const;
- static inline bool wasDeleted(QObject *);
+ static inline bool wasDeleted(const QObject *);
static void markAsDeleted(QObject *);
static void setQueuedForDeletion(QObject *);
@@ -272,6 +283,9 @@ public:
return createPropertyCache(engine, object);
}
+ Q_ALWAYS_INLINE static uint offsetForBit(int bit) { return static_cast<uint>(bit) / BitsPerType; }
+ Q_ALWAYS_INLINE static BindingBitsType bitFlagForBit(int bit) { return BindingBitsType(1) << (static_cast<uint>(bit) & (BitsPerType - 1)); }
+
private:
// For attachedProperties
mutable QQmlDataExtended *extendedData;
@@ -283,26 +297,26 @@ private:
Q_ALWAYS_INLINE bool hasBitSet(int bit) const
{
- if (bindingBitsSize <= bit)
+ uint offset = offsetForBit(bit);
+ if (bindingBitsArraySize <= offset)
return false;
- if (bindingBitsSize == MaxInlineBits)
- return bindingBitsValue & (BindingBitsType(1) << bit);
- else
- return bindingBits[bit / MaxInlineBits] & (BindingBitsType(1) << (bit % MaxInlineBits));
+ const BindingBitsType *bits = (bindingBitsArraySize == InlineBindingArraySize) ? bindingBitsValue : bindingBits;
+ return bits[offset] & bitFlagForBit(bit);
}
+ Q_DISABLE_COPY(QQmlData);
};
-bool QQmlData::wasDeleted(QObject *object)
+bool QQmlData::wasDeleted(const QObject *object)
{
if (!object)
return true;
- QObjectPrivate *priv = QObjectPrivate::get(object);
+ const QObjectPrivate *priv = QObjectPrivate::get(object);
if (!priv || priv->wasDeleted)
return true;
- QQmlData *ddata = QQmlData::get(object);
+ const QQmlData *ddata = QQmlData::get(object);
return ddata && ddata->isQueuedForDeletion;
}
@@ -311,7 +325,7 @@ QQmlNotifierEndpoint *QQmlData::notify(int index)
Q_ASSERT(index <= 0xFFFF);
if (!notifyList || !(notifyList->connectionMask & (1ULL << quint64(index % 64)))) {
- return 0;
+ return nullptr;
} else if (index < notifyList->notifiesSize) {
return notifyList->notifies[index];
} else if (index <= notifyList->maximumTodoIndex) {
@@ -321,7 +335,7 @@ QQmlNotifierEndpoint *QQmlData::notify(int index)
if (index < notifyList->notifiesSize) {
return notifyList->notifies[index];
} else {
- return 0;
+ return nullptr;
}
}
diff --git a/src/qml/qml/qqmldelayedcallqueue.cpp b/src/qml/qml/qqmldelayedcallqueue.cpp
index df4030e522..5bcf5cd586 100644
--- a/src/qml/qml/qqmldelayedcallqueue.cpp
+++ b/src/qml/qml/qqmldelayedcallqueue.cpp
@@ -89,7 +89,7 @@ void QQmlDelayedCallQueue::DelayedFunctionCall::execute(QV4::ExecutionEngine *en
//
QQmlDelayedCallQueue::QQmlDelayedCallQueue()
- : QObject(0), m_engine(0), m_callbackOutstanding(false)
+ : QObject(nullptr), m_engine(nullptr), m_callbackOutstanding(false)
{
}
@@ -106,18 +106,19 @@ void QQmlDelayedCallQueue::init(QV4::ExecutionEngine* engine)
m_tickedMethod = metaObject.method(methodIndex);
}
-QV4::ReturnedValue QQmlDelayedCallQueue::addUniquelyAndExecuteLater(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQmlDelayedCallQueue::addUniquelyAndExecuteLater(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() == 0)
+ if (argc == 0)
THROW_GENERIC_ERROR("Qt.callLater: no arguments given");
- const QV4::FunctionObject *func = callData->args[0].as<QV4::FunctionObject>();
+ const QV4::FunctionObject *func = argv[0].as<QV4::FunctionObject>();
if (!func)
THROW_GENERIC_ERROR("Qt.callLater: first argument not a function or signal");
QPair<QObject *, int> functionData = QV4::QObjectMethod::extractQtMethod(func);
+ QV4::ReturnedValue arg0 = argc ? argv[0].asReturnedValue() : QV4::Encode::undefined();
QVector<DelayedFunctionCall>::Iterator iter;
if (functionData.second != -1) {
@@ -136,7 +137,7 @@ QV4::ReturnedValue QQmlDelayedCallQueue::addUniquelyAndExecuteLater(const QV4::B
iter = m_delayedFunctionCalls.begin();
while (iter != m_delayedFunctionCalls.end()) {
DelayedFunctionCall& dfc = *iter;
- if (callData->argument(0) == dfc.m_function.value()) {
+ if (arg0 == dfc.m_function.value()) {
break; // Already stored!
}
++iter;
@@ -149,7 +150,7 @@ QV4::ReturnedValue QQmlDelayedCallQueue::addUniquelyAndExecuteLater(const QV4::B
m_delayedFunctionCalls.erase(iter);
m_delayedFunctionCalls.append(dfc);
} else {
- m_delayedFunctionCalls.append(QV4::PersistentValue(m_engine, callData->argument(0)));
+ m_delayedFunctionCalls.append(QV4::PersistentValue(m_engine, arg0));
}
DelayedFunctionCall& dfc = m_delayedFunctionCalls.last();
@@ -165,7 +166,7 @@ QV4::ReturnedValue QQmlDelayedCallQueue::addUniquelyAndExecuteLater(const QV4::B
dfc.m_guarded = true;
}
}
- storeAnyArguments(dfc, callData, 1, m_engine);
+ storeAnyArguments(dfc, argv, argc, 1, m_engine);
if (!m_callbackOutstanding) {
m_tickedMethod.invoke(this, Qt::QueuedConnection);
@@ -174,9 +175,9 @@ QV4::ReturnedValue QQmlDelayedCallQueue::addUniquelyAndExecuteLater(const QV4::B
return QV4::Encode::undefined();
}
-void QQmlDelayedCallQueue::storeAnyArguments(DelayedFunctionCall &dfc, const QV4::CallData *callData, int offset, QV4::ExecutionEngine *engine)
+void QQmlDelayedCallQueue::storeAnyArguments(DelayedFunctionCall &dfc, const QV4::Value *argv, int argc, int offset, QV4::ExecutionEngine *engine)
{
- const int length = callData->argc() - offset;
+ const int length = argc - offset;
if (length == 0) {
dfc.m_args.clear();
return;
@@ -184,8 +185,8 @@ void QQmlDelayedCallQueue::storeAnyArguments(DelayedFunctionCall &dfc, const QV4
QV4::Scope scope(engine);
QV4::ScopedArrayObject array(scope, engine->newArrayObject(length));
uint i = 0;
- for (int j = offset, ej = callData->argc(); j < ej; ++i, ++j)
- array->putIndexed(i, callData->args[j]);
+ for (int j = offset, ej = argc; j < ej; ++i, ++j)
+ array->putIndexed(i, argv[j]);
dfc.m_args.set(engine, array);
}
diff --git a/src/qml/qml/qqmldelayedcallqueue_p.h b/src/qml/qml/qqmldelayedcallqueue_p.h
index 5b3043cfed..7962318561 100644
--- a/src/qml/qml/qqmldelayedcallqueue_p.h
+++ b/src/qml/qml/qqmldelayedcallqueue_p.h
@@ -60,17 +60,16 @@
QT_BEGIN_NAMESPACE
-class QV8Engine;
class QQmlDelayedCallQueue : public QObject
{
Q_OBJECT
public:
QQmlDelayedCallQueue();
- ~QQmlDelayedCallQueue();
+ ~QQmlDelayedCallQueue() override;
void init(QV4::ExecutionEngine *);
- QV4::ReturnedValue addUniquelyAndExecuteLater(const QV4::BuiltinFunction *, QV4::CallData *callData);
+ QV4::ReturnedValue addUniquelyAndExecuteLater(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
public Q_SLOTS:
void ticked();
@@ -90,7 +89,7 @@ private:
bool m_guarded;
};
- void storeAnyArguments(DelayedFunctionCall& dfc, const QV4::CallData *callData, int offset, QV4::ExecutionEngine *engine);
+ void storeAnyArguments(DelayedFunctionCall& dfc, const QV4::Value *argv, int argc, int offset, QV4::ExecutionEngine *engine);
void executeAllExpired_Later();
QV4::ExecutionEngine *m_engine;
diff --git a/src/qml/qml/qqmldirparser_p.h b/src/qml/qml/qqmldirparser_p.h
index 1530b7a6cf..95370398ad 100644
--- a/src/qml/qml/qqmldirparser_p.h
+++ b/src/qml/qml/qqmldirparser_p.h
@@ -91,8 +91,7 @@ public:
struct Component
{
- Component()
- : majorVersion(0), minorVersion(0), internal(false), singleton(false) {}
+ Component() {}
Component(const QString &typeName, const QString &fileName, int majorVersion, int minorVersion)
: typeName(typeName), fileName(fileName), majorVersion(majorVersion), minorVersion(minorVersion),
@@ -100,24 +99,23 @@ public:
QString typeName;
QString fileName;
- int majorVersion;
- int minorVersion;
- bool internal;
- bool singleton;
+ int majorVersion = 0;
+ int minorVersion = 0;
+ bool internal = false;
+ bool singleton = false;
};
struct Script
{
- Script()
- : majorVersion(0), minorVersion(0) {}
+ Script() {}
Script(const QString &nameSpace, const QString &fileName, int majorVersion, int minorVersion)
: nameSpace(nameSpace), fileName(fileName), majorVersion(majorVersion), minorVersion(minorVersion) {}
QString nameSpace;
QString fileName;
- int majorVersion;
- int minorVersion;
+ int majorVersion = 0;
+ int minorVersion = 0;
};
QHash<QString,Component> components() const;
diff --git a/src/qml/qml/qqmlengine.cpp b/src/qml/qml/qqmlengine.cpp
index 9ef47b2c2e..4054d2f0be 100644
--- a/src/qml/qml/qqmlengine.cpp
+++ b/src/qml/qml/qqmlengine.cpp
@@ -110,7 +110,10 @@ Q_DECLARE_METATYPE(QQmlProperty)
QT_BEGIN_NAMESPACE
typedef QQmlData::BindingBitsType BindingBitsType;
-enum { MaxInlineBits = QQmlData::MaxInlineBits };
+enum {
+ BitsPerType = QQmlData::BitsPerType,
+ InlineBindingArraySize = QQmlData::InlineBindingArraySize
+};
void qmlRegisterBaseTypes(const char *uri, int versionMajor, int versionMinor)
{
@@ -666,19 +669,19 @@ the same object as is returned from the Qt.include() call.
// Qt.include() is implemented in qv4include.cpp
QQmlEnginePrivate::QQmlEnginePrivate(QQmlEngine *e)
-: propertyCapture(0), rootContext(0),
+: propertyCapture(nullptr), rootContext(nullptr),
#if QT_CONFIG(qml_debug)
- profiler(0),
+ profiler(nullptr),
#endif
outputWarningsToMsgLog(true),
- cleanup(0), erroredBindings(0), inProgressCreations(0),
- workerScriptEngine(0),
- activeObjectCreator(0),
+ cleanup(nullptr), erroredBindings(nullptr), inProgressCreations(0),
+ workerScriptEngine(nullptr),
+ activeObjectCreator(nullptr),
#if QT_CONFIG(qml_network)
- networkAccessManager(0), networkAccessManagerFactory(0),
+ networkAccessManager(nullptr), networkAccessManagerFactory(nullptr),
#endif
- urlInterceptor(0), scarceResourcesRefCount(0), importDatabase(e), typeLoader(e),
- uniqueId(1), incubatorCount(0), incubationController(0)
+ urlInterceptor(nullptr), scarceResourcesRefCount(0), importDatabase(e), typeLoader(e),
+ uniqueId(1), incubatorCount(0), incubationController(nullptr)
{
}
@@ -691,15 +694,15 @@ QQmlEnginePrivate::~QQmlEnginePrivate()
QQmlCleanup *c = cleanup;
cleanup = c->next;
if (cleanup) cleanup->prev = &cleanup;
- c->next = 0;
- c->prev = 0;
+ c->next = nullptr;
+ c->prev = nullptr;
c->clear();
}
doDeleteInEngineThread();
- if (incubationController) incubationController->d = 0;
- incubationController = 0;
+ if (incubationController) incubationController->d = nullptr;
+ incubationController = nullptr;
QQmlMetaType::freeUnusedTypesAndCaches();
@@ -720,13 +723,16 @@ void QQmlPrivate::qdeclarativeelement_destructor(QObject *o)
{
if (QQmlData *d = QQmlData::get(o)) {
if (d->ownContext) {
- for (QQmlContextData *lc = d->ownContext->linkedContext; lc; lc = lc->linkedContext)
+ for (QQmlContextData *lc = d->ownContext->linkedContext; lc; lc = lc->linkedContext) {
lc->invalidate();
+ if (lc->contextObject == o)
+ lc->contextObject = nullptr;
+ }
d->ownContext->invalidate();
if (d->ownContext->contextObject == o)
d->ownContext->contextObject = nullptr;
- d->ownContext = 0;
- d->context = 0;
+ d->ownContext = nullptr;
+ d->context = nullptr;
}
// Mark this object as in the process of deletion to
@@ -744,14 +750,19 @@ QQmlData::QQmlData()
: ownedByQml1(false), ownMemory(true), indestructible(true), explicitIndestructibleSet(false),
hasTaintedV4Object(false), isQueuedForDeletion(false), rootObjectInCreation(false),
hasInterceptorMetaObject(false), hasVMEMetaObject(false), parentFrozen(false),
- bindingBitsSize(MaxInlineBits), bindingBitsValue(0), notifyList(0),
- bindings(0), signalHandlers(0), nextContextObject(0), prevContextObject(0),
- lineNumber(0), columnNumber(0), jsEngineId(0), compilationUnit(0),
- propertyCache(0), guards(0), extendedData(0)
+ bindingBitsArraySize(InlineBindingArraySize), notifyList(nullptr),
+ bindings(nullptr), signalHandlers(nullptr), nextContextObject(nullptr), prevContextObject(nullptr),
+ lineNumber(0), columnNumber(0), jsEngineId(0),
+ propertyCache(nullptr), guards(nullptr), extendedData(nullptr)
{
+ memset(bindingBitsValue, 0, sizeof(bindingBitsValue));
init();
}
+QQmlData::~QQmlData()
+{
+}
+
void QQmlData::destroyed(QAbstractDeclarativeData *d, QObject *o)
{
QQmlData *ddata = static_cast<QQmlData *>(d);
@@ -815,7 +826,7 @@ void QQmlData::signalEmitted(QAbstractDeclarativeData *, QObject *object, int in
void **args = (void **) malloc((parameterTypes.count() + 1) *sizeof(void *));
types[0] = 0; // return type
- args[0] = 0; // return value
+ args[0] = nullptr; // return value
for (int ii = 0; ii < parameterTypes.count(); ++ii) {
const QByteArray &typeName = parameterTypes.at(ii);
@@ -836,7 +847,7 @@ void QQmlData::signalEmitted(QAbstractDeclarativeData *, QObject *object, int in
args[ii + 1] = QMetaType::create(types[ii + 1], a[ii + 1]);
}
- QMetaCallEvent *ev = new QMetaCallEvent(m.methodIndex(), 0, 0, object, index,
+ QMetaCallEvent *ev = new QMetaCallEvent(m.methodIndex(), 0, nullptr, object, index,
parameterTypes.count() + 1, types, args);
QQmlThreadNotifierProxyObject *mpo = new QQmlThreadNotifierProxyObject;
@@ -897,8 +908,10 @@ void QQmlData::setQueuedForDeletion(QObject *object)
if (ddata->ownContext) {
Q_ASSERT(ddata->ownContext == ddata->context);
ddata->context->emitDestruction();
- ddata->ownContext = 0;
- ddata->context = 0;
+ if (ddata->ownContext->contextObject == object)
+ ddata->ownContext->contextObject = nullptr;
+ ddata->ownContext = nullptr;
+ ddata->context = nullptr;
}
ddata->isQueuedForDeletion = true;
}
@@ -921,6 +934,14 @@ void QQmlData::flushPendingBindingImpl(QQmlPropertyIndex index)
QQmlPropertyData::DontRemoveBinding);
}
+QQmlData::DeferredData::DeferredData()
+{
+}
+
+QQmlData::DeferredData::~DeferredData()
+{
+}
+
bool QQmlEnginePrivate::baseModulesUninitialized = true;
void QQmlEnginePrivate::init()
{
@@ -1041,7 +1062,7 @@ QQmlEngine::~QQmlEngine()
currType.singletonInstanceInfo()->destroy(this);
delete d->rootContext;
- d->rootContext = 0;
+ d->rootContext = nullptr;
}
/*! \fn void QQmlEngine::quit()
@@ -1154,7 +1175,7 @@ void QQmlEnginePrivate::registerFinalizeCallback(QObject *obj, int index)
if (activeObjectCreator) {
activeObjectCreator->finalizeCallbacks()->append(qMakePair(QPointer<QObject>(obj), index));
} else {
- void *args[] = { 0 };
+ void *args[] = { nullptr };
QMetaObject::metacall(obj, QMetaObject::InvokeMetaMethod, index, args);
}
}
@@ -1371,13 +1392,13 @@ void QQmlEngine::retranslate()
QQmlContext *QQmlEngine::contextForObject(const QObject *object)
{
if(!object)
- return 0;
+ return nullptr;
QQmlData *data = QQmlData::get(object);
if (data && data->outerContext)
return data->outerContext->asQQmlContext();
- return 0;
+ return nullptr;
}
/*!
@@ -1525,7 +1546,7 @@ QQmlEngine *qmlEngine(const QObject *obj)
{
QQmlData *data = QQmlData::get(obj, false);
if (!data || !data->context)
- return 0;
+ return nullptr;
return data->context->engine;
}
@@ -1533,7 +1554,7 @@ QObject *qmlAttachedPropertiesObjectById(int id, const QObject *object, bool cre
{
QQmlData *data = QQmlData::get(object, create);
if (!data)
- return 0; // Attached properties are only on objects created by QML, unless explicitly requested (create==true)
+ return nullptr; // Attached properties are only on objects created by QML, unless explicitly requested (create==true)
QObject *rv = data->hasExtendedData()?data->attachedProperties()->value(id):0;
if (rv || !create)
@@ -1542,7 +1563,7 @@ QObject *qmlAttachedPropertiesObjectById(int id, const QObject *object, bool cre
QQmlEnginePrivate *engine = QQmlEnginePrivate::get(data->context);
QQmlAttachedPropertiesFunc pf = QQmlMetaType::attachedPropertiesFuncById(engine, id);
if (!pf)
- return 0;
+ return nullptr;
rv = pf(const_cast<QObject *>(object));
@@ -1556,12 +1577,12 @@ QObject *qmlAttachedPropertiesObject(int *idCache, const QObject *object,
const QMetaObject *attachedMetaObject, bool create)
{
if (*idCache == -1) {
- QQmlEngine *engine = object ? qmlEngine(object) : 0;
- *idCache = QQmlMetaType::attachedPropertiesFuncId(engine ? QQmlEnginePrivate::get(engine) : 0, attachedMetaObject);
+ QQmlEngine *engine = object ? qmlEngine(object) : nullptr;
+ *idCache = QQmlMetaType::attachedPropertiesFuncId(engine ? QQmlEnginePrivate::get(engine) : nullptr, attachedMetaObject);
}
if (*idCache == -1 || !object)
- return 0;
+ return nullptr;
return qmlAttachedPropertiesObjectById(*idCache, object, create);
}
@@ -1621,7 +1642,7 @@ void QQmlData::NotifyList::layout(QQmlNotifierEndpoint *endpoint)
{
// Add a temporary sentinel at beginning of list. This will be overwritten
// when the end point is inserted into the notifies further down.
- endpoint->prev = 0;
+ endpoint->prev = nullptr;
while (endpoint->next) {
Q_ASSERT(reinterpret_cast<QQmlNotifierEndpoint *>(endpoint->next->prev) == endpoint);
@@ -1667,16 +1688,41 @@ void QQmlData::NotifyList::layout()
}
maximumTodoIndex = 0;
- todo = 0;
+ todo = nullptr;
+}
+
+void QQmlData::deferData(int objectIndex, QV4::CompiledData::CompilationUnit *compilationUnit, QQmlContextData *context)
+{
+ QQmlData::DeferredData *deferData = new QQmlData::DeferredData;
+ deferData->deferredIdx = objectIndex;
+ deferData->compilationUnit = compilationUnit;
+ deferData->context = context;
+
+ const QV4::CompiledData::Object *compiledObject = compilationUnit->objectAt(objectIndex);
+ const QV4::CompiledData::BindingPropertyData &propertyData = compilationUnit->bindingPropertyDataPerObject.at(objectIndex);
+
+ const QV4::CompiledData::Binding *binding = compiledObject->bindingTable();
+ for (quint32 i = 0; i < compiledObject->nBindings; ++i, ++binding) {
+ const QQmlPropertyData *property = propertyData.at(i);
+ if (property && binding->flags & QV4::CompiledData::Binding::IsDeferredBinding)
+ deferData->bindings.insert(property->coreIndex(), binding);
+ }
+
+ deferredData.append(deferData);
}
void QQmlData::releaseDeferredData()
{
- for (DeferredData *deferData : qAsConst(deferredData)) {
- deferData->compilationUnit->release();
- delete deferData;
+ auto it = deferredData.begin();
+ while (it != deferredData.end()) {
+ DeferredData *deferData = *it;
+ if (deferData->bindings.isEmpty()) {
+ delete deferData;
+ it = deferredData.erase(it);
+ } else {
+ ++it;
+ }
}
- deferredData.clear();
}
void QQmlData::addNotify(int index, QQmlNotifierEndpoint *endpoint)
@@ -1686,8 +1732,8 @@ void QQmlData::addNotify(int index, QQmlNotifierEndpoint *endpoint)
notifyList->connectionMask = 0;
notifyList->maximumTodoIndex = 0;
notifyList->notifiesSize = 0;
- notifyList->todo = 0;
- notifyList->notifies = 0;
+ notifyList->todo = nullptr;
+ notifyList->notifies = nullptr;
}
Q_ASSERT(!endpoint->isConnected());
@@ -1723,7 +1769,7 @@ void QQmlData::disconnectNotifiers()
}
free(notifyList->notifies);
free(notifyList);
- notifyList = 0;
+ notifyList = nullptr;
}
}
@@ -1748,12 +1794,10 @@ void QQmlData::destroyed(QObject *object)
if (bindings && !bindings->ref.deref())
delete bindings;
- if (compilationUnit) {
- compilationUnit->release();
- compilationUnit = 0;
- }
+ compilationUnit = nullptr;
- releaseDeferredData();
+ qDeleteAll(deferredData);
+ deferredData.clear();
QQmlBoundSignal *signalHandler = signalHandlers;
while (signalHandler) {
@@ -1787,23 +1831,23 @@ void QQmlData::destroyed(QObject *object)
}
QQmlBoundSignal *next = signalHandler->m_nextSignal;
- signalHandler->m_prevSignal = 0;
- signalHandler->m_nextSignal = 0;
+ signalHandler->m_prevSignal = nullptr;
+ signalHandler->m_nextSignal = nullptr;
delete signalHandler;
signalHandler = next;
}
- if (bindingBitsSize > MaxInlineBits)
+ if (bindingBitsArraySize > InlineBindingArraySize)
free(bindingBits);
if (propertyCache)
propertyCache->release();
- ownContext = 0;
+ ownContext = nullptr;
while (guards) {
QQmlGuard<QObject> *guard = static_cast<QQmlGuard<QObject> *>(guards);
- *guard = (QObject *)0;
+ *guard = (QObject *)nullptr;
guard->objectDestroyed(object);
}
@@ -1842,47 +1886,35 @@ void QQmlData::parentChanged(QObject *object, QObject *parent)
static void QQmlData_setBit(QQmlData *data, QObject *obj, int bit)
{
- if (Q_UNLIKELY(data->bindingBitsSize <= bit)) {
+ uint offset = QQmlData::offsetForBit(bit);
+ BindingBitsType *bits = (data->bindingBitsArraySize == InlineBindingArraySize) ? data->bindingBitsValue : data->bindingBits;
+ if (Q_UNLIKELY(data->bindingBitsArraySize <= offset)) {
int props = QQmlMetaObject(obj).propertyCount();
Q_ASSERT(bit < 2 * props);
- int arraySize = (2 * props + MaxInlineBits - 1) / MaxInlineBits;
- Q_ASSERT(arraySize > 1);
-
- // special handling for 32 here is to make sure we wipe the first byte
- // when going from bindingBitsValue to bindingBits, and preserve the old
- // set bits so we can restore them after the allocation
- int oldArraySize = data->bindingBitsSize > MaxInlineBits ? data->bindingBitsSize / MaxInlineBits : 0;
- quintptr oldValue = data->bindingBitsSize == MaxInlineBits ? data->bindingBitsValue : 0;
+ uint arraySize = (2 * static_cast<uint>(props) + BitsPerType - 1) / BitsPerType;
+ Q_ASSERT(arraySize > InlineBindingArraySize && arraySize > data->bindingBitsArraySize);
- data->bindingBits = static_cast<BindingBitsType *>(realloc((data->bindingBitsSize == MaxInlineBits) ? 0 : data->bindingBits,
- arraySize * sizeof(BindingBitsType)));
+ BindingBitsType *newBits = static_cast<BindingBitsType *>(malloc(arraySize*sizeof(BindingBitsType)));
+ memcpy(newBits, bits, data->bindingBitsArraySize * sizeof(BindingBitsType));
+ memset(newBits + data->bindingBitsArraySize, 0, sizeof(BindingBitsType) * (arraySize - data->bindingBitsArraySize));
- memset(data->bindingBits + oldArraySize,
- 0x00,
- sizeof(BindingBitsType) * (arraySize - oldArraySize));
-
- data->bindingBitsSize = arraySize * MaxInlineBits;
-
- // reinstate bindingBitsValue after we dropped it
- if (oldValue) {
- memcpy(data->bindingBits, &oldValue, sizeof(oldValue));
- }
+ if (data->bindingBitsArraySize > InlineBindingArraySize)
+ free(bits);
+ data->bindingBits = newBits;
+ bits = newBits;
+ data->bindingBitsArraySize = arraySize;
}
-
- if (data->bindingBitsSize == MaxInlineBits)
- data->bindingBitsValue |= BindingBitsType(1) << bit;
- else
- data->bindingBits[bit / MaxInlineBits] |= (BindingBitsType(1) << (bit % MaxInlineBits));
+ Q_ASSERT(offset < data->bindingBitsArraySize);
+ bits[offset] |= QQmlData::bitFlagForBit(bit);
}
static void QQmlData_clearBit(QQmlData *data, int bit)
{
- if (data->bindingBitsSize > bit) {
- if (data->bindingBitsSize == MaxInlineBits)
- data->bindingBitsValue &= ~(BindingBitsType(1) << (bit % MaxInlineBits));
- else
- data->bindingBits[bit / MaxInlineBits] &= ~(BindingBitsType(1) << (bit % MaxInlineBits));
+ uint offset = QQmlData::offsetForBit(bit);
+ if (data->bindingBitsArraySize > offset) {
+ BindingBitsType *bits = (data->bindingBitsArraySize == InlineBindingArraySize) ? data->bindingBitsValue : data->bindingBits;
+ bits[offset] &= ~QQmlData::bitFlagForBit(bit);
}
}
@@ -1953,23 +1985,23 @@ static void dumpwarning(const QQmlError &error)
switch (error.messageType()) {
case QtDebugMsg:
QMessageLogger(error.url().toString().toLatin1().constData(),
- error.line(), 0).debug().nospace()
+ error.line(), nullptr).debug().nospace()
<< qPrintable(error.toString());
break;
case QtInfoMsg:
QMessageLogger(error.url().toString().toLatin1().constData(),
- error.line(), 0).info().nospace()
+ error.line(), nullptr).info().nospace()
<< qPrintable(error.toString());
break;
case QtWarningMsg:
case QtFatalMsg: // fatal does not support streaming, and furthermore, is actually fatal. Probably not desirable for QML.
QMessageLogger(error.url().toString().toLatin1().constData(),
- error.line(), 0).warning().nospace()
+ error.line(), nullptr).warning().nospace()
<< qPrintable(error.toString());
break;
case QtCriticalMsg:
QMessageLogger(error.url().toString().toLatin1().constData(),
- error.line(), 0).critical().nospace()
+ error.line(), nullptr).critical().nospace()
<< qPrintable(error.toString());
break;
}
@@ -2048,7 +2080,7 @@ void QQmlEnginePrivate::cleanupScarceResources()
// note that the actual SRD is owned by the JS engine,
// so we cannot delete the SRD; but we can free the
// memory used by the variant in the SRD.
- QV4::ExecutionEngine *engine = QV8Engine::getV4(v8engine());
+ QV4::ExecutionEngine *engine = v4engine();
while (QV4::ExecutionEngine::ScarceResourceData *sr = engine->scarceResources.first()) {
sr->data = QVariant();
engine->scarceResources.remove(sr);
@@ -2306,11 +2338,11 @@ QQmlPropertyCache *QQmlEnginePrivate::propertyCacheForType(int t)
} else {
QQmlType type = QQmlMetaType::qmlType(t);
locker.unlock();
- return type.isValid() ? cache(type.metaObject()) : 0;
+ return type.isValid() ? cache(type.metaObject()) : nullptr;
}
}
-QQmlPropertyCache *QQmlEnginePrivate::rawPropertyCacheForType(int t)
+QQmlPropertyCache *QQmlEnginePrivate::rawPropertyCacheForType(int t, int minorVersion)
{
Locker locker(this);
auto iter = m_compositeTypes.constFind(t);
@@ -2319,7 +2351,11 @@ QQmlPropertyCache *QQmlEnginePrivate::rawPropertyCacheForType(int t)
} else {
QQmlType type = QQmlMetaType::qmlType(t);
locker.unlock();
- return type.isValid() ? cache(type.baseMetaObject()) : 0;
+
+ if (minorVersion >= 0)
+ return type.isValid() ? cache(type, minorVersion) : nullptr;
+ else
+ return type.isValid() ? cache(type.baseMetaObject()) : nullptr;
}
}
diff --git a/src/qml/qml/qqmlengine.h b/src/qml/qml/qqmlengine.h
index 937920e191..73ad2754c8 100644
--- a/src/qml/qml/qqmlengine.h
+++ b/src/qml/qml/qqmlengine.h
@@ -97,7 +97,7 @@ class Q_QML_EXPORT QQmlEngine : public QJSEngine
Q_OBJECT
public:
explicit QQmlEngine(QObject *p = nullptr);
- virtual ~QQmlEngine();
+ ~QQmlEngine() override;
QQmlContext *rootContext() const;
diff --git a/src/qml/qml/qqmlengine_p.h b/src/qml/qml/qqmlengine_p.h
index 791660cac7..d6110c6699 100644
--- a/src/qml/qml/qqmlengine_p.h
+++ b/src/qml/qml/qqmlengine_p.h
@@ -122,7 +122,7 @@ class Q_QML_PRIVATE_EXPORT QQmlEnginePrivate : public QJSEnginePrivate
Q_DECLARE_PUBLIC(QQmlEngine)
public:
QQmlEnginePrivate(QQmlEngine *);
- ~QQmlEnginePrivate();
+ ~QQmlEnginePrivate() override;
void init();
// No mutex protecting baseModulesUninitialized, because use outside QQmlEngine
@@ -150,8 +150,8 @@ public:
QQmlDelayedError *erroredBindings;
int inProgressCreations;
- QV8Engine *v8engine() const { return q_func()->handle(); }
- QV4::ExecutionEngine *v4engine() const { return QV8Engine::getV4(q_func()->handle()); }
+ QV8Engine *v8engine() const { return q_func()->handle()->v8Engine; }
+ QV4::ExecutionEngine *v4engine() const { return q_func()->handle(); }
QQuickWorkerScriptEngine *getWorkerScriptEngine();
QQuickWorkerScriptEngine *workerScriptEngine;
@@ -213,14 +213,14 @@ public:
// These methods may be called from the loader thread
bool isQObject(int);
- QObject *toQObject(const QVariant &, bool *ok = 0) const;
+ QObject *toQObject(const QVariant &, bool *ok = nullptr) const;
QQmlMetaType::TypeCategory typeCategory(int) const;
bool isList(int) const;
int listType(int) const;
QQmlMetaObject rawMetaObjectForType(int) const;
QQmlMetaObject metaObjectForType(int) const;
QQmlPropertyCache *propertyCacheForType(int);
- QQmlPropertyCache *rawPropertyCacheForType(int);
+ QQmlPropertyCache *rawPropertyCacheForType(int, int minorVersion = -1);
void registerInternalCompositeType(QV4::CompiledData::CompilationUnit *compilationUnit);
void unregisterInternalCompositeType(QV4::CompiledData::CompilationUnit *compilationUnit);
@@ -265,7 +265,7 @@ private:
static bool s_designerMode;
// These members is protected by the full QQmlEnginePrivate::mutex mutex
- struct Deletable { Deletable():next(0) {} virtual ~Deletable() {} Deletable *next; };
+ struct Deletable { Deletable():next(nullptr) {} virtual ~Deletable() {} Deletable *next; };
QFieldList<Deletable, &Deletable::next> toDeleteInEngineThread;
void doDeleteInEngineThread();
@@ -295,7 +295,7 @@ inline void QQmlEnginePrivate::dereferenceScarceResources()
// expression must have completed. We can safely release the
// scarce resources.
if (Q_LIKELY(scarceResourcesRefCount == 0)) {
- QV4::ExecutionEngine *engine = QV8Engine::getV4(v8engine());
+ QV4::ExecutionEngine *engine = v4engine();
if (Q_UNLIKELY(!engine->scarceResources.isEmpty())) {
cleanupScarceResources();
}
@@ -341,7 +341,7 @@ void QQmlEnginePrivate::deleteInEngineThread(T *value)
} else {
struct I : public Deletable {
I(T *value) : value(value) {}
- ~I() { delete value; }
+ ~I() override { delete value; }
T *value;
};
I *i = new I(value);
@@ -385,14 +385,14 @@ QV8Engine *QQmlEnginePrivate::getV8Engine(QQmlEngine *e)
{
Q_ASSERT(e);
- return e->d_func()->v8engine();
+ return e->handle()->v8Engine;
}
QV4::ExecutionEngine *QQmlEnginePrivate::getV4Engine(QQmlEngine *e)
{
Q_ASSERT(e);
- return e->d_func()->v4engine();
+ return e->handle();
}
QQmlEnginePrivate *QQmlEnginePrivate::get(QQmlEngine *e)
@@ -411,12 +411,12 @@ const QQmlEnginePrivate *QQmlEnginePrivate::get(const QQmlEngine *e)
QQmlEnginePrivate *QQmlEnginePrivate::get(QQmlContext *c)
{
- return (c && c->engine()) ? QQmlEnginePrivate::get(c->engine()) : 0;
+ return (c && c->engine()) ? QQmlEnginePrivate::get(c->engine()) : nullptr;
}
QQmlEnginePrivate *QQmlEnginePrivate::get(QQmlContextData *c)
{
- return (c && c->engine) ? QQmlEnginePrivate::get(c->engine) : 0;
+ return (c && c->engine) ? QQmlEnginePrivate::get(c->engine) : nullptr;
}
QQmlEngine *QQmlEnginePrivate::get(QQmlEnginePrivate *p)
@@ -428,11 +428,9 @@ QQmlEngine *QQmlEnginePrivate::get(QQmlEnginePrivate *p)
QQmlEnginePrivate *QQmlEnginePrivate::get(QV4::ExecutionEngine *e)
{
- if (!e->v8Engine)
- return 0;
- QQmlEngine *qmlEngine = e->v8Engine->engine();
+ QQmlEngine *qmlEngine = e->qmlEngine();
if (!qmlEngine)
- return 0;
+ return nullptr;
return get(qmlEngine);
}
diff --git a/src/qml/qml/qqmlerror.cpp b/src/qml/qml/qqmlerror.cpp
index 64f008cd32..fc5b186b29 100644
--- a/src/qml/qml/qqmlerror.cpp
+++ b/src/qml/qml/qqmlerror.cpp
@@ -99,7 +99,7 @@ QQmlErrorPrivate::QQmlErrorPrivate()
Creates an empty error object.
*/
QQmlError::QQmlError()
-: d(0)
+: d(nullptr)
{
}
@@ -107,7 +107,7 @@ QQmlError::QQmlError()
Creates a copy of \a other.
*/
QQmlError::QQmlError(const QQmlError &other)
-: d(0)
+: d(nullptr)
{
*this = other;
}
@@ -119,7 +119,7 @@ QQmlError &QQmlError::operator=(const QQmlError &other)
{
if (!other.d) {
delete d;
- d = 0;
+ d = nullptr;
} else {
if (!d)
d = new QQmlErrorPrivate;
@@ -138,7 +138,7 @@ QQmlError &QQmlError::operator=(const QQmlError &other)
*/
QQmlError::~QQmlError()
{
- delete d; d = 0;
+ delete d; d = nullptr;
}
/*!
@@ -146,7 +146,7 @@ QQmlError::~QQmlError()
*/
bool QQmlError::isValid() const
{
- return d != 0;
+ return d != nullptr;
}
/*!
@@ -239,7 +239,7 @@ QObject *QQmlError::object() const
{
if (d)
return d->object;
- return 0;
+ return nullptr;
}
/*!
@@ -268,7 +268,7 @@ QtMsgType QQmlError::messageType() const
\since 5.9
Sets the \a messageType for this message. The message type determines which
- QDebug handlers are responsible for recieving the message.
+ QDebug handlers are responsible for receiving the message.
*/
void QQmlError::setMessageType(QtMsgType messageType)
{
diff --git a/src/qml/qml/qqmlexpression.cpp b/src/qml/qml/qqmlexpression.cpp
index 35dbaccbbe..59cc9bb09f 100644
--- a/src/qml/qml/qqmlexpression.cpp
+++ b/src/qml/qml/qqmlexpression.cpp
@@ -74,7 +74,7 @@ void QQmlExpressionPrivate::init(QQmlContextData *ctxt, const QString &expr, QOb
void QQmlExpressionPrivate::init(QQmlContextData *ctxt, QV4::Function *runtimeFunction, QObject *me)
{
expressionFunctionValid = true;
- QV4::ExecutionEngine *engine = QQmlEnginePrivate::getV4Engine(ctxt->engine);
+ QV4::ExecutionEngine *engine = ctxt->engine->handle();
QV4::Scope scope(engine);
QV4::Scoped<QV4::QmlContext> qmlContext(scope, QV4::QmlContext::create(engine->rootContext(), ctxt, me));
setupFunction(qmlContext, runtimeFunction);
@@ -121,7 +121,7 @@ void QQmlExpressionPrivate::init(QQmlContextData *ctxt, QV4::Function *runtimeFu
null expression object and its value will always be an invalid QVariant.
*/
QQmlExpression::QQmlExpression()
-: QObject(*new QQmlExpressionPrivate, 0)
+: QObject(*new QQmlExpressionPrivate, nullptr)
{
}
@@ -147,7 +147,7 @@ QQmlExpression::QQmlExpression(const QQmlScriptString &script, QQmlContext *ctxt
QQmlContextData *evalCtxtData = QQmlContextData::get(ctxt ? ctxt : scriptPrivate->context);
QObject *scopeObject = scope ? scope : scriptPrivate->scope;
- QV4::Function *runtimeFunction = 0;
+ QV4::Function *runtimeFunction = nullptr;
if (scriptPrivate->context) {
QQmlContextData *ctxtdata = QQmlContextData::get(scriptPrivate->context);
@@ -191,7 +191,7 @@ QQmlExpression::QQmlExpression(QQmlContext *ctxt,
*/
QQmlExpression::QQmlExpression(QQmlContextData *ctxt, QObject *scope,
const QString &expression)
-: QObject(*new QQmlExpressionPrivate, 0)
+: QObject(*new QQmlExpressionPrivate, nullptr)
{
Q_D(QQmlExpression);
d->init(ctxt, expression, scope);
@@ -211,7 +211,7 @@ QQmlExpression::~QQmlExpression()
QQmlEngine *QQmlExpression::engine() const
{
Q_D(const QQmlExpression);
- return d->context()?d->context()->engine:0;
+ return d->context()?d->context()->engine:nullptr;
}
/*!
@@ -222,7 +222,7 @@ QQmlContext *QQmlExpression::context() const
{
Q_D(const QQmlExpression);
QQmlContextData *data = d->context();
- return data?data->asQQmlContext():0;
+ return data?data->asQQmlContext():nullptr;
}
/*!
@@ -266,13 +266,14 @@ QVariant QQmlExpressionPrivate::value(bool *isUndefined)
return QVariant();
}
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(q->engine());
+ QQmlEngine *engine = q->engine();
+ QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
QVariant rv;
ep->referenceScarceResources(); // "hold" scarce resources in memory during evaluation.
{
- QV4::Scope scope(QV8Engine::getV4(ep->v8engine()));
+ QV4::Scope scope(engine->handle());
QV4::ScopedValue result(scope, v4value(isUndefined));
if (!hasError())
rv = scope.engine->toVariant(result, -1);
diff --git a/src/qml/qml/qqmlexpression.h b/src/qml/qml/qqmlexpression.h
index e9c8770e92..0eceeb12e1 100644
--- a/src/qml/qml/qqmlexpression.h
+++ b/src/qml/qml/qqmlexpression.h
@@ -62,7 +62,7 @@ public:
QQmlExpression();
QQmlExpression(QQmlContext *, QObject *, const QString &, QObject * = nullptr);
explicit QQmlExpression(const QQmlScriptString &, QQmlContext * = nullptr, QObject * = nullptr, QObject * = nullptr);
- virtual ~QQmlExpression();
+ ~QQmlExpression() override;
QQmlEngine *engine() const;
QQmlContext *context() const;
diff --git a/src/qml/qml/qqmlexpression_p.h b/src/qml/qml/qqmlexpression_p.h
index a94ca0fc2d..da10b31b2c 100644
--- a/src/qml/qml/qqmlexpression_p.h
+++ b/src/qml/qml/qqmlexpression_p.h
@@ -68,14 +68,14 @@ class QQmlExpressionPrivate : public QObjectPrivate,
Q_DECLARE_PUBLIC(QQmlExpression)
public:
QQmlExpressionPrivate();
- ~QQmlExpressionPrivate();
+ ~QQmlExpressionPrivate() override;
void init(QQmlContextData *, const QString &, QObject *);
void init(QQmlContextData *, QV4::Function *runtimeFunction, QObject *);
- QVariant value(bool *isUndefined = 0);
+ QVariant value(bool *isUndefined = nullptr);
- QV4::ReturnedValue v4value(bool *isUndefined = 0);
+ QV4::ReturnedValue v4value(bool *isUndefined = nullptr);
static inline QQmlExpressionPrivate *get(QQmlExpression *expr);
static inline QQmlExpression *get(QQmlExpressionPrivate *expr);
diff --git a/src/qml/qml/qqmlextensioninterface.h b/src/qml/qml/qqmlextensioninterface.h
index 62b9b26569..c2d20ef0a3 100644
--- a/src/qml/qml/qqmlextensioninterface.h
+++ b/src/qml/qml/qqmlextensioninterface.h
@@ -58,7 +58,7 @@ public:
class Q_QML_EXPORT QQmlExtensionInterface : public QQmlTypesExtensionInterface
{
public:
- virtual ~QQmlExtensionInterface() {}
+ ~QQmlExtensionInterface() override {}
virtual void initializeEngine(QQmlEngine *engine, const char *uri) = 0;
};
diff --git a/src/qml/qml/qqmlextensionplugin.cpp b/src/qml/qml/qqmlextensionplugin.cpp
index b0e6a24616..818ff7c34f 100644
--- a/src/qml/qml/qqmlextensionplugin.cpp
+++ b/src/qml/qml/qqmlextensionplugin.cpp
@@ -121,7 +121,9 @@ void QQmlExtensionPlugin::initializeEngine(QQmlEngine *engine, const char *uri)
\class QQmlExtensionInterface
\internal
\inmodule QtQml
+*/
+/*!
\class QQmlTypesExtensionInterface
\internal
\inmodule QtQml
diff --git a/src/qml/qml/qqmlextensionplugin.h b/src/qml/qml/qqmlextensionplugin.h
index 84a46fb93e..55e9b89dae 100644
--- a/src/qml/qml/qqmlextensionplugin.h
+++ b/src/qml/qml/qqmlextensionplugin.h
@@ -59,7 +59,7 @@ class Q_QML_EXPORT QQmlExtensionPlugin
Q_INTERFACES(QQmlTypesExtensionInterface)
public:
explicit QQmlExtensionPlugin(QObject *parent = nullptr);
- ~QQmlExtensionPlugin();
+ ~QQmlExtensionPlugin() override;
QUrl baseUrl() const;
diff --git a/src/qml/qml/qqmlfile.cpp b/src/qml/qml/qqmlfile.cpp
index 93c3e8e00c..99031e1e74 100644
--- a/src/qml/qml/qqmlfile.cpp
+++ b/src/qml/qml/qqmlfile.cpp
@@ -131,7 +131,7 @@ int QQmlFileNetworkReply::replyFinishedIndex = -1;
int QQmlFileNetworkReply::replyDownloadProgressIndex = -1;
QQmlFileNetworkReply::QQmlFileNetworkReply(QQmlEngine *e, QQmlFilePrivate *p, const QUrl &url)
-: m_engine(e), m_p(p), m_redirectCount(0), m_reply(0)
+: m_engine(e), m_p(p), m_redirectCount(0), m_reply(nullptr)
{
if (finishedIndex == -1) {
finishedIndex = QMetaMethod::fromSignal(&QQmlFileNetworkReply::finished).methodIndex();
@@ -194,9 +194,9 @@ void QQmlFileNetworkReply::networkFinished()
}
m_reply->deleteLater();
- m_reply = 0;
+ m_reply = nullptr;
- m_p->reply = 0;
+ m_p->reply = nullptr;
emit finished();
delete this;
}
@@ -210,7 +210,7 @@ void QQmlFileNetworkReply::networkDownloadProgress(qint64 a, qint64 b)
QQmlFilePrivate::QQmlFilePrivate()
: error(None)
#if QT_CONFIG(qml_network)
-, reply(0)
+, reply(nullptr)
#endif
{
}
@@ -237,7 +237,7 @@ QQmlFile::~QQmlFile()
delete d->reply;
#endif
delete d;
- d = 0;
+ d = nullptr;
}
bool QQmlFile::isNull() const
diff --git a/src/qml/qml/qqmlfileselector.cpp b/src/qml/qml/qqmlfileselector.cpp
index be6216d3ff..8666144096 100644
--- a/src/qml/qml/qqmlfileselector.cpp
+++ b/src/qml/qml/qqmlfileselector.cpp
@@ -115,8 +115,8 @@ QQmlFileSelector::~QQmlFileSelector()
{
Q_D(QQmlFileSelector);
if (d->engine && QQmlFileSelector::get(d->engine) == this) {
- d->engine->setUrlInterceptor(0);
- d->engine = 0;
+ d->engine->setUrlInterceptor(nullptr);
+ d->engine = nullptr;
}
interceptorInstances()->remove(d->myInstance.data());
}
@@ -200,7 +200,7 @@ QQmlFileSelector* QQmlFileSelector::get(QQmlEngine* engine)
QQmlAbstractUrlInterceptor* current = engine->urlInterceptor();
if (current && interceptorInstances()->contains(current))
return interceptorInstances()->value(current);
- return 0;
+ return nullptr;
}
/*!
diff --git a/src/qml/qml/qqmlfileselector.h b/src/qml/qml/qqmlfileselector.h
index 4eaf92c918..9b70e3936d 100644
--- a/src/qml/qml/qqmlfileselector.h
+++ b/src/qml/qml/qqmlfileselector.h
@@ -55,7 +55,7 @@ class Q_QML_EXPORT QQmlFileSelector : public QObject
Q_DECLARE_PRIVATE(QQmlFileSelector)
public:
explicit QQmlFileSelector(QQmlEngine *engine, QObject *parent = nullptr);
- ~QQmlFileSelector();
+ ~QQmlFileSelector() override;
QFileSelector *selector() const Q_DECL_NOTHROW;
void setSelector(QFileSelector *selector);
void setExtraSelectors(QStringList &strings); // TODO Qt6: remove
diff --git a/src/qml/qml/qqmlglobal.cpp b/src/qml/qml/qqmlglobal.cpp
index 6418812bae..1d60c518c4 100644
--- a/src/qml/qml/qqmlglobal.cpp
+++ b/src/qml/qml/qqmlglobal.cpp
@@ -48,7 +48,7 @@
QT_BEGIN_NAMESPACE
QQmlValueTypeProvider::QQmlValueTypeProvider()
- : next(0)
+ : next(nullptr)
{
}
@@ -65,7 +65,7 @@ const QMetaObject *QQmlValueTypeProvider::metaObjectForMetaType(int type)
return mo;
} while ((p = p->next));
- return 0;
+ return nullptr;
}
bool QQmlValueTypeProvider::initValueType(int type, QVariant& dst)
@@ -218,7 +218,7 @@ bool QQmlValueTypeProvider::writeValueType(int type, const void *src, QVariant&
return false;
}
-const QMetaObject *QQmlValueTypeProvider::getMetaObjectForMetaType(int) { return 0; }
+const QMetaObject *QQmlValueTypeProvider::getMetaObjectForMetaType(int) { return nullptr; }
bool QQmlValueTypeProvider::init(int, QVariant&) { return false; }
bool QQmlValueTypeProvider::create(int, int, const void *[], QVariant *) { return false; }
bool QQmlValueTypeProvider::createFromString(int, const QString &, void *, size_t) { return false; }
@@ -232,11 +232,11 @@ bool QQmlValueTypeProvider::read(const QVariant&, void *, int) { return false; }
bool QQmlValueTypeProvider::write(int, const void *, QVariant&) { return false; }
Q_GLOBAL_STATIC(QQmlValueTypeProvider, nullValueTypeProvider)
-static QQmlValueTypeProvider *valueTypeProvider = 0;
+static QQmlValueTypeProvider *valueTypeProvider = nullptr;
static QQmlValueTypeProvider **getValueTypeProvider(void)
{
- if (valueTypeProvider == 0) {
+ if (valueTypeProvider == nullptr) {
valueTypeProvider = nullValueTypeProvider;
}
@@ -294,7 +294,7 @@ QVariant QQmlColorProvider::lighter(const QVariant &, qreal) { return QVariant()
QVariant QQmlColorProvider::darker(const QVariant &, qreal) { return QVariant(); }
QVariant QQmlColorProvider::tint(const QVariant &, const QVariant &) { return QVariant(); }
-static QQmlColorProvider *colorProvider = 0;
+static QQmlColorProvider *colorProvider = nullptr;
Q_QML_PRIVATE_EXPORT QQmlColorProvider *QQml_setColorProvider(QQmlColorProvider *newProvider)
{
@@ -305,7 +305,7 @@ Q_QML_PRIVATE_EXPORT QQmlColorProvider *QQml_setColorProvider(QQmlColorProvider
static QQmlColorProvider **getColorProvider(void)
{
- if (colorProvider == 0) {
+ if (colorProvider == nullptr) {
qWarning() << "Warning: QQml_colorProvider: no color provider has been set!";
static QQmlColorProvider nullColorProvider;
colorProvider = &nullColorProvider;
@@ -345,7 +345,7 @@ QObject *QQmlGuiProvider::styleHints()
QString QQmlGuiProvider::pluginName() const { return QString(); }
-static QQmlGuiProvider *guiProvider = 0;
+static QQmlGuiProvider *guiProvider = nullptr;
Q_QML_PRIVATE_EXPORT QQmlGuiProvider *QQml_setGuiProvider(QQmlGuiProvider *newProvider)
{
@@ -356,7 +356,7 @@ Q_QML_PRIVATE_EXPORT QQmlGuiProvider *QQml_setGuiProvider(QQmlGuiProvider *newPr
static QQmlGuiProvider **getGuiProvider(void)
{
- if (guiProvider == 0) {
+ if (guiProvider == nullptr) {
static QQmlGuiProvider nullGuiProvider; //Still provides an application with no GUI support
guiProvider = &nullGuiProvider;
}
diff --git a/src/qml/qml/qqmlglobal_p.h b/src/qml/qml/qqmlglobal_p.h
index a6c113f5a7..302fdd56c4 100644
--- a/src/qml/qml/qqmlglobal_p.h
+++ b/src/qml/qml/qqmlglobal_p.h
@@ -193,16 +193,6 @@ do { \
return QObjectPrivate::get(sender)->isSignalConnected(signalIdx); \
} while (0)
-struct QQmlGraphics_DerivedObject : public QObject
-{
- void setParent_noEvent(QObject *parent) {
- bool sce = d_ptr->sendChildEvents;
- d_ptr->sendChildEvents = false;
- setParent(parent);
- d_ptr->sendChildEvents = sce;
- }
-};
-
/*!
Returns true if the case of \a fileName is equivalent to the file case of
\a fileName on disk, and false otherwise.
@@ -230,7 +220,11 @@ bool QQml_isFileCaseCorrect(const QString &fileName, int length = -1);
*/
inline void QQml_setParent_noEvent(QObject *object, QObject *parent)
{
- static_cast<QQmlGraphics_DerivedObject *>(object)->setParent_noEvent(parent);
+ QObjectPrivate *d_ptr = QObjectPrivate::get(object);
+ bool sce = d_ptr->sendChildEvents;
+ d_ptr->sendChildEvents = false;
+ object->setParent(parent);
+ d_ptr->sendChildEvents = sce;
}
class Q_QML_PRIVATE_EXPORT QQmlValueTypeProvider
@@ -329,7 +323,7 @@ class Q_QML_PRIVATE_EXPORT QQmlApplication : public QObject
Q_PROPERTY(QString organization READ organization WRITE setOrganization NOTIFY organizationChanged)
Q_PROPERTY(QString domain READ domain WRITE setDomain NOTIFY domainChanged)
public:
- QQmlApplication(QObject* parent=0);
+ QQmlApplication(QObject* parent=nullptr);
QStringList args();
@@ -353,7 +347,7 @@ Q_SIGNALS:
void domainChanged();
protected:
- QQmlApplication(QQmlApplicationPrivate &dd, QObject* parent=0);
+ QQmlApplication(QQmlApplicationPrivate &dd, QObject* parent=nullptr);
private:
Q_DISABLE_COPY(QQmlApplication)
@@ -374,12 +368,12 @@ public:
struct QQmlSourceLocation
{
- QQmlSourceLocation() : line(0), column(0) {}
+ QQmlSourceLocation() {}
QQmlSourceLocation(const QString &sourceFile, quint16 line, quint16 column)
: sourceFile(sourceFile), line(line), column(column) {}
QString sourceFile;
- quint16 line;
- quint16 column;
+ quint16 line = 0;
+ quint16 column = 0;
};
QT_END_NAMESPACE
diff --git a/src/qml/qml/qqmlguard_p.h b/src/qml/qml/qqmlguard_p.h
index 52526276be..808bf4c709 100644
--- a/src/qml/qml/qqmlguard_p.h
+++ b/src/qml/qml/qqmlguard_p.h
@@ -65,9 +65,9 @@ public:
inline QQmlGuardImpl(const QQmlGuardImpl &);
inline ~QQmlGuardImpl();
- QObject *o;
- QQmlGuardImpl *next;
- QQmlGuardImpl **prev;
+ QObject *o = nullptr;
+ QQmlGuardImpl *next = nullptr;
+ QQmlGuardImpl **prev = nullptr;
inline void addGuard();
inline void remGuard();
@@ -113,18 +113,17 @@ Q_DECLARE_METATYPE(QQmlGuard<QObject>)
QT_BEGIN_NAMESPACE
QQmlGuardImpl::QQmlGuardImpl()
-: o(0), next(0), prev(0)
{
}
QQmlGuardImpl::QQmlGuardImpl(QObject *g)
-: o(g), next(0), prev(0)
+: o(g)
{
if (o) addGuard();
}
QQmlGuardImpl::QQmlGuardImpl(const QQmlGuardImpl &g)
-: o(g.o), next(0), prev(0)
+: o(g.o)
{
if (o) addGuard();
}
@@ -132,7 +131,7 @@ QQmlGuardImpl::QQmlGuardImpl(const QQmlGuardImpl &g)
QQmlGuardImpl::~QQmlGuardImpl()
{
if (prev) remGuard();
- o = 0;
+ o = nullptr;
}
void QQmlGuardImpl::addGuard()
@@ -155,8 +154,8 @@ void QQmlGuardImpl::remGuard()
if (next) next->prev = prev;
*prev = next;
- next = 0;
- prev = 0;
+ next = nullptr;
+ prev = nullptr;
}
template<class T>
diff --git a/src/qml/qml/qqmlimport.cpp b/src/qml/qml/qqmlimport.cpp
index 0fbe934bb9..92cecf9f0d 100644
--- a/src/qml/qml/qqmlimport.cpp
+++ b/src/qml/qml/qqmlimport.cpp
@@ -728,7 +728,7 @@ bool QQmlImports::resolveType(QQmlImportNamespace *ns, const QHashedStringRef &t
QQmlType *type_return, int *vmaj, int *vmin,
QQmlType::RegistrationType registrationType) const
{
- return ns->resolveType(d->typeLoader, type, vmaj, vmin, type_return, 0, 0, registrationType);
+ return ns->resolveType(d->typeLoader, type, vmaj, vmin, type_return, nullptr, nullptr, registrationType);
}
bool QQmlImportInstance::resolveType(QQmlTypeLoader *typeLoader, const QHashedStringRef& type,
@@ -803,7 +803,7 @@ bool QQmlImportInstance::resolveType(QQmlTypeLoader *typeLoader, const QHashedSt
int major = vmajor ? *vmajor : -1;
int minor = vminor ? *vminor : -1;
QQmlType returnType = fetchOrCreateTypeForUrl(componentUrl, type, isCompositeSingleton,
- 0, major, minor);
+ nullptr, major, minor);
if (type_return)
*type_return = returnType;
return returnType.isValid();
@@ -831,7 +831,7 @@ bool QQmlImportInstance::resolveType(QQmlTypeLoader *typeLoader, const QHashedSt
*typeRecursionDetected = true;
} else {
QQmlType returnType = fetchOrCreateTypeForUrl(
- qmlUrl, type, registrationType == QQmlType::CompositeSingletonType, 0);
+ qmlUrl, type, registrationType == QQmlType::CompositeSingletonType, nullptr);
if (type_return)
*type_return = returnType;
return returnType.isValid();
@@ -847,7 +847,7 @@ bool QQmlImportsPrivate::resolveType(const QHashedStringRef& type, int *vmajor,
QQmlType::RegistrationType registrationType,
QQmlImport::RecursionRestriction recursionRestriction)
{
- QQmlImportNamespace *s = 0;
+ QQmlImportNamespace *s = nullptr;
int dot = type.indexOf(Dot);
if (dot >= 0) {
QHashedStringRef namespaceName(type.constData(), dot);
@@ -978,10 +978,10 @@ QQmlImportNamespace *QQmlImportsPrivate::findQualifiedNamespace(const QHashedStr
if (prefix == ns->prefix)
return ns;
}
- return 0;
+ return nullptr;
}
-/*!
+/*
Returns the list of possible versioned URI combinations. For example, if \a uri is
QtQml.Models, \a vmaj is 2, and \a vmin is 0, this method returns the following:
[QtQml.Models.2.0, QtQml.2.0.Models, QtQml.Models.2, QtQml.2.Models, QtQml.Models]
@@ -1017,7 +1017,7 @@ static QVector<QStaticPlugin> makePlugins()
return plugins;
}
-/*!
+/*
Get all static plugins that are QML plugins and has a meta data URI that matches with one of
\a versionUris, which is a list of all possible versioned URI combinations - see versionUriList()
above.
@@ -1059,7 +1059,7 @@ static inline QString msgCannotLoadPlugin(const QString &uri, const QString &why
}
#endif
-/*!
+/*
Import an extension defined by a qmldir file.
\a qmldirFilePath is a raw file path.
@@ -1231,10 +1231,12 @@ QString QQmlImportsPrivate::resolvedUri(const QString &dir_arg, QQmlImportDataba
stableRelativePath.replace(Backslash, Slash);
// remove optional versioning in dot notation from uri
- int lastSlash = stableRelativePath.lastIndexOf(Slash);
- if (lastSlash >= 0) {
- int versionDot = stableRelativePath.indexOf(Dot, lastSlash);
- if (versionDot >= 0)
+ int versionDot = stableRelativePath.lastIndexOf(Dot);
+ if (versionDot >= 0) {
+ int nextSlash = stableRelativePath.indexOf(Slash, versionDot);
+ if (nextSlash >= 0)
+ stableRelativePath.remove(versionDot, nextSlash - versionDot);
+ else
stableRelativePath = stableRelativePath.left(versionDot);
}
@@ -1255,7 +1257,7 @@ bool QQmlImportsPrivate::locateQmldir(const QString &uri, int vmaj, int vmin, QQ
// Check cache first
- QQmlImportDatabase::QmldirCache *cacheHead = 0;
+ QQmlImportDatabase::QmldirCache *cacheHead = nullptr;
{
QQmlImportDatabase::QmldirCache **cachePtr = database->qmldirCache.value(uri);
if (cachePtr) {
@@ -1274,10 +1276,19 @@ bool QQmlImportsPrivate::locateQmldir(const QString &uri, int vmaj, int vmin, QQ
QQmlTypeLoader &typeLoader = QQmlEnginePrivate::get(database->engine)->typeLoader;
+ // Interceptor might redirect remote files to local ones.
+ QQmlAbstractUrlInterceptor *interceptor = typeLoader.engine()->urlInterceptor();
+ QStringList localImportPaths = database->importPathList(
+ interceptor ? QQmlImportDatabase::LocalOrRemote : QQmlImportDatabase::Local);
// Search local import paths for a matching version
- QStringList localImportPaths = database->importPathList(QQmlImportDatabase::Local);
const QStringList qmlDirPaths = QQmlImports::completeQmldirPaths(uri, localImportPaths, vmaj, vmin);
- for (const QString &qmldirPath : qmlDirPaths) {
+ for (QString qmldirPath : qmlDirPaths) {
+ if (interceptor) {
+ qmldirPath = QQmlFile::urlToLocalFileOrQrc(
+ interceptor->intercept(QQmlImports::urlFromLocalFileOrQrcOrUrl(qmldirPath),
+ QQmlAbstractUrlInterceptor::QmldirFile));
+ }
+
QString absoluteFilePath = typeLoader.absoluteFilePath(qmldirPath);
if (!absoluteFilePath.isEmpty()) {
QString url;
@@ -1377,7 +1388,7 @@ bool QQmlImportsPrivate::validateQmldirVersion(const QQmlTypeLoaderQmldirContent
QQmlImportNamespace *QQmlImportsPrivate::importNamespace(const QString &prefix) const
{
- QQmlImportNamespace *nameSpace = 0;
+ QQmlImportNamespace *nameSpace = nullptr;
if (prefix.isEmpty()) {
nameSpace = &unqualifiedset;
@@ -1434,7 +1445,7 @@ bool QQmlImportsPrivate::addLibraryImport(const QString& uri, const QString &pre
Q_ASSERT(inserted);
if (!incomplete) {
- const QQmlTypeLoaderQmldirContent *qmldir = 0;
+ const QQmlTypeLoaderQmldirContent *qmldir = nullptr;
if (!qmldirIdentifier.isEmpty()) {
if (!getQmldirContent(qmldirIdentifier, uri, &qmldir, errors))
@@ -1486,6 +1497,10 @@ bool QQmlImportsPrivate::addFileImport(const QString& uri, const QString &prefix
QString qmldirUrl = resolveLocalUrl(base, importUri + (importUri.endsWith(Slash)
? String_qmldir
: Slash_qmldir));
+ if (QQmlAbstractUrlInterceptor *interceptor = typeLoader->engine()->urlInterceptor()) {
+ qmldirUrl = interceptor->intercept(QUrl(qmldirUrl),
+ QQmlAbstractUrlInterceptor::QmldirFile).toString();
+ }
QString qmldirIdentifier;
if (QQmlFile::isLocalFile(qmldirUrl)) {
@@ -1538,7 +1553,7 @@ bool QQmlImportsPrivate::addFileImport(const QString& uri, const QString &prefix
if (isImplicitImport) {
for (QList<QQmlImportInstance *>::const_iterator it = nameSpace->imports.constBegin();
it != nameSpace->imports.constEnd(); ++it) {
- if ((*it)->uri == importUri) {
+ if ((*it)->url == url) {
(*it)->implicitlyImported = true;
return true;
}
@@ -1549,7 +1564,7 @@ bool QQmlImportsPrivate::addFileImport(const QString& uri, const QString &prefix
Q_ASSERT(inserted);
if (!incomplete && !qmldirIdentifier.isEmpty()) {
- const QQmlTypeLoaderQmldirContent *qmldir = 0;
+ const QQmlTypeLoaderQmldirContent *qmldir = nullptr;
if (!getQmldirContent(qmldirIdentifier, importUri, &qmldir, errors))
return false;
@@ -1573,7 +1588,7 @@ bool QQmlImportsPrivate::updateQmldirContent(const QString &uri, const QString &
Q_ASSERT(nameSpace);
if (QQmlImportInstance *import = nameSpace->findImport(uri)) {
- const QQmlTypeLoaderQmldirContent *qmldir = 0;
+ const QQmlTypeLoaderQmldirContent *qmldir = nullptr;
if (!getQmldirContent(qmldirIdentifier, uri, &qmldir, errors))
return false;
@@ -1585,8 +1600,8 @@ bool QQmlImportsPrivate::updateQmldirContent(const QString &uri, const QString &
if (import->setQmldirContent(qmldirUrl, qmldir, nameSpace, errors)) {
if (import->qmlDirComponents.isEmpty() && import->qmlDirScripts.isEmpty()) {
- // The implicit import qmldir can be empty
- if (uri != QLatin1String(".")) {
+ // The implicit import qmldir can be empty, and plugins have no extra versions
+ if (uri != QLatin1String(".") && !QQmlMetaType::isModule(uri, vmaj, vmin)) {
QQmlError error;
if (QQmlMetaType::isAnyModule(uri))
error.setDescription(QQmlImportDatabase::tr("module \"%1\" version %2.%3 is not installed").arg(uri).arg(vmaj).arg(vmin));
@@ -1714,6 +1729,16 @@ bool QQmlImports::isLocal(const QUrl &url)
return !QQmlFile::urlToLocalFileOrQrc(url).isEmpty();
}
+QUrl QQmlImports::urlFromLocalFileOrQrcOrUrl(const QString &file)
+{
+ QUrl url(QLatin1String(file.at(0) == Colon ? "qrc" : "") + file);
+
+ // We don't support single character schemes as those conflict with windows drive letters.
+ if (url.scheme().length() < 2)
+ return QUrl::fromLocalFile(file);
+ return url;
+}
+
void QQmlImports::setDesignerSupportRequired(bool b)
{
designerSupportRequired = b;
@@ -2060,29 +2085,38 @@ bool QQmlImportDatabase::importStaticPlugin(QObject *instance, const QString &ba
// Dynamic plugins are differentiated by their filepath. For static plugins we
// don't have that information so we use their address as key instead.
const QString uniquePluginID = QString::asprintf("%p", instance);
- StringRegisteredPluginMap *plugins = qmlEnginePluginsWithRegisteredTypes();
- QMutexLocker lock(&plugins->mutex);
+ {
+ StringRegisteredPluginMap *plugins = qmlEnginePluginsWithRegisteredTypes();
+ QMutexLocker lock(&plugins->mutex);
- // Plugin types are global across all engines and should only be
- // registered once. But each engine still needs to be initialized.
- bool typesRegistered = plugins->contains(uniquePluginID);
- bool engineInitialized = initializedPlugins.contains(uniquePluginID);
+ // Plugin types are global across all engines and should only be
+ // registered once. But each engine still needs to be initialized.
+ bool typesRegistered = plugins->contains(uniquePluginID);
- if (typesRegistered) {
- Q_ASSERT_X(plugins->value(uniquePluginID).uri == uri,
- "QQmlImportDatabase::importStaticPlugin",
- "Internal error: Static plugin imported previously with different uri");
- } else {
- RegisteredPlugin plugin;
- plugin.uri = uri;
- plugin.loader = 0;
- plugins->insert(uniquePluginID, plugin);
+ if (typesRegistered) {
+ Q_ASSERT_X(plugins->value(uniquePluginID).uri == uri,
+ "QQmlImportDatabase::importStaticPlugin",
+ "Internal error: Static plugin imported previously with different uri");
+ } else {
+ RegisteredPlugin plugin;
+ plugin.uri = uri;
+ plugin.loader = nullptr;
+ plugins->insert(uniquePluginID, plugin);
- if (!registerPluginTypes(instance, basePath, uri, typeNamespace, vmaj, errors))
- return false;
+ if (!registerPluginTypes(instance, basePath, uri, typeNamespace, vmaj, errors))
+ return false;
+ }
+
+ // Release the lock on plugins early as we're done with the global part. Releasing the lock
+ // also allows other QML loader threads to acquire the lock while this thread is blocking
+ // in the initializeEngine call to the gui thread (which in turn may be busy waiting for
+ // other QML loader threads and thus not process the initializeEngine call).
}
- if (!engineInitialized) {
+ // The plugin's per-engine initialization does not need lock protection, as this function is
+ // only called from the engine specific loader thread and importDynamicPlugin as well as
+ // importStaticPlugin are the only places of access.
+ if (!initializedPlugins.contains(uniquePluginID)) {
initializedPlugins.insert(uniquePluginID);
if (QQmlExtensionInterface *eiface = qobject_cast<QQmlExtensionInterface *>(instance)) {
@@ -2104,68 +2138,77 @@ bool QQmlImportDatabase::importDynamicPlugin(const QString &filePath, const QStr
QFileInfo fileInfo(filePath);
const QString absoluteFilePath = fileInfo.absoluteFilePath();
+ QObject *instance = nullptr;
bool engineInitialized = initializedPlugins.contains(absoluteFilePath);
- StringRegisteredPluginMap *plugins = qmlEnginePluginsWithRegisteredTypes();
- QMutexLocker lock(&plugins->mutex);
- bool typesRegistered = plugins->contains(absoluteFilePath);
-
- if (typesRegistered) {
- Q_ASSERT_X(plugins->value(absoluteFilePath).uri == uri,
- "QQmlImportDatabase::importDynamicPlugin",
- "Internal error: Plugin imported previously with different uri");
- }
-
- if (!engineInitialized || !typesRegistered) {
- if (!QQml_isFileCaseCorrect(absoluteFilePath)) {
- if (errors) {
- QQmlError error;
- error.setDescription(tr("File name case mismatch for \"%1\"").arg(absoluteFilePath));
- errors->prepend(error);
- }
- return false;
+ {
+ StringRegisteredPluginMap *plugins = qmlEnginePluginsWithRegisteredTypes();
+ QMutexLocker lock(&plugins->mutex);
+ bool typesRegistered = plugins->contains(absoluteFilePath);
+
+ if (typesRegistered) {
+ Q_ASSERT_X(plugins->value(absoluteFilePath).uri == uri,
+ "QQmlImportDatabase::importDynamicPlugin",
+ "Internal error: Plugin imported previously with different uri");
}
- QPluginLoader* loader = 0;
- if (!typesRegistered) {
- loader = new QPluginLoader(absoluteFilePath);
-
- if (!loader->load()) {
+ if (!engineInitialized || !typesRegistered) {
+ if (!QQml_isFileCaseCorrect(absoluteFilePath)) {
if (errors) {
QQmlError error;
- error.setDescription(loader->errorString());
+ error.setDescription(tr("File name case mismatch for \"%1\"").arg(absoluteFilePath));
errors->prepend(error);
}
- delete loader;
return false;
}
- } else {
- loader = plugins->value(absoluteFilePath).loader;
- }
- QObject *instance = loader->instance();
+ QPluginLoader* loader = nullptr;
+ if (!typesRegistered) {
+ loader = new QPluginLoader(absoluteFilePath);
- if (!typesRegistered) {
- RegisteredPlugin plugin;
- plugin.uri = uri;
- plugin.loader = loader;
- plugins->insert(absoluteFilePath, plugin);
+ if (!loader->load()) {
+ if (errors) {
+ QQmlError error;
+ error.setDescription(loader->errorString());
+ errors->prepend(error);
+ }
+ delete loader;
+ return false;
+ }
+ } else {
+ loader = plugins->value(absoluteFilePath).loader;
+ }
- // Continue with shared code path for dynamic and static plugins:
- if (!registerPluginTypes(instance, fileInfo.absolutePath(), uri, typeNamespace, vmaj, errors))
- return false;
+ instance = loader->instance();
+
+ if (!typesRegistered) {
+ RegisteredPlugin plugin;
+ plugin.uri = uri;
+ plugin.loader = loader;
+ plugins->insert(absoluteFilePath, plugin);
+
+ // Continue with shared code path for dynamic and static plugins:
+ if (!registerPluginTypes(instance, fileInfo.absolutePath(), uri, typeNamespace, vmaj, errors))
+ return false;
+ }
}
- if (!engineInitialized) {
- // things on the engine (eg. adding new global objects) have to be done for every
- // engine.
- // XXX protect against double initialization
- initializedPlugins.insert(absoluteFilePath);
-
- if (QQmlExtensionInterface *eiface = qobject_cast<QQmlExtensionInterface *>(instance)) {
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
- ep->typeLoader.initializeEngine(eiface, uri.toUtf8().constData());
- }
- }
+ // Release the lock on plugins early as we're done with the global part. Releasing the lock
+ // also allows other QML loader threads to acquire the lock while this thread is blocking
+ // in the initializeEngine call to the gui thread (which in turn may be busy waiting for
+ // other QML loader threads and thus not process the initializeEngine call).
+ }
+
+
+ if (!engineInitialized) {
+ // The plugin's per-engine initialization does not need lock protection, as this function is
+ // only called from the engine specific loader thread and importDynamicPlugin as well as
+ // importStaticPlugin are the only places of access.
+ initializedPlugins.insert(absoluteFilePath);
+
+ if (QQmlExtensionInterface *eiface = qobject_cast<QQmlExtensionInterface *>(instance)) {
+ QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
+ ep->typeLoader.initializeEngine(eiface, uri.toUtf8().constData());
+ }
}
return true;
diff --git a/src/qml/qml/qqmlimport_p.h b/src/qml/qml/qqmlimport_p.h
index a7b65c1048..b70bb5253c 100644
--- a/src/qml/qml/qqmlimport_p.h
+++ b/src/qml/qml/qqmlimport_p.h
@@ -92,7 +92,7 @@ struct QQmlImportInstance
bool resolveType(QQmlTypeLoader *typeLoader, const QHashedStringRef &type,
int *vmajor, int *vminor, QQmlType* type_return,
- QString *base = 0, bool *typeRecursionDetected = 0,
+ QString *base = nullptr, bool *typeRecursionDetected = nullptr,
QQmlType::RegistrationType = QQmlType::AnyRegistrationType,
QQmlImport::RecursionRestriction recursionRestriction = QQmlImport::PreventRecursion) const;
};
@@ -100,7 +100,7 @@ struct QQmlImportInstance
class QQmlImportNamespace
{
public:
- QQmlImportNamespace() : nextNamespace(0) {}
+ QQmlImportNamespace() : nextNamespace(nullptr) {}
~QQmlImportNamespace() { qDeleteAll(imports); }
QList<QQmlImportInstance *> imports;
@@ -109,7 +109,7 @@ public:
bool resolveType(QQmlTypeLoader *typeLoader, const QHashedStringRef& type,
int *vmajor, int *vminor, QQmlType* type_return,
- QString *base = 0, QList<QQmlError> *errors = 0,
+ QString *base = nullptr, QList<QQmlError> *errors = nullptr,
QQmlType::RegistrationType registrationType = QQmlType::AnyRegistrationType,
QQmlImport::RecursionRestriction recursionRestriction = QQmlImport::PreventRecursion);
@@ -137,7 +137,7 @@ public:
QQmlType *type_return,
int *version_major, int *version_minor,
QQmlImportNamespace **ns_return,
- QList<QQmlError> *errors = 0,
+ QList<QQmlError> *errors = nullptr,
QQmlType::RegistrationType registrationType = QQmlType::AnyRegistrationType,
QQmlImport::RecursionRestriction recursionRestriction
= QQmlImport::PreventRecursion) const;
@@ -191,6 +191,7 @@ public:
static bool isLocal(const QString &url);
static bool isLocal(const QUrl &url);
+ static QUrl urlFromLocalFileOrQrcOrUrl(const QString &);
static void setDesignerSupportRequired(bool b);
diff --git a/src/qml/qml/qqmlincubator.cpp b/src/qml/qml/qqmlincubator.cpp
index 6d0e4b915a..4546a4423f 100644
--- a/src/qml/qml/qqmlincubator.cpp
+++ b/src/qml/qml/qqmlincubator.cpp
@@ -110,7 +110,7 @@ void QQmlEngine::setIncubationController(QQmlIncubationController *controller)
{
Q_D(QQmlEngine);
if (d->incubationController)
- d->incubationController->d = 0;
+ d->incubationController->d = nullptr;
d->incubationController = controller;
if (controller) controller->d = d;
}
@@ -128,7 +128,7 @@ QQmlIncubationController *QQmlEngine::incubationController() const
QQmlIncubatorPrivate::QQmlIncubatorPrivate(QQmlIncubator *q, QQmlIncubator::IncubationMode m)
: q(q), status(QQmlIncubator::Null), mode(m), isAsynchronous(false), progress(Execute),
- result(0), enginePriv(0), waitingOnMe(0)
+ result(nullptr), enginePriv(nullptr), waitingOnMe(nullptr)
{
}
@@ -147,16 +147,16 @@ void QQmlIncubatorPrivate::clear()
if (controller)
controller->incubatingObjectCountChanged(enginePriv->incubatorCount);
}
- enginePriv = 0;
+ enginePriv = nullptr;
if (!rootContext.isNull()) {
- rootContext->incubator = 0;
- rootContext = 0;
+ rootContext->incubator = nullptr;
+ rootContext = nullptr;
}
if (nextWaitingFor.isInList()) {
Q_ASSERT(waitingOnMe);
nextWaitingFor.remove();
- waitingOnMe = 0;
+ waitingOnMe = nullptr;
}
// if we're waiting on any incubators then they should be cleared too.
@@ -171,7 +171,7 @@ void QQmlIncubatorPrivate::clear()
vmeGuard.clear();
if (creator && guardOk)
creator->clear();
- creator.reset(0);
+ creator.reset(nullptr);
}
/*!
@@ -218,15 +218,15 @@ than a static amount like 5 milliseconds - while not disturbing the application.
Create a new incubation controller.
*/
QQmlIncubationController::QQmlIncubationController()
-: d(0)
+: d(nullptr)
{
}
/*! \internal */
QQmlIncubationController::~QQmlIncubationController()
{
- if (d) QQmlEnginePrivate::get(d)->setIncubationController(0);
- d = 0;
+ if (d) QQmlEnginePrivate::get(d)->setIncubationController(nullptr);
+ d = nullptr;
}
/*!
@@ -272,7 +272,7 @@ void QQmlIncubatorPrivate::incubate(QQmlInstantiationInterrupt &i)
if (!compilationUnit)
return;
- QML_MEMORY_SCOPE_URL(compilationUnit->url());
+ QML_MEMORY_SCOPE_URL(compilationUnit->finalUrl());
QExplicitlySharedDataPointer<QQmlIncubatorPrivate> protectThis(this);
@@ -294,8 +294,8 @@ void QQmlIncubatorPrivate::incubate(QQmlInstantiationInterrupt &i)
if (progress == QQmlIncubatorPrivate::Execute) {
enginePriv->referenceScarceResources();
- QObject *tresult = 0;
- tresult = creator->create(subComponentToCreate, /*parent*/0, &i);
+ QObject *tresult = nullptr;
+ tresult = creator->create(subComponentToCreate, /*parent*/nullptr, &i);
if (!tresult)
errors = creator->errors;
enginePriv->dereferenceScarceResources();
@@ -304,7 +304,7 @@ void QQmlIncubatorPrivate::incubate(QQmlInstantiationInterrupt &i)
return;
result = tresult;
- if (errors.isEmpty() && result == 0)
+ if (errors.isEmpty() && result == nullptr)
goto finishIncubate;
if (result) {
@@ -340,7 +340,7 @@ void QQmlIncubatorPrivate::incubate(QQmlInstantiationInterrupt &i)
if (watcher.hasRecursed())
return;
- QQmlContextData *ctxt = 0;
+ QQmlContextData *ctxt = nullptr;
ctxt = creator->finalize(i);
if (ctxt) {
rootContext = ctxt;
@@ -377,23 +377,6 @@ finishIncubate:
}
}
-void QQmlIncubatorPrivate::cancel(QObject *object, QQmlContext *context)
-{
- if (!context)
- context = qmlContext(object);
- if (!context)
- return;
-
- QQmlContextData *data = QQmlContextData::get(context);
- QQmlIncubatorPrivate *p = data->incubator;
- if (!p)
- return;
-
- p->vmeGuard.unguard(object);
- if (!p->creator.isNull())
- p->creator->cancel(object);
-}
-
/*!
Incubate objects for \a msecs, or until there are no more objects to incubate.
*/
@@ -523,12 +506,12 @@ QQmlIncubator::QQmlIncubator(IncubationMode mode)
/*! \internal */
QQmlIncubator::~QQmlIncubator()
{
- d->q = 0;
+ d->q = nullptr;
if (!d->ref.deref()) {
delete d;
}
- d = 0;
+ d = nullptr;
}
/*!
@@ -574,18 +557,18 @@ void QQmlIncubator::clear()
if (s == Loading) {
Q_ASSERT(d->compilationUnit);
if (d->result) d->result->deleteLater();
- d->result = 0;
+ d->result = nullptr;
}
d->clear();
Q_ASSERT(d->compilationUnit.isNull());
- Q_ASSERT(d->waitingOnMe.data() == 0);
+ Q_ASSERT(d->waitingOnMe.data() == nullptr);
Q_ASSERT(d->waitingFor.isEmpty());
d->errors.clear();
d->progress = QQmlIncubatorPrivate::Execute;
- d->result = 0;
+ d->result = nullptr;
if (s == Loading) {
Q_ASSERT(enginePriv);
@@ -674,7 +657,7 @@ Return the incubated object if the status is Ready, otherwise 0.
QObject *QQmlIncubator::object() const
{
if (status() != Ready)
- return 0;
+ return nullptr;
else
return d->result;
}
diff --git a/src/qml/qml/qqmlincubator_p.h b/src/qml/qml/qqmlincubator_p.h
index 758e0a29f6..676ba1a29a 100644
--- a/src/qml/qml/qqmlincubator_p.h
+++ b/src/qml/qml/qqmlincubator_p.h
@@ -102,9 +102,6 @@ public:
void forceCompletion(QQmlInstantiationInterrupt &i);
void incubate(QQmlInstantiationInterrupt &i);
-
- // used by Qt Quick Controls 2
- Q_QML_PRIVATE_EXPORT static void cancel(QObject *object, QQmlContext *context = 0);
};
QT_END_NAMESPACE
diff --git a/src/qml/qml/qqmlinfo.cpp b/src/qml/qml/qqmlinfo.cpp
index dae15e2eca..c8f5ba506f 100644
--- a/src/qml/qml/qqmlinfo.cpp
+++ b/src/qml/qml/qqmlinfo.cpp
@@ -182,7 +182,7 @@ QQmlInfo::~QQmlInfo()
if (0 == --d->ref) {
QList<QQmlError> errors = d->errors;
- QQmlEngine *engine = 0;
+ QQmlEngine *engine = nullptr;
if (!d->buffer.isEmpty()) {
QQmlError error;
diff --git a/src/qml/qml/qqmljavascriptexpression.cpp b/src/qml/qml/qqmljavascriptexpression.cpp
index 006611e089..74148e3ca4 100644
--- a/src/qml/qml/qqmljavascriptexpression.cpp
+++ b/src/qml/qml/qqmljavascriptexpression.cpp
@@ -93,12 +93,12 @@ void QQmlDelayedError::catchJavaScriptException(QV4::ExecutionEngine *engine)
QQmlJavaScriptExpression::QQmlJavaScriptExpression()
- : m_error(0),
- m_context(0),
- m_prevExpression(0),
- m_nextExpression(0),
- m_v4Function(0),
- m_sourceLocation(0)
+ : m_error(nullptr),
+ m_context(nullptr),
+ m_prevExpression(nullptr),
+ m_nextExpression(nullptr),
+ m_v4Function(nullptr),
+ m_sourceLocation(nullptr)
{
}
@@ -114,7 +114,7 @@ QQmlJavaScriptExpression::~QQmlJavaScriptExpression()
clearPermanentGuards();
clearError();
if (m_scopeObject.isT2()) // notify DeleteWatcher of our deletion.
- m_scopeObject.asT2()->_s = 0;
+ m_scopeObject.asT2()->_s = nullptr;
delete m_sourceLocation;
}
@@ -157,8 +157,8 @@ void QQmlJavaScriptExpression::setContext(QQmlContextData *context)
*m_prevExpression = m_nextExpression;
if (m_nextExpression)
m_nextExpression->m_prevExpression = m_prevExpression;
- m_prevExpression = 0;
- m_nextExpression = 0;
+ m_prevExpression = nullptr;
+ m_nextExpression = nullptr;
}
m_context = context;
@@ -183,7 +183,7 @@ void QQmlJavaScriptExpression::refresh()
QV4::ReturnedValue QQmlJavaScriptExpression::evaluate(bool *isUndefined)
{
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(m_context->engine);
+ QV4::ExecutionEngine *v4 = m_context->engine->handle();
QV4::Scope scope(v4);
QV4::JSCallData jsCall(scope);
@@ -211,13 +211,13 @@ QV4::ReturnedValue QQmlJavaScriptExpression::evaluate(QV4::CallData *callData, b
QQmlPropertyCapture capture(m_context->engine, this, &watcher);
QQmlPropertyCapture *lastPropertyCapture = ep->propertyCapture;
- ep->propertyCapture = notifyOnValueChanged() ? &capture : 0;
+ ep->propertyCapture = notifyOnValueChanged() ? &capture : nullptr;
if (notifyOnValueChanged())
capture.guards.copyAndClearPrepend(activeGuards);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(ep->v8engine());
+ QV4::ExecutionEngine *v4 = m_context->engine->handle();
callData->thisObject = v4->globalObject;
if (scopeObject()) {
QV4::ReturnedValue scope = QV4::QObjectWrapper::wrap(v4, scopeObject());
@@ -253,7 +253,7 @@ QV4::ReturnedValue QQmlJavaScriptExpression::evaluate(QV4::CallData *callData, b
for (int ii = 0; ii < capture.errorString->count(); ++ii)
qWarning("%s", qPrintable(capture.errorString->at(ii)));
delete capture.errorString;
- capture.errorString = 0;
+ capture.errorString = nullptr;
}
while (QQmlJavaScriptExpressionGuard *g = capture.guards.takeFirst())
@@ -274,7 +274,7 @@ void QQmlPropertyCapture::captureProperty(QQmlNotifier *n, Duration duration)
while (!guards.isEmpty() && !guards.first()->isConnected(n))
guards.takeFirst()->Delete();
- QQmlJavaScriptExpressionGuard *g = 0;
+ QQmlJavaScriptExpressionGuard *g = nullptr;
if (!guards.isEmpty()) {
g = guards.takeFirst();
g->cancelNotify();
@@ -323,7 +323,7 @@ void QQmlPropertyCapture::captureProperty(QObject *o, int c, int n, Duration dur
while (!guards.isEmpty() && !guards.first()->isConnected(o, n))
guards.takeFirst()->Delete();
- QQmlJavaScriptExpressionGuard *g = 0;
+ QQmlJavaScriptExpressionGuard *g = nullptr;
if (!guards.isEmpty()) {
g = guards.takeFirst();
g->cancelNotify();
@@ -414,7 +414,7 @@ QQmlJavaScriptExpression::evalFunction(QQmlContextData *ctxt, QObject *scopeObje
QQmlEngine *engine = ctxt->engine;
QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(ep->v8engine());
+ QV4::ExecutionEngine *v4 = engine->handle();
QV4::Scope scope(v4);
QV4::Scoped<QV4::QmlContext> qmlContext(scope, QV4::QmlContext::create(v4->rootContext(), ctxt, scopeObject));
@@ -444,7 +444,7 @@ void QQmlJavaScriptExpression::createQmlBinding(QQmlContextData *ctxt, QObject *
QQmlEngine *engine = ctxt->engine;
QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(ep->v8engine());
+ QV4::ExecutionEngine *v4 = engine->handle();
QV4::Scope scope(v4);
QV4::Scoped<QV4::QmlContext> qmlContext(scope, QV4::QmlContext::create(v4->rootContext(), ctxt, qmlScope));
diff --git a/src/qml/qml/qqmljavascriptexpression_p.h b/src/qml/qml/qqmljavascriptexpression_p.h
index 1cb6d7bfd1..a028850074 100644
--- a/src/qml/qml/qqmljavascriptexpression_p.h
+++ b/src/qml/qml/qqmljavascriptexpression_p.h
@@ -62,7 +62,7 @@ struct QQmlSourceLocation;
class QQmlDelayedError
{
public:
- inline QQmlDelayedError() : nextError(0), prevError(0) {}
+ inline QQmlDelayedError() : nextError(nullptr), prevError(nullptr) {}
inline ~QQmlDelayedError() { removeError(); }
bool addError(QQmlEnginePrivate *);
@@ -71,8 +71,8 @@ public:
if (!prevError) return;
if (nextError) nextError->prevError = prevError;
*prevError = nextError;
- nextError = 0;
- prevError = 0;
+ nextError = nullptr;
+ prevError = nullptr;
}
inline bool isValid() const { return m_error.isValid(); }
@@ -117,7 +117,7 @@ public:
QQmlSourceLocation sourceLocation() const;
void setSourceLocation(const QQmlSourceLocation &location);
- bool isValid() const { return context() != 0; }
+ bool isValid() const { return context() != nullptr; }
QQmlContextData *context() const { return m_context; }
void setContext(QQmlContextData *context);
@@ -193,11 +193,11 @@ class QQmlPropertyCapture
{
public:
QQmlPropertyCapture(QQmlEngine *engine, QQmlJavaScriptExpression *e, QQmlJavaScriptExpression::DeleteWatcher *w)
- : engine(engine), expression(e), watcher(w), errorString(0) { }
+ : engine(engine), expression(e), watcher(w), errorString(nullptr) { }
~QQmlPropertyCapture() {
Q_ASSERT(guards.isEmpty());
- Q_ASSERT(errorString == 0);
+ Q_ASSERT(errorString == nullptr);
}
enum Duration {
@@ -217,7 +217,7 @@ public:
};
QQmlJavaScriptExpression::DeleteWatcher::DeleteWatcher(QQmlJavaScriptExpression *e)
-: _c(0), _w(0), _s(e)
+: _c(nullptr), _w(nullptr), _s(e)
{
if (e->m_scopeObject.isT1()) {
_w = &_s;
@@ -231,14 +231,14 @@ QQmlJavaScriptExpression::DeleteWatcher::DeleteWatcher(QQmlJavaScriptExpression
QQmlJavaScriptExpression::DeleteWatcher::~DeleteWatcher()
{
- Q_ASSERT(*_w == 0 || (*_w == _s && _s->m_scopeObject.isT2()));
+ Q_ASSERT(*_w == nullptr || (*_w == _s && _s->m_scopeObject.isT2()));
if (*_w && _s->m_scopeObject.asT2() == this)
_s->m_scopeObject = _c;
}
bool QQmlJavaScriptExpression::DeleteWatcher::wasDeleted() const
{
- return *_w == 0;
+ return *_w == nullptr;
}
bool QQmlJavaScriptExpression::notifyOnValueChanged() const
@@ -272,12 +272,12 @@ inline void QQmlJavaScriptExpression::clearError()
{
if (m_error)
delete m_error;
- m_error = 0;
+ m_error = nullptr;
}
QQmlJavaScriptExpressionGuard::QQmlJavaScriptExpressionGuard(QQmlJavaScriptExpression *e)
: QQmlNotifierEndpoint(QQmlNotifierEndpoint::QQmlJavaScriptExpressionGuard),
- expression(e), next(0)
+ expression(e), next(nullptr)
{
}
diff --git a/src/qml/qml/qqmllist.cpp b/src/qml/qml/qqmllist.cpp
index 71be2e82a3..ac6e3695fe 100644
--- a/src/qml/qml/qqmllist.cpp
+++ b/src/qml/qml/qqmllist.cpp
@@ -55,7 +55,7 @@ QQmlListReference QQmlListReferencePrivate::init(const QQmlListProperty<QObject>
if (!prop.object) return rv;
- QQmlEnginePrivate *p = engine?QQmlEnginePrivate::get(engine):0;
+ QQmlEnginePrivate *p = engine?QQmlEnginePrivate::get(engine):nullptr;
int listType = p?p->listType(propType):QQmlMetaType::listType(propType);
if (listType == -1) return rv;
@@ -117,7 +117,7 @@ The \l {Qt Quick 1} version of this class is named QDeclarativeListReference.
Constructs an invalid instance.
*/
QQmlListReference::QQmlListReference()
-: d(0)
+: d(nullptr)
{
}
@@ -131,17 +131,17 @@ Passing \a engine is required to access some QML created list properties. If in
is available, pass it.
*/
QQmlListReference::QQmlListReference(QObject *object, const char *property, QQmlEngine *engine)
-: d(0)
+: d(nullptr)
{
if (!object || !property) return;
QQmlPropertyData local;
QQmlPropertyData *data =
- QQmlPropertyCache::property(engine, object, QLatin1String(property), 0, local);
+ QQmlPropertyCache::property(engine, object, QLatin1String(property), nullptr, local);
if (!data || !data->isQList()) return;
- QQmlEnginePrivate *p = engine?QQmlEnginePrivate::get(engine):0;
+ QQmlEnginePrivate *p = engine?QQmlEnginePrivate::get(engine):nullptr;
int listType = p?p->listType(data->propType()):QQmlMetaType::listType(data->propType());
if (listType == -1) return;
@@ -151,7 +151,7 @@ QQmlListReference::QQmlListReference(QObject *object, const char *property, QQml
d->elementType = p ? p->rawMetaObjectForType(listType) : QQmlMetaType::qmlType(listType).baseMetaObject();
d->propertyType = data->propType();
- void *args[] = { &d->property, 0 };
+ void *args[] = { &d->property, nullptr };
QMetaObject::metacall(object, QMetaObject::ReadProperty, data->coreIndex(), args);
}
@@ -191,7 +191,7 @@ Returns the list property's object. Returns 0 if the reference is invalid.
QObject *QQmlListReference::object() const
{
if (isValid()) return d->object;
- else return 0;
+ else return nullptr;
}
/*!
@@ -204,7 +204,7 @@ to a list.
const QMetaObject *QQmlListReference::listElementType() const
{
if (isValid()) return d->elementType.metaObject();
- else return 0;
+ else return nullptr;
}
/*!
@@ -301,7 +301,7 @@ Returns the list element at \a index, or 0 if the operation failed.
*/
QObject *QQmlListReference::at(int index) const
{
- if (!canAt()) return 0;
+ if (!canAt()) return nullptr;
return d->property.at(&d->property, index);
}
@@ -374,12 +374,12 @@ The \l {Qt Quick 1} version of this class is named QDeclarativeListProperty.
*/
/*!
-\fn QQmlListProperty::QQmlListProperty()
+\fn template<typename T> QQmlListProperty<T>::QQmlListProperty()
\internal
*/
/*!
-\fn QQmlListProperty::QQmlListProperty(QObject *object, QList<T *> &list)
+\fn template<typename T> QQmlListProperty<T>::QQmlListProperty(QObject *object, QList<T *> &list)
Convenience constructor for making a QQmlListProperty value from an existing
QList \a list. The \a list reference must remain valid for as long as \a object
@@ -391,7 +391,7 @@ can be very useful while prototyping.
*/
/*!
-\fn QQmlListProperty::QQmlListProperty(QObject *object, void *data,
+\fn template<typename T> QQmlListProperty<T>::QQmlListProperty(QObject *object, void *data,
CountFunction count, AtFunction at)
Construct a readonly QQmlListProperty from a set of operation functions
@@ -401,7 +401,7 @@ remains valid while \a object exists.
*/
/*!
-\fn QQmlListProperty::QQmlListProperty(QObject *object, void *data, AppendFunction append,
+\fn template<typename T> QQmlListProperty<T>::QQmlListProperty(QObject *object, void *data, AppendFunction append,
CountFunction count, AtFunction at,
ClearFunction clear)
@@ -432,7 +432,7 @@ Return the number of elements in the list \a property.
*/
/*!
-\fn bool QQmlListProperty::operator==(const QQmlListProperty &other) const
+\fn template<typename T> bool QQmlListProperty<T>::operator==(const QQmlListProperty &other) const
Returns true if this QQmlListProperty is equal to \a other, otherwise false.
*/
diff --git a/src/qml/qml/qqmllist.h b/src/qml/qml/qqmllist.h
index 4c6ae0cb8f..90ec57c911 100644
--- a/src/qml/qml/qqmllist.h
+++ b/src/qml/qml/qqmllist.h
@@ -61,20 +61,15 @@ public:
typedef void (*ClearFunction)(QQmlListProperty<T> *);
QQmlListProperty()
- : object(nullptr),
- data(nullptr),
- append(nullptr),
+ : append(nullptr),
count(nullptr),
at(nullptr),
- clear(nullptr),
- dummy1(nullptr),
- dummy2(nullptr)
+ clear(nullptr)
{}
QQmlListProperty(QObject *o, QList<T *> &list)
: object(o), data(&list), append(qlist_append), count(qlist_count), at(qlist_at),
- clear(qlist_clear),
- dummy1(nullptr),
- dummy2(nullptr)
+ clear(qlist_clear)
+
{}
QQmlListProperty(QObject *o, void *d, AppendFunction a, CountFunction c, AtFunction t,
ClearFunction r )
@@ -83,18 +78,15 @@ public:
append(a),
count(c),
at(t),
- clear(r),
- dummy1(nullptr),
- dummy2(nullptr)
+ clear(r)
+
{}
QQmlListProperty(QObject *o, void *d, CountFunction c, AtFunction t)
: object(o),
data(d),
append(nullptr),
count(c), at(t),
- clear(nullptr),
- dummy1(nullptr),
- dummy2(nullptr)
+ clear(nullptr)
{}
bool operator==(const QQmlListProperty &o) const {
return object == o.object &&
@@ -105,8 +97,8 @@ public:
clear == o.clear;
}
- QObject *object;
- void *data;
+ QObject *object = nullptr;
+ void *data = nullptr;
AppendFunction append;
@@ -115,8 +107,8 @@ public:
ClearFunction clear;
- void *dummy1;
- void *dummy2;
+ void *dummy1 = nullptr;
+ void *dummy2 = nullptr;
private:
static void qlist_append(QQmlListProperty *p, T *v) {
diff --git a/src/qml/qml/qqmllistwrapper.cpp b/src/qml/qml/qqmllistwrapper.cpp
index b4be83a156..3fbe3df2ab 100644
--- a/src/qml/qml/qqmllistwrapper.cpp
+++ b/src/qml/qml/qqmllistwrapper.cpp
@@ -77,7 +77,7 @@ ReturnedValue QmlListWrapper::create(ExecutionEngine *engine, QObject *object, i
Scoped<QmlListWrapper> r(scope, engine->memoryManager->allocObject<QmlListWrapper>());
r->d()->object = object;
r->d()->propertyType = propType;
- void *args[] = { &r->d()->property(), 0 };
+ void *args[] = { &r->d()->property(), nullptr };
QMetaObject::metacall(object, QMetaObject::ReadProperty, propId, args);
return r.asReturnedValue();
}
@@ -151,7 +151,7 @@ bool QmlListWrapper::put(Managed *m, String *name, const Value &value)
void QmlListWrapper::advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint *index, Property *p, PropertyAttributes *attrs)
{
- name->setM(0);
+ name->setM(nullptr);
*index = UINT_MAX;
Q_ASSERT(m->as<QmlListWrapper>());
QmlListWrapper *w = static_cast<QmlListWrapper *>(m);
@@ -171,10 +171,10 @@ void PropertyListPrototype::init(ExecutionEngine *)
defineDefaultProperty(QStringLiteral("push"), method_push, 1);
}
-ReturnedValue PropertyListPrototype::method_push(const BuiltinFunction *b, CallData *callData)
+ReturnedValue PropertyListPrototype::method_push(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- ScopedObject instance(scope, callData->thisObject.toObject(scope.engine));
+ ScopedObject instance(scope, thisObject->toObject(scope.engine));
if (!instance)
RETURN_UNDEFINED();
QmlListWrapper *w = instance->as<QmlListWrapper>();
@@ -184,9 +184,9 @@ ReturnedValue PropertyListPrototype::method_push(const BuiltinFunction *b, CallD
THROW_GENERIC_ERROR("List doesn't define an Append function");
QV4::ScopedObject so(scope);
- for (int i = 0, ei = callData->argc(); i < ei; ++i)
+ for (int i = 0, ei = argc; i < ei; ++i)
{
- so = callData->args[i].toObject(scope.engine);
+ so = argv[i].toObject(scope.engine);
if (QV4::QObjectWrapper *wrapper = so->as<QV4::QObjectWrapper>())
w->d()->property().append(&w->d()->property(), wrapper->object() );
}
diff --git a/src/qml/qml/qqmllistwrapper_p.h b/src/qml/qml/qqmllistwrapper_p.h
index 0b53395d2b..e02831c8d1 100644
--- a/src/qml/qml/qqmllistwrapper_p.h
+++ b/src/qml/qml/qqmllistwrapper_p.h
@@ -103,7 +103,7 @@ struct PropertyListPrototype : Object
{
void init(ExecutionEngine *engine);
- static ReturnedValue method_push(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_push(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
};
}
diff --git a/src/qml/qml/qqmllocale.cpp b/src/qml/qml/qqmllocale.cpp
index 3f2a373966..2a5c58b47b 100644
--- a/src/qml/qml/qqmllocale.cpp
+++ b/src/qml/qml/qqmllocale.cpp
@@ -86,37 +86,37 @@ void QQmlDateExtension::registerExtension(QV4::ExecutionEngine *engine)
engine->dateCtor()->defineDefaultProperty(QStringLiteral("timeZoneUpdated"), method_timeZoneUpdated);
}
-ReturnedValue QQmlDateExtension::method_toLocaleString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlDateExtension::method_toLocaleString(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
Scope scope(b);
- if (callData->argc() > 2)
- return QV4::DatePrototype::method_toLocaleString(b, &callData->thisObject, callData->args, callData->argc());
+ if (argc > 2)
+ return QV4::DatePrototype::method_toLocaleString(b, thisObject, argv, argc);
- QV4::DateObject *date = callData->thisObject.as<DateObject>();
+ const QV4::DateObject *date = thisObject->as<DateObject>();
if (!date)
- return QV4::DatePrototype::method_toLocaleString(b, &callData->thisObject, callData->args, callData->argc());
+ return QV4::DatePrototype::method_toLocaleString(b, thisObject, argv, argc);
QDateTime dt = date->toQDateTime();
- if (callData->argc() == 0) {
+ if (argc == 0) {
// Use QLocale for standard toLocaleString() function
QLocale locale;
RETURN_RESULT(scope.engine->newString(locale.toString(dt)));
}
- if (!isLocaleObject(callData->args[0]))
- return QV4::DatePrototype::method_toLocaleString(b, &callData->thisObject, callData->args, callData->argc()); // Use the default Date toLocaleString()
+ if (!isLocaleObject(argv[0]))
+ return QV4::DatePrototype::method_toLocaleString(b, thisObject, argv, argc); // Use the default Date toLocaleString()
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
QLocale::FormatType enumFormat = QLocale::LongFormat;
QString formattedDt;
- if (callData->argc() == 2) {
- if (String *s = callData->args[1].stringValue()) {
+ if (argc == 2) {
+ if (String *s = argv[1].stringValue()) {
QString format = s->toQString();
formattedDt = r->d()->locale->toString(dt, format);
- } else if (callData->args[1].isNumber()) {
- quint32 intFormat = callData->args[1].toNumber();
+ } else if (argv[1].isNumber()) {
+ quint32 intFormat = argv[1].toNumber();
QLocale::FormatType format = QLocale::FormatType(intFormat);
formattedDt = r->d()->locale->toString(dt, format);
} else {
@@ -129,38 +129,38 @@ ReturnedValue QQmlDateExtension::method_toLocaleString(const BuiltinFunction *b,
RETURN_RESULT(scope.engine->newString(formattedDt));
}
-ReturnedValue QQmlDateExtension::method_toLocaleTimeString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlDateExtension::method_toLocaleTimeString(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
Scope scope(b);
- if (callData->argc() > 2)
- return QV4::DatePrototype::method_toLocaleTimeString(b, &callData->thisObject, callData->args, callData->argc());
+ if (argc > 2)
+ return QV4::DatePrototype::method_toLocaleTimeString(b, thisObject, argv, argc);
- QV4::DateObject *date = callData->thisObject.as<DateObject>();
+ const QV4::DateObject *date = thisObject->as<DateObject>();
if (!date)
- return QV4::DatePrototype::method_toLocaleTimeString(b, &callData->thisObject, callData->args, callData->argc());
+ return QV4::DatePrototype::method_toLocaleTimeString(b, thisObject, argv, argc);
QDateTime dt = date->toQDateTime();
QTime time = dt.time();
- if (callData->argc() == 0) {
+ if (argc == 0) {
// Use QLocale for standard toLocaleString() function
QLocale locale;
RETURN_RESULT(scope.engine->newString(locale.toString(time)));
}
- if (!isLocaleObject(callData->args[0]))
- return QV4::DatePrototype::method_toLocaleTimeString(b, &callData->thisObject, callData->args, callData->argc()); // Use the default Date toLocaleTimeString()
+ if (!isLocaleObject(argv[0]))
+ return QV4::DatePrototype::method_toLocaleTimeString(b, thisObject, argv, argc); // Use the default Date toLocaleTimeString()
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
QLocale::FormatType enumFormat = QLocale::LongFormat;
QString formattedTime;
- if (callData->argc() == 2) {
- if (String *s = callData->args[1].stringValue()) {
+ if (argc == 2) {
+ if (String *s = argv[1].stringValue()) {
QString format = s->toQString();
formattedTime = r->d()->locale->toString(time, format);
- } else if (callData->args[1].isNumber()) {
- quint32 intFormat = callData->args[1].toNumber();
+ } else if (argv[1].isNumber()) {
+ quint32 intFormat = argv[1].toNumber();
QLocale::FormatType format = QLocale::FormatType(intFormat);
formattedTime = r->d()->locale->toString(time, format);
} else {
@@ -173,38 +173,38 @@ ReturnedValue QQmlDateExtension::method_toLocaleTimeString(const BuiltinFunction
RETURN_RESULT(scope.engine->newString(formattedTime));
}
-ReturnedValue QQmlDateExtension::method_toLocaleDateString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlDateExtension::method_toLocaleDateString(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
Scope scope(b);
- if (callData->argc() > 2)
- return QV4::DatePrototype::method_toLocaleDateString(b, &callData->thisObject, callData->args, callData->argc());
+ if (argc > 2)
+ return QV4::DatePrototype::method_toLocaleDateString(b, thisObject, argv, argc);
- QV4::DateObject *dateObj = callData->thisObject.as<DateObject>();
+ const QV4::DateObject *dateObj = thisObject->as<DateObject>();
if (!dateObj)
- return QV4::DatePrototype::method_toLocaleDateString(b, &callData->thisObject, callData->args, callData->argc());
+ return QV4::DatePrototype::method_toLocaleDateString(b, thisObject, argv, argc);
QDateTime dt = dateObj->toQDateTime();
QDate date = dt.date();
- if (callData->argc() == 0) {
+ if (argc == 0) {
// Use QLocale for standard toLocaleString() function
QLocale locale;
RETURN_RESULT(scope.engine->newString(locale.toString(date)));
}
- if (!isLocaleObject(callData->args[0]))
- return QV4::DatePrototype::method_toLocaleDateString(b, &callData->thisObject, callData->args, callData->argc()); // Use the default Date toLocaleDateString()
+ if (!isLocaleObject(argv[0]))
+ return QV4::DatePrototype::method_toLocaleDateString(b, thisObject, argv, argc); // Use the default Date toLocaleDateString()
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
QLocale::FormatType enumFormat = QLocale::LongFormat;
QString formattedDate;
- if (callData->argc() == 2) {
- if (String *s = callData->args[1].stringValue()) {
+ if (argc == 2) {
+ if (String *s = argv[1].stringValue()) {
QString format = s->toQString();
formattedDate = r->d()->locale->toString(date, format);
- } else if (callData->args[1].isNumber()) {
- quint32 intFormat = callData->args[1].toNumber();
+ } else if (argv[1].isNumber()) {
+ quint32 intFormat = argv[1].toNumber();
QLocale::FormatType format = QLocale::FormatType(intFormat);
formattedDate = r->d()->locale->toString(date, format);
} else {
@@ -217,12 +217,12 @@ ReturnedValue QQmlDateExtension::method_toLocaleDateString(const BuiltinFunction
RETURN_RESULT(scope.engine->newString(formattedDate));
}
-ReturnedValue QQmlDateExtension::method_fromLocaleString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlDateExtension::method_fromLocaleString(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
QV4::ExecutionEngine * const engine = scope.engine;
- if (callData->argc() == 1) {
- if (String *s = callData->args[0].stringValue()) {
+ if (argc == 1) {
+ if (String *s = argv[0].stringValue()) {
QLocale locale;
QString dateString = s->toQString();
QDateTime dt = locale.toDateTime(dateString);
@@ -230,20 +230,20 @@ ReturnedValue QQmlDateExtension::method_fromLocaleString(const BuiltinFunction *
}
}
- if (callData->argc() < 1 || callData->argc() > 3 || !isLocaleObject(callData->args[0]))
+ if (argc < 1 || argc > 3 || !isLocaleObject(argv[0]))
THROW_ERROR("Locale: Date.fromLocaleString(): Invalid arguments");
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
QLocale::FormatType enumFormat = QLocale::LongFormat;
QDateTime dt;
- QString dateString = callData->args[1].toQStringNoThrow();
- if (callData->argc() == 3) {
- if (String *s = callData->args[2].stringValue()) {
+ QString dateString = argv[1].toQStringNoThrow();
+ if (argc == 3) {
+ if (String *s = argv[2].stringValue()) {
QString format = s->toQString();
dt = r->d()->locale->toDateTime(dateString, format);
- } else if (callData->args[2].isNumber()) {
- quint32 intFormat = callData->args[2].toNumber();
+ } else if (argv[2].isNumber()) {
+ quint32 intFormat = argv[2].toNumber();
QLocale::FormatType format = QLocale::FormatType(intFormat);
dt = r->d()->locale->toDateTime(dateString, format);
} else {
@@ -256,13 +256,13 @@ ReturnedValue QQmlDateExtension::method_fromLocaleString(const BuiltinFunction *
RETURN_RESULT(engine->newDateObject(dt));
}
-ReturnedValue QQmlDateExtension::method_fromLocaleTimeString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlDateExtension::method_fromLocaleTimeString(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
QV4::ExecutionEngine * const engine = scope.engine;
- if (callData->argc() == 1) {
- if (String *s = callData->args[0].stringValue()) {
+ if (argc == 1) {
+ if (String *s = argv[0].stringValue()) {
QLocale locale;
QString timeString = s->toQString();
QTime time = locale.toTime(timeString);
@@ -272,20 +272,20 @@ ReturnedValue QQmlDateExtension::method_fromLocaleTimeString(const BuiltinFuncti
}
}
- if (callData->argc() < 1 || callData->argc() > 3 || !isLocaleObject(callData->args[0]))
+ if (argc < 1 || argc > 3 || !isLocaleObject(argv[0]))
THROW_ERROR("Locale: Date.fromLocaleTimeString(): Invalid arguments");
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
QLocale::FormatType enumFormat = QLocale::LongFormat;
QTime tm;
- QString dateString = callData->args[1].toQStringNoThrow();
- if (callData->argc() == 3) {
- if (String *s = callData->args[2].stringValue()) {
+ QString dateString = argv[1].toQStringNoThrow();
+ if (argc == 3) {
+ if (String *s = argv[2].stringValue()) {
QString format = s->toQString();
tm = r->d()->locale->toTime(dateString, format);
- } else if (callData->args[2].isNumber()) {
- quint32 intFormat = callData->args[2].toNumber();
+ } else if (argv[2].isNumber()) {
+ quint32 intFormat = argv[2].toNumber();
QLocale::FormatType format = QLocale::FormatType(intFormat);
tm = r->d()->locale->toTime(dateString, format);
} else {
@@ -304,13 +304,13 @@ ReturnedValue QQmlDateExtension::method_fromLocaleTimeString(const BuiltinFuncti
RETURN_RESULT(engine->newDateObject(dt));
}
-ReturnedValue QQmlDateExtension::method_fromLocaleDateString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlDateExtension::method_fromLocaleDateString(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
QV4::ExecutionEngine * const engine = scope.engine;
- if (callData->argc() == 1) {
- if (String *s = callData->args[0].stringValue()) {
+ if (argc == 1) {
+ if (String *s = argv[0].stringValue()) {
QLocale locale;
QString dateString = s->toQString();
QDate date = locale.toDate(dateString);
@@ -318,20 +318,20 @@ ReturnedValue QQmlDateExtension::method_fromLocaleDateString(const BuiltinFuncti
}
}
- if (callData->argc() < 1 || callData->argc() > 3 || !isLocaleObject(callData->args[0]))
+ if (argc < 1 || argc > 3 || !isLocaleObject(argv[0]))
THROW_ERROR("Locale: Date.fromLocaleDateString(): Invalid arguments");
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
QLocale::FormatType enumFormat = QLocale::LongFormat;
QDate dt;
- QString dateString = callData->args[1].toQStringNoThrow();
- if (callData->argc() == 3) {
- if (String *s = callData->args[2].stringValue()) {
+ QString dateString = argv[1].toQStringNoThrow();
+ if (argc == 3) {
+ if (String *s = argv[2].stringValue()) {
QString format = s->toQString();
dt = r->d()->locale->toDate(dateString, format);
- } else if (callData->args[2].isNumber()) {
- quint32 intFormat = callData->args[2].toNumber();
+ } else if (argv[2].isNumber()) {
+ quint32 intFormat = argv[2].toNumber();
QLocale::FormatType format = QLocale::FormatType(intFormat);
dt = r->d()->locale->toDate(dateString, format);
} else {
@@ -344,10 +344,10 @@ ReturnedValue QQmlDateExtension::method_fromLocaleDateString(const BuiltinFuncti
RETURN_RESULT(engine->newDateObject(QDateTime(dt)));
}
-ReturnedValue QQmlDateExtension::method_timeZoneUpdated(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlDateExtension::method_timeZoneUpdated(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 0)
+ if (argc != 0)
THROW_ERROR("Locale: Date.timeZoneUpdated(): Invalid arguments");
QV4::DatePrototype::timezoneUpdated();
@@ -365,92 +365,92 @@ void QQmlNumberExtension::registerExtension(QV4::ExecutionEngine *engine)
engine->numberCtor()->defineDefaultProperty(QStringLiteral("fromLocaleString"), method_fromLocaleString);
}
-QV4::ReturnedValue QQmlNumberExtension::method_toLocaleString(const BuiltinFunction *b, CallData *callData)
+QV4::ReturnedValue QQmlNumberExtension::method_toLocaleString(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() > 3)
+ if (argc > 3)
THROW_ERROR("Locale: Number.toLocaleString(): Invalid arguments");
- double number = callData->thisObject.toNumber();
+ double number = thisObject->toNumber();
- if (callData->argc() == 0) {
+ if (argc == 0) {
// Use QLocale for standard toLocaleString() function
QLocale locale;
RETURN_RESULT(scope.engine->newString(locale.toString(number)));
}
- if (!isLocaleObject(callData->args[0]))
- return QV4::NumberPrototype::method_toLocaleString(b, &callData->thisObject, callData->args, callData->argc()); // Use the default Number toLocaleString()
+ if (!isLocaleObject(argv[0]))
+ return QV4::NumberPrototype::method_toLocaleString(b, thisObject, argv, argc); // Use the default Number toLocaleString()
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
quint16 format = 'f';
- if (callData->argc() > 1) {
- if (!callData->args[1].isString())
+ if (argc > 1) {
+ if (!argv[1].isString())
THROW_ERROR("Locale: Number.toLocaleString(): Invalid arguments");
- QString fs = callData->args[1].toQString();
+ QString fs = argv[1].toQString();
if (fs.length())
format = fs.at(0).unicode();
}
int prec = 2;
- if (callData->argc() > 2) {
- if (!callData->args[2].isNumber())
+ if (argc > 2) {
+ if (!argv[2].isNumber())
THROW_ERROR("Locale: Number.toLocaleString(): Invalid arguments");
- prec = callData->args[2].toInt32();
+ prec = argv[2].toInt32();
}
RETURN_RESULT(scope.engine->newString(r->d()->locale->toString(number, (char)format, prec)));
}
-ReturnedValue QQmlNumberExtension::method_toLocaleCurrencyString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlNumberExtension::method_toLocaleCurrencyString(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() > 2)
+ if (argc > 2)
THROW_ERROR("Locale: Number.toLocaleCurrencyString(): Invalid arguments");
- double number = callData->thisObject.toNumber();
+ double number = thisObject->toNumber();
- if (callData->argc() == 0) {
+ if (argc == 0) {
// Use QLocale for standard toLocaleString() function
QLocale locale;
RETURN_RESULT(scope.engine->newString(locale.toString(number)));
}
- if (!isLocaleObject(callData->args[0]))
+ if (!isLocaleObject(argv[0]))
THROW_ERROR("Locale: Number.toLocaleCurrencyString(): Invalid arguments");
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
QString symbol;
- if (callData->argc() > 1) {
- if (!callData->args[1].isString())
+ if (argc > 1) {
+ if (!argv[1].isString())
THROW_ERROR("Locale: Number.toLocaleString(): Invalid arguments");
- symbol = callData->args[1].toQStringNoThrow();
+ symbol = argv[1].toQStringNoThrow();
}
RETURN_RESULT(scope.engine->newString(r->d()->locale->toCurrencyString(number, symbol)));
}
-ReturnedValue QQmlNumberExtension::method_fromLocaleString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlNumberExtension::method_fromLocaleString(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 1 || callData->argc() > 2)
+ if (argc < 1 || argc > 2)
THROW_ERROR("Locale: Number.fromLocaleString(): Invalid arguments");
int numberIdx = 0;
QLocale locale;
- if (callData->argc() == 2) {
- if (!isLocaleObject(callData->args[0]))
+ if (argc == 2) {
+ if (!isLocaleObject(argv[0]))
THROW_ERROR("Locale: Number.fromLocaleString(): Invalid arguments");
- GET_LOCALE_DATA_RESOURCE(callData->args[0]);
+ GET_LOCALE_DATA_RESOURCE(argv[0]);
locale = *r->d()->locale;
numberIdx = 1;
}
- QString ns = callData->args[numberIdx].toQString();
+ QString ns = argv[numberIdx].toQString();
if (!ns.length())
RETURN_RESULT(QV4::Encode(Q_QNAN));
@@ -466,10 +466,10 @@ ReturnedValue QQmlNumberExtension::method_fromLocaleString(const BuiltinFunction
//--------------
// Locale object
-ReturnedValue QQmlLocaleData::method_get_firstDayOfWeek(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlLocaleData::method_get_firstDayOfWeek(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QLocale *locale = getThisLocale(scope, callData);
+ const QLocale *locale = getThisLocale(scope, thisObject);
if (!locale)
return Encode::undefined();
int fdow = int(locale->firstDayOfWeek());
@@ -478,29 +478,29 @@ ReturnedValue QQmlLocaleData::method_get_firstDayOfWeek(const BuiltinFunction *b
RETURN_RESULT(fdow);
}
-ReturnedValue QQmlLocaleData::method_get_measurementSystem(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlLocaleData::method_get_measurementSystem(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QLocale *locale = getThisLocale(scope, callData);
+ const QLocale *locale = getThisLocale(scope, thisObject);
if (!locale)
return Encode::undefined();
return QV4::Encode(locale->measurementSystem());
}
-ReturnedValue QQmlLocaleData::method_get_textDirection(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlLocaleData::method_get_textDirection(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QLocale *locale = getThisLocale(scope, callData);
+ const QLocale *locale = getThisLocale(scope, thisObject);
if (!locale)
return Encode::undefined();
return QV4::Encode(locale->textDirection());
}
-ReturnedValue QQmlLocaleData::method_get_weekDays(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlLocaleData::method_get_weekDays(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QLocale *locale = getThisLocale(scope, callData);
+ const QLocale *locale = getThisLocale(scope, thisObject);
if (!locale)
return Encode::undefined();
@@ -519,10 +519,10 @@ ReturnedValue QQmlLocaleData::method_get_weekDays(const BuiltinFunction *b, Call
return result.asReturnedValue();
}
-ReturnedValue QQmlLocaleData::method_get_uiLanguages(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlLocaleData::method_get_uiLanguages(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QLocale *locale = getThisLocale(scope, callData);
+ const QLocale *locale = getThisLocale(scope, thisObject);
if (!locale)
return Encode::undefined();
@@ -538,19 +538,19 @@ ReturnedValue QQmlLocaleData::method_get_uiLanguages(const BuiltinFunction *b, C
return result.asReturnedValue();
}
-ReturnedValue QQmlLocaleData::method_currencySymbol(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlLocaleData::method_currencySymbol(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QLocale *locale = getThisLocale(scope, callData);
+ const QLocale *locale = getThisLocale(scope, thisObject);
if (!locale)
return Encode::undefined();
- if (callData->argc() > 1)
+ if (argc > 1)
THROW_ERROR("Locale: currencySymbol(): Invalid arguments");
QLocale::CurrencySymbolFormat format = QLocale::CurrencySymbol;
- if (callData->argc() == 1) {
- quint32 intFormat = callData->args[0].toNumber();
+ if (argc == 1) {
+ quint32 intFormat = argv[0].toNumber();
format = QLocale::CurrencySymbolFormat(intFormat);
}
@@ -558,16 +558,16 @@ ReturnedValue QQmlLocaleData::method_currencySymbol(const BuiltinFunction *b, Ca
}
#define LOCALE_FORMAT(FUNC) \
-ReturnedValue QQmlLocaleData::method_ ##FUNC (const BuiltinFunction *b, CallData *callData) { \
+ReturnedValue QQmlLocaleData::method_ ##FUNC (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc) { \
QV4::Scope scope(b); \
- QLocale *locale = getThisLocale(scope, callData); \
+ const QLocale *locale = getThisLocale(scope, thisObject); \
if (!locale) \
return Encode::undefined(); \
- if (callData->argc() > 1) \
+ if (argc > 1) \
THROW_ERROR("Locale: " #FUNC "(): Invalid arguments"); \
QLocale::FormatType format = QLocale::LongFormat;\
- if (callData->argc() == 1) { \
- quint32 intFormat = callData->args[0].toUInt32(); \
+ if (argc == 1) { \
+ quint32 intFormat = argv[0].toUInt32(); \
format = QLocale::FormatType(intFormat); \
} \
RETURN_RESULT(scope.engine->newString(locale-> FUNC (format))); \
@@ -579,21 +579,21 @@ LOCALE_FORMAT(dateFormat)
// +1 added to idx because JS is 0-based, whereas QLocale months begin at 1.
#define LOCALE_FORMATTED_MONTHNAME(VARIABLE) \
-ReturnedValue QQmlLocaleData::method_ ## VARIABLE (const BuiltinFunction *b, CallData *callData) {\
+ReturnedValue QQmlLocaleData::method_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc) {\
Scope scope(b); \
- QLocale *locale = getThisLocale(scope, callData); \
+ const QLocale *locale = getThisLocale(scope, thisObject); \
if (!locale) \
return Encode::undefined(); \
- if (callData->argc() < 1 || callData->argc() > 2) \
+ if (argc < 1 || argc > 2) \
THROW_ERROR("Locale: " #VARIABLE "(): Invalid arguments"); \
QLocale::FormatType enumFormat = QLocale::LongFormat; \
- int idx = callData->args[0].toInt32() + 1; \
+ int idx = argv[0].toInt32() + 1; \
if (idx < 1 || idx > 12) \
THROW_ERROR("Locale: Invalid month"); \
QString name; \
- if (callData->argc() == 2) { \
- if (callData->args[1].isNumber()) { \
- quint32 intFormat = callData->args[1].toUInt32(); \
+ if (argc == 2) { \
+ if (argv[1].isNumber()) { \
+ quint32 intFormat = argv[1].toUInt32(); \
QLocale::FormatType format = QLocale::FormatType(intFormat); \
name = locale-> VARIABLE(idx, format); \
} else { \
@@ -607,22 +607,22 @@ ReturnedValue QQmlLocaleData::method_ ## VARIABLE (const BuiltinFunction *b, Cal
// 0 -> 7 as Qt::Sunday is 7, but Sunday is 0 in JS Date
#define LOCALE_FORMATTED_DAYNAME(VARIABLE) \
-ReturnedValue QQmlLocaleData::method_ ## VARIABLE (const BuiltinFunction *b, CallData *callData) {\
+ReturnedValue QQmlLocaleData::method_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc) {\
Scope scope(b); \
- QLocale *locale = getThisLocale(scope, callData); \
+ const QLocale *locale = getThisLocale(scope, thisObject); \
if (!locale) \
return Encode::undefined(); \
- if (callData->argc() < 1 || callData->argc() > 2) \
+ if (argc < 1 || argc > 2) \
THROW_ERROR("Locale: " #VARIABLE "(): Invalid arguments"); \
QLocale::FormatType enumFormat = QLocale::LongFormat; \
- int idx = callData->args[0].toInt32(); \
+ int idx = argv[0].toInt32(); \
if (idx < 0 || idx > 7) \
THROW_ERROR("Locale: Invalid day"); \
if (idx == 0) idx = 7; \
QString name; \
- if (callData->argc() == 2) { \
- if (callData->args[1].isNumber()) { \
- quint32 intFormat = callData->args[1].toUInt32(); \
+ if (argc == 2) { \
+ if (argv[1].isNumber()) { \
+ quint32 intFormat = argv[1].toUInt32(); \
QLocale::FormatType format = QLocale::FormatType(intFormat); \
name = locale-> VARIABLE(idx, format); \
} else { \
@@ -640,10 +640,10 @@ LOCALE_FORMATTED_DAYNAME(dayName)
LOCALE_FORMATTED_DAYNAME(standaloneDayName)
#define LOCALE_STRING_PROPERTY(VARIABLE) \
-ReturnedValue QQmlLocaleData::method_get_ ## VARIABLE (const BuiltinFunction *b, CallData *callData) \
+ReturnedValue QQmlLocaleData::method_get_ ## VARIABLE (const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int) \
{ \
Scope scope(b); \
- QLocale *locale = getThisLocale(scope, callData); \
+ const QLocale *locale = getThisLocale(scope, thisObject); \
if (!locale) \
return Encode::undefined(); \
RETURN_RESULT(scope.engine->newString(locale-> VARIABLE()));\
@@ -684,23 +684,23 @@ QV4LocaleDataDeletable::QV4LocaleDataDeletable(QV4::ExecutionEngine *engine)
o->defineDefaultProperty(QStringLiteral("monthName"), QQmlLocaleData::method_monthName, 0);
o->defineDefaultProperty(QStringLiteral("currencySymbol"), QQmlLocaleData::method_currencySymbol, 0);
o->defineDefaultProperty(QStringLiteral("dateTimeFormat"), QQmlLocaleData::method_dateTimeFormat, 0);
- o->defineAccessorProperty(QStringLiteral("name"), QQmlLocaleData::method_get_name, 0);
- o->defineAccessorProperty(QStringLiteral("positiveSign"), QQmlLocaleData::method_get_positiveSign, 0);
- o->defineAccessorProperty(QStringLiteral("uiLanguages"), QQmlLocaleData::method_get_uiLanguages, 0);
- o->defineAccessorProperty(QStringLiteral("firstDayOfWeek"), QQmlLocaleData::method_get_firstDayOfWeek, 0);
- o->defineAccessorProperty(QStringLiteral("pmText"), QQmlLocaleData::method_get_pmText, 0);
- o->defineAccessorProperty(QStringLiteral("percent"), QQmlLocaleData::method_get_percent, 0);
- o->defineAccessorProperty(QStringLiteral("textDirection"), QQmlLocaleData::method_get_textDirection, 0);
- o->defineAccessorProperty(QStringLiteral("weekDays"), QQmlLocaleData::method_get_weekDays, 0);
- o->defineAccessorProperty(QStringLiteral("negativeSign"), QQmlLocaleData::method_get_negativeSign, 0);
- o->defineAccessorProperty(QStringLiteral("groupSeparator"), QQmlLocaleData::method_get_groupSeparator, 0);
- o->defineAccessorProperty(QStringLiteral("decimalPoint"), QQmlLocaleData::method_get_decimalPoint, 0);
- o->defineAccessorProperty(QStringLiteral("nativeLanguageName"), QQmlLocaleData::method_get_nativeLanguageName, 0);
- o->defineAccessorProperty(QStringLiteral("nativeCountryName"), QQmlLocaleData::method_get_nativeCountryName, 0);
- o->defineAccessorProperty(QStringLiteral("zeroDigit"), QQmlLocaleData::method_get_zeroDigit, 0);
- o->defineAccessorProperty(QStringLiteral("amText"), QQmlLocaleData::method_get_amText, 0);
- o->defineAccessorProperty(QStringLiteral("measurementSystem"), QQmlLocaleData::method_get_measurementSystem, 0);
- o->defineAccessorProperty(QStringLiteral("exponential"), QQmlLocaleData::method_get_exponential, 0);
+ o->defineAccessorProperty(QStringLiteral("name"), QQmlLocaleData::method_get_name, nullptr);
+ o->defineAccessorProperty(QStringLiteral("positiveSign"), QQmlLocaleData::method_get_positiveSign, nullptr);
+ o->defineAccessorProperty(QStringLiteral("uiLanguages"), QQmlLocaleData::method_get_uiLanguages, nullptr);
+ o->defineAccessorProperty(QStringLiteral("firstDayOfWeek"), QQmlLocaleData::method_get_firstDayOfWeek, nullptr);
+ o->defineAccessorProperty(QStringLiteral("pmText"), QQmlLocaleData::method_get_pmText, nullptr);
+ o->defineAccessorProperty(QStringLiteral("percent"), QQmlLocaleData::method_get_percent, nullptr);
+ o->defineAccessorProperty(QStringLiteral("textDirection"), QQmlLocaleData::method_get_textDirection, nullptr);
+ o->defineAccessorProperty(QStringLiteral("weekDays"), QQmlLocaleData::method_get_weekDays, nullptr);
+ o->defineAccessorProperty(QStringLiteral("negativeSign"), QQmlLocaleData::method_get_negativeSign, nullptr);
+ o->defineAccessorProperty(QStringLiteral("groupSeparator"), QQmlLocaleData::method_get_groupSeparator, nullptr);
+ o->defineAccessorProperty(QStringLiteral("decimalPoint"), QQmlLocaleData::method_get_decimalPoint, nullptr);
+ o->defineAccessorProperty(QStringLiteral("nativeLanguageName"), QQmlLocaleData::method_get_nativeLanguageName, nullptr);
+ o->defineAccessorProperty(QStringLiteral("nativeCountryName"), QQmlLocaleData::method_get_nativeCountryName, nullptr);
+ o->defineAccessorProperty(QStringLiteral("zeroDigit"), QQmlLocaleData::method_get_zeroDigit, nullptr);
+ o->defineAccessorProperty(QStringLiteral("amText"), QQmlLocaleData::method_get_amText, nullptr);
+ o->defineAccessorProperty(QStringLiteral("measurementSystem"), QQmlLocaleData::method_get_measurementSystem, nullptr);
+ o->defineAccessorProperty(QStringLiteral("exponential"), QQmlLocaleData::method_get_exponential, nullptr);
prototype.set(engine, o);
}
@@ -837,16 +837,16 @@ void QQmlLocale::registerStringLocaleCompare(QV4::ExecutionEngine *engine)
engine->stringPrototype()->defineDefaultProperty(QStringLiteral("localeCompare"), method_localeCompare);
}
-ReturnedValue QQmlLocale::method_localeCompare(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlLocale::method_localeCompare(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
- if (callData->argc() != 1 || (!callData->args[0].isString() && !callData->args[0].as<StringObject>()))
- return QV4::StringPrototype::method_localeCompare(b, &callData->thisObject, callData->args, callData->argc());
+ if (argc != 1 || (!argv[0].isString() && !argv[0].as<StringObject>()))
+ return QV4::StringPrototype::method_localeCompare(b, thisObject, argv, argc);
- if (!callData->thisObject.isString() && !callData->thisObject.as<StringObject>())
- return QV4::StringPrototype::method_localeCompare(b, &callData->thisObject, callData->args, callData->argc());
+ if (!thisObject->isString() && !thisObject->as<StringObject>())
+ return QV4::StringPrototype::method_localeCompare(b, thisObject, argv, argc);
- QString thisString = callData->thisObject.toQStringNoThrow();
- QString thatString = callData->args[0].toQStringNoThrow();
+ QString thisString = thisObject->toQStringNoThrow();
+ QString thatString = argv[0].toQStringNoThrow();
return QV4::Encode(QString::localeAwareCompare(thisString, thatString));
}
diff --git a/src/qml/qml/qqmllocale_p.h b/src/qml/qml/qqmllocale_p.h
index a81fe07b8e..8341b1f555 100644
--- a/src/qml/qml/qqmllocale_p.h
+++ b/src/qml/qml/qqmllocale_p.h
@@ -67,13 +67,13 @@ public:
static void registerExtension(QV4::ExecutionEngine *engine);
private:
- static QV4::ReturnedValue method_toLocaleString(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_toLocaleTimeString(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_toLocaleDateString(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_fromLocaleString(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_fromLocaleTimeString(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_fromLocaleDateString(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_timeZoneUpdated(const QV4::BuiltinFunction *, QV4::CallData *callData);
+ static QV4::ReturnedValue method_toLocaleString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_toLocaleTimeString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_toLocaleDateString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_fromLocaleString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_fromLocaleTimeString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_fromLocaleDateString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_timeZoneUpdated(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
@@ -83,9 +83,9 @@ public:
static void registerExtension(QV4::ExecutionEngine *engine);
private:
- static QV4::ReturnedValue method_toLocaleString(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_fromLocaleString(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_toLocaleCurrencyString(const QV4::BuiltinFunction *, QV4::CallData *callData);
+ static QV4::ReturnedValue method_toLocaleString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_fromLocaleString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_toLocaleCurrencyString(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
@@ -135,7 +135,7 @@ public:
private:
QQmlLocale();
- static QV4::ReturnedValue method_localeCompare(const QV4::BuiltinFunction *, QV4::CallData *callData);
+ static QV4::ReturnedValue method_localeCompare(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
namespace QV4 {
@@ -158,43 +158,43 @@ struct QQmlLocaleData : public QV4::Object
V4_OBJECT2(QQmlLocaleData, Object)
V4_NEEDS_DESTROY
- static QLocale *getThisLocale(QV4::Scope &scope, QV4::CallData *callData) {
- QV4::Object *o = callData->thisObject.as<Object>();
- QQmlLocaleData *thisObject = o ? o->as<QQmlLocaleData>() : 0;
- if (!thisObject) {
+ static QLocale *getThisLocale(QV4::Scope &scope, const QV4::Value *thisObject) {
+ const QV4::Object *o = thisObject->as<Object>();
+ const QQmlLocaleData *data = o ? o->as<QQmlLocaleData>() : nullptr;
+ if (!data) {
scope.engine->throwTypeError();
- return 0;
+ return nullptr;
}
- return thisObject->d()->locale;
+ return data->d()->locale;
}
- static QV4::ReturnedValue method_currencySymbol(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_dateTimeFormat(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_timeFormat(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_dateFormat(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_monthName(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_standaloneMonthName(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_dayName(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_standaloneDayName(const QV4::BuiltinFunction *, QV4::CallData *callData);
-
- static QV4::ReturnedValue method_get_firstDayOfWeek(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_measurementSystem(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_textDirection(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_weekDays(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_uiLanguages(const QV4::BuiltinFunction *, QV4::CallData *callData);
-
- static QV4::ReturnedValue method_get_name(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_nativeLanguageName(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_nativeCountryName(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_decimalPoint(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_groupSeparator(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_percent(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_zeroDigit(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_negativeSign(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_positiveSign(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_exponential(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_amText(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_pmText(const QV4::BuiltinFunction *, QV4::CallData *callData);
+ static QV4::ReturnedValue method_currencySymbol(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_dateTimeFormat(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_timeFormat(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_dateFormat(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_monthName(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_standaloneMonthName(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_dayName(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_standaloneDayName(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+
+ static QV4::ReturnedValue method_get_firstDayOfWeek(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_measurementSystem(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_textDirection(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_weekDays(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_uiLanguages(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+
+ static QV4::ReturnedValue method_get_name(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_nativeLanguageName(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_nativeCountryName(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_decimalPoint(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_groupSeparator(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_percent(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_zeroDigit(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_negativeSign(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_positiveSign(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_exponential(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_amText(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_pmText(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
}
diff --git a/src/qml/qml/qqmlloggingcategory_p.h b/src/qml/qml/qqmlloggingcategory_p.h
index 2b7f2f5b53..544db1fe33 100644
--- a/src/qml/qml/qqmlloggingcategory_p.h
+++ b/src/qml/qml/qqmlloggingcategory_p.h
@@ -67,7 +67,7 @@ class QQmlLoggingCategory : public QObject, public QQmlParserStatus
Q_PROPERTY(QString name READ name WRITE setName)
public:
- QQmlLoggingCategory(QObject *parent = 0);
+ QQmlLoggingCategory(QObject *parent = nullptr);
virtual ~QQmlLoggingCategory();
QString name() const;
diff --git a/src/qml/qml/qqmlmetatype.cpp b/src/qml/qml/qqmlmetatype.cpp
index 5836c85666..7754f0fddc 100644
--- a/src/qml/qml/qqmlmetatype.cpp
+++ b/src/qml/qml/qqmlmetatype.cpp
@@ -170,7 +170,7 @@ public:
~QQmlTypePrivate();
void init() const;
- void initEnums(const QQmlPropertyCache *cache = 0) const;
+ void initEnums(const QQmlPropertyCache *cache = nullptr) const;
void insertEnums(const QMetaObject *metaObject) const;
void insertEnumsFromPropertyCache(const QQmlPropertyCache *cache) const;
@@ -272,8 +272,10 @@ void QQmlType::SingletonInstanceInfo::init(QQmlEngine *e)
QQmlData::ensurePropertyCache(e, o);
} else if (!url.isEmpty() && !qobjectApi(e)) {
QQmlComponent component(e, url, QQmlComponent::PreferSynchronous);
- QObject *o = component.create();
+ QObject *o = component.beginCreate(e->rootContext());
setQObjectApi(e, o);
+ if (o)
+ component.completeCreate();
}
}
@@ -313,31 +315,31 @@ QJSValue QQmlType::SingletonInstanceInfo::scriptApi(QQmlEngine *e) const
QHash<const QMetaObject *, int> QQmlTypePrivate::attachedPropertyIds;
QQmlTypePrivate::QQmlTypePrivate(QQmlType::RegistrationType type)
-: refCount(1), regType(type), iid(0), typeId(0), listId(0), revision(0),
- containsRevisionedAttributes(false), baseMetaObject(0),
+: refCount(1), regType(type), iid(nullptr), typeId(0), listId(0), revision(0),
+ containsRevisionedAttributes(false), baseMetaObject(nullptr),
index(-1), isSetup(false), isEnumSetup(false), haveSuperType(false)
{
switch (type) {
case QQmlType::CppType:
extraData.cd = new QQmlCppTypeData;
extraData.cd->allocationSize = 0;
- extraData.cd->newFunc = 0;
+ extraData.cd->newFunc = nullptr;
extraData.cd->parserStatusCast = -1;
- extraData.cd->extFunc = 0;
- extraData.cd->extMetaObject = 0;
- extraData.cd->customParser = 0;
- extraData.cd->attachedPropertiesFunc = 0;
- extraData.cd->attachedPropertiesType = 0;
+ extraData.cd->extFunc = nullptr;
+ extraData.cd->extMetaObject = nullptr;
+ extraData.cd->customParser = nullptr;
+ extraData.cd->attachedPropertiesFunc = nullptr;
+ extraData.cd->attachedPropertiesType = nullptr;
extraData.cd->propertyValueSourceCast = -1;
extraData.cd->propertyValueInterceptorCast = -1;
break;
case QQmlType::SingletonType:
case QQmlType::CompositeSingletonType:
extraData.sd = new QQmlSingletonTypeData;
- extraData.sd->singletonInstanceInfo = 0;
+ extraData.sd->singletonInstanceInfo = nullptr;
break;
case QQmlType::InterfaceType:
- extraData.cd = 0;
+ extraData.cd = nullptr;
break;
case QQmlType::CompositeType:
extraData.fd = new QQmlCompositeTypeData;
@@ -404,7 +406,7 @@ QQmlType::QQmlType(QQmlMetaTypeData *data, const QString &elementName, const QQm
d->extraData.sd->singletonInstanceInfo->qobjectCallback = type.qobjectApi;
d->extraData.sd->singletonInstanceInfo->typeName = QString::fromUtf8(type.typeName);
d->extraData.sd->singletonInstanceInfo->instanceMetaObject
- = (type.qobjectApi && type.version >= 1) ? type.instanceMetaObject : 0;
+ = (type.qobjectApi && type.version >= 1) ? type.instanceMetaObject : nullptr;
}
QQmlType::QQmlType(QQmlMetaTypeData *data, const QString &elementName, const QQmlPrivate::RegisterCompositeSingletonType &type)
@@ -476,7 +478,7 @@ QQmlType::QQmlType(QQmlMetaTypeData *data, const QString &elementName, const QQm
}
QQmlType::QQmlType()
- : d(0)
+ : d(nullptr)
{
}
@@ -584,10 +586,10 @@ QQmlPropertyCache *QQmlType::compositePropertyCache(QQmlEnginePrivate *engine) c
// similar logic to resolveCompositeBaseType
Q_ASSERT(isComposite());
if (!engine)
- return 0;
+ return nullptr;
QQmlRefPointer<QQmlTypeData> td(engine->typeLoader.getType(sourceUrl()), QQmlRefPointer<QQmlTypeData>::Adopt);
if (td.isNull() || !td->isComplete())
- return 0;
+ return nullptr;
QV4::CompiledData::CompilationUnit *compilationUnit = td->compilationUnit();
return compilationUnit->rootPropertyCache();
}
@@ -737,7 +739,7 @@ void QQmlTypePrivate::init() const
// Check for revisioned details
{
- const QMetaObject *mo = 0;
+ const QMetaObject *mo = nullptr;
if (metaObjects.isEmpty())
mo = baseMetaObject;
else
@@ -790,7 +792,7 @@ void QQmlTypePrivate::insertEnums(const QMetaObject *metaObject) const
for (int ii = 0; ii < metaObject->enumeratorCount(); ++ii) {
QMetaEnum e = metaObject->enumerator(ii);
const bool isScoped = e.isScoped();
- QStringHash<int> *scoped = isScoped ? new QStringHash<int>() : 0;
+ QStringHash<int> *scoped = isScoped ? new QStringHash<int>() : nullptr;
for (int jj = 0; jj < e.keyCount(); ++jj) {
const QString key = QString::fromUtf8(e.key(jj));
@@ -886,7 +888,7 @@ QString QQmlType::qmlTypeName() const
QObject *QQmlType::create() const
{
if (!d || !isCreatable())
- return 0;
+ return nullptr;
d->init();
@@ -919,25 +921,25 @@ void QQmlType::create(QObject **out, void **memory, size_t additionalMemory) con
QQmlType::SingletonInstanceInfo *QQmlType::singletonInstanceInfo() const
{
if (!d)
- return 0;
+ return nullptr;
if (d->regType != SingletonType && d->regType != CompositeSingletonType)
- return 0;
+ return nullptr;
return d->extraData.sd->singletonInstanceInfo;
}
QQmlCustomParser *QQmlType::customParser() const
{
if (!d)
- return 0;
+ return nullptr;
if (d->regType != CppType)
- return 0;
+ return nullptr;
return d->extraData.cd->customParser;
}
QQmlType::CreateFunc QQmlType::createFunction() const
{
if (!d || d->regType != CppType)
- return 0;
+ return nullptr;
return d->extraData.cd->newFunc;
}
@@ -1002,7 +1004,7 @@ int QQmlType::qListTypeId() const
const QMetaObject *QQmlType::metaObject() const
{
if (!d)
- return 0;
+ return nullptr;
d->init();
if (d->metaObjects.isEmpty())
@@ -1014,7 +1016,7 @@ const QMetaObject *QQmlType::metaObject() const
const QMetaObject *QQmlType::baseMetaObject() const
{
- return d ? d->baseMetaObject : 0;
+ return d ? d->baseMetaObject : nullptr;
}
bool QQmlType::containsRevisionedAttributes() const
@@ -1034,7 +1036,7 @@ int QQmlType::metaObjectRevision() const
QQmlAttachedPropertiesFunc QQmlType::attachedPropertiesFunction(QQmlEnginePrivate *engine) const
{
if (!d)
- return 0;
+ return nullptr;
if (d->regType == CppType)
return d->extraData.cd->attachedPropertiesFunc;
@@ -1047,7 +1049,7 @@ QQmlAttachedPropertiesFunc QQmlType::attachedPropertiesFunction(QQmlEnginePrivat
const QMetaObject *QQmlType::attachedPropertiesType(QQmlEnginePrivate *engine) const
{
if (!d)
- return 0;
+ return nullptr;
if (d->regType == CppType)
return d->extraData.cd->attachedPropertiesType;
@@ -1099,7 +1101,7 @@ int QQmlType::propertyValueInterceptorCast() const
const char *QQmlType::interfaceIId() const
{
if (!d || d->regType != InterfaceType)
- return 0;
+ return nullptr;
return d->iid;
}
@@ -1123,7 +1125,7 @@ int QQmlType::enumValue(QQmlEnginePrivate *engine, const QHashedStringRef &name,
{
Q_ASSERT(ok);
if (d) {
- const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : 0;
+ const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : nullptr;
*ok = true;
@@ -1142,7 +1144,7 @@ int QQmlType::enumValue(QQmlEnginePrivate *engine, const QHashedCStringRef &name
{
Q_ASSERT(ok);
if (d) {
- const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : 0;
+ const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : nullptr;
*ok = true;
@@ -1161,7 +1163,7 @@ int QQmlType::enumValue(QQmlEnginePrivate *engine, const QV4::String *name, bool
{
Q_ASSERT(ok);
if (d) {
- const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : 0;
+ const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : nullptr;
*ok = true;
d->initEnums(cache);
@@ -1179,7 +1181,7 @@ int QQmlType::scopedEnumIndex(QQmlEnginePrivate *engine, const QV4::String *name
{
Q_ASSERT(ok);
if (d) {
- const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : 0;
+ const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : nullptr;
*ok = true;
d->initEnums(cache);
@@ -1197,7 +1199,7 @@ int QQmlType::scopedEnumIndex(QQmlEnginePrivate *engine, const QString &name, bo
{
Q_ASSERT(ok);
if (d) {
- const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : 0;
+ const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : nullptr;
*ok = true;
d->initEnums(cache);
@@ -1249,7 +1251,7 @@ int QQmlType::scopedEnumValue(QQmlEnginePrivate *engine, const QByteArray &scope
{
Q_ASSERT(ok);
if (d) {
- const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : 0;
+ const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : nullptr;
*ok = true;
d->initEnums(cache);
@@ -1272,7 +1274,7 @@ int QQmlType::scopedEnumValue(QQmlEnginePrivate *engine, const QStringRef &scope
{
Q_ASSERT(ok);
if (d) {
- const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : 0;
+ const QQmlPropertyCache *cache = isComposite() ? compositePropertyCache(engine) : nullptr;
*ok = true;
d->initEnums(cache);
@@ -1338,7 +1340,7 @@ QQmlTypeModule::QQmlTypeModule()
QQmlTypeModule::~QQmlTypeModule()
{
- delete d; d = 0;
+ delete d; d = nullptr;
}
QString QQmlTypeModule::module() const
@@ -1437,7 +1439,7 @@ void QQmlTypeModule::walkCompositeSingletons(const std::function<void(const QQml
}
QQmlTypeModuleVersion::QQmlTypeModuleVersion()
-: m_module(0), m_minor(0)
+: m_module(nullptr), m_minor(0)
{
}
@@ -1564,6 +1566,12 @@ QString registrationTypeString(QQmlType::RegistrationType typeType)
bool checkRegistration(QQmlType::RegistrationType typeType, QQmlMetaTypeData *data, const char *uri, const QString &typeName, int majorVersion = -1)
{
if (!typeName.isEmpty()) {
+ if (typeName.at(0).isLower()) {
+ QString failure(QCoreApplication::translate("qmlRegisterType", "Invalid QML %1 name \"%2\"; type names must begin with an uppercase letter"));
+ data->typeRegistrationFailures.append(failure.arg(registrationTypeString(typeType)).arg(typeName));
+ return false;
+ }
+
int typeNameLen = typeName.length();
for (int ii = 0; ii < typeNameLen; ++ii) {
if (!(typeName.at(ii).isLetterOrNumber() || typeName.at(ii) == '_')) {
@@ -1577,15 +1585,7 @@ bool checkRegistration(QQmlType::RegistrationType typeType, QQmlMetaTypeData *da
if (uri && !typeName.isEmpty()) {
QString nameSpace = QString::fromUtf8(uri);
- if (!data->typeRegistrationNamespace.isEmpty()) {
- // We can only install types into the registered namespace
- if (nameSpace != data->typeRegistrationNamespace) {
- QString failure(QCoreApplication::translate("qmlRegisterType",
- "Cannot install %1 '%2' into unregistered namespace '%3'"));
- data->typeRegistrationFailures.append(failure.arg(registrationTypeString(typeType)).arg(typeName).arg(nameSpace));
- return false;
- }
- } else if (data->typeRegistrationNamespace != nameSpace) {
+ if (data->typeRegistrationNamespace.isEmpty() && !nameSpace.isEmpty()) {
// Is the target namespace protected against further registrations?
if (data->protectedNamespaces.contains(nameSpace)) {
QString failure(QCoreApplication::translate("qmlRegisterType",
@@ -1699,7 +1699,7 @@ QQmlType QQmlMetaType::registerCompositeSingletonType(const QQmlPrivate::Registe
bool fileImport = false;
if (*(type.uri) == '\0')
fileImport = true;
- if (!checkRegistration(QQmlType::CompositeSingletonType, data, fileImport ? 0 : type.uri, typeName))
+ if (!checkRegistration(QQmlType::CompositeSingletonType, data, fileImport ? nullptr : type.uri, typeName))
return QQmlType();
QQmlType dtype(data, typeName, type);
@@ -1721,7 +1721,7 @@ QQmlType QQmlMetaType::registerCompositeType(const QQmlPrivate::RegisterComposit
bool fileImport = false;
if (*(type.uri) == '\0')
fileImport = true;
- if (!checkRegistration(QQmlType::CompositeType, data, fileImport?0:type.uri, typeName, type.versionMajor))
+ if (!checkRegistration(QQmlType::CompositeType, data, fileImport?nullptr:type.uri, typeName, type.versionMajor))
return QQmlType();
QQmlType dtype(data, typeName, type);
@@ -1745,13 +1745,13 @@ void QQmlMetaType::registerInternalCompositeType(QV4::CompiledData::CompilationU
QtMetaTypePrivate::QMetaTypeFunctionHelper<QObject*>::Construct,
sizeof(QObject*),
static_cast<QFlags<QMetaType::TypeFlag> >(QtPrivate::QMetaTypeTypeFlags<QObject*>::Flags),
- 0);
+ nullptr);
int lst_type = QMetaType::registerNormalizedType(lst,
QtMetaTypePrivate::QMetaTypeFunctionHelper<QQmlListProperty<QObject> >::Destruct,
QtMetaTypePrivate::QMetaTypeFunctionHelper<QQmlListProperty<QObject> >::Construct,
sizeof(QQmlListProperty<QObject>),
static_cast<QFlags<QMetaType::TypeFlag> >(QtPrivate::QMetaTypeTypeFlags<QQmlListProperty<QObject> >::Flags),
- static_cast<QMetaObject*>(0));
+ static_cast<QMetaObject*>(nullptr));
compilationUnit->metaTypeId = ptr_type;
compilationUnit->listMetaTypeId = lst_type;
@@ -1809,6 +1809,9 @@ int QQmlPrivate::qmlregister(RegistrationType type, void *data)
else
return -1;
+ if (!dtype.isValid())
+ return -1;
+
QMutexLocker lock(metaTypeDataLock());
QQmlMetaTypeData *typeData = metaTypeData();
typeData->undeletableTypes.insert(dtype);
@@ -1961,7 +1964,7 @@ QObject *QQmlMetaType::toQObject(const QVariant &v, bool *ok)
{
if (!isQObject(v.userType())) {
if (ok) *ok = false;
- return 0;
+ return nullptr;
}
if (ok) *ok = true;
@@ -2011,7 +2014,7 @@ int QQmlMetaType::attachedPropertiesFuncId(QQmlEnginePrivate *engine, const QMet
QQmlAttachedPropertiesFunc QQmlMetaType::attachedPropertiesFuncById(QQmlEnginePrivate *engine, int id)
{
if (id < 0)
- return 0;
+ return nullptr;
QMutexLocker lock(metaTypeDataLock());
QQmlMetaTypeData *data = metaTypeData();
return data->types.at(id).attachedPropertiesFunction(engine);
@@ -2104,7 +2107,7 @@ const char *QQmlMetaType::interfaceIId(int userType)
if (type.isInterface() && type.typeId() == userType)
return type.interfaceIId();
else
- return 0;
+ return nullptr;
}
bool QQmlMetaType::isList(int userType)
@@ -2397,6 +2400,27 @@ QQmlPropertyCache *QQmlMetaType::propertyCache(const QQmlType &type, int minorVe
return data->propertyCache(type, minorVersion);
}
+void qmlUnregisterType(int typeIndex)
+{
+ QMutexLocker lock(metaTypeDataLock());
+ QQmlMetaTypeData *data = metaTypeData();
+ {
+ const QQmlTypePrivate *d = data->types.value(typeIndex).priv();
+ if (d) {
+ removeQQmlTypePrivate(data->idToType, d);
+ removeQQmlTypePrivate(data->nameToType, d);
+ removeQQmlTypePrivate(data->urlToType, d);
+ removeQQmlTypePrivate(data->urlToNonFileImportType, d);
+ removeQQmlTypePrivate(data->metaObjectToType, d);
+ for (QQmlMetaTypeData::TypeModules::Iterator module = data->uriToModule.begin(); module != data->uriToModule.end(); ++module) {
+ QQmlTypeModulePrivate *modulePrivate = (*module)->priv();
+ modulePrivate->remove(d);
+ }
+ data->types[typeIndex] = QQmlType();
+ }
+ }
+}
+
void QQmlMetaType::freeUnusedTypesAndCaches()
{
QMutexLocker lock(metaTypeDataLock());
@@ -2515,16 +2539,16 @@ QList<QQmlType> QQmlMetaType::qmlSingletonTypes()
return retn;
}
-const QQmlPrivate::CachedQmlUnit *QQmlMetaType::findCachedCompilationUnit(const QUrl &uri)
+const QV4::CompiledData::Unit *QQmlMetaType::findCachedCompilationUnit(const QUrl &uri)
{
QMutexLocker lock(metaTypeDataLock());
QQmlMetaTypeData *data = metaTypeData();
for (const auto lookup : qAsConst(data->lookupCachedQmlUnit)) {
if (const QQmlPrivate::CachedQmlUnit *unit = lookup(uri))
- return unit;
+ return unit->qmlData;
}
- return 0;
+ return nullptr;
}
/*!
diff --git a/src/qml/qml/qqmlmetatype_p.h b/src/qml/qml/qqmlmetatype_p.h
index 85ee4d7b97..07bef526ba 100644
--- a/src/qml/qml/qqmlmetatype_p.h
+++ b/src/qml/qml/qqmlmetatype_p.h
@@ -75,6 +75,8 @@ class QQmlCompiledData;
namespace QV4 { struct String; }
+void Q_QML_PRIVATE_EXPORT qmlUnregisterType(int type);
+
class Q_QML_PRIVATE_EXPORT QQmlMetaType
{
public:
@@ -107,7 +109,7 @@ public:
static QMetaMethod defaultMethod(QObject *);
static bool isQObject(int);
- static QObject *toQObject(const QVariant &, bool *ok = 0);
+ static QObject *toQObject(const QVariant &, bool *ok = nullptr);
static int listType(int);
static int attachedPropertiesFuncId(QQmlEnginePrivate *engine, const QMetaObject *);
@@ -131,7 +133,7 @@ public:
static QList<QQmlPrivate::AutoParentFunction> parentFunctions();
- static const QQmlPrivate::CachedQmlUnit *findCachedCompilationUnit(const QUrl &uri);
+ static const QV4::CompiledData::Unit *findCachedCompilationUnit(const QUrl &uri);
static bool namespaceContainsRegistrations(const QString &, int majorVersion);
@@ -161,7 +163,7 @@ public:
return d == other.d;
}
- bool isValid() const { return d != 0; }
+ bool isValid() const { return d != nullptr; }
const QQmlTypePrivate *key() const { return d; }
QByteArray typeName() const;
@@ -216,7 +218,7 @@ public:
{
public:
SingletonInstanceInfo()
- : scriptCallback(0), qobjectCallback(0), instanceMetaObject(0) {}
+ : scriptCallback(nullptr), qobjectCallback(nullptr), instanceMetaObject(nullptr) {}
QJSValue (*scriptCallback)(QQmlEngine *, QJSEngine *);
QObject *(*qobjectCallback)(QQmlEngine *, QJSEngine *);
diff --git a/src/qml/qml/qqmlnotifier.cpp b/src/qml/qml/qqmlnotifier.cpp
index e068ad174a..ac247ae0ad 100644
--- a/src/qml/qml/qqmlnotifier.cpp
+++ b/src/qml/qml/qqmlnotifier.cpp
@@ -51,7 +51,7 @@ void QQmlJavaScriptExpressionGuard_callback(QQmlNotifierEndpoint *, void **);
void QQmlVMEMetaObjectEndpoint_callback(QQmlNotifierEndpoint *, void **);
static Callback QQmlNotifier_callbacks[] = {
- 0,
+ nullptr,
QQmlBoundSignal_callback,
QQmlJavaScriptExpressionGuard_callback,
QQmlVMEMetaObjectEndpoint_callback
@@ -59,9 +59,9 @@ static Callback QQmlNotifier_callbacks[] = {
namespace {
struct NotifyListTraversalData {
- NotifyListTraversalData(QQmlNotifierEndpoint *ep = 0)
+ NotifyListTraversalData(QQmlNotifierEndpoint *ep = nullptr)
: originalSenderPtr(0)
- , disconnectWatch(0)
+ , disconnectWatch(nullptr)
, endpoint(ep)
{}
diff --git a/src/qml/qml/qqmlnotifier_p.h b/src/qml/qml/qqmlnotifier_p.h
index a99b13f155..d77e314de5 100644
--- a/src/qml/qml/qqmlnotifier_p.h
+++ b/src/qml/qml/qqmlnotifier_p.h
@@ -73,7 +73,7 @@ private:
friend class QQmlThreadNotifierProxyObject;
static void emitNotify(QQmlNotifierEndpoint *, void **a);
- QQmlNotifierEndpoint *endpoints;
+ QQmlNotifierEndpoint *endpoints = nullptr;
};
class QQmlEngine;
@@ -129,7 +129,6 @@ private:
};
QQmlNotifier::QQmlNotifier()
-: endpoints(0)
{
}
@@ -142,22 +141,22 @@ QQmlNotifier::~QQmlNotifier()
if (n->isNotifying()) *((qintptr *)(n->senderPtr & ~0x1)) = 0;
- n->next = 0;
- n->prev = 0;
+ n->next = nullptr;
+ n->prev = nullptr;
n->senderPtr = 0;
n->sourceSignal = -1;
}
- endpoints = 0;
+ endpoints = nullptr;
}
void QQmlNotifier::notify()
{
- void *args[] = { 0 };
+ void *args[] = { nullptr };
if (endpoints) emitNotify(endpoints, args);
}
QQmlNotifierEndpoint::QQmlNotifierEndpoint(Callback callback)
-: next(0), prev(0), senderPtr(0), callback(callback), needsConnectNotify(false), sourceSignal(-1)
+: next(nullptr), prev(nullptr), senderPtr(0), callback(callback), needsConnectNotify(false), sourceSignal(-1)
{
}
@@ -168,7 +167,7 @@ QQmlNotifierEndpoint::~QQmlNotifierEndpoint()
bool QQmlNotifierEndpoint::isConnected() const
{
- return prev != 0;
+ return prev != nullptr;
}
/*! \internal
@@ -212,8 +211,8 @@ void QQmlNotifierEndpoint::disconnect()
}
if (isNotifying()) *((qintptr *)(senderPtr & ~0x1)) = 0;
- next = 0;
- prev = 0;
+ next = nullptr;
+ prev = nullptr;
senderPtr = 0;
sourceSignal = -1;
}
diff --git a/src/qml/qml/qqmlobjectcreator.cpp b/src/qml/qml/qqmlobjectcreator.cpp
index d009536767..36e56a01f8 100644
--- a/src/qml/qml/qqmlobjectcreator.cpp
+++ b/src/qml/qml/qqmlobjectcreator.cpp
@@ -82,13 +82,13 @@ QQmlObjectCreator::QQmlObjectCreator(QQmlContextData *parentContext, QV4::Compil
{
init(parentContext);
- sharedState->componentAttached = 0;
+ sharedState->componentAttached = nullptr;
sharedState->allCreatedBindings.allocate(compilationUnit->totalBindingsCount);
sharedState->allParserStatusCallbacks.allocate(compilationUnit->totalParserStatusCount);
sharedState->allCreatedObjects.allocate(compilationUnit->totalObjectCount);
- sharedState->allJavaScriptObjects = 0;
+ sharedState->allJavaScriptObjects = nullptr;
sharedState->creationContext = creationContext;
- sharedState->rootContext = 0;
+ sharedState->rootContext = nullptr;
if (auto profiler = QQmlEnginePrivate::get(engine)->profiler) {
Q_QML_PROFILE_IF_ENABLED(QQmlProfilerDefinitions::ProfileCreating, profiler,
@@ -105,7 +105,7 @@ QQmlObjectCreator::QQmlObjectCreator(QQmlContextData *parentContext, QV4::Compil
, propertyCaches(&compilationUnit->propertyCaches)
, sharedState(inheritedSharedState)
, topLevelCreator(false)
- , incubator(0)
+ , incubator(nullptr)
{
init(parentContext);
}
@@ -114,23 +114,23 @@ void QQmlObjectCreator::init(QQmlContextData *providedParentContext)
{
parentContext = providedParentContext;
engine = parentContext->engine;
- v4 = QV8Engine::getV4(engine);
+ v4 = engine->handle();
if (compilationUnit && !compilationUnit->engine)
compilationUnit->linkToEngine(v4);
qmlUnit = compilationUnit->data;
- context = 0;
- _qobject = 0;
- _scopeObject = 0;
- _bindingTarget = 0;
- _valueTypeProperty = 0;
- _compiledObject = 0;
+ context = nullptr;
+ _qobject = nullptr;
+ _scopeObject = nullptr;
+ _bindingTarget = nullptr;
+ _valueTypeProperty = nullptr;
+ _compiledObject = nullptr;
_compiledObjectIndex = -1;
- _ddata = 0;
- _propertyCache = 0;
- _vmeMetaObject = 0;
- _qmlContext = 0;
+ _ddata = nullptr;
+ _propertyCache = nullptr;
+ _vmeMetaObject = nullptr;
+ _qmlContext = nullptr;
}
QQmlObjectCreator::~QQmlObjectCreator()
@@ -142,7 +142,7 @@ QQmlObjectCreator::~QQmlObjectCreator()
for (int i = 0; i < sharedState->allParserStatusCallbacks.count(); ++i) {
QQmlParserStatus *ps = sharedState->allParserStatusCallbacks.at(i);
if (ps)
- ps->d = 0;
+ ps->d = nullptr;
}
while (sharedState->componentAttached) {
QQmlComponentAttached *a = sharedState->componentAttached;
@@ -203,19 +203,16 @@ QObject *QQmlObjectCreator::create(int subComponentIndex, QObject *parent, QQmlI
if (instance) {
QQmlData *ddata = QQmlData::get(instance);
Q_ASSERT(ddata);
- if (ddata->compilationUnit)
- ddata->compilationUnit->release();
ddata->compilationUnit = compilationUnit;
- ddata->compilationUnit->addref();
}
if (topLevelCreator)
- sharedState->allJavaScriptObjects = 0;
+ sharedState->allJavaScriptObjects = nullptr;
phase = CreatingObjectsPhase2;
if (interrupt && interrupt->shouldInterrupt())
- return 0;
+ return nullptr;
phase = ObjectsCreated;
@@ -233,6 +230,7 @@ QObject *QQmlObjectCreator::create(int subComponentIndex, QObject *parent, QQmlI
return instance;
}
+// ### unify or keep in sync with populateDeferredBinding()
bool QQmlObjectCreator::populateDeferredProperties(QObject *instance, QQmlData::DeferredData *deferredData)
{
QQmlData *declarativeData = QQmlData::get(instance);
@@ -283,6 +281,80 @@ bool QQmlObjectCreator::populateDeferredProperties(QObject *instance, QQmlData::
qSwap(_qmlContext, qmlContext);
qSwap(_scopeObject, scopeObject);
+ deferredData->bindings.clear();
+ phase = ObjectsCreated;
+
+ return errors.isEmpty();
+}
+
+// ### unify or keep in sync with populateDeferredProperties()
+bool QQmlObjectCreator::populateDeferredBinding(const QQmlProperty &qmlProperty, QQmlData::DeferredData *deferredData, const QV4::CompiledData::Binding *binding)
+{
+ Q_ASSERT(binding->flags & QV4::CompiledData::Binding::IsDeferredBinding);
+
+ QObject *instance = qmlProperty.object();
+ QQmlData *declarativeData = QQmlData::get(instance);
+ context = deferredData->context;
+ sharedState->rootContext = context;
+
+ QObject *bindingTarget = instance;
+
+ QQmlRefPointer<QQmlPropertyCache> cache = declarativeData->propertyCache;
+ QQmlVMEMetaObject *vmeMetaObject = QQmlVMEMetaObject::get(instance);
+
+ QObject *scopeObject = instance;
+ qSwap(_scopeObject, scopeObject);
+
+ QV4::Scope valueScope(v4);
+
+ Q_ASSERT(topLevelCreator);
+ if (!sharedState->allJavaScriptObjects)
+ sharedState->allJavaScriptObjects = valueScope.alloc(compilationUnit->totalObjectCount);
+
+ QV4::QmlContext *qmlContext = static_cast<QV4::QmlContext *>(valueScope.alloc(1));
+
+ qSwap(_qmlContext, qmlContext);
+
+ qSwap(_propertyCache, cache);
+ qSwap(_qobject, instance);
+
+ int objectIndex = deferredData->deferredIdx;
+ qSwap(_compiledObjectIndex, objectIndex);
+
+ const QV4::CompiledData::Object *obj = qmlUnit->objectAt(_compiledObjectIndex);
+ qSwap(_compiledObject, obj);
+
+ qSwap(_ddata, declarativeData);
+ qSwap(_bindingTarget, bindingTarget);
+ qSwap(_vmeMetaObject, vmeMetaObject);
+
+ QQmlListProperty<void> savedList;
+ qSwap(_currentList, savedList);
+
+ const QQmlPropertyData &property = QQmlPropertyPrivate::get(qmlProperty)->core;
+
+ if (property.isQList()) {
+ void *argv[1] = { (void*)&_currentList };
+ QMetaObject::metacall(_qobject, QMetaObject::ReadProperty, property.coreIndex(), argv);
+ } else if (_currentList.object) {
+ _currentList = QQmlListProperty<void>();
+ }
+
+ setPropertyBinding(&property, binding);
+
+ qSwap(_currentList, savedList);
+
+ qSwap(_vmeMetaObject, vmeMetaObject);
+ qSwap(_bindingTarget, bindingTarget);
+ qSwap(_ddata, declarativeData);
+ qSwap(_compiledObject, obj);
+ qSwap(_compiledObjectIndex, objectIndex);
+ qSwap(_qobject, instance);
+ qSwap(_propertyCache, cache);
+
+ qSwap(_qmlContext, qmlContext);
+ qSwap(_scopeObject, scopeObject);
+
phase = ObjectsCreated;
return errors.isEmpty();
@@ -370,7 +442,7 @@ void QQmlObjectCreator::setPropertyValue(const QQmlPropertyData *property, const
QString string = binding->valueAsString(qmlUnit);
// Encoded dir-separators defeat QUrl processing - decode them first
string.replace(QLatin1String("%2f"), QLatin1String("/"), Qt::CaseInsensitive);
- QUrl value = string.isEmpty() ? QUrl() : compilationUnit->url().resolved(QUrl(string));
+ QUrl value = string.isEmpty() ? QUrl() : compilationUnit->finalUrl().resolved(QUrl(string));
// Apply URL interceptor
if (engine->urlInterceptor())
value = engine->urlInterceptor()->intercept(value, QQmlAbstractUrlInterceptor::UrlString);
@@ -568,7 +640,8 @@ void QQmlObjectCreator::setPropertyValue(const QQmlPropertyData *property, const
} else if (property->propType() == qMetaTypeId<QList<QUrl> >()) {
Q_ASSERT(binding->type == QV4::CompiledData::Binding::Type_String);
QString urlString = binding->valueAsString(qmlUnit);
- QUrl u = urlString.isEmpty() ? QUrl() : compilationUnit->url().resolved(QUrl(urlString));
+ QUrl u = urlString.isEmpty() ? QUrl()
+ : compilationUnit->finalUrl().resolved(QUrl(urlString));
QList<QUrl> value;
value.append(u);
property->writeProperty(_qobject, &value, propertyWriteFlags);
@@ -723,7 +796,7 @@ bool QQmlObjectCreator::setPropertyBinding(const QQmlPropertyData *property, con
}
const int id = attachedType.attachedPropertiesId(QQmlEnginePrivate::get(engine));
QObject *qmlObject = qmlAttachedPropertiesObjectById(id, _qobject);
- if (!populateInstance(binding->value.objectIndex, qmlObject, qmlObject, /*value type property*/0))
+ if (!populateInstance(binding->value.objectIndex, qmlObject, qmlObject, /*value type property*/nullptr))
return false;
return true;
}
@@ -741,12 +814,12 @@ bool QQmlObjectCreator::setPropertyBinding(const QQmlPropertyData *property, con
QQmlPropertyData::WriteFlags propertyWriteFlags = QQmlPropertyData::BypassInterceptor |
QQmlPropertyData::RemoveBindingOnAliasWrite;
int propertyWriteStatus = -1;
- void *argv[] = { &ss, 0, &propertyWriteStatus, &propertyWriteFlags };
+ void *argv[] = { &ss, nullptr, &propertyWriteStatus, &propertyWriteFlags };
QMetaObject::metacall(_qobject, QMetaObject::WriteProperty, property->coreIndex(), argv);
return true;
}
- QObject *createdSubObject = 0;
+ QObject *createdSubObject = nullptr;
if (binding->type == QV4::CompiledData::Binding::Type_Object) {
createdSubObject = createInstance(binding->value.objectIndex, _bindingTarget);
if (!createdSubObject)
@@ -760,9 +833,9 @@ bool QQmlObjectCreator::setPropertyBinding(const QQmlPropertyData *property, con
const QV4::CompiledData::Object *obj = qmlUnit->objectAt(binding->value.objectIndex);
if (stringAt(obj->inheritedTypeNameIndex).isEmpty()) {
- QObject *groupObject = 0;
- QQmlValueType *valueType = 0;
- const QQmlPropertyData *valueTypeProperty = 0;
+ QObject *groupObject = nullptr;
+ QQmlValueType *valueType = nullptr;
+ const QQmlPropertyData *valueTypeProperty = nullptr;
QObject *bindingTarget = _bindingTarget;
if (QQmlValueTypeFactory::isValueType(property->propType())) {
@@ -935,7 +1008,7 @@ bool QQmlObjectCreator::setPropertyBinding(const QQmlPropertyData *property, con
QQmlPropertyData::WriteFlags propertyWriteFlags = QQmlPropertyData::BypassInterceptor |
QQmlPropertyData::RemoveBindingOnAliasWrite;
int propertyWriteStatus = -1;
- void *argv[] = { 0, 0, &propertyWriteStatus, &propertyWriteFlags };
+ void *argv[] = { nullptr, nullptr, &propertyWriteStatus, &propertyWriteFlags };
if (const char *iid = QQmlMetaType::interfaceIId(property->propType())) {
void *ptr = createdSubObject->qt_metacast(iid);
@@ -949,7 +1022,7 @@ bool QQmlObjectCreator::setPropertyBinding(const QQmlPropertyData *property, con
} else if (property->propType() == QMetaType::QVariant) {
if (property->isVarProperty()) {
QV4::Scope scope(v4);
- QV4::ScopedValue wrappedObject(scope, QV4::QObjectWrapper::wrap(QV8Engine::getV4(engine), createdSubObject));
+ QV4::ScopedValue wrappedObject(scope, QV4::QObjectWrapper::wrap(engine->handle(), createdSubObject));
_vmeMetaObject->setVMEProperty(property->coreIndex(), wrappedObject);
} else {
QVariant value = QVariant::fromValue(createdSubObject);
@@ -961,7 +1034,7 @@ bool QQmlObjectCreator::setPropertyBinding(const QQmlPropertyData *property, con
void *itemToAdd = createdSubObject;
- const char *iid = 0;
+ const char *iid = nullptr;
int listItemType = QQmlEnginePrivate::get(engine)->listType(property->propType());
if (listItemType != -1)
iid = QQmlMetaType::interfaceIId(listItemType);
@@ -1028,12 +1101,9 @@ void QQmlObjectCreator::registerObjectWithContextById(const QV4::CompiledData::O
context->setIdProperty(object->id, instance);
}
-QV4::QmlContext *QQmlObjectCreator::currentQmlContext()
+void QQmlObjectCreator::createQmlContext()
{
- if (!_qmlContext->isManaged())
- _qmlContext->setM(QV4::QmlContext::create(v4->rootContext(), context, _scopeObject));
-
- return _qmlContext;
+ _qmlContext->setM(QV4::QmlContext::create(v4->rootContext(), context, _scopeObject));
}
QObject *QQmlObjectCreator::createInstance(int index, QObject *parent, bool isContextObject)
@@ -1044,10 +1114,10 @@ QObject *QQmlObjectCreator::createInstance(int index, QObject *parent, bool isCo
ActiveOCRestorer ocRestorer(this, QQmlEnginePrivate::get(engine));
bool isComponent = false;
- QObject *instance = 0;
- QQmlData *ddata = 0;
- QQmlCustomParser *customParser = 0;
- QQmlParserStatus *parserStatus = 0;
+ QObject *instance = nullptr;
+ QQmlData *ddata = nullptr;
+ QQmlCustomParser *customParser = nullptr;
+ QQmlParserStatus *parserStatus = nullptr;
bool installPropertyCache = true;
if (obj->flags & QV4::CompiledData::Object::IsComponent) {
@@ -1067,11 +1137,11 @@ QObject *QQmlObjectCreator::createInstance(int index, QObject *parent, bool isCo
Q_QML_OC_PROFILE(sharedState->profiler, profiler.update(
compilationUnit, obj, type.qmlTypeName(), context->url()));
- void *ddataMemory = 0;
+ void *ddataMemory = nullptr;
type.create(&instance, &ddataMemory, sizeof(QQmlData));
if (!instance) {
recordError(obj->location, tr("Unable to create object of type %1").arg(stringAt(obj->inheritedTypeNameIndex)));
- return 0;
+ return nullptr;
}
{
@@ -1103,14 +1173,14 @@ QObject *QQmlObjectCreator::createInstance(int index, QObject *parent, bool isCo
if (typeRef->compilationUnit->data->isSingleton())
{
recordError(obj->location, tr("Composite Singleton Type %1 is not creatable").arg(stringAt(obj->inheritedTypeNameIndex)));
- return 0;
+ return nullptr;
}
QQmlObjectCreator subCreator(context, typeRef->compilationUnit, sharedState.data());
instance = subCreator.create();
if (!instance) {
errors += subCreator.errors;
- return 0;
+ return nullptr;
}
}
if (instance->isWidgetType()) {
@@ -1174,8 +1244,8 @@ QObject *QQmlObjectCreator::createInstance(int index, QObject *parent, bool isCo
}
customParser->applyBindings(instance, compilationUnit, bindings);
- customParser->engine = 0;
- customParser->imports = (QQmlTypeNameCache*)0;
+ customParser->engine = nullptr;
+ customParser->imports = (QQmlTypeNameCache*)nullptr;
}
if (isComponent) {
@@ -1204,12 +1274,12 @@ QObject *QQmlObjectCreator::createInstance(int index, QObject *parent, bool isCo
qSwap(_qmlContext, qmlContext);
- bool result = populateInstance(index, instance, /*binding target*/instance, /*value type property*/0);
+ bool result = populateInstance(index, instance, /*binding target*/instance, /*value type property*/nullptr);
qSwap(_qmlContext, qmlContext);
qSwap(_scopeObject, scopeObject);
- return result ? instance : 0;
+ return result ? instance : nullptr;
}
QQmlContextData *QQmlObjectCreator::finalize(QQmlInstantiationInterrupt &interrupt)
@@ -1233,7 +1303,7 @@ QQmlContextData *QQmlObjectCreator::finalize(QQmlInstantiationInterrupt &interru
QQmlPropertyData::DontRemoveBinding);
if (watcher.hasRecursed() || interrupt.shouldInterrupt())
- return 0;
+ return nullptr;
}
if (QQmlVME::componentCompleteEnabled()) { // the qml designer does the component complete later
@@ -1242,12 +1312,12 @@ QQmlContextData *QQmlObjectCreator::finalize(QQmlInstantiationInterrupt &interru
QQmlParserStatus *status = sharedState->allParserStatusCallbacks.pop();
if (status && status->d) {
- status->d = 0;
+ status->d = nullptr;
status->componentComplete();
}
if (watcher.hasRecursed() || interrupt.shouldInterrupt())
- return 0;
+ return nullptr;
}
}
@@ -1255,11 +1325,11 @@ QQmlContextData *QQmlObjectCreator::finalize(QQmlInstantiationInterrupt &interru
QQmlEnginePrivate::FinalizeCallback callback = sharedState->finalizeCallbacks.at(ii);
QObject *obj = callback.first;
if (obj) {
- void *args[] = { 0 };
+ void *args[] = { nullptr };
QMetaObject::metacall(obj, QMetaObject::InvokeMetaMethod, callback.second, args);
}
if (watcher.hasRecursed())
- return 0;
+ return nullptr;
}
sharedState->finalizeCallbacks.clear();
@@ -1274,7 +1344,7 @@ QQmlContextData *QQmlObjectCreator::finalize(QQmlInstantiationInterrupt &interru
emit a->completed();
if (watcher.hasRecursed() || interrupt.shouldInterrupt())
- return 0;
+ return nullptr;
}
phase = Done;
@@ -1282,21 +1352,6 @@ QQmlContextData *QQmlObjectCreator::finalize(QQmlInstantiationInterrupt &interru
return sharedState->rootContext;
}
-void QQmlObjectCreator::cancel(QObject *object)
-{
- int last = sharedState->allCreatedObjects.count() - 1;
- int i = last;
- while (i >= 0) {
- if (sharedState->allCreatedObjects.at(i) == object) {
- if (i < last)
- qSwap(sharedState->allCreatedObjects[i], sharedState->allCreatedObjects[last]);
- sharedState->allCreatedObjects.pop();
- break;
- }
- --i;
- }
-}
-
void QQmlObjectCreator::clear()
{
if (phase == Done || phase == Finalizing || phase == Startup)
@@ -1331,7 +1386,7 @@ bool QQmlObjectCreator::populateInstance(int index, QObject *instance, QObject *
QQmlRefPointer<QQmlPropertyCache> cache = propertyCaches->at(_compiledObjectIndex);
- QQmlVMEMetaObject *vmeMetaObject = 0;
+ QQmlVMEMetaObject *vmeMetaObject = nullptr;
if (propertyCaches->needsVMEMetaObject(_compiledObjectIndex)) {
Q_ASSERT(!cache.isNull());
// install on _object
@@ -1350,14 +1405,8 @@ bool QQmlObjectCreator::populateInstance(int index, QObject *instance, QObject *
qSwap(_propertyCache, cache);
qSwap(_vmeMetaObject, vmeMetaObject);
- if (_compiledObject->flags & QV4::CompiledData::Object::HasDeferredBindings) {
- QQmlData::DeferredData *deferData = new QQmlData::DeferredData;
- deferData->deferredIdx = _compiledObjectIndex;
- deferData->compilationUnit = compilationUnit;
- deferData->compilationUnit->addref();
- deferData->context = context;
- _ddata->deferredData.append(deferData);
- }
+ if (_compiledObject->flags & QV4::CompiledData::Object::HasDeferredBindings)
+ _ddata->deferData(_compiledObjectIndex, compilationUnit, context);
if (_compiledObject->nFunctions > 0)
setupFunctions();
diff --git a/src/qml/qml/qqmlobjectcreator_p.h b/src/qml/qml/qqmlobjectcreator_p.h
index aa0165ec06..399a5f6d4a 100644
--- a/src/qml/qml/qqmlobjectcreator_p.h
+++ b/src/qml/qml/qqmlobjectcreator_p.h
@@ -81,17 +81,17 @@ struct QQmlObjectCreatorSharedState : public QSharedData
QRecursionNode recursionNode;
};
-class QQmlObjectCreator
+class Q_QML_PRIVATE_EXPORT QQmlObjectCreator
{
Q_DECLARE_TR_FUNCTIONS(QQmlObjectCreator)
public:
- QQmlObjectCreator(QQmlContextData *parentContext, QV4::CompiledData::CompilationUnit *compilationUnit, QQmlContextData *creationContext, QQmlIncubatorPrivate *incubator = 0);
+ QQmlObjectCreator(QQmlContextData *parentContext, QV4::CompiledData::CompilationUnit *compilationUnit, QQmlContextData *creationContext, QQmlIncubatorPrivate *incubator = nullptr);
~QQmlObjectCreator();
- QObject *create(int subComponentIndex = -1, QObject *parent = 0, QQmlInstantiationInterrupt *interrupt = 0);
+ QObject *create(int subComponentIndex = -1, QObject *parent = nullptr, QQmlInstantiationInterrupt *interrupt = nullptr);
bool populateDeferredProperties(QObject *instance, QQmlData::DeferredData *deferredData);
+ bool populateDeferredBinding(const QQmlProperty &qmlProperty, QQmlData::DeferredData *deferredData, const QV4::CompiledData::Binding *binding);
QQmlContextData *finalize(QQmlInstantiationInterrupt &interrupt);
- void cancel(QObject *object);
void clear();
QQmlComponentAttached **componentAttachment() const { return &sharedState->componentAttached; }
@@ -108,7 +108,7 @@ private:
void init(QQmlContextData *parentContext);
- QObject *createInstance(int index, QObject *parent = 0, bool isContextObject = false);
+ QObject *createInstance(int index, QObject *parent = nullptr, bool isContextObject = false);
bool populateInstance(int index, QObject *instance,
QObject *bindingTarget, const QQmlPropertyData *valueTypeProperty);
@@ -123,7 +123,8 @@ private:
void registerObjectWithContextById(const QV4::CompiledData::Object *object, QObject *instance) const;
- QV4::QmlContext *currentQmlContext();
+ inline QV4::QmlContext *currentQmlContext();
+ Q_NEVER_INLINE void createQmlContext();
enum Phase {
Startup,
@@ -136,7 +137,7 @@ private:
QQmlEngine *engine;
QV4::ExecutionEngine *v4;
- QV4::CompiledData::CompilationUnit *compilationUnit;
+ QQmlRefPointer<QV4::CompiledData::CompilationUnit> compilationUnit;
const QV4::CompiledData::Unit *qmlUnit;
QQmlGuardedContextData parentContext;
QQmlContextData *context;
@@ -173,6 +174,14 @@ private:
QRecursionWatcher<QQmlObjectCreatorSharedState, &QQmlObjectCreatorSharedState::recursionNode> watcher;
};
+QV4::QmlContext *QQmlObjectCreator::currentQmlContext()
+{
+ if (!_qmlContext->isManaged())
+ _qmlContext->setM(QV4::QmlContext::create(v4->rootContext(), context, _scopeObject));
+
+ return _qmlContext;
+}
+
QT_END_NAMESPACE
#endif // QQMLOBJECTCREATOR_P_H
diff --git a/src/qml/qml/qqmlopenmetaobject.cpp b/src/qml/qml/qqmlopenmetaobject.cpp
index fc85030b3d..1b44bbdda3 100644
--- a/src/qml/qml/qqmlopenmetaobject.cpp
+++ b/src/qml/qml/qqmlopenmetaobject.cpp
@@ -51,7 +51,7 @@ QT_BEGIN_NAMESPACE
class QQmlOpenMetaObjectTypePrivate
{
public:
- QQmlOpenMetaObjectTypePrivate() : mem(0), cache(0), engine(0) {}
+ QQmlOpenMetaObjectTypePrivate() : mem(nullptr), cache(nullptr), engine(nullptr) {}
void init(const QMetaObject *metaObj);
@@ -83,7 +83,7 @@ QQmlOpenMetaObjectType::~QQmlOpenMetaObjectType()
void QQmlOpenMetaObjectType::clear()
{
- d->engine = 0;
+ d->engine = nullptr;
}
int QQmlOpenMetaObjectType::propertyOffset() const
@@ -182,7 +182,7 @@ class QQmlOpenMetaObjectPrivate
{
public:
QQmlOpenMetaObjectPrivate(QQmlOpenMetaObject *_q)
- : q(_q), parent(0), type(0), cacheProperties(false) {}
+ : q(_q), parent(nullptr), type(nullptr), cacheProperties(false) {}
inline QPair<QVariant, bool> &getDataRef(int idx) {
while (data.count() <= idx)
@@ -220,7 +220,7 @@ QQmlOpenMetaObject::QQmlOpenMetaObject(QObject *obj, const QMetaObject *base, bo
d->autoCreate = automatic;
d->object = obj;
- d->type = new QQmlOpenMetaObjectType(base ? base : obj->metaObject(), 0);
+ d->type = new QQmlOpenMetaObjectType(base ? base : obj->metaObject(), nullptr);
d->type->d->referers.insert(this);
QObjectPrivate *op = QObjectPrivate::get(obj);
@@ -264,7 +264,7 @@ void QQmlOpenMetaObject::emitPropertyNotification(const QByteArray &propertyName
QHash<QByteArray, int>::ConstIterator iter = d->type->d->names.constFind(propertyName);
if (iter == d->type->d->names.constEnd())
return;
- activate(d->object, *iter + d->type->d->signalOffset, 0);
+ activate(d->object, *iter + d->type->d->signalOffset, nullptr);
}
int QQmlOpenMetaObject::metaCall(QObject *o, QMetaObject::Call c, int id, void **a)
@@ -284,7 +284,7 @@ int QQmlOpenMetaObject::metaCall(QObject *o, QMetaObject::Call c, int id, void *
prop.first = propertyWriteValue(propId, *reinterpret_cast<QVariant *>(a[0]));
prop.second = true;
propertyWritten(propId);
- activate(o, d->type->d->signalOffset + propId, 0);
+ activate(o, d->type->d->signalOffset + propId, nullptr);
}
}
return -1;
@@ -311,7 +311,7 @@ void QQmlOpenMetaObject::setValue(int id, const QVariant &value)
QPair<QVariant, bool> &prop = d->getDataRef(id);
prop.first = propertyWriteValue(id, value);
prop.second = true;
- activate(d->object, id + d->type->d->signalOffset, 0);
+ activate(d->object, id + d->type->d->signalOffset, nullptr);
}
QVariant QQmlOpenMetaObject::value(const QByteArray &name) const
@@ -353,7 +353,7 @@ bool QQmlOpenMetaObject::setValue(const QByteArray &name, const QVariant &val)
return false;
dataVal = val;
- activate(d->object, id + d->type->d->signalOffset, 0);
+ activate(d->object, id + d->type->d->signalOffset, nullptr);
return true;
}
@@ -382,7 +382,7 @@ void QQmlOpenMetaObject::setCached(bool c)
} else {
if (d->type->d->cache)
d->type->d->cache->release();
- qmldata->propertyCache = 0;
+ qmldata->propertyCache = nullptr;
}
}
@@ -395,7 +395,7 @@ int QQmlOpenMetaObject::createProperty(const char *name, const char *)
if (QQmlData *ddata = QQmlData::get(d->object, /*create*/false)) {
if (ddata->propertyCache) {
ddata->propertyCache->release();
- ddata->propertyCache = 0;
+ ddata->propertyCache = nullptr;
}
}
diff --git a/src/qml/qml/qqmlopenmetaobject_p.h b/src/qml/qml/qqmlopenmetaobject_p.h
index 4bb92489a5..4905190b75 100644
--- a/src/qml/qml/qqmlopenmetaobject_p.h
+++ b/src/qml/qml/qqmlopenmetaobject_p.h
@@ -69,7 +69,7 @@ class Q_QML_PRIVATE_EXPORT QQmlOpenMetaObjectType : public QQmlRefCount, public
{
public:
QQmlOpenMetaObjectType(const QMetaObject *base, QQmlEngine *engine);
- ~QQmlOpenMetaObjectType();
+ ~QQmlOpenMetaObjectType() override;
void createProperties(const QVector<QByteArray> &names);
int createProperty(const QByteArray &name);
@@ -95,9 +95,9 @@ class QQmlOpenMetaObjectPrivate;
class Q_QML_PRIVATE_EXPORT QQmlOpenMetaObject : public QAbstractDynamicMetaObject
{
public:
- QQmlOpenMetaObject(QObject *, const QMetaObject * = 0, bool = true);
+ QQmlOpenMetaObject(QObject *, const QMetaObject * = nullptr, bool = true);
QQmlOpenMetaObject(QObject *, QQmlOpenMetaObjectType *, bool = true);
- ~QQmlOpenMetaObject();
+ ~QQmlOpenMetaObject() override;
QVariant value(const QByteArray &) const;
bool setValue(const QByteArray &, const QVariant &);
diff --git a/src/qml/qml/qqmlparserstatus.cpp b/src/qml/qml/qqmlparserstatus.cpp
index ad07cac7ef..1082c318cb 100644
--- a/src/qml/qml/qqmlparserstatus.cpp
+++ b/src/qml/qml/qqmlparserstatus.cpp
@@ -87,7 +87,7 @@ QT_BEGIN_NAMESPACE
/*! \internal */
QQmlParserStatus::QQmlParserStatus()
-: d(0)
+: d(nullptr)
{
}
@@ -95,7 +95,7 @@ QQmlParserStatus::QQmlParserStatus()
QQmlParserStatus::~QQmlParserStatus()
{
if(d)
- (*d) = 0;
+ (*d) = nullptr;
}
/*!
diff --git a/src/qml/qml/qqmlplatform_p.h b/src/qml/qml/qqmlplatform_p.h
index 6246ca7105..af33dffca3 100644
--- a/src/qml/qml/qqmlplatform_p.h
+++ b/src/qml/qml/qqmlplatform_p.h
@@ -64,7 +64,7 @@ class Q_QML_PRIVATE_EXPORT QQmlPlatform : public QObject
Q_PROPERTY(QString pluginName READ pluginName CONSTANT)
public:
- explicit QQmlPlatform(QObject *parent = 0);
+ explicit QQmlPlatform(QObject *parent = nullptr);
virtual ~QQmlPlatform();
static QString os();
diff --git a/src/qml/qml/qqmlprivate.h b/src/qml/qml/qqmlprivate.h
index eeb5b4c302..fabdcacc36 100644
--- a/src/qml/qml/qqmlprivate.h
+++ b/src/qml/qml/qqmlprivate.h
@@ -69,7 +69,6 @@ namespace CompiledData {
struct Unit;
struct CompilationUnit;
}
-typedef CompiledData::CompilationUnit *(*CompilationUnitFactoryFunction)();
}
namespace QmlIR {
struct Document;
@@ -99,7 +98,7 @@ namespace QQmlPrivate
class QQmlElement : public T
{
public:
- virtual ~QQmlElement() {
+ ~QQmlElement() override {
QQmlPrivate::qdeclarativeelement_destructor(this);
}
};
@@ -168,8 +167,8 @@ namespace QQmlPrivate
class AttachedPropertySelector
{
public:
- static inline QQmlAttachedPropertiesFunc func() { return 0; }
- static inline const QMetaObject *metaObject() { return 0; }
+ static inline QQmlAttachedPropertiesFunc func() { return nullptr; }
+ static inline const QMetaObject *metaObject() { return nullptr; }
};
template<typename T>
class AttachedPropertySelector<T, 1>
@@ -284,8 +283,8 @@ namespace QQmlPrivate
struct CachedQmlUnit {
const QV4::CompiledData::Unit *qmlData;
- QV4::CompilationUnitFactoryFunction createCompilationUnit;
- QmlIR::IRLoaderFunction loadIR;
+ void *unused1;
+ void *unused2;
};
typedef const CachedQmlUnit *(*QmlUnitCacheLookupFunction)(const QUrl &url);
diff --git a/src/qml/qml/qqmlproperty.cpp b/src/qml/qml/qqmlproperty.cpp
index 9a138dcf80..ebf296b29d 100644
--- a/src/qml/qml/qqmlproperty.cpp
+++ b/src/qml/qml/qqmlproperty.cpp
@@ -119,7 +119,7 @@ The \l {Qt Quick 1} version of this class was named QDeclarativeProperty.
Create an invalid QQmlProperty.
*/
QQmlProperty::QQmlProperty()
-: d(0)
+: d(nullptr)
{
}
@@ -128,7 +128,7 @@ QQmlProperty::~QQmlProperty()
{
if (d)
d->release();
- d = 0;
+ d = nullptr;
}
/*!
@@ -150,8 +150,8 @@ QQmlProperty::QQmlProperty(QObject *obj)
QQmlProperty::QQmlProperty(QObject *obj, QQmlContext *ctxt)
: d(new QQmlPropertyPrivate)
{
- d->context = ctxt?QQmlContextData::get(ctxt):0;
- d->engine = ctxt?ctxt->engine():0;
+ d->context = ctxt?QQmlContextData::get(ctxt):nullptr;
+ d->engine = ctxt?ctxt->engine():nullptr;
d->initDefault(obj);
}
@@ -164,7 +164,7 @@ QQmlProperty::QQmlProperty(QObject *obj, QQmlContext *ctxt)
QQmlProperty::QQmlProperty(QObject *obj, QQmlEngine *engine)
: d(new QQmlPropertyPrivate)
{
- d->context = 0;
+ d->context = nullptr;
d->engine = engine;
d->initDefault(obj);
}
@@ -190,7 +190,7 @@ QQmlProperty::QQmlProperty(QObject *obj, const QString &name)
: d(new QQmlPropertyPrivate)
{
d->initProperty(obj, name);
- if (!isValid()) d->object = 0;
+ if (!isValid()) d->object = nullptr;
}
/*!
@@ -203,10 +203,10 @@ QQmlProperty::QQmlProperty(QObject *obj, const QString &name)
QQmlProperty::QQmlProperty(QObject *obj, const QString &name, QQmlContext *ctxt)
: d(new QQmlPropertyPrivate)
{
- d->context = ctxt?QQmlContextData::get(ctxt):0;
- d->engine = ctxt?ctxt->engine():0;
+ d->context = ctxt?QQmlContextData::get(ctxt):nullptr;
+ d->engine = ctxt?ctxt->engine():nullptr;
d->initProperty(obj, name);
- if (!isValid()) { d->object = 0; d->context = 0; d->engine = 0; }
+ if (!isValid()) { d->object = nullptr; d->context = nullptr; d->engine = nullptr; }
}
/*!
@@ -217,14 +217,30 @@ QQmlProperty::QQmlProperty(QObject *obj, const QString &name, QQmlContext *ctxt)
QQmlProperty::QQmlProperty(QObject *obj, const QString &name, QQmlEngine *engine)
: d(new QQmlPropertyPrivate)
{
- d->context = 0;
+ d->context = nullptr;
d->engine = engine;
d->initProperty(obj, name);
- if (!isValid()) { d->object = 0; d->context = 0; d->engine = 0; }
+ if (!isValid()) { d->object = nullptr; d->context = nullptr; d->engine = nullptr; }
+}
+
+QQmlProperty QQmlPropertyPrivate::create(QObject *target, const QString &propertyName, QQmlContextData *context)
+{
+ QQmlProperty result;
+ auto d = new QQmlPropertyPrivate;
+ result.d = d;
+ d->context = context;
+ d->engine = context ? context->engine : nullptr;
+ d->initProperty(target, propertyName);
+ if (!result.isValid()) {
+ d->object = nullptr;
+ d->context = nullptr;
+ d->engine = nullptr;
+ }
+ return result;
}
QQmlPropertyPrivate::QQmlPropertyPrivate()
-: context(0), engine(0), object(0), isNameCached(false)
+: context(nullptr), engine(nullptr), object(nullptr), isNameCached(false)
{
}
@@ -232,98 +248,104 @@ QQmlContextData *QQmlPropertyPrivate::effectiveContext() const
{
if (context) return context;
else if (engine) return QQmlContextData::get(engine->rootContext());
- else return 0;
+ else return nullptr;
}
void QQmlPropertyPrivate::initProperty(QObject *obj, const QString &name)
{
if (!obj) return;
- QQmlTypeNameCache *typeNameCache = context?context->imports:0;
-
- const auto path = name.splitRef(QLatin1Char('.'));
- if (path.isEmpty()) return;
+ QQmlTypeNameCache *typeNameCache = context?context->imports:nullptr;
QObject *currentObject = obj;
-
- // Everything up to the last property must be an "object type" property
- for (int ii = 0; ii < path.count() - 1; ++ii) {
- const QStringRef &pathName = path.at(ii);
-
- if (typeNameCache) {
- QQmlTypeNameCache::Result r = typeNameCache->query(pathName);
- if (r.isValid()) {
- if (r.type.isValid()) {
- QQmlEnginePrivate *enginePrivate = QQmlEnginePrivate::get(engine);
- QQmlAttachedPropertiesFunc func = r.type.attachedPropertiesFunction(enginePrivate);
- if (!func) return; // Not an attachable type
-
- currentObject = qmlAttachedPropertiesObjectById(r.type.attachedPropertiesId(enginePrivate), currentObject);
- if (!currentObject) return; // Something is broken with the attachable type
- } else if (r.importNamespace) {
- if ((ii + 1) == path.count()) return; // No type following the namespace
-
- ++ii; r = typeNameCache->query(path.at(ii), r.importNamespace);
- if (!r.type.isValid()) return; // Invalid type in namespace
-
- QQmlEnginePrivate *enginePrivate = QQmlEnginePrivate::get(engine);
- QQmlAttachedPropertiesFunc func = r.type.attachedPropertiesFunction(enginePrivate);
- if (!func) return; // Not an attachable type
-
- currentObject = qmlAttachedPropertiesObjectById(r.type.attachedPropertiesId(enginePrivate), currentObject);
- if (!currentObject) return; // Something is broken with the attachable type
-
- } else if (r.scriptIndex != -1) {
- return; // Not a type
- } else {
- Q_ASSERT(!"Unreachable");
+ QVector<QStringRef> path;
+ QStringRef terminal(&name);
+
+ if (name.contains(QLatin1Char('.'))) {
+ path = name.splitRef(QLatin1Char('.'));
+ if (path.isEmpty()) return;
+
+ // Everything up to the last property must be an "object type" property
+ for (int ii = 0; ii < path.count() - 1; ++ii) {
+ const QStringRef &pathName = path.at(ii);
+
+ // Types must begin with an uppercase letter (see checkRegistration()
+ // in qqmlmetatype.cpp for the enforcement of this).
+ if (typeNameCache && !pathName.isEmpty() && pathName.at(0).isUpper()) {
+ QQmlTypeNameCache::Result r = typeNameCache->query(pathName);
+ if (r.isValid()) {
+ if (r.type.isValid()) {
+ QQmlEnginePrivate *enginePrivate = QQmlEnginePrivate::get(engine);
+ QQmlAttachedPropertiesFunc func = r.type.attachedPropertiesFunction(enginePrivate);
+ if (!func) return; // Not an attachable type
+
+ currentObject = qmlAttachedPropertiesObjectById(r.type.attachedPropertiesId(enginePrivate), currentObject);
+ if (!currentObject) return; // Something is broken with the attachable type
+ } else if (r.importNamespace) {
+ if ((ii + 1) == path.count()) return; // No type following the namespace
+
+ ++ii; r = typeNameCache->query(path.at(ii), r.importNamespace);
+ if (!r.type.isValid()) return; // Invalid type in namespace
+
+ QQmlEnginePrivate *enginePrivate = QQmlEnginePrivate::get(engine);
+ QQmlAttachedPropertiesFunc func = r.type.attachedPropertiesFunction(enginePrivate);
+ if (!func) return; // Not an attachable type
+
+ currentObject = qmlAttachedPropertiesObjectById(r.type.attachedPropertiesId(enginePrivate), currentObject);
+ if (!currentObject) return; // Something is broken with the attachable type
+
+ } else if (r.scriptIndex != -1) {
+ return; // Not a type
+ } else {
+ Q_ASSERT(!"Unreachable");
+ }
+ continue;
}
- continue;
+
}
- }
+ QQmlPropertyData local;
+ QQmlPropertyData *property =
+ QQmlPropertyCache::property(engine, currentObject, pathName, context, local);
- QQmlPropertyData local;
- QQmlPropertyData *property =
- QQmlPropertyCache::property(engine, currentObject, pathName, context, local);
+ if (!property) return; // Not a property
+ if (property->isFunction())
+ return; // Not an object property
- if (!property) return; // Not a property
- if (property->isFunction())
- return; // Not an object property
+ if (ii == (path.count() - 2) && QQmlValueTypeFactory::isValueType(property->propType())) {
+ // We're now at a value type property
+ const QMetaObject *valueTypeMetaObject = QQmlValueTypeFactory::metaObjectForMetaType(property->propType());
+ if (!valueTypeMetaObject) return; // Not a value type
- if (ii == (path.count() - 2) && QQmlValueTypeFactory::isValueType(property->propType())) {
- // We're now at a value type property
- const QMetaObject *valueTypeMetaObject = QQmlValueTypeFactory::metaObjectForMetaType(property->propType());
- if (!valueTypeMetaObject) return; // Not a value type
+ int idx = valueTypeMetaObject->indexOfProperty(path.last().toUtf8().constData());
+ if (idx == -1) return; // Value type property does not exist
- int idx = valueTypeMetaObject->indexOfProperty(path.last().toUtf8().constData());
- if (idx == -1) return; // Value type property does not exist
+ QMetaProperty vtProp = valueTypeMetaObject->property(idx);
- QMetaProperty vtProp = valueTypeMetaObject->property(idx);
+ Q_ASSERT(vtProp.userType() <= 0x0000FFFF);
+ Q_ASSERT(idx <= 0x0000FFFF);
- Q_ASSERT(vtProp.userType() <= 0x0000FFFF);
- Q_ASSERT(idx <= 0x0000FFFF);
+ object = currentObject;
+ core = *property;
+ valueTypeData.setFlags(QQmlPropertyData::flagsForProperty(vtProp));
+ valueTypeData.setPropType(vtProp.userType());
+ valueTypeData.setCoreIndex(idx);
- object = currentObject;
- core = *property;
- valueTypeData.setFlags(QQmlPropertyData::flagsForProperty(vtProp));
- valueTypeData.setPropType(vtProp.userType());
- valueTypeData.setCoreIndex(idx);
+ return;
+ } else {
+ if (!property->isQObject())
+ return; // Not an object property
- return;
- } else {
- if (!property->isQObject())
- return; // Not an object property
+ property->readProperty(currentObject, &currentObject);
+ if (!currentObject) return; // No value
- property->readProperty(currentObject, &currentObject);
- if (!currentObject) return; // No value
+ }
}
+ terminal = path.last();
}
- const QStringRef &terminal = path.last();
-
if (terminal.count() >= 3 &&
terminal.at(0) == QLatin1Char('o') &&
terminal.at(1) == QLatin1Char('n') &&
@@ -467,7 +489,7 @@ QQmlPropertyPrivate::propertyTypeCategory() const
const char *QQmlProperty::propertyTypeName() const
{
if (!d)
- return 0;
+ return nullptr;
if (d->isValueType()) {
const QMetaObject *valueTypeMetaObject = QQmlValueTypeFactory::metaObjectForMetaType(d->core.propType());
Q_ASSERT(valueTypeMetaObject);
@@ -475,7 +497,7 @@ const char *QQmlProperty::propertyTypeName() const
} else if (d->object && type() & Property && d->core.isValid()) {
return d->object->metaObject()->property(d->core.coreIndex()).typeName();
} else {
- return 0;
+ return nullptr;
}
}
@@ -559,7 +581,7 @@ bool QQmlProperty::isSignalProperty() const
*/
QObject *QQmlProperty::object() const
{
- return d ? d->object : 0;
+ return d ? d->object : nullptr;
}
/*!
@@ -697,7 +719,7 @@ QQmlAbstractBinding *
QQmlPropertyPrivate::binding(const QQmlProperty &that)
{
if (!that.d || !that.isProperty() || !that.d->object)
- return 0;
+ return nullptr;
QQmlPropertyIndex thatIndex(that.d->core.coreIndex(), that.d->valueTypeData.coreIndex());
return binding(that.d->object, thatIndex);
@@ -759,7 +781,7 @@ static void removeOldBinding(QObject *object, QQmlPropertyIndex index, QQmlPrope
return;
if (!(flags & QQmlPropertyPrivate::DontEnable))
- oldBinding->setEnabled(false, 0);
+ oldBinding->setEnabled(false, nullptr);
oldBinding->removeFromObject();
}
@@ -793,13 +815,13 @@ QQmlPropertyPrivate::binding(QObject *object, QQmlPropertyIndex index)
QQmlData *data = QQmlData::get(object);
if (!data)
- return 0;
+ return nullptr;
const int coreIndex = index.coreIndex();
const int valueTypeIndex = index.valueTypeIndex();
if (coreIndex < 0 || !data->hasBindingBit(coreIndex))
- return 0;
+ return nullptr;
QQmlAbstractBinding *binding = data->bindings;
while (binding && (binding->targetPropertyIndex().coreIndex() != coreIndex ||
@@ -825,11 +847,11 @@ void QQmlPropertyPrivate::findAliasTarget(QObject *object, QQmlPropertyIndex bin
int valueTypeIndex = bindingIndex.valueTypeIndex();
QQmlPropertyData *propertyData =
- data->propertyCache?data->propertyCache->property(coreIndex):0;
+ data->propertyCache?data->propertyCache->property(coreIndex):nullptr;
if (propertyData && propertyData->isAlias()) {
QQmlVMEMetaObject *vme = QQmlVMEMetaObject::getForProperty(object, coreIndex);
- QObject *aObject = 0; int aCoreIndex = -1; int aValueTypeIndex = -1;
+ QObject *aObject = nullptr; int aCoreIndex = -1; int aValueTypeIndex = -1;
if (vme->aliasTarget(coreIndex, &aObject, &aCoreIndex, &aValueTypeIndex)) {
// This will either be a value type sub-reference or an alias to a value-type sub-reference not both
Q_ASSERT(valueTypeIndex == -1 || aValueTypeIndex == -1);
@@ -884,11 +906,11 @@ QQmlBoundSignalExpression *
QQmlPropertyPrivate::signalExpression(const QQmlProperty &that)
{
if (!(that.type() & QQmlProperty::SignalProperty))
- return 0;
+ return nullptr;
QQmlData *data = QQmlData::get(that.d->object);
if (!data)
- return 0;
+ return nullptr;
QQmlBoundSignal *signalHandler = data->signalHandlers;
@@ -898,7 +920,7 @@ QQmlPropertyPrivate::signalExpression(const QQmlProperty &that)
if (signalHandler)
return signalHandler->expression();
- return 0;
+ return nullptr;
}
/*!
@@ -925,7 +947,7 @@ void QQmlPropertyPrivate::takeSignalExpression(const QQmlProperty &that,
return;
}
- QQmlData *data = QQmlData::get(that.d->object, 0 != expr);
+ QQmlData *data = QQmlData::get(that.d->object, nullptr != expr);
if (!data)
return;
@@ -1032,7 +1054,7 @@ QVariant QQmlPropertyPrivate::readValueProperty()
} else if (core.isQObject()) {
- QObject *rv = 0;
+ QObject *rv = nullptr;
core.readProperty(object, &rv);
return QVariant::fromValue(rv);
@@ -1043,11 +1065,11 @@ QVariant QQmlPropertyPrivate::readValueProperty()
QVariant value;
int status = -1;
- void *args[] = { 0, &value, &status };
+ void *args[] = { nullptr, &value, &status };
if (core.propType() == QMetaType::QVariant) {
args[0] = &value;
} else {
- value = QVariant(core.propType(), (void*)0);
+ value = QVariant(core.propType(), (void*)nullptr);
args[0] = value.data();
}
core.readPropertyWithArgs(object, args);
@@ -1406,7 +1428,7 @@ QQmlMetaObject QQmlPropertyPrivate::rawMetaObjectForType(QQmlEnginePrivate *engi
*/
bool QQmlProperty::write(const QVariant &value) const
{
- return QQmlPropertyPrivate::write(*this, value, 0);
+ return QQmlPropertyPrivate::write(*this, value, nullptr);
}
/*!
@@ -1475,7 +1497,7 @@ bool QQmlProperty::write(QObject *object, const QString &name, const QVariant &v
bool QQmlProperty::reset() const
{
if (isResettable()) {
- void *args[] = { 0 };
+ void *args[] = { nullptr };
QMetaObject::metacall(d->object, QMetaObject::ResetProperty, d->core.coreIndex(), args);
return true;
} else {
diff --git a/src/qml/qml/qqmlproperty_p.h b/src/qml/qml/qqmlproperty_p.h
index 53062a2f13..544eab4c7f 100644
--- a/src/qml/qml/qqmlproperty_p.h
+++ b/src/qml/qml/qqmlproperty_p.h
@@ -104,9 +104,9 @@ public:
static bool writeValueProperty(QObject *,
const QQmlPropertyData &, const QQmlPropertyData &valueTypeData,
const QVariant &, QQmlContextData *,
- QQmlPropertyData::WriteFlags flags = 0);
+ QQmlPropertyData::WriteFlags flags = nullptr);
static bool write(QObject *, const QQmlPropertyData &, const QVariant &,
- QQmlContextData *, QQmlPropertyData::WriteFlags flags = 0);
+ QQmlContextData *, QQmlPropertyData::WriteFlags flags = nullptr);
static void findAliasTarget(QObject *, QQmlPropertyIndex, QObject **, QQmlPropertyIndex *);
enum BindingFlag {
@@ -140,10 +140,12 @@ public:
static QMetaMethod findSignalByName(const QMetaObject *mo, const QByteArray &);
static bool connect(const QObject *sender, int signal_index,
const QObject *receiver, int method_index,
- int type = 0, int *types = 0);
+ int type = 0, int *types = nullptr);
static void flushSignal(const QObject *sender, int signal_index);
static QVariant resolvedUrlSequence(const QVariant &value, QQmlContextData *context);
+ static QQmlProperty create(QObject *target, const QString &propertyName, QQmlContextData *context);
+
};
Q_DECLARE_OPERATORS_FOR_FLAGS(QQmlPropertyPrivate::BindingFlags)
diff --git a/src/qml/qml/qqmlpropertycache.cpp b/src/qml/qml/qqmlpropertycache.cpp
index 7178dffa8b..88eda9c020 100644
--- a/src/qml/qml/qqmlpropertycache.cpp
+++ b/src/qml/qml/qqmlpropertycache.cpp
@@ -243,9 +243,9 @@ void QQmlPropertyData::lazyLoad(const QMetaMethod &m)
Creates a new empty QQmlPropertyCache.
*/
QQmlPropertyCache::QQmlPropertyCache()
- : _parent(0), propertyIndexCacheStart(0), methodIndexCacheStart(0),
+ : _parent(nullptr), propertyIndexCacheStart(0), methodIndexCacheStart(0),
signalHandlerIndexCacheStart(0), _hasPropertyOverrides(false), _ownMetaObject(false),
- _metaObject(0), argumentsCache(0), _jsFactoryMethodIndex(-1)
+ _metaObject(nullptr), argumentsCache(nullptr), _jsFactoryMethodIndex(-1)
{
}
@@ -277,8 +277,8 @@ QQmlPropertyCache::~QQmlPropertyCache()
if (_parent) _parent->release();
if (_ownMetaObject) free(const_cast<QMetaObject *>(_metaObject));
- _metaObject = 0;
- _parent = 0;
+ _metaObject = nullptr;
+ _parent = nullptr;
}
QQmlPropertyCache *QQmlPropertyCache::copy(int reserve)
@@ -310,7 +310,7 @@ QQmlPropertyCache *QQmlPropertyCache::copyAndReserve(int propertyCount, int meth
rv->methodIndexCache.reserve(methodCount);
rv->signalHandlerIndexCache.reserve(signalCount);
rv->enumCache.reserve(enumCount);
- rv->_metaObject = 0;
+ rv->_metaObject = nullptr;
return rv;
}
@@ -321,13 +321,14 @@ QQmlPropertyCache *QQmlPropertyCache::copyAndReserve(int propertyCount, int meth
This is different from QMetaMethod::methodIndex().
*/
void QQmlPropertyCache::appendProperty(const QString &name, QQmlPropertyData::Flags flags,
- int coreIndex, int propType, int notifyIndex)
+ int coreIndex, int propType, int minorVersion, int notifyIndex)
{
QQmlPropertyData data;
data.setPropType(propType);
data.setCoreIndex(coreIndex);
data.setNotifyIndex(notifyIndex);
data.setFlags(flags);
+ data.setTypeMinorVersion(minorVersion);
QQmlPropertyData *old = findNamedProperty(name);
if (old)
@@ -336,7 +337,7 @@ void QQmlPropertyCache::appendProperty(const QString &name, QQmlPropertyData::Fl
int index = propertyIndexCache.count();
propertyIndexCache.append(data);
- setNamedProperty(name, index + propertyOffset(), propertyIndexCache.data() + index, (old != 0));
+ setNamedProperty(name, index + propertyOffset(), propertyIndexCache.data() + index, (old != nullptr));
}
void QQmlPropertyCache::appendSignal(const QString &name, QQmlPropertyData::Flags flags,
@@ -373,8 +374,8 @@ void QQmlPropertyCache::appendSignal(const QString &name, QQmlPropertyData::Flag
QString handlerName = QLatin1String("on") + name;
handlerName[2] = handlerName.at(2).toUpper();
- setNamedProperty(name, methodIndex + methodOffset(), methodIndexCache.data() + methodIndex, (old != 0));
- setNamedProperty(handlerName, signalHandlerIndex + signalOffset(), signalHandlerIndexCache.data() + signalHandlerIndex, (old != 0));
+ setNamedProperty(name, methodIndex + methodOffset(), methodIndexCache.data() + methodIndex, (old != nullptr));
+ setNamedProperty(handlerName, signalHandlerIndex + signalOffset(), signalHandlerIndexCache.data() + signalHandlerIndex, (old != nullptr));
}
void QQmlPropertyCache::appendMethod(const QString &name, QQmlPropertyData::Flags flags,
@@ -401,7 +402,7 @@ void QQmlPropertyCache::appendMethod(const QString &name, QQmlPropertyData::Flag
int methodIndex = methodIndexCache.count();
methodIndexCache.append(data);
- setNamedProperty(name, methodIndex + methodOffset(), methodIndexCache.data() + methodIndex, (old != 0));
+ setNamedProperty(name, methodIndex + methodOffset(), methodIndexCache.data() + methodIndex, (old != nullptr));
}
void QQmlPropertyCache::appendEnum(const QString &name, const QVector<QQmlEnumValue> &values)
@@ -429,7 +430,7 @@ const QMetaObject *QQmlPropertyCache::createMetaObject()
QQmlPropertyData *QQmlPropertyCache::defaultProperty() const
{
- return property(defaultPropertyName(), 0, 0);
+ return property(defaultPropertyName(), nullptr, nullptr);
}
void QQmlPropertyCache::setParent(QQmlPropertyCache *newParent)
@@ -542,7 +543,7 @@ void QQmlPropertyCache::append(const QMetaObject *metaObject,
}
QQmlPropertyData *data = &methodIndexCache[ii - methodIndexCacheStart];
- QQmlPropertyData *sigdata = 0;
+ QQmlPropertyData *sigdata = nullptr;
if (m.methodType() == QMetaMethod::Signal)
data->setFlags(signalFlags);
@@ -561,24 +562,24 @@ void QQmlPropertyCache::append(const QMetaObject *metaObject,
sigdata->_flags.isSignalHandler = true;
}
- QQmlPropertyData *old = 0;
+ QQmlPropertyData *old = nullptr;
if (utf8) {
QHashedString methodName(QString::fromUtf8(rawName, cptr - rawName));
if (StringCache::mapped_type *it = stringCache.value(methodName))
old = it->second;
- setNamedProperty(methodName, ii, data, (old != 0));
+ setNamedProperty(methodName, ii, data, (old != nullptr));
if (data->isSignal()) {
QHashedString on(QLatin1String("on") % methodName.at(0).toUpper() % methodName.midRef(1));
- setNamedProperty(on, ii, sigdata, (old != 0));
+ setNamedProperty(on, ii, sigdata, (old != nullptr));
++signalHandlerIndex;
}
} else {
QHashedCStringRef methodName(rawName, cptr - rawName);
if (StringCache::mapped_type *it = stringCache.value(methodName))
old = it->second;
- setNamedProperty(methodName, ii, data, (old != 0));
+ setNamedProperty(methodName, ii, data, (old != nullptr));
if (data->isSignal()) {
int length = methodName.length();
@@ -592,7 +593,7 @@ void QQmlPropertyCache::append(const QMetaObject *metaObject,
str[length + 2] = '\0';
QHashedString on(QString::fromLatin1(str.data()));
- setNamedProperty(on, ii, data, (old != 0));
+ setNamedProperty(on, ii, data, (old != nullptr));
++signalHandlerIndex;
}
}
@@ -635,18 +636,18 @@ void QQmlPropertyCache::append(const QMetaObject *metaObject,
Q_ASSERT((allowedRevisionCache.count() - 1) < Q_INT16_MAX);
data->setMetaObjectOffset(allowedRevisionCache.count() - 1);
- QQmlPropertyData *old = 0;
+ QQmlPropertyData *old = nullptr;
if (utf8) {
QHashedString propName(QString::fromUtf8(str, cptr - str));
if (StringCache::mapped_type *it = stringCache.value(propName))
old = it->second;
- setNamedProperty(propName, ii, data, (old != 0));
+ setNamedProperty(propName, ii, data, (old != nullptr));
} else {
QHashedCStringRef propName(str, cptr - str);
if (StringCache::mapped_type *it = stringCache.value(propName))
old = it->second;
- setNamedProperty(propName, ii, data, (old != 0));
+ setNamedProperty(propName, ii, data, (old != nullptr));
}
bool isGadget = true;
@@ -749,7 +750,7 @@ void QQmlPropertyCache::invalidate(const QMetaObject *metaObject)
signalHandlerIndexCache.clear();
_hasPropertyOverrides = false;
- argumentsCache = 0;
+ argumentsCache = nullptr;
int pc = metaObject->propertyCount();
int mc = metaObject->methodCount();
@@ -772,8 +773,8 @@ void QQmlPropertyCache::invalidate(const QMetaObject *metaObject)
QQmlPropertyData *QQmlPropertyCache::findProperty(StringCache::ConstIterator it, QObject *object, QQmlContextData *context) const
{
- QQmlData *data = (object ? QQmlData::get(object) : 0);
- const QQmlVMEMetaObject *vmemo = 0;
+ QQmlData *data = (object ? QQmlData::get(object) : nullptr);
+ const QQmlVMEMetaObject *vmemo = nullptr;
if (data && data->hasVMEMetaObject) {
QObjectPrivate *op = QObjectPrivate::get(object);
vmemo = static_cast<const QQmlVMEMetaObject *>(op->metaObject);
@@ -848,7 +849,7 @@ QQmlPropertyData *QQmlPropertyCache::findProperty(StringCache::ConstIterator it,
return ensureResolved(result);
}
- return 0;
+ return nullptr;
}
QString QQmlPropertyData::name(QObject *object) const
@@ -918,9 +919,9 @@ QQmlPropertyCacheMethodArguments *QQmlPropertyCache::createArgumentsObject(int a
A *args = static_cast<A *>(malloc(sizeof(A) + (argc) * sizeof(int)));
args->arguments[0] = argc;
args->argumentsValid = false;
- args->signalParameterStringForJS = 0;
+ args->signalParameterStringForJS = nullptr;
args->parameterError = false;
- args->names = argc ? new QList<QByteArray>(names) : 0;
+ args->names = argc ? new QList<QByteArray>(names) : nullptr;
args->next = argumentsCache;
argumentsCache = args;
return args;
@@ -1026,10 +1027,10 @@ static QQmlPropertyData qQmlPropertyCacheCreate(const QMetaObject *metaObject, c
}
/* If the "cmo" variable didn't change, set it to 0 to
* avoid running into an infinite loop */
- if (!changed) cmo = 0;
+ if (!changed) cmo = nullptr;
}
} else {
- cmo = 0;
+ cmo = nullptr;
}
}
}
@@ -1056,7 +1057,7 @@ QQmlPropertyData *
qQmlPropertyCacheProperty(QJSEngine *engine, QObject *obj, T name,
QQmlContextData *context, QQmlPropertyData &local)
{
- QQmlPropertyCache *cache = 0;
+ QQmlPropertyCache *cache = nullptr;
QQmlData *ddata = QQmlData::get(obj, false);
@@ -1072,7 +1073,7 @@ qQmlPropertyCacheProperty(QJSEngine *engine, QObject *obj, T name,
}
}
- QQmlPropertyData *rv = 0;
+ QQmlPropertyData *rv = nullptr;
if (cache) {
rv = cache->property(name, obj, context);
@@ -1213,7 +1214,7 @@ void QQmlPropertyCache::toMetaObjectBuilder(QMetaObjectBuilder &builder)
// '+=' reserves extra capacity. Follow-up appending will be probably free.
signature += methods.at(ii).first.toUtf8() + '(';
- QQmlPropertyCacheMethodArguments *arguments = 0;
+ QQmlPropertyCacheMethodArguments *arguments = nullptr;
if (data->hasArguments()) {
arguments = (QQmlPropertyCacheMethodArguments *)data->arguments();
Q_ASSERT(arguments->argumentsValid);
@@ -1251,7 +1252,7 @@ void QQmlPropertyCache::toMetaObjectBuilder(QMetaObjectBuilder &builder)
}
if (!_defaultPropertyName.isEmpty()) {
- QQmlPropertyData *dp = property(_defaultPropertyName, 0, 0);
+ QQmlPropertyData *dp = property(_defaultPropertyName, nullptr, nullptr);
if (dp && dp->coreIndex() >= propertyIndexCacheStart) {
Q_ASSERT(!dp->isFunction());
builder.addClassInfo("DefaultProperty", _defaultPropertyName.toUtf8());
@@ -1576,7 +1577,7 @@ void QQmlMetaObject::resolveGadgetMethodOrPropertyIndex(QMetaObject::Call type,
QQmlPropertyCache *QQmlMetaObject::propertyCache(QQmlEnginePrivate *e) const
{
- if (_m.isNull()) return 0;
+ if (_m.isNull()) return nullptr;
if (_m.isT1()) return _m.asT1();
else return e->cache(_m.asT2());
}
@@ -1587,7 +1588,7 @@ int QQmlMetaObject::methodReturnType(const QQmlPropertyData &data, QByteArray *u
int type = data.propType();
- const char *propTypeName = 0;
+ const char *propTypeName = nullptr;
if (type == QMetaType::UnknownType) {
// Find the return type name from the method info
@@ -1675,7 +1676,7 @@ int *QQmlMetaObject::methodParameterTypes(int index, ArgTypeStorage *argStorage,
}
if (type == QMetaType::UnknownType) {
if (unknownTypeError) *unknownTypeError = argTypeNames.at(ii);
- return 0;
+ return nullptr;
}
args->arguments[ii + 1] = type;
}
@@ -1714,7 +1715,7 @@ int *QQmlMetaObject::methodParameterTypes(const QMetaMethod &m, ArgTypeStorage *
}
if (type == QMetaType::UnknownType) {
if (unknownTypeError) *unknownTypeError = argTypeNames.at(ii);
- return 0;
+ return nullptr;
}
argStorage->operator[](ii + 1) = type;
}
@@ -1726,7 +1727,7 @@ void QQmlObjectOrGadget::metacall(QMetaObject::Call type, int index, void **argv
{
if (ptr.isNull()) {
const QMetaObject *metaObject = _m.asT2();
- metaObject->d.static_metacall(0, type, index, argv);
+ metaObject->d.static_metacall(nullptr, type, index, argv);
}
else if (ptr.isT1()) {
QMetaObject::metacall(ptr.asT1(), type, index, argv);
diff --git a/src/qml/qml/qqmlpropertycache_p.h b/src/qml/qml/qqmlpropertycache_p.h
index 6f4879baa2..5553fe6b80 100644
--- a/src/qml/qml/qqmlpropertycache_p.h
+++ b/src/qml/qml/qqmlpropertycache_p.h
@@ -245,12 +245,36 @@ public:
_coreIndex = qint16(idx);
}
- int revision() const { return _revision; }
- void setRevision(int rev)
+ quint8 revision() const { return _revision; }
+ void setRevision(quint8 rev)
{
- Q_ASSERT(rev >= std::numeric_limits<qint16>::min());
- Q_ASSERT(rev <= std::numeric_limits<qint16>::max());
- _revision = qint16(rev);
+ Q_ASSERT(rev <= std::numeric_limits<quint8>::max());
+ _revision = quint8(rev);
+ }
+
+ /* If a property is a C++ type, then we store the minor
+ * version of this type.
+ * This is required to resolve property or signal revisions
+ * if this property is used as a grouped property.
+ *
+ * Test.qml
+ * property TextEdit someTextEdit: TextEdit {}
+ *
+ * Test {
+ * someTextEdit.preeditText: "test" //revision 7
+ * someTextEdit.onEditingFinished: console.log("test") //revision 6
+ * }
+ *
+ * To determine if these properties with revisions are available we need
+ * the minor version of TextEdit as imported in Test.qml.
+ *
+ */
+
+ quint8 typeMinorVersion() const { return _typeMinorVersion; }
+ void setTypeMinorVersion(quint8 rev)
+ {
+ Q_ASSERT(rev <= std::numeric_limits<quint8>::max());
+ _typeMinorVersion = quint8(rev);
}
QQmlPropertyCacheMethodArguments *arguments() const { return _arguments; }
@@ -284,7 +308,8 @@ private:
qint16 _notifyIndex;
qint16 _overrideIndex;
- qint16 _revision;
+ quint8 _revision;
+ quint8 _typeMinorVersion;
qint16 _metaObjectOffset;
QQmlPropertyCacheMethodArguments *_arguments;
@@ -325,7 +350,7 @@ public:
inline void readProperty(QObject *target, void *property) const
{
- void *args[] = { property, 0 };
+ void *args[] = { property, nullptr };
readPropertyWithArgs(target, args);
}
@@ -342,7 +367,7 @@ public:
bool writeProperty(QObject *target, void *value, WriteFlags flags) const
{
int status = -1;
- void *argv[] = { value, 0, &status, &flags };
+ void *argv[] = { value, nullptr, &status, &flags };
if (flags.testFlag(BypassInterceptor) && hasStaticMetaCallFunction())
staticMetaCallFunction()(target, QMetaObject::WriteProperty, relativePropertyIndex(), argv);
else if (flags.testFlag(BypassInterceptor) && isDirect())
@@ -378,10 +403,10 @@ private:
struct QQmlEnumValue
{
- QQmlEnumValue() : value(-1) {}
+ QQmlEnumValue() {}
QQmlEnumValue(const QString &n, int v) : namedValue(n), value(v) {}
QString namedValue;
- int value;
+ int value = -1;
};
struct QQmlEnumData
@@ -396,7 +421,7 @@ class Q_QML_PRIVATE_EXPORT QQmlPropertyCache : public QQmlRefCount
public:
QQmlPropertyCache();
QQmlPropertyCache(const QMetaObject *);
- virtual ~QQmlPropertyCache();
+ ~QQmlPropertyCache() override;
void update(const QMetaObject *);
void invalidate(const QMetaObject *);
@@ -417,9 +442,9 @@ public:
QQmlPropertyCache *copyAndReserve(int propertyCount,
int methodCount, int signalCount, int enumCount);
void appendProperty(const QString &, QQmlPropertyRawData::Flags flags, int coreIndex,
- int propType, int notifyIndex);
+ int propType, int revision, int notifyIndex);
void appendSignal(const QString &, QQmlPropertyRawData::Flags, int coreIndex,
- const int *types = 0, const QList<QByteArray> &names = QList<QByteArray>());
+ const int *types = nullptr, const QList<QByteArray> &names = QList<QByteArray>());
void appendMethod(const QString &, QQmlPropertyData::Flags flags, int coreIndex,
const QList<QByteArray> &names = QList<QByteArray>());
void appendEnum(const QString &, const QVector<QQmlEnumValue> &);
@@ -467,7 +492,7 @@ public:
static int originalClone(QObject *, int index);
QList<QByteArray> signalParameterNames(int index) const;
- static QString signalParameterStringForJS(QV4::ExecutionEngine *engine, const QList<QByteArray> &parameterNameList, QString *errorString = 0);
+ static QString signalParameterStringForJS(QV4::ExecutionEngine *engine, const QList<QByteArray> &parameterNameList, QString *errorString = nullptr);
const char *className() const;
@@ -741,7 +766,7 @@ inline const QMetaObject *QQmlPropertyCache::metaObject() const
// QML
inline const QMetaObject *QQmlPropertyCache::firstCppMetaObject() const
{
- while (_parent && (_metaObject == 0 || _ownMetaObject))
+ while (_parent && (_metaObject == nullptr || _ownMetaObject))
return _parent->firstCppMetaObject();
return _metaObject;
}
@@ -749,7 +774,7 @@ inline const QMetaObject *QQmlPropertyCache::firstCppMetaObject() const
inline QQmlPropertyData *QQmlPropertyCache::property(int index) const
{
if (index < 0 || index >= (propertyIndexCacheStart + propertyIndexCache.count()))
- return 0;
+ return nullptr;
if (index < propertyIndexCacheStart)
return _parent->property(index);
@@ -761,7 +786,7 @@ inline QQmlPropertyData *QQmlPropertyCache::property(int index) const
inline QQmlPropertyData *QQmlPropertyCache::method(int index) const
{
if (index < 0 || index >= (methodIndexCacheStart + methodIndexCache.count()))
- return 0;
+ return nullptr;
if (index < methodIndexCacheStart)
return _parent->method(index);
@@ -777,7 +802,7 @@ inline QQmlPropertyData *QQmlPropertyCache::method(int index) const
inline QQmlPropertyData *QQmlPropertyCache::signal(int index) const
{
if (index < 0 || index >= (signalHandlerIndexCacheStart + signalHandlerIndexCache.count()))
- return 0;
+ return nullptr;
if (index < signalHandlerIndexCacheStart)
return _parent->signal(index);
@@ -790,7 +815,7 @@ inline QQmlPropertyData *QQmlPropertyCache::signal(int index) const
inline QQmlEnumData *QQmlPropertyCache::qmlEnum(int index) const
{
if (index < 0 || index >= enumCache.count())
- return 0;
+ return nullptr;
return const_cast<QQmlEnumData *>(&enumCache.at(index));
}
@@ -821,7 +846,7 @@ QQmlPropertyData *
QQmlPropertyCache::overrideData(QQmlPropertyData *data) const
{
if (!data->hasOverride())
- return 0;
+ return nullptr;
if (data->overrideIndexIsProperty())
return property(data->overrideIndex());
@@ -923,7 +948,7 @@ bool QQmlMetaObject::isNull() const
const char *QQmlMetaObject::className() const
{
if (_m.isNull()) {
- return 0;
+ return nullptr;
} else if (_m.isT1()) {
return _m.asT1()->className();
} else {
@@ -949,7 +974,7 @@ bool QQmlMetaObject::hasMetaObject() const
const QMetaObject *QQmlMetaObject::metaObject() const
{
- if (_m.isNull()) return 0;
+ if (_m.isNull()) return nullptr;
if (_m.isT1()) return _m.asT1()->createMetaObject();
else return _m.asT2();
}
diff --git a/src/qml/qml/qqmlpropertyvalueinterceptor.cpp b/src/qml/qml/qqmlpropertyvalueinterceptor.cpp
index 52c003ab59..603245f29d 100644
--- a/src/qml/qml/qqmlpropertyvalueinterceptor.cpp
+++ b/src/qml/qml/qqmlpropertyvalueinterceptor.cpp
@@ -55,7 +55,7 @@ QT_BEGIN_NAMESPACE
/*!
Constructs a QQmlPropertyValueInterceptor.
*/
-QQmlPropertyValueInterceptor::QQmlPropertyValueInterceptor() : m_next(0)
+QQmlPropertyValueInterceptor::QQmlPropertyValueInterceptor() : m_next(nullptr)
{
}
diff --git a/src/qml/qml/qqmlproxymetaobject.cpp b/src/qml/qml/qqmlproxymetaobject.cpp
index 27e3c13ff8..e1500f70fb 100644
--- a/src/qml/qml/qqmlproxymetaobject.cpp
+++ b/src/qml/qml/qqmlproxymetaobject.cpp
@@ -43,7 +43,7 @@
QT_BEGIN_NAMESPACE
QQmlProxyMetaObject::QQmlProxyMetaObject(QObject *obj, QList<ProxyData> *mList)
-: metaObjects(mList), proxies(0), parent(0), object(obj)
+: metaObjects(mList), proxies(nullptr), parent(nullptr), object(obj)
{
*static_cast<QMetaObject *>(this) = *metaObjects->constFirst().metaObject;
@@ -58,11 +58,11 @@ QQmlProxyMetaObject::~QQmlProxyMetaObject()
{
if (parent)
delete parent;
- parent = 0;
+ parent = nullptr;
if (proxies)
delete [] proxies;
- proxies = 0;
+ proxies = nullptr;
}
int QQmlProxyMetaObject::metaCall(QObject *o, QMetaObject::Call c, int id, void **a)
diff --git a/src/qml/qml/qqmlscriptstring_p.h b/src/qml/qml/qqmlscriptstring_p.h
index 2dfb817186..fd8ccd5d53 100644
--- a/src/qml/qml/qqmlscriptstring_p.h
+++ b/src/qml/qml/qqmlscriptstring_p.h
@@ -59,7 +59,7 @@ QT_BEGIN_NAMESPACE
class Q_AUTOTEST_EXPORT QQmlScriptStringPrivate : public QSharedData
{
public:
- QQmlScriptStringPrivate() : context(0), scope(0), bindingId(-1), lineNumber(0), columnNumber(0),
+ QQmlScriptStringPrivate() : context(nullptr), scope(nullptr), bindingId(-1), lineNumber(0), columnNumber(0),
numberValue(0), isStringLiteral(false), isNumberLiteral(false) {}
//for testing
diff --git a/src/qml/qml/qqmlstringconverters_p.h b/src/qml/qml/qqmlstringconverters_p.h
index af344e3344..215f0c0aaf 100644
--- a/src/qml/qml/qqmlstringconverters_p.h
+++ b/src/qml/qml/qqmlstringconverters_p.h
@@ -67,19 +67,19 @@ class QByteArray;
namespace QQmlStringConverters
{
Q_QML_PRIVATE_EXPORT QVariant variantFromString(const QString &);
- Q_QML_PRIVATE_EXPORT QVariant variantFromString(const QString &, int preferredType, bool *ok = 0);
+ Q_QML_PRIVATE_EXPORT QVariant variantFromString(const QString &, int preferredType, bool *ok = nullptr);
- Q_QML_PRIVATE_EXPORT QVariant colorFromString(const QString &, bool *ok = 0);
- Q_QML_PRIVATE_EXPORT unsigned rgbaFromString(const QString &, bool *ok = 0);
+ Q_QML_PRIVATE_EXPORT QVariant colorFromString(const QString &, bool *ok = nullptr);
+ Q_QML_PRIVATE_EXPORT unsigned rgbaFromString(const QString &, bool *ok = nullptr);
#if QT_CONFIG(datestring)
- Q_QML_PRIVATE_EXPORT QDate dateFromString(const QString &, bool *ok = 0);
- Q_QML_PRIVATE_EXPORT QTime timeFromString(const QString &, bool *ok = 0);
- Q_QML_PRIVATE_EXPORT QDateTime dateTimeFromString(const QString &, bool *ok = 0);
+ Q_QML_PRIVATE_EXPORT QDate dateFromString(const QString &, bool *ok = nullptr);
+ Q_QML_PRIVATE_EXPORT QTime timeFromString(const QString &, bool *ok = nullptr);
+ Q_QML_PRIVATE_EXPORT QDateTime dateTimeFromString(const QString &, bool *ok = nullptr);
#endif
- Q_QML_PRIVATE_EXPORT QPointF pointFFromString(const QString &, bool *ok = 0);
- Q_QML_PRIVATE_EXPORT QSizeF sizeFFromString(const QString &, bool *ok = 0);
- Q_QML_PRIVATE_EXPORT QRectF rectFFromString(const QString &, bool *ok = 0);
+ Q_QML_PRIVATE_EXPORT QPointF pointFFromString(const QString &, bool *ok = nullptr);
+ Q_QML_PRIVATE_EXPORT QSizeF sizeFFromString(const QString &, bool *ok = nullptr);
+ Q_QML_PRIVATE_EXPORT QRectF rectFFromString(const QString &, bool *ok = nullptr);
Q_QML_PRIVATE_EXPORT bool createFromString(int, const QString &, void *, size_t);
}
diff --git a/src/qml/qml/qqmltypeloader.cpp b/src/qml/qml/qqmltypeloader.cpp
index 9285328892..5212b49670 100644
--- a/src/qml/qml/qqmltypeloader.cpp
+++ b/src/qml/qml/qqmltypeloader.cpp
@@ -156,8 +156,8 @@ public:
void loadAsync(QQmlDataBlob *b);
void loadWithStaticData(QQmlDataBlob *b, const QByteArray &);
void loadWithStaticDataAsync(QQmlDataBlob *b, const QByteArray &);
- void loadWithCachedUnit(QQmlDataBlob *b, const QQmlPrivate::CachedQmlUnit *unit);
- void loadWithCachedUnitAsync(QQmlDataBlob *b, const QQmlPrivate::CachedQmlUnit *unit);
+ void loadWithCachedUnit(QQmlDataBlob *b, const QV4::CompiledData::Unit *unit);
+ void loadWithCachedUnitAsync(QQmlDataBlob *b, const QV4::CompiledData::Unit *unit);
void callCompleted(QQmlDataBlob *b);
void callDownloadProgressChanged(QQmlDataBlob *b, qreal p);
void initializeEngine(QQmlExtensionInterface *, const char *);
@@ -168,7 +168,7 @@ protected:
private:
void loadThread(QQmlDataBlob *b);
void loadWithStaticDataThread(QQmlDataBlob *b, const QByteArray &);
- void loadWithCachedUnitThread(QQmlDataBlob *b, const QQmlPrivate::CachedQmlUnit *unit);
+ void loadWithCachedUnitThread(QQmlDataBlob *b, const QV4::CompiledData::Unit *unit);
void callCompletedMain(QQmlDataBlob *b);
void callDownloadProgressChangedMain(QQmlDataBlob *b, qreal p);
void initializeEngineMain(QQmlExtensionInterface *iface, const char *uri);
@@ -317,7 +317,8 @@ Returns true if the status is WaitingForDependencies.
*/
bool QQmlDataBlob::isWaiting() const
{
- return status() == WaitingForDependencies;
+ return status() == WaitingForDependencies ||
+ status() == ResolvingDependencies;
}
/*!
@@ -356,8 +357,10 @@ qreal QQmlDataBlob::progress() const
}
/*!
-Returns the blob url passed to the constructor. If a network redirect
-happens while fetching the data, this url remains the same.
+Returns the physical url of the data. Initially this is the same as
+finalUrl(), but if a network redirect happens while fetching the data, this url
+is updated to reflect the new location. Also, if a URL interceptor is set, it
+will work on this URL and leave finalUrl() alone.
\sa finalUrl()
*/
@@ -366,16 +369,25 @@ QUrl QQmlDataBlob::url() const
return m_url;
}
+QString QQmlDataBlob::urlString() const
+{
+ if (m_urlString.isEmpty())
+ m_urlString = m_url.toString();
+
+ return m_urlString;
+}
+
/*!
-Returns the final url of the data. Initially this is the same as
-url(), but if a network redirect happens while fetching the data, this url
-is updated to reflect the new location.
+Returns the logical URL to be used for resolving further URLs referred to in
+the code.
-May only be called from the load thread, or after the blob isCompleteOrError().
+This is the blob url passed to the constructor. If a network redirect
+happens while fetching the data, this url remains the same.
+
+\sa url()
*/
QUrl QQmlDataBlob::finalUrl() const
{
- Q_ASSERT(isCompleteOrError() || (m_typeLoader && m_typeLoader->m_thread->isThisThread()));
return m_finalUrl;
}
@@ -384,7 +396,6 @@ Returns the finalUrl() as a string.
*/
QString QQmlDataBlob::finalUrlString() const
{
- Q_ASSERT(isCompleteOrError() || (m_typeLoader && m_typeLoader->m_thread->isThisThread()));
if (m_finalUrlString.isEmpty())
m_finalUrlString = m_finalUrl.toString();
@@ -433,7 +444,7 @@ void QQmlDataBlob::setError(const QList<QQmlError> &errors)
m_data.setStatus(Error);
if (dumpErrors()) {
- qWarning().nospace() << "Errors for " << m_finalUrl.toString();
+ qWarning().nospace() << "Errors for " << urlString();
for (int ii = 0; ii < errors.count(); ++ii)
qWarning().nospace() << " " << qPrintable(errors.at(ii).toString());
}
@@ -472,7 +483,7 @@ void QQmlDataBlob::setError(const QString &description)
{
QQmlError e;
e.setDescription(description);
- e.setUrl(finalUrl());
+ e.setUrl(url());
setError(e);
}
@@ -538,9 +549,9 @@ void QQmlDataBlob::networkError(QNetworkReply::NetworkError networkError)
Q_UNUSED(networkError);
QQmlError error;
- error.setUrl(m_finalUrl);
+ error.setUrl(m_url);
- const char *errorString = 0;
+ const char *errorString = nullptr;
switch (networkError) {
default:
errorString = "Network error";
@@ -610,6 +621,7 @@ The default implementation does nothing.
*/
void QQmlDataBlob::allDependenciesDone()
{
+ m_data.setStatus(QQmlDataBlob::ResolvingDependencies);
}
/*!
@@ -654,7 +666,7 @@ void QQmlDataBlob::tryDone()
addref();
#ifdef DATABLOB_DEBUG
- qWarning("QQmlDataBlob::done() %s", qPrintable(url().toString()));
+ qWarning("QQmlDataBlob::done() %s", qPrintable(urlString()));
#endif
done();
@@ -780,7 +792,7 @@ void QQmlDataBlob::ThreadData::setProgress(quint8 v)
QQmlTypeLoaderThread::QQmlTypeLoaderThread(QQmlTypeLoader *loader)
: m_loader(loader)
#if QT_CONFIG(qml_network)
-, m_networkAccessManager(0), m_networkReplyProxy(0)
+, m_networkAccessManager(nullptr), m_networkReplyProxy(nullptr)
#endif // qml_network
{
// Do that after initializing all the members.
@@ -792,7 +804,7 @@ QNetworkAccessManager *QQmlTypeLoaderThread::networkAccessManager() const
{
Q_ASSERT(isThisThread());
if (!m_networkAccessManager) {
- m_networkAccessManager = QQmlEnginePrivate::get(m_loader->engine())->createNetworkAccessManager(0);
+ m_networkAccessManager = QQmlEnginePrivate::get(m_loader->engine())->createNetworkAccessManager(nullptr);
m_networkReplyProxy = new QQmlTypeLoaderNetworkReplyProxy(m_loader);
}
@@ -831,13 +843,13 @@ void QQmlTypeLoaderThread::loadWithStaticDataAsync(QQmlDataBlob *b, const QByteA
postMethodToThread(&This::loadWithStaticDataThread, b, d);
}
-void QQmlTypeLoaderThread::loadWithCachedUnit(QQmlDataBlob *b, const QQmlPrivate::CachedQmlUnit *unit)
+void QQmlTypeLoaderThread::loadWithCachedUnit(QQmlDataBlob *b, const QV4::CompiledData::Unit *unit)
{
b->addref();
callMethodInThread(&This::loadWithCachedUnitThread, b, unit);
}
-void QQmlTypeLoaderThread::loadWithCachedUnitAsync(QQmlDataBlob *b, const QQmlPrivate::CachedQmlUnit *unit)
+void QQmlTypeLoaderThread::loadWithCachedUnitAsync(QQmlDataBlob *b, const QV4::CompiledData::Unit *unit)
{
b->addref();
postMethodToThread(&This::loadWithCachedUnitThread, b, unit);
@@ -865,9 +877,9 @@ void QQmlTypeLoaderThread::shutdownThread()
{
#if QT_CONFIG(qml_network)
delete m_networkAccessManager;
- m_networkAccessManager = 0;
+ m_networkAccessManager = nullptr;
delete m_networkReplyProxy;
- m_networkReplyProxy = 0;
+ m_networkReplyProxy = nullptr;
#endif // qml_network
}
@@ -883,7 +895,7 @@ void QQmlTypeLoaderThread::loadWithStaticDataThread(QQmlDataBlob *b, const QByte
b->release();
}
-void QQmlTypeLoaderThread::loadWithCachedUnitThread(QQmlDataBlob *b, const QQmlPrivate::CachedQmlUnit *unit)
+void QQmlTypeLoaderThread::loadWithCachedUnitThread(QQmlDataBlob *b, const QV4::CompiledData::Unit *unit)
{
m_loader->loadWithCachedUnitThread(b, unit);
b->release();
@@ -893,7 +905,7 @@ void QQmlTypeLoaderThread::callCompletedMain(QQmlDataBlob *b)
{
QML_MEMORY_SCOPE_URL(b->url());
#ifdef DATABLOB_DEBUG
- qWarning("QQmlTypeLoaderThread: %s completed() callback", qPrintable(b->url().toString()));
+ qWarning("QQmlTypeLoaderThread: %s completed() callback", qPrintable(b->urlString()));
#endif
b->completed();
b->release();
@@ -903,7 +915,7 @@ void QQmlTypeLoaderThread::callDownloadProgressChangedMain(QQmlDataBlob *b, qrea
{
#ifdef DATABLOB_DEBUG
qWarning("QQmlTypeLoaderThread: %s downloadProgressChanged(%f) callback",
- qPrintable(b->url().toString()), p);
+ qPrintable(b->urlString()), p);
#endif
b->downloadProgressChanged(p);
b->release();
@@ -951,7 +963,7 @@ void QQmlTypeLoader::invalidate()
if (m_thread) {
shutdownThread();
delete m_thread;
- m_thread = 0;
+ m_thread = nullptr;
}
#if QT_CONFIG(qml_network)
@@ -1021,8 +1033,8 @@ struct StaticLoader {
};
struct CachedLoader {
- const QQmlPrivate::CachedQmlUnit *unit;
- CachedLoader(const QQmlPrivate::CachedQmlUnit *unit) : unit(unit) {}
+ const QV4::CompiledData::Unit *unit;
+ CachedLoader(const QV4::CompiledData::Unit *unit) : unit(unit) {}
void loadThread(QQmlTypeLoader *loader, QQmlDataBlob *blob) const
{
@@ -1042,7 +1054,7 @@ template<typename Loader>
void QQmlTypeLoader::doLoad(const Loader &loader, QQmlDataBlob *blob, Mode mode)
{
#ifdef DATABLOB_DEBUG
- qWarning("QQmlTypeLoader::doLoad(%s): %s thread", qPrintable(blob->m_url.toString()),
+ qWarning("QQmlTypeLoader::doLoad(%s): %s thread", qPrintable(blob->urlString()),
m_thread->isThisThread()?"Compile":"Engine");
#endif
#ifdef Q_OS_HTML5
@@ -1095,7 +1107,7 @@ void QQmlTypeLoader::loadWithStaticData(QQmlDataBlob *blob, const QByteArray &da
doLoad(StaticLoader(data), blob, mode);
}
-void QQmlTypeLoader::loadWithCachedUnit(QQmlDataBlob *blob, const QQmlPrivate::CachedQmlUnit *unit, Mode mode)
+void QQmlTypeLoader::loadWithCachedUnit(QQmlDataBlob *blob, const QV4::CompiledData::Unit *unit, Mode mode)
{
doLoad(CachedLoader(unit), blob, mode);
}
@@ -1107,7 +1119,7 @@ void QQmlTypeLoader::loadWithStaticDataThread(QQmlDataBlob *blob, const QByteArr
setData(blob, data);
}
-void QQmlTypeLoader::loadWithCachedUnitThread(QQmlDataBlob *blob, const QQmlPrivate::CachedQmlUnit *unit)
+void QQmlTypeLoader::loadWithCachedUnitThread(QQmlDataBlob *blob, const QV4::CompiledData::Unit *unit)
{
ASSERT_LOADTHREAD();
@@ -1165,7 +1177,7 @@ void QQmlTypeLoader::loadThread(QQmlDataBlob *blob)
}
#ifdef DATABLOB_DEBUG
- qWarning("QQmlDataBlob: requested %s", qPrintable(blob->url().toString()));
+ qWarning("QQmlDataBlob: requested %s", qPrintable(blob->urlString()));
#endif // DATABLOB_DEBUG
#endif // qml_network
}
@@ -1191,14 +1203,15 @@ void QQmlTypeLoader::networkReplyFinished(QNetworkReply *reply)
QVariant redirect = reply->attribute(QNetworkRequest::RedirectionTargetAttribute);
if (redirect.isValid()) {
QUrl url = reply->url().resolved(redirect.toUrl());
- blob->m_finalUrl = url;
+ blob->m_url = url;
+ blob->m_urlString.clear();
QNetworkReply *reply = m_thread->networkAccessManager()->get(QNetworkRequest(url));
QObject *nrp = m_thread->networkReplyProxy();
QObject::connect(reply, SIGNAL(finished()), nrp, SLOT(finished()));
m_networkReplies.insert(reply, blob);
#ifdef DATABLOB_DEBUG
- qWarning("QQmlDataBlob: redirected to %s", qPrintable(blob->m_finalUrl.toString()));
+ qWarning("QQmlDataBlob: redirected to %s", qPrintable(blob->urlString()));
#endif
return;
}
@@ -1294,7 +1307,7 @@ void QQmlTypeLoader::setData(QQmlDataBlob *blob, const QQmlDataBlob::SourceCodeD
blob->tryDone();
}
-void QQmlTypeLoader::setCachedUnit(QQmlDataBlob *blob, const QQmlPrivate::CachedQmlUnit *unit)
+void QQmlTypeLoader::setCachedUnit(QQmlDataBlob *blob, const QV4::CompiledData::Unit *unit)
{
QML_MEMORY_SCOPE_URL(blob->url());
QQmlCompilingProfiler prof(profiler(), blob);
@@ -1354,7 +1367,7 @@ bool QQmlTypeLoader::Blob::fetchQmldir(const QUrl &url, const QV4::CompiledData:
bool QQmlTypeLoader::Blob::updateQmldir(QQmlQmldirData *data, const QV4::CompiledData::Import *import, QList<QQmlError> *errors)
{
- QString qmldirIdentifier = data->url().toString();
+ QString qmldirIdentifier = data->urlString();
QString qmldirUrl = qmldirIdentifier.left(qmldirIdentifier.lastIndexOf(QLatin1Char('/')) + 1);
typeLoader()->setQmldirContent(qmldirIdentifier, data->content());
@@ -1442,8 +1455,13 @@ bool QQmlTypeLoader::Blob::addImport(const QV4::CompiledData::Import *import, QL
// We haven't yet resolved this import
m_unresolvedImports.insert(import, 0);
- // Query any network import paths for this library
- QStringList remotePathList = importDatabase->importPathList(QQmlImportDatabase::Remote);
+ QQmlAbstractUrlInterceptor *interceptor = typeLoader()->engine()->urlInterceptor();
+
+ // Query any network import paths for this library.
+ // Interceptor might redirect local paths.
+ QStringList remotePathList = importDatabase->importPathList(
+ interceptor ? QQmlImportDatabase::LocalOrRemote
+ : QQmlImportDatabase::Remote);
if (!remotePathList.isEmpty()) {
// Add this library and request the possible locations for it
if (!m_importCache.addLibraryImport(importDatabase, importUri, importQualifier, import->majorVersion,
@@ -1454,8 +1472,18 @@ bool QQmlTypeLoader::Blob::addImport(const QV4::CompiledData::Import *import, QL
int priority = 0;
const QStringList qmlDirPaths = QQmlImports::completeQmldirPaths(importUri, remotePathList, import->majorVersion, import->minorVersion);
for (const QString &qmldirPath : qmlDirPaths) {
- if (!fetchQmldir(QUrl(qmldirPath), import, ++priority, errors))
+ if (interceptor) {
+ QUrl url = interceptor->intercept(
+ QQmlImports::urlFromLocalFileOrQrcOrUrl(qmldirPath),
+ QQmlAbstractUrlInterceptor::QmldirFile);
+ if (!QQmlFile::isLocalFile(url)
+ && !fetchQmldir(url, import, ++priority, errors)) {
+ return false;
+ }
+ } else if (!fetchQmldir(QUrl(qmldirPath), import, ++priority, errors)) {
return false;
+ }
+
}
}
}
@@ -1514,7 +1542,7 @@ void QQmlTypeLoader::Blob::dependencyComplete(QQmlDataBlob *blob)
bool QQmlTypeLoader::Blob::isDebugging() const
{
- return QV8Engine::getV4(typeLoader()->engine())->debugger() != 0;
+ return typeLoader()->engine()->handle()->debugger() != nullptr;
}
bool QQmlTypeLoader::Blob::qmldirDataAvailable(QQmlQmldirData *data, QList<QQmlError> *errors)
@@ -1522,7 +1550,7 @@ bool QQmlTypeLoader::Blob::qmldirDataAvailable(QQmlQmldirData *data, QList<QQmlE
bool resolve = true;
const QV4::CompiledData::Import *import = data->import(this);
- data->setImport(this, 0);
+ data->setImport(this, nullptr);
int priority = data->priority(this);
data->setPriority(this, 0);
@@ -1656,7 +1684,7 @@ QQmlTypeData *QQmlTypeLoader::getType(const QUrl &url, Mode mode)
typeData = new QQmlTypeData(url, this);
// TODO: if (compiledData == 0), is it safe to omit this insertion?
m_typeCache.insert(url, typeData);
- if (const QQmlPrivate::CachedQmlUnit *cachedUnit = QQmlMetaType::findCachedCompilationUnit(typeData->url())) {
+ if (const QV4::CompiledData::Unit *cachedUnit = QQmlMetaType::findCachedCompilationUnit(typeData->url())) {
QQmlTypeLoader::loadWithCachedUnit(typeData, cachedUnit, mode);
} else {
QQmlTypeLoader::load(typeData, mode);
@@ -1717,7 +1745,7 @@ QQmlScriptBlob *QQmlTypeLoader::getScript(const QUrl &url)
scriptBlob = new QQmlScriptBlob(url, this);
m_scriptCache.insert(url, scriptBlob);
- if (const QQmlPrivate::CachedQmlUnit *cachedUnit = QQmlMetaType::findCachedCompilationUnit(scriptBlob->url())) {
+ if (const QV4::CompiledData::Unit *cachedUnit = QQmlMetaType::findCachedCompilationUnit(scriptBlob->url())) {
QQmlTypeLoader::loadWithCachedUnit(scriptBlob, cachedUnit);
} else {
QQmlTypeLoader::load(scriptBlob);
@@ -1805,7 +1833,7 @@ QString QQmlTypeLoader::absoluteFilePath(const QString &path)
if (!m_importDirCache.contains(dirPath)) {
bool exists = QDir(dirPath).exists();
- QCache<QString, bool> *entry = exists ? new QCache<QString, bool> : 0;
+ QCache<QString, bool> *entry = exists ? new QCache<QString, bool> : nullptr;
m_importDirCache.insert(dirPath, entry);
}
QCache<QString, bool> *fileSet = m_importDirCache.object(dirPath);
@@ -1868,12 +1896,12 @@ bool QQmlTypeLoader::directoryExists(const QString &path)
if (!m_importDirCache.contains(dirPath)) {
bool exists = QDir(dirPath).exists();
- QCache<QString, bool> *files = exists ? new QCache<QString, bool> : 0;
+ QCache<QString, bool> *files = exists ? new QCache<QString, bool> : nullptr;
m_importDirCache.insert(dirPath, files);
}
QCache<QString, bool> *fileSet = m_importDirCache.object(dirPath);
- return fileSet != 0;
+ return fileSet != nullptr;
}
@@ -1886,19 +1914,22 @@ It can also be a remote path for a remote directory import, but it will have bee
*/
const QQmlTypeLoaderQmldirContent *QQmlTypeLoader::qmldirContent(const QString &filePathIn)
{
- QUrl url(filePathIn); //May already contain http scheme
- if (url.scheme() == QLatin1String("http") || url.scheme() == QLatin1String("https"))
- return *(m_importQmlDirCache.value(filePathIn)); //Can't load the remote here, but should be cached
- else
- url = QUrl::fromLocalFile(filePathIn);
- if (engine() && engine()->urlInterceptor())
- url = engine()->urlInterceptor()->intercept(url, QQmlAbstractUrlInterceptor::QmldirFile);
- Q_ASSERT(url.scheme() == QLatin1String("file"));
QString filePath;
- if (url.scheme() == QLatin1String("file"))
- filePath = url.toLocalFile();
- else
- filePath = url.path();
+
+ // Try to guess if filePathIn is already a URL. This is necessarily fragile, because
+ // - paths can contain ':', which might make them appear as URLs with schemes.
+ // - windows drive letters appear as schemes (thus "< 2" below).
+ // - a "file:" URL is equivalent to the respective file, but will be treated differently.
+ // Yet, this heuristic is the best we can do until we pass more structured information here,
+ // for example a QUrl also for local files.
+ QUrl url(filePathIn);
+ if (url.scheme().length() < 2) {
+ filePath = filePathIn;
+ } else {
+ filePath = QQmlFile::urlToLocalFileOrQrc(url);
+ if (filePath.isEmpty()) // Can't load the remote here, but should be cached
+ return *(m_importQmlDirCache.value(filePathIn));
+ }
QQmlTypeLoaderQmldirContent *qmldir;
QQmlTypeLoaderQmldirContent **val = m_importQmlDirCache.value(filePath);
@@ -2092,7 +2123,7 @@ bool QQmlTypeData::tryLoadFromDiskCache()
if (isDebugging())
return false;
- QV4::ExecutionEngine *v4 = QQmlEnginePrivate::getV4Engine(typeLoader()->engine());
+ QV4::ExecutionEngine *v4 = typeLoader()->engine()->handle();
if (!v4)
return false;
@@ -2100,7 +2131,7 @@ bool QQmlTypeData::tryLoadFromDiskCache()
{
QString error;
if (!unit->loadFromDisk(url(), m_backupSourceCode.sourceTimeStamp(), &error)) {
- qCDebug(DBG_DISK_CACHE) << "Error loading" << url().toString() << "from disk cache:" << error;
+ qCDebug(DBG_DISK_CACHE) << "Error loading" << urlString() << "from disk cache:" << error;
return false;
}
}
@@ -2171,8 +2202,12 @@ void QQmlTypeData::createTypeAndPropertyCaches(const QQmlRefPointer<QQmlTypeName
QQmlEnginePrivate * const engine = QQmlEnginePrivate::get(typeLoader()->engine());
+ QQmlPendingGroupPropertyBindings pendingGroupPropertyBindings;
+
{
- QQmlPropertyCacheCreator<QV4::CompiledData::CompilationUnit> propertyCacheCreator(&m_compiledData->propertyCaches, engine, m_compiledData, &m_importCache);
+ QQmlPropertyCacheCreator<QV4::CompiledData::CompilationUnit> propertyCacheCreator(&m_compiledData->propertyCaches,
+ &pendingGroupPropertyBindings,
+ engine, m_compiledData, &m_importCache);
QQmlCompileError error = propertyCacheCreator.buildMetaObjects();
if (error.isSet()) {
setError(error);
@@ -2182,6 +2217,8 @@ void QQmlTypeData::createTypeAndPropertyCaches(const QQmlRefPointer<QQmlTypeName
QQmlPropertyCacheAliasCreator<QV4::CompiledData::CompilationUnit> aliasCreator(&m_compiledData->propertyCaches, m_compiledData);
aliasCreator.appendAliasPropertiesToMetaObjects();
+
+ pendingGroupPropertyBindings.resolveMissingPropertyCaches(engine, &m_compiledData->propertyCaches);
}
static bool addTypeReferenceChecksumsToHash(const QList<QQmlTypeData::TypeReference> &typeRefs, QCryptographicHash *hash, QQmlEngine *engine)
@@ -2220,10 +2257,10 @@ void QQmlTypeData::done()
if (script.script->isError()) {
QList<QQmlError> errors = script.script->errors();
QQmlError error;
- error.setUrl(finalUrl());
+ error.setUrl(url());
error.setLine(script.location.line);
error.setColumn(script.location.column);
- error.setDescription(QQmlTypeLoader::tr("Script %1 unavailable").arg(script.script->url().toString()));
+ error.setDescription(QQmlTypeLoader::tr("Script %1 unavailable").arg(script.script->urlString()));
errors.prepend(error);
setError(errors);
return;
@@ -2240,7 +2277,7 @@ void QQmlTypeData::done()
QList<QQmlError> errors = type.typeData->errors();
QQmlError error;
- error.setUrl(finalUrl());
+ error.setUrl(url());
error.setLine(type.location.line);
error.setColumn(type.location.column);
error.setDescription(QQmlTypeLoader::tr("Type %1 unavailable").arg(typeName));
@@ -2259,7 +2296,7 @@ void QQmlTypeData::done()
QList<QQmlError> errors = type.typeData->errors();
QQmlError error;
- error.setUrl(finalUrl());
+ error.setUrl(url());
error.setLine(type.location.line);
error.setColumn(type.location.column);
error.setDescription(QQmlTypeLoader::tr("Type %1 unavailable").arg(typeName));
@@ -2289,7 +2326,7 @@ void QQmlTypeData::done()
// verify if any dependencies changed if we're using a cache
if (m_document.isNull() && !m_compiledData->verifyChecksum(dependencyHasher)) {
- qCDebug(DBG_DISK_CACHE) << "Checksum mismatch for cached version of" << m_compiledData->url().toString();
+ qCDebug(DBG_DISK_CACHE) << "Checksum mismatch for cached version of" << m_compiledData->fileName();
if (!loadFromSource())
return;
m_backupSourceCode = SourceCodeData();
@@ -2420,10 +2457,14 @@ void QQmlTypeData::dataReceived(const SourceCodeData &data)
continueLoadFromIR();
}
-void QQmlTypeData::initializeFromCachedUnit(const QQmlPrivate::CachedQmlUnit *unit)
+void QQmlTypeData::initializeFromCachedUnit(const QV4::CompiledData::Unit *unit)
{
m_document.reset(new QmlIR::Document(isDebugging()));
- unit->loadIR(m_document.data(), unit);
+ QmlIR::IRLoader loader(unit, m_document.data());
+ loader.load();
+ m_document->jsModule.fileName = urlString();
+ m_document->jsModule.finalUrl = finalUrlString();
+ m_document->javaScriptCompilationUnit.adopt(new QV4::CompiledData::CompilationUnit(unit));
continueLoadFromIR();
}
@@ -2432,7 +2473,7 @@ bool QQmlTypeData::loadFromSource()
m_document.reset(new QmlIR::Document(isDebugging()));
m_document->jsModule.sourceTimeStamp = m_backupSourceCode.sourceTimeStamp();
QQmlEngine *qmlEngine = typeLoader()->engine();
- QmlIR::IRBuilder compiler(QV8Engine::get(qmlEngine)->illegalNames());
+ QmlIR::IRBuilder compiler(qmlEngine->handle()->v8Engine->illegalNames());
QString sourceError;
const QString source = m_backupSourceCode.readAll(&sourceError);
@@ -2446,7 +2487,7 @@ bool QQmlTypeData::loadFromSource()
errors.reserve(compiler.errors.count());
for (const QQmlJS::DiagnosticMessage &msg : qAsConst(compiler.errors)) {
QQmlError e;
- e.setUrl(finalUrl());
+ e.setUrl(url());
e.setLine(msg.loc.startLine);
e.setColumn(msg.loc.startColumn);
e.setDescription(msg.message);
@@ -2463,7 +2504,8 @@ void QQmlTypeData::restoreIR(QQmlRefPointer<QV4::CompiledData::CompilationUnit>
m_document.reset(new QmlIR::Document(isDebugging()));
QmlIR::IRLoader loader(unit->data, m_document.data());
loader.load();
- m_document->jsModule.fileName = finalUrlString();
+ m_document->jsModule.fileName = urlString();
+ m_document->jsModule.finalUrl = finalUrlString();
m_document->javaScriptCompilationUnit = unit;
continueLoadFromIR();
}
@@ -2515,6 +2557,8 @@ void QQmlTypeData::continueLoadFromIR()
void QQmlTypeData::allDependenciesDone()
{
+ QQmlTypeLoader::Blob::allDependenciesDone();
+
if (!m_typesResolved) {
// Check that all imports were resolved
QList<QQmlError> errors;
@@ -2584,7 +2628,7 @@ void QQmlTypeData::compile(const QQmlRefPointer<QQmlTypeNameCache> &typeNameCach
// ignore error, keep using the in-memory compilation unit.
}
} else {
- qCDebug(DBG_DISK_CACHE) << "Error saving cached version of" << m_compiledData->url().toString() << "to disk:" << errorString;
+ qCDebug(DBG_DISK_CACHE) << "Error saving cached version of" << m_compiledData->fileName() << "to disk:" << errorString;
}
}
}
@@ -2634,6 +2678,10 @@ void QQmlTypeData::resolveTypes()
if (ref.type.isCompositeSingleton()) {
ref.typeData = typeLoader()->getType(ref.type.sourceUrl());
+ if (ref.typeData->status() == QQmlDataBlob::ResolvingDependencies) {
+ // TODO: give an error message? If so, we should record and show the path of the cycle.
+ continue;
+ }
addDependency(ref.typeData);
ref.prefix = csRef.prefix;
@@ -2737,7 +2785,7 @@ bool QQmlTypeData::resolveType(const QString &typeName, int &majorVersion, int &
TypeReference &ref, int lineNumber, int columnNumber,
bool reportErrors, QQmlType::RegistrationType registrationType)
{
- QQmlImportNamespace *typeNamespace = 0;
+ QQmlImportNamespace *typeNamespace = nullptr;
QList<QQmlError> errors;
bool typeFound = m_importCache.resolveType(typeName, &ref.type, &majorVersion, &minorVersion,
@@ -2797,9 +2845,9 @@ void QQmlTypeData::scriptImported(QQmlScriptBlob *blob, const QV4::CompiledData:
}
QQmlScriptData::QQmlScriptData()
- : typeNameCache(0)
+ : typeNameCache(nullptr)
, m_loaded(false)
- , m_program(0)
+ , m_program(nullptr)
{
}
@@ -2814,11 +2862,9 @@ void QQmlScriptData::initialize(QQmlEngine *engine)
Q_ASSERT(engine);
Q_ASSERT(!hasEngine());
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
- QV8Engine *v8engine = ep->v8engine();
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(v8engine);
+ QV4::ExecutionEngine *v4 = engine->handle();
- m_program = new QV4::Script(v4, 0, m_precompiledScript);
+ m_program = new QV4::Script(v4, nullptr, m_precompiledScript);
addToEngine(engine);
@@ -2832,14 +2878,14 @@ QV4::ReturnedValue QQmlScriptData::scriptValueForContext(QQmlContextData *parent
Q_ASSERT(parentCtxt && parentCtxt->engine);
QQmlEnginePrivate *ep = QQmlEnginePrivate::get(parentCtxt->engine);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(parentCtxt->engine);
+ QV4::ExecutionEngine *v4 = parentCtxt->engine->handle();
QV4::Scope scope(v4);
bool shared = m_precompiledScript->data->flags & QV4::CompiledData::Unit::IsSharedLibrary;
QQmlContextData *effectiveCtxt = parentCtxt;
if (shared)
- effectiveCtxt = 0;
+ effectiveCtxt = nullptr;
// Create the script context if required
QQmlContextDataRef ctxt(new QQmlContextData);
@@ -2887,10 +2933,11 @@ QV4::ReturnedValue QQmlScriptData::scriptValueForContext(QQmlContextData *parent
return QV4::Encode::undefined();
}
- QV4::Scoped<QV4::QmlContext> qmlContext(scope, QV4::QmlContext::create(v4->rootContext(), ctxt, 0));
+ QV4::Scoped<QV4::QmlContext> qmlContext(scope, QV4::QmlContext::create(v4->rootContext(), ctxt, nullptr));
m_program->qmlContext.set(scope.engine, qmlContext);
m_program->run();
+ m_program->qmlContext.clear();
if (scope.engine->hasException) {
QQmlError error = scope.engine->catchExceptionAsQmlError();
if (error.isValid())
@@ -2910,7 +2957,7 @@ void QQmlScriptData::clear()
{
if (typeNameCache) {
typeNameCache->release();
- typeNameCache = 0;
+ typeNameCache = nullptr;
}
for (int ii = 0; ii < scripts.count(); ++ii)
@@ -2922,7 +2969,7 @@ void QQmlScriptData::clear()
}
QQmlScriptBlob::QQmlScriptBlob(const QUrl &url, QQmlTypeLoader *loader)
-: QQmlTypeLoader::Blob(url, JavaScriptFile, loader), m_scriptData(0)
+: QQmlTypeLoader::Blob(url, JavaScriptFile, loader), m_scriptData(nullptr)
{
}
@@ -2930,7 +2977,7 @@ QQmlScriptBlob::~QQmlScriptBlob()
{
if (m_scriptData) {
m_scriptData->release();
- m_scriptData = 0;
+ m_scriptData = nullptr;
}
}
@@ -2948,7 +2995,7 @@ void QQmlScriptBlob::dataReceived(const SourceCodeData &data)
initializeFromCompilationUnit(unit);
return;
} else {
- qCDebug(DBG_DISK_CACHE()) << "Error loading" << url().toString() << "from disk cache:" << error;
+ qCDebug(DBG_DISK_CACHE()) << "Error loading" << urlString() << "from disk cache:" << error;
}
}
@@ -2966,7 +3013,9 @@ void QQmlScriptBlob::dataReceived(const SourceCodeData &data)
QmlIR::ScriptDirectivesCollector collector(&irUnit.jsParserEngine, &irUnit.jsGenerator);
QList<QQmlError> errors;
- QQmlRefPointer<QV4::CompiledData::CompilationUnit> unit = QV4::Script::precompile(&irUnit.jsModule, &irUnit.jsGenerator, finalUrl(), source, &errors, &collector);
+ QQmlRefPointer<QV4::CompiledData::CompilationUnit> unit = QV4::Script::precompile(
+ &irUnit.jsModule, &irUnit.jsGenerator, urlString(), finalUrlString(),
+ source, &errors, &collector);
// No need to addref on unit, it's initial refcount is 1
source.clear();
if (!errors.isEmpty()) {
@@ -2987,19 +3036,21 @@ void QQmlScriptBlob::dataReceived(const SourceCodeData &data)
// The js unit owns the data and will free the qml unit.
unit->data = unitData;
- if (!disableDiskCache() || forceDiskCache()) {
+ if ((!disableDiskCache() || forceDiskCache()) && !isDebugging()) {
QString errorString;
if (!unit->saveToDisk(url(), &errorString)) {
- qCDebug(DBG_DISK_CACHE()) << "Error saving cached version of" << unit->url().toString() << "to disk:" << errorString;
+ qCDebug(DBG_DISK_CACHE()) << "Error saving cached version of" << unit->fileName() << "to disk:" << errorString;
}
}
initializeFromCompilationUnit(unit);
}
-void QQmlScriptBlob::initializeFromCachedUnit(const QQmlPrivate::CachedQmlUnit *unit)
+void QQmlScriptBlob::initializeFromCachedUnit(const QV4::CompiledData::Unit *unit)
{
- initializeFromCompilationUnit(unit->createCompilationUnit());
+ QQmlRefPointer<QV4::CompiledData::CompilationUnit> compilationUnit;
+ compilationUnit.adopt(new QV4::CompiledData::CompilationUnit(unit));
+ initializeFromCompilationUnit(compilationUnit);
}
void QQmlScriptBlob::done()
@@ -3014,10 +3065,10 @@ void QQmlScriptBlob::done()
if (script.script->isError()) {
QList<QQmlError> errors = script.script->errors();
QQmlError error;
- error.setUrl(finalUrl());
+ error.setUrl(url());
error.setLine(script.location.line);
error.setColumn(script.location.column);
- error.setDescription(QQmlTypeLoader::tr("Script %1 unavailable").arg(script.script->url().toString()));
+ error.setDescription(QQmlTypeLoader::tr("Script %1 unavailable").arg(script.script->urlString()));
errors.prepend(error);
setError(errors);
return;
@@ -3061,7 +3112,7 @@ void QQmlScriptBlob::scriptImported(QQmlScriptBlob *blob, const QV4::CompiledDat
m_scripts << ref;
}
-void QQmlScriptBlob::initializeFromCompilationUnit(QV4::CompiledData::CompilationUnit *unit)
+void QQmlScriptBlob::initializeFromCompilationUnit(const QQmlRefPointer<QV4::CompiledData::CompilationUnit> &unit)
{
Q_ASSERT(!m_scriptData);
m_scriptData = new QQmlScriptData();
@@ -3105,7 +3156,7 @@ const QV4::CompiledData::Import *QQmlQmldirData::import(QQmlTypeLoader::Blob *bl
QHash<QQmlTypeLoader::Blob *, const QV4::CompiledData::Import *>::const_iterator it =
m_imports.find(blob);
if (it == m_imports.end())
- return 0;
+ return nullptr;
return *it;
}
@@ -3137,7 +3188,7 @@ void QQmlQmldirData::dataReceived(const SourceCodeData &data)
}
}
-void QQmlQmldirData::initializeFromCachedUnit(const QQmlPrivate::CachedQmlUnit *)
+void QQmlQmldirData::initializeFromCachedUnit(const QV4::CompiledData::Unit *)
{
Q_UNIMPLEMENTED();
}
diff --git a/src/qml/qml/qqmltypeloader_p.h b/src/qml/qml/qqmltypeloader_p.h
index 7218858726..e1a7ac7f06 100644
--- a/src/qml/qml/qqmltypeloader_p.h
+++ b/src/qml/qml/qqmltypeloader_p.h
@@ -98,6 +98,7 @@ public:
Null, // Prior to QQmlTypeLoader::load()
Loading, // Prior to data being received and dataReceived() being called
WaitingForDependencies, // While there are outstanding addDependency()s
+ ResolvingDependencies, // While resolving outstanding dependencies, to detect cycles
Complete, // Finished
Error // Error
};
@@ -109,7 +110,7 @@ public:
};
QQmlDataBlob(const QUrl &, Type, QQmlTypeLoader* manager);
- virtual ~QQmlDataBlob();
+ ~QQmlDataBlob() override;
void startLoading();
@@ -128,6 +129,7 @@ public:
qreal progress() const;
QUrl url() const;
+ QString urlString() const;
QUrl finalUrl() const;
QString finalUrlString() const;
@@ -156,7 +158,7 @@ protected:
// Callbacks made in load thread
virtual void dataReceived(const SourceCodeData &) = 0;
- virtual void initializeFromCachedUnit(const QQmlPrivate::CachedQmlUnit*) = 0;
+ virtual void initializeFromCachedUnit(const QV4::CompiledData::Unit*) = 0;
virtual void done();
#if QT_CONFIG(qml_network)
virtual void networkError(QNetworkReply::NetworkError);
@@ -206,6 +208,7 @@ private:
QUrl m_url;
QUrl m_finalUrl;
+ mutable QString m_urlString;
mutable QString m_finalUrlString;
// List of QQmlDataBlob's that are waiting for me to complete.
@@ -265,7 +268,7 @@ public:
{
public:
Blob(const QUrl &url, QQmlDataBlob::Type type, QQmlTypeLoader *loader);
- ~Blob();
+ ~Blob() override;
const QQmlImports &imports() const { return m_importCache; }
@@ -321,7 +324,7 @@ public:
void load(QQmlDataBlob *, Mode = PreferSynchronous);
void loadWithStaticData(QQmlDataBlob *, const QByteArray &, Mode = PreferSynchronous);
- void loadWithCachedUnit(QQmlDataBlob *blob, const QQmlPrivate::CachedQmlUnit *unit, Mode mode = PreferSynchronous);
+ void loadWithCachedUnit(QQmlDataBlob *blob, const QV4::CompiledData::Unit *unit, Mode mode = PreferSynchronous);
QQmlEngine *engine() const;
void initializeEngine(QQmlExtensionInterface *, const char *);
@@ -347,7 +350,7 @@ private:
void loadThread(QQmlDataBlob *);
void loadWithStaticDataThread(QQmlDataBlob *, const QByteArray &);
- void loadWithCachedUnitThread(QQmlDataBlob *blob, const QQmlPrivate::CachedQmlUnit *unit);
+ void loadWithCachedUnitThread(QQmlDataBlob *blob, const QV4::CompiledData::Unit *unit);
#if QT_CONFIG(qml_network)
void networkReplyFinished(QNetworkReply *);
void networkReplyProgress(QNetworkReply *, qint64, qint64);
@@ -358,7 +361,7 @@ private:
void setData(QQmlDataBlob *, const QByteArray &);
void setData(QQmlDataBlob *, const QString &fileName);
void setData(QQmlDataBlob *, const QQmlDataBlob::SourceCodeData &);
- void setCachedUnit(QQmlDataBlob *blob, const QQmlPrivate::CachedQmlUnit *unit);
+ void setCachedUnit(QQmlDataBlob *blob, const QV4::CompiledData::Unit *unit);
template<typename T>
struct TypedCallback
@@ -414,7 +417,7 @@ class Q_AUTOTEST_EXPORT QQmlTypeData : public QQmlTypeLoader::Blob
public:
struct TypeReference
{
- TypeReference() : majorVersion(0), minorVersion(0), typeData(0), needsCreation(true) {}
+ TypeReference() : majorVersion(0), minorVersion(0), typeData(nullptr), needsCreation(true) {}
QV4::CompiledData::Location location;
QQmlType type;
@@ -428,7 +431,7 @@ public:
struct ScriptReference
{
- ScriptReference() : script(0) {}
+ ScriptReference() : script(nullptr) {}
QV4::CompiledData::Location location;
QString qualifier;
@@ -441,7 +444,7 @@ private:
QQmlTypeData(const QUrl &, QQmlTypeLoader *);
public:
- ~QQmlTypeData();
+ ~QQmlTypeData() override;
const QList<ScriptReference> &resolvedScripts() const;
@@ -460,7 +463,7 @@ protected:
void done() override;
void completed() override;
void dataReceived(const SourceCodeData &) override;
- void initializeFromCachedUnit(const QQmlPrivate::CachedQmlUnit *unit) override;
+ void initializeFromCachedUnit(const QV4::CompiledData::Unit *unit) override;
void allDependenciesDone() override;
void downloadProgressChanged(qreal) override;
@@ -526,7 +529,7 @@ private:
QQmlScriptData();
public:
- ~QQmlScriptData();
+ ~QQmlScriptData() override;
QUrl url;
QString urlString;
@@ -557,11 +560,11 @@ private:
QQmlScriptBlob(const QUrl &, QQmlTypeLoader *);
public:
- ~QQmlScriptBlob();
+ ~QQmlScriptBlob() override;
struct ScriptReference
{
- ScriptReference() : script(0) {}
+ ScriptReference() : script(nullptr) {}
QV4::CompiledData::Location location;
QString qualifier;
@@ -573,14 +576,14 @@ public:
protected:
void dataReceived(const SourceCodeData &) override;
- void initializeFromCachedUnit(const QQmlPrivate::CachedQmlUnit *unit) override;
+ void initializeFromCachedUnit(const QV4::CompiledData::Unit *unit) override;
void done() override;
QString stringAt(int index) const override;
private:
void scriptImported(QQmlScriptBlob *blob, const QV4::CompiledData::Location &location, const QString &qualifier, const QString &nameSpace) override;
- void initializeFromCompilationUnit(QV4::CompiledData::CompilationUnit *unit);
+ void initializeFromCompilationUnit(const QQmlRefPointer<QV4::CompiledData::CompilationUnit> &unit);
QList<ScriptReference> m_scripts;
QQmlScriptData *m_scriptData;
@@ -604,7 +607,7 @@ public:
protected:
void dataReceived(const SourceCodeData &) override;
- void initializeFromCachedUnit(const QQmlPrivate::CachedQmlUnit*) override;
+ void initializeFromCachedUnit(const QV4::CompiledData::Unit *) override;
private:
QString m_content;
diff --git a/src/qml/qml/qqmltypenamecache.cpp b/src/qml/qml/qqmltypenamecache.cpp
index 32b0fa16c4..8f1a61e6ad 100644
--- a/src/qml/qml/qqmltypenamecache.cpp
+++ b/src/qml/qml/qqmltypenamecache.cpp
@@ -56,7 +56,7 @@ void QQmlTypeNameCache::add(const QHashedString &name, const QUrl &url, const QH
{
if (nameSpace.length() != 0) {
QQmlImportRef *i = m_namedImports.value(nameSpace);
- Q_ASSERT(i != 0);
+ Q_ASSERT(i != nullptr);
i->compositeSingletons.insert(name, url);
return;
}
@@ -75,7 +75,7 @@ void QQmlTypeNameCache::add(const QHashedString &name, int importedScriptIndex,
if (nameSpace.length() != 0) {
QQmlImportRef *i = m_namedImports.value(nameSpace);
- Q_ASSERT(i != 0);
+ Q_ASSERT(i != nullptr);
m_namespacedImports[i].insert(name, import);
return;
}
@@ -98,10 +98,10 @@ QQmlTypeNameCache::Result QQmlTypeNameCache::query(const QHashedStringRef &name)
if (!result.isValid()) {
// Look up anonymous types from the imports of this document
- QQmlImportNamespace *typeNamespace = 0;
+ QQmlImportNamespace *typeNamespace = nullptr;
QList<QQmlError> errors;
QQmlType t;
- bool typeFound = m_imports.resolveType(name, &t, 0, 0, &typeNamespace, &errors);
+ bool typeFound = m_imports.resolveType(name, &t, nullptr, nullptr, &typeNamespace, &errors);
if (typeFound) {
return Result(t);
}
@@ -126,10 +126,10 @@ QQmlTypeNameCache::Result QQmlTypeNameCache::query(const QHashedStringRef &name,
// ### it would be nice if QQmlImports allowed us to resolve a namespace
// first, and then types on it.
QString qualifiedTypeName = importNamespace->m_qualifier + QLatin1Char('.') + name.toString();
- QQmlImportNamespace *typeNamespace = 0;
+ QQmlImportNamespace *typeNamespace = nullptr;
QList<QQmlError> errors;
QQmlType t;
- bool typeFound = m_imports.resolveType(qualifiedTypeName, &t, 0, 0, &typeNamespace, &errors);
+ bool typeFound = m_imports.resolveType(qualifiedTypeName, &t, nullptr, nullptr, &typeNamespace, &errors);
if (typeFound) {
return Result(t);
}
@@ -151,10 +151,10 @@ QQmlTypeNameCache::Result QQmlTypeNameCache::query(const QV4::String *name, QQml
if (!result.isValid()) {
// Look up anonymous types from the imports of this document
QString typeName = name->toQStringNoThrow();
- QQmlImportNamespace *typeNamespace = 0;
+ QQmlImportNamespace *typeNamespace = nullptr;
QList<QQmlError> errors;
QQmlType t;
- bool typeFound = m_imports.resolveType(typeName, &t, 0, 0, &typeNamespace, &errors,
+ bool typeFound = m_imports.resolveType(typeName, &t, nullptr, nullptr, &typeNamespace, &errors,
QQmlType::AnyRegistrationType, recursionRestriction);
if (typeFound) {
return Result(t);
@@ -186,10 +186,10 @@ QQmlTypeNameCache::Result QQmlTypeNameCache::query(const QV4::String *name, cons
// ### it would be nice if QQmlImports allowed us to resolve a namespace
// first, and then types on it.
QString qualifiedTypeName = importNamespace->m_qualifier + QLatin1Char('.') + name->toQStringNoThrow();
- QQmlImportNamespace *typeNamespace = 0;
+ QQmlImportNamespace *typeNamespace = nullptr;
QList<QQmlError> errors;
QQmlType t;
- bool typeFound = m_imports.resolveType(qualifiedTypeName, &t, 0, 0, &typeNamespace, &errors);
+ bool typeFound = m_imports.resolveType(qualifiedTypeName, &t, nullptr, nullptr, &typeNamespace, &errors);
if (typeFound) {
return Result(t);
}
diff --git a/src/qml/qml/qqmltypenamecache_p.h b/src/qml/qml/qqmltypenamecache_p.h
index 8ac25c4fbe..28b5e7f0ad 100644
--- a/src/qml/qml/qqmltypenamecache_p.h
+++ b/src/qml/qml/qqmltypenamecache_p.h
@@ -85,7 +85,7 @@ class Q_QML_PRIVATE_EXPORT QQmlTypeNameCache : public QQmlRefCount
{
public:
QQmlTypeNameCache(const QQmlImports &imports);
- virtual ~QQmlTypeNameCache();
+ ~QQmlTypeNameCache() override;
inline bool isEmpty() const;
@@ -162,7 +162,7 @@ private:
};
QQmlTypeNameCache::Result::Result()
-: importNamespace(0), scriptIndex(-1)
+: importNamespace(nullptr), scriptIndex(-1)
{
}
@@ -172,12 +172,12 @@ QQmlTypeNameCache::Result::Result(const QQmlImportRef *importNamespace)
}
QQmlTypeNameCache::Result::Result(const QQmlType &type)
-: type(type), importNamespace(0), scriptIndex(-1)
+: type(type), importNamespace(nullptr), scriptIndex(-1)
{
}
QQmlTypeNameCache::Result::Result(int scriptIndex)
-: importNamespace(0), scriptIndex(scriptIndex)
+: importNamespace(nullptr), scriptIndex(scriptIndex)
{
}
diff --git a/src/qml/qml/qqmltypewrapper.cpp b/src/qml/qml/qqmltypewrapper.cpp
index 404bc0612e..6dbf6ad8c1 100644
--- a/src/qml/qml/qqmltypewrapper.cpp
+++ b/src/qml/qml/qqmltypewrapper.cpp
@@ -85,7 +85,7 @@ bool QQmlTypeWrapper::isSingleton() const
QObject* QQmlTypeWrapper::singletonObject() const
{
if (!isSingleton())
- return 0;
+ return nullptr;
QQmlEngine *e = engine()->qmlEngine();
QQmlType::SingletonInstanceInfo *siinfo = d()->type().singletonInstanceInfo();
@@ -134,11 +134,11 @@ ReturnedValue QQmlTypeWrapper::create(QV4::ExecutionEngine *engine, QObject *o,
}
static int enumForSingleton(QV4::ExecutionEngine *v4, String *name, QObject *qobjectSingleton,
- const QQmlType &type)
+ const QQmlType &type, bool *ok)
{
- bool ok;
- int value = type.enumValue(QQmlEnginePrivate::get(v4->qmlEngine()), name, &ok);
- if (ok)
+ Q_ASSERT(ok != nullptr);
+ int value = type.enumValue(QQmlEnginePrivate::get(v4->qmlEngine()), name, ok);
+ if (*ok)
return value;
// ### Optimize
@@ -146,10 +146,11 @@ static int enumForSingleton(QV4::ExecutionEngine *v4, String *name, QObject *qob
const QMetaObject *metaObject = qobjectSingleton->metaObject();
for (int ii = metaObject->enumeratorCount() - 1; ii >= 0; --ii) {
QMetaEnum e = metaObject->enumerator(ii);
- value = e.keyToValue(enumName.constData(), &ok);
- if (ok)
+ value = e.keyToValue(enumName.constData(), ok);
+ if (*ok)
return value;
}
+ *ok = false;
return -1;
}
@@ -192,8 +193,9 @@ ReturnedValue QQmlTypeWrapper::get(const Managed *m, String *name, bool *hasProp
// check for enum value
const bool includeEnums = w->d()->mode == Heap::QQmlTypeWrapper::IncludeEnums;
if (includeEnums && name->startsWithUpper()) {
- const int value = enumForSingleton(v4, name, qobjectSingleton, type);
- if (value != -1)
+ bool ok = false;
+ const int value = enumForSingleton(v4, name, qobjectSingleton, type, &ok);
+ if (ok)
return QV4::Primitive::fromInt32(value).asReturnedValue();
}
@@ -205,8 +207,8 @@ ReturnedValue QQmlTypeWrapper::get(const Managed *m, String *name, bool *hasProp
// Warn when attempting to access a lowercased enum value, singleton case
if (!ok && includeEnums && !name->startsWithUpper()) {
- const int value = enumForSingleton(v4, name, qobjectSingleton, type);
- if (value != -1)
+ enumForSingleton(v4, name, qobjectSingleton, type, &ok);
+ if (ok)
return throwLowercaseEnumError(v4, name, type);
}
diff --git a/src/qml/qml/qqmlvaluetype.cpp b/src/qml/qml/qqmlvaluetype.cpp
index 520f512b1a..270414a676 100644
--- a/src/qml/qml/qqmlvaluetype.cpp
+++ b/src/qml/qml/qqmlvaluetype.cpp
@@ -68,7 +68,7 @@ struct QQmlValueTypeFactoryImpl
QQmlValueTypeFactoryImpl::QQmlValueTypeFactoryImpl()
{
for (unsigned int ii = 0; ii < QVariant::UserType; ++ii)
- valueTypes[ii] = 0;
+ valueTypes[ii] = nullptr;
// See types wrapped in qqmlmodelindexvaluetype_p.h
qRegisterMetaType<QItemSelectionRange>();
@@ -83,7 +83,7 @@ QQmlValueTypeFactoryImpl::~QQmlValueTypeFactoryImpl()
bool QQmlValueTypeFactoryImpl::isValueType(int idx)
{
if (idx >= (int)QVariant::UserType) {
- return (valueType(idx) != 0);
+ return (valueType(idx) != nullptr);
} else if (idx >= 0
&& idx != QVariant::StringList
&& idx != QMetaType::QObjectStar
@@ -130,7 +130,7 @@ const QMetaObject *QQmlValueTypeFactoryImpl::metaObjectForMetaType(int t)
QMetaType metaType(t);
if (metaType.flags() & QMetaType::IsGadget)
return metaType.metaObject();
- return 0;
+ return nullptr;
}
QQmlValueType *QQmlValueTypeFactoryImpl::valueType(int idx)
@@ -141,7 +141,7 @@ QQmlValueType *QQmlValueTypeFactoryImpl::valueType(int idx)
QHash<int, QQmlValueType *>::iterator it = userTypes.find(idx);
if (it == userTypes.end()) {
- QQmlValueType *vt = 0;
+ QQmlValueType *vt = nullptr;
if (const QMetaObject *mo = metaObjectForMetaType(idx))
vt = new QQmlValueType(idx, mo);
it = userTypes.insert(idx, vt);
@@ -209,14 +209,14 @@ QQmlValueType::~QQmlValueType()
{
QObjectPrivate *op = QObjectPrivate::get(this);
Q_ASSERT(op->metaObject == this);
- op->metaObject = 0;
+ op->metaObject = nullptr;
::free(const_cast<QMetaObject *>(_metaObject));
metaType.destroy(gadgetPtr);
}
void QQmlValueType::read(QObject *obj, int idx)
{
- void *a[] = { gadgetPtr, 0 };
+ void *a[] = { gadgetPtr, nullptr };
QMetaObject::metacall(obj, QMetaObject::ReadProperty, idx, a);
}
@@ -224,7 +224,7 @@ void QQmlValueType::write(QObject *obj, int idx, QQmlPropertyData::WriteFlags fl
{
Q_ASSERT(gadgetPtr);
int status = -1;
- void *a[] = { gadgetPtr, 0, &status, &flags };
+ void *a[] = { gadgetPtr, nullptr, &status, &flags };
QMetaObject::metacall(obj, QMetaObject::WriteProperty, idx, a);
}
diff --git a/src/qml/qml/qqmlvaluetype_p.h b/src/qml/qml/qqmlvaluetype_p.h
index 0502a5d665..4ea71e8955 100644
--- a/src/qml/qml/qqmlvaluetype_p.h
+++ b/src/qml/qml/qqmlvaluetype_p.h
@@ -67,7 +67,7 @@ class Q_QML_PRIVATE_EXPORT QQmlValueType : public QObject, public QAbstractDynam
{
public:
QQmlValueType(int userType, const QMetaObject *metaObject);
- ~QQmlValueType();
+ ~QQmlValueType() override;
void read(QObject *, int);
void write(QObject *, int, QQmlPropertyData::WriteFlags flags);
QVariant value();
@@ -272,19 +272,19 @@ int qmlRegisterValueTypeEnums(const char *uri, int versionMajor, int versionMino
QQmlPrivate::RegisterType type = {
0,
- qRegisterNormalizedMetaType<T *>(pointerName.constData()), 0, 0, 0,
+ qRegisterNormalizedMetaType<T *>(pointerName.constData()), 0, 0, nullptr,
QString(),
uri, versionMajor, versionMinor, qmlName, &T::staticMetaObject,
- 0, 0,
+ nullptr, nullptr,
0, 0, 0,
- 0, 0,
+ nullptr, nullptr,
- 0,
+ nullptr,
0
};
diff --git a/src/qml/qml/qqmlvaluetypeproxybinding.cpp b/src/qml/qml/qqmlvaluetypeproxybinding.cpp
index 7a3e4b2df4..d5cff26444 100644
--- a/src/qml/qml/qqmlvaluetypeproxybinding.cpp
+++ b/src/qml/qml/qqmlvaluetypeproxybinding.cpp
@@ -43,7 +43,7 @@ QT_BEGIN_NAMESPACE
QQmlValueTypeProxyBinding::QQmlValueTypeProxyBinding(QObject *o, QQmlPropertyIndex index)
: QQmlAbstractBinding(),
- m_bindings(0)
+ m_bindings(nullptr)
{
m_target = o;
m_targetIndex = index;
@@ -93,7 +93,7 @@ Removes a collection of bindings, corresponding to the set bits in \a mask.
void QQmlValueTypeProxyBinding::removeBindings(quint32 mask)
{
QQmlAbstractBinding *binding = m_bindings.data();
- QQmlAbstractBinding *lastBinding = 0;
+ QQmlAbstractBinding *lastBinding = nullptr;
while (binding) {
const int valueTypeIndex = binding->targetPropertyIndex().valueTypeIndex();
@@ -102,7 +102,7 @@ void QQmlValueTypeProxyBinding::removeBindings(quint32 mask)
remove->setAddedToObject(false);
binding = remove->nextBinding();
- if (lastBinding == 0)
+ if (lastBinding == nullptr)
m_bindings = remove->nextBinding();
else
lastBinding->setNextBinding(remove->nextBinding());
diff --git a/src/qml/qml/qqmlvaluetypewrapper.cpp b/src/qml/qml/qqmlvaluetypewrapper.cpp
index 90ca08537c..a28115d192 100644
--- a/src/qml/qml/qqmlvaluetypewrapper.cpp
+++ b/src/qml/qml/qqmlvaluetypewrapper.cpp
@@ -98,6 +98,8 @@ void Heap::QQmlValueTypeWrapper::destroy()
valueType->metaType.destruct(gadgetPtr);
::operator delete(gadgetPtr);
}
+ if (_propertyCache)
+ _propertyCache->release();
Object::destroy();
}
@@ -129,7 +131,7 @@ bool QQmlValueTypeReference::readReferenceValue() const
// variant-containing-value-type reference
QVariant variantReferenceValue;
- void *a[] = { &variantReferenceValue, 0 };
+ void *a[] = { &variantReferenceValue, nullptr };
QMetaObject::metacall(d()->object, QMetaObject::ReadProperty, d()->property, a);
int variantReferenceType = variantReferenceValue.userType();
@@ -139,14 +141,14 @@ bool QQmlValueTypeReference::readReferenceValue() const
// We need to modify this reference to the updated value type, if
// possible, or return false if it is not a value type.
if (QQmlValueTypeFactory::isValueType(variantReferenceType)) {
- QQmlPropertyCache *cache = 0;
+ QQmlPropertyCache *cache = nullptr;
if (const QMetaObject *mo = QQmlValueTypeFactory::metaObjectForMetaType(variantReferenceType))
cache = QJSEnginePrivate::get(engine())->cache(mo);
if (d()->gadgetPtr) {
d()->valueType->metaType.destruct(d()->gadgetPtr);
::operator delete(d()->gadgetPtr);
}
- d()->gadgetPtr =0;
+ d()->gadgetPtr =nullptr;
d()->setPropertyCache(cache);
d()->valueType = QQmlValueTypeFactory::valueType(variantReferenceType);
if (!cache)
@@ -159,10 +161,10 @@ bool QQmlValueTypeReference::readReferenceValue() const
} else {
if (!d()->gadgetPtr) {
d()->gadgetPtr = ::operator new(d()->valueType->metaType.sizeOf());
- d()->valueType->metaType.construct(d()->gadgetPtr, 0);
+ d()->valueType->metaType.construct(d()->gadgetPtr, nullptr);
}
// value-type reference
- void *args[] = { d()->gadgetPtr, 0 };
+ void *args[] = { d()->gadgetPtr, nullptr };
QMetaObject::metacall(d()->object, QMetaObject::ReadProperty, d()->property, args);
}
return true;
@@ -189,7 +191,7 @@ ReturnedValue QQmlValueTypeWrapper::create(ExecutionEngine *engine, QObject *obj
r->d()->property = property;
r->d()->setPropertyCache(QJSEnginePrivate::get(engine)->cache(metaObject));
r->d()->valueType = QQmlValueTypeFactory::valueType(typeId);
- r->d()->gadgetPtr = 0;
+ r->d()->gadgetPtr = nullptr;
return r->asReturnedValue();
}
@@ -201,7 +203,7 @@ ReturnedValue QQmlValueTypeWrapper::create(ExecutionEngine *engine, const QVaria
Scoped<QQmlValueTypeWrapper> r(scope, engine->memoryManager->allocObject<QQmlValueTypeWrapper>());
r->d()->setPropertyCache(QJSEnginePrivate::get(engine)->cache(metaObject));
r->d()->valueType = QQmlValueTypeFactory::valueType(typeId);
- r->d()->gadgetPtr = 0;
+ r->d()->gadgetPtr = nullptr;
r->d()->setValue(value);
return r->asReturnedValue();
}
@@ -244,13 +246,13 @@ PropertyAttributes QQmlValueTypeWrapper::query(const Managed *m, String *name)
Q_ASSERT(m->as<const QQmlValueTypeWrapper>());
const QQmlValueTypeWrapper *r = static_cast<const QQmlValueTypeWrapper *>(m);
- QQmlPropertyData *result = r->d()->propertyCache()->property(name, 0, 0);
+ QQmlPropertyData *result = r->d()->propertyCache()->property(name, nullptr, nullptr);
return result ? Attr_Data : Attr_Invalid;
}
void QQmlValueTypeWrapper::advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint *index, Property *p, PropertyAttributes *attributes)
{
- name->setM(0);
+ name->setM(nullptr);
*index = UINT_MAX;
QQmlValueTypeWrapper *that = static_cast<QQmlValueTypeWrapper*>(m);
@@ -297,7 +299,7 @@ bool QQmlValueTypeWrapper::write(QObject *target, int propertyIndex) const
if (!d()->gadgetPtr) {
Q_ALLOCA_ASSIGN(void, gadget, d()->valueType->metaType.sizeOf());
d()->gadgetPtr = gadget;
- d()->valueType->metaType.construct(d()->gadgetPtr, 0);
+ d()->valueType->metaType.construct(d()->gadgetPtr, nullptr);
destructGadgetOnExit = true;
}
if (!ref->readReferenceValue())
@@ -306,27 +308,26 @@ bool QQmlValueTypeWrapper::write(QObject *target, int propertyIndex) const
int flags = 0;
int status = -1;
- void *a[] = { d()->gadgetPtr, 0, &status, &flags };
+ void *a[] = { d()->gadgetPtr, nullptr, &status, &flags };
QMetaObject::metacall(target, QMetaObject::WriteProperty, propertyIndex, a);
if (destructGadgetOnExit) {
d()->valueType->metaType.destruct(d()->gadgetPtr);
- d()->gadgetPtr = 0;
+ d()->gadgetPtr = nullptr;
}
return true;
}
-ReturnedValue QQmlValueTypeWrapper::method_toString(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QQmlValueTypeWrapper::method_toString(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
- Scope scope(b);
- Object *o = callData->thisObject.as<Object>();
+ const Object *o = thisObject->as<Object>();
if (!o)
- THROW_TYPE_ERROR();
- QQmlValueTypeWrapper *w = o->as<QQmlValueTypeWrapper>();
+ return b->engine()->throwTypeError();
+ const QQmlValueTypeWrapper *w = o->as<QQmlValueTypeWrapper>();
if (!w)
- THROW_TYPE_ERROR();
+ return b->engine()->throwTypeError();
- if (QQmlValueTypeReference *ref = w->as<QQmlValueTypeReference>())
+ if (const QQmlValueTypeReference *ref = w->as<QQmlValueTypeReference>())
if (!ref->readReferenceValue())
RETURN_UNDEFINED();
@@ -351,7 +352,7 @@ ReturnedValue QQmlValueTypeWrapper::method_toString(const BuiltinFunction *b, Ca
}
result += QLatin1Char(')');
}
- return Encode(scope.engine->newString(result));
+ return Encode(b->engine()->newString(result));
}
ReturnedValue QQmlValueTypeWrapper::get(const Managed *m, String *name, bool *hasProperty)
@@ -366,7 +367,7 @@ ReturnedValue QQmlValueTypeWrapper::get(const Managed *m, String *name, bool *ha
return Primitive::undefinedValue().asReturnedValue();
}
- QQmlPropertyData *result = r->d()->propertyCache()->property(name, 0, 0);
+ QQmlPropertyData *result = r->d()->propertyCache()->property(name, nullptr, nullptr);
if (!result)
return Object::get(m, name, hasProperty);
@@ -435,7 +436,7 @@ bool QQmlValueTypeWrapper::put(Managed *m, String *name, const Value &value)
}
const QMetaObject *metaObject = r->d()->propertyCache()->metaObject();
- const QQmlPropertyData *pd = r->d()->propertyCache()->property(name, 0, 0);
+ const QQmlPropertyData *pd = r->d()->propertyCache()->property(name, nullptr, nullptr);
if (!pd)
return false;
@@ -504,13 +505,13 @@ bool QQmlValueTypeWrapper::put(Managed *m, String *name, const Value &value)
int flags = 0;
int status = -1;
- void *a[] = { &variantReferenceValue, 0, &status, &flags };
+ void *a[] = { &variantReferenceValue, nullptr, &status, &flags };
QMetaObject::metacall(reference->d()->object, QMetaObject::WriteProperty, reference->d()->property, a);
} else {
int flags = 0;
int status = -1;
- void *a[] = { r->d()->gadgetPtr, 0, &status, &flags };
+ void *a[] = { r->d()->gadgetPtr, nullptr, &status, &flags };
QMetaObject::metacall(reference->d()->object, QMetaObject::WriteProperty, reference->d()->property, a);
}
}
diff --git a/src/qml/qml/qqmlvaluetypewrapper_p.h b/src/qml/qml/qqmlvaluetypewrapper_p.h
index da03af6dbc..f99d207d68 100644
--- a/src/qml/qml/qqmlvaluetypewrapper_p.h
+++ b/src/qml/qml/qqmlvaluetypewrapper_p.h
@@ -112,7 +112,7 @@ public:
static PropertyAttributes query(const Managed *, String *name);
static void advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint *index, Property *p, PropertyAttributes *attributes);
- static ReturnedValue method_toString(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_toString(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
static void initProto(ExecutionEngine *v4);
};
diff --git a/src/qml/qml/qqmlvme.cpp b/src/qml/qml/qqmlvme.cpp
index c60f4edc80..018769948d 100644
--- a/src/qml/qml/qqmlvme.cpp
+++ b/src/qml/qml/qqmlvme.cpp
@@ -96,7 +96,7 @@ bool QQmlVME::componentCompleteEnabled()
}
QQmlVMEGuard::QQmlVMEGuard()
-: m_objectCount(0), m_objects(0), m_contextCount(0), m_contexts(0)
+: m_objectCount(0), m_objects(nullptr), m_contextCount(0), m_contexts(nullptr)
{
}
@@ -120,27 +120,15 @@ void QQmlVMEGuard::guard(QQmlObjectCreator *creator)
m_contexts[0] = creator->parentContextData();
}
-void QQmlVMEGuard::unguard(QObject *object)
-{
- for (int ii = 0; ii < m_objectCount; ++ii) {
- if (m_objects[ii] == object) {
- if (ii < m_objectCount - 1)
- ::memmove((void *) m_objects[ii], (void *) m_objects[ii + 1], sizeof(QPointer<QObject> *));
- delete m_objects[--m_objectCount];
- break;
- }
- }
-}
-
void QQmlVMEGuard::clear()
{
delete [] m_objects;
delete [] m_contexts;
m_objectCount = 0;
- m_objects = 0;
+ m_objects = nullptr;
m_contextCount = 0;
- m_contexts = 0;
+ m_contexts = nullptr;
}
bool QQmlVMEGuard::isOK() const
diff --git a/src/qml/qml/qqmlvme_p.h b/src/qml/qml/qqmlvme_p.h
index 9585b5b6df..9a94ac6258 100644
--- a/src/qml/qml/qqmlvme_p.h
+++ b/src/qml/qml/qqmlvme_p.h
@@ -83,7 +83,7 @@ namespace QQmlVMETypes {
struct State {
enum Flag { Deferred = 0x00000001 };
- State() : flags(0), context(0), instructionStream(0) {}
+ State() : flags(0), context(nullptr), instructionStream(nullptr) {}
quint32 flags;
QQmlContextData *context;
const char *instructionStream;
@@ -131,7 +131,6 @@ public:
~QQmlVMEGuard();
void guard(QQmlObjectCreator *);
- void unguard(QObject *);
void clear();
bool isOK() const;
@@ -144,7 +143,7 @@ private:
};
QQmlInstantiationInterrupt::QQmlInstantiationInterrupt()
- : mode(None), nsecs(0), runWhile(0)
+ : mode(None), nsecs(0), runWhile(nullptr)
{
}
@@ -154,7 +153,7 @@ QQmlInstantiationInterrupt::QQmlInstantiationInterrupt(volatile bool *runWhile,
}
QQmlInstantiationInterrupt::QQmlInstantiationInterrupt(int nsecs)
- : mode(Time), nsecs(nsecs), runWhile(0)
+ : mode(Time), nsecs(nsecs), runWhile(nullptr)
{
}
diff --git a/src/qml/qml/qqmlvmemetaobject.cpp b/src/qml/qml/qqmlvmemetaobject.cpp
index 281d64ac79..c1d3980b58 100644
--- a/src/qml/qml/qqmlvmemetaobject.cpp
+++ b/src/qml/qml/qqmlvmemetaobject.cpp
@@ -64,7 +64,7 @@ static void list_append(QQmlListProperty<QObject> *prop, QObject *o)
{
QList<QObject *> *list = static_cast<QList<QObject *> *>(prop->data);
list->append(o);
- static_cast<QQmlVMEMetaObject *>(prop->dummy1)->activate(prop->object, reinterpret_cast<quintptr>(prop->dummy2), 0);
+ static_cast<QQmlVMEMetaObject *>(prop->dummy1)->activate(prop->object, reinterpret_cast<quintptr>(prop->dummy2), nullptr);
}
static int list_count(QQmlListProperty<QObject> *prop)
@@ -83,11 +83,11 @@ static void list_clear(QQmlListProperty<QObject> *prop)
{
QList<QObject *> *list = static_cast<QList<QObject *> *>(prop->data);
list->clear();
- static_cast<QQmlVMEMetaObject *>(prop->dummy1)->activate(prop->object, reinterpret_cast<quintptr>(prop->dummy2), 0);
+ static_cast<QQmlVMEMetaObject *>(prop->dummy1)->activate(prop->object, reinterpret_cast<quintptr>(prop->dummy2), nullptr);
}
QQmlVMEVariantQObjectPtr::QQmlVMEVariantQObjectPtr()
- : QQmlGuard<QObject>(0), m_target(0), m_index(-1)
+ : QQmlGuard<QObject>(nullptr), m_target(nullptr), m_index(-1)
{
}
@@ -111,7 +111,7 @@ void QQmlVMEVariantQObjectPtr::objectDestroyed(QObject *)
}
}
- m_target->activate(m_target->object, m_target->methodOffset() + m_index, 0);
+ m_target->activate(m_target->object, m_target->methodOffset() + m_index, nullptr);
}
}
@@ -150,7 +150,7 @@ void QQmlVMEMetaObjectEndpoint::tryConnect()
if (metaObject.flag()) {
// This is actually notify
int sigIdx = metaObject->methodOffset() + aliasId + metaObject->compiledObject->nProperties;
- metaObject->activate(metaObject->object, sigIdx, 0);
+ metaObject->activate(metaObject->object, sigIdx, nullptr);
} else {
const QV4::CompiledData::Alias *aliasData = &metaObject->compiledObject->aliasTable()[aliasId];
if (!aliasData->isObjectAlias()) {
@@ -179,7 +179,7 @@ void QQmlVMEMetaObjectEndpoint::tryConnect()
QQmlInterceptorMetaObject::QQmlInterceptorMetaObject(QObject *obj, QQmlPropertyCache *cache)
: object(obj),
cache(cache),
- interceptors(0),
+ interceptors(nullptr),
hasAssignedMetaObjectData(false)
{
QObjectPrivate *op = QObjectPrivate::get(obj);
@@ -320,7 +320,7 @@ QQmlVMEMetaObject::QQmlVMEMetaObject(QV4::ExecutionEngine *engine,
: QQmlInterceptorMetaObject(obj, cache),
engine(engine),
ctxt(QQmlData::get(obj, true)->outerContext),
- aliasEndpoints(0), compilationUnit(qmlCompilationUnit), compiledObject(0)
+ aliasEndpoints(nullptr), compilationUnit(qmlCompilationUnit), compiledObject(nullptr)
{
Q_ASSERT(engine);
QQmlData::get(obj)->hasVMEMetaObject = true;
@@ -358,7 +358,7 @@ QV4::MemberData *QQmlVMEMetaObject::propertyAndMethodStorageAsMemberData() const
// such as the varProperties array) will have been cleaned up, but the
// QObject ptr will not yet have been deleted (eg, waiting on deleteLater).
// In this situation, return 0.
- return 0;
+ return nullptr;
}
return static_cast<QV4::MemberData*>(propertyAndMethodStorage.asManaged());
@@ -575,13 +575,13 @@ QObject* QQmlVMEMetaObject::readPropertyAsQObject(int id) const
{
QV4::MemberData *md = propertyAndMethodStorageAsMemberData();
if (!md)
- return 0;
+ return nullptr;
QV4::Scope scope(engine);
QV4::ScopedValue sv(scope, *(md->data() + id));
const QV4::QObjectWrapper *wrapper = sv->as<QV4::QObjectWrapper>();
if (!wrapper)
- return 0;
+ return nullptr;
return wrapper->object();
}
@@ -589,7 +589,7 @@ QList<QObject *> *QQmlVMEMetaObject::readPropertyAsList(int id) const
{
QV4::MemberData *md = propertyAndMethodStorageAsMemberData();
if (!md)
- return 0;
+ return nullptr;
QV4::Scope scope(engine);
QV4::Scoped<QV4::VariantObject> v(scope, *(md->data() + id));
@@ -643,7 +643,7 @@ int QQmlVMEMetaObject::metaCall(QObject *o, QMetaObject::Call c, int _id, void *
if (t == QV4::CompiledData::Property::Var) {
// the context can be null if accessing var properties from cpp after re-parenting an item.
- QQmlEnginePrivate *ep = (ctxt == 0 || ctxt->engine == 0) ? 0 : QQmlEnginePrivate::get(ctxt->engine);
+ QQmlEnginePrivate *ep = (ctxt == nullptr || ctxt->engine == nullptr) ? nullptr : QQmlEnginePrivate::get(ctxt->engine);
if (ep) {
if (c == QMetaObject::ReadProperty) {
*reinterpret_cast<QVariant *>(a[0]) = readPropertyAsVariant(id);
@@ -836,7 +836,7 @@ int QQmlVMEMetaObject::metaCall(QObject *o, QMetaObject::Call c, int _id, void *
}
if (c == QMetaObject::WriteProperty && needActivate) {
- activate(object, methodOffset() + id, 0);
+ activate(object, methodOffset() + id, nullptr);
}
return -1;
@@ -848,7 +848,7 @@ int QQmlVMEMetaObject::metaCall(QObject *o, QMetaObject::Call c, int _id, void *
const QV4::CompiledData::Alias *aliasData = &compiledObject->aliasTable()[id];
if ((aliasData->flags & QV4::CompiledData::Alias::AliasPointsToPointerObject) && c == QMetaObject::ReadProperty)
- *reinterpret_cast<void **>(a[0]) = 0;
+ *reinterpret_cast<void **>(a[0]) = nullptr;
if (!ctxt) return -1;
@@ -899,7 +899,7 @@ int QQmlVMEMetaObject::metaCall(QObject *o, QMetaObject::Call c, int _id, void *
int rv = QMetaObject::metacall(valueType, c, valueTypePropertyIndex, a);
if (c == QMetaObject::WriteProperty)
- valueType->write(target, coreIndex, 0x00);
+ valueType->write(target, coreIndex, nullptr);
return rv;
@@ -926,12 +926,14 @@ int QQmlVMEMetaObject::metaCall(QObject *o, QMetaObject::Call c, int _id, void *
id -= plainSignals;
if (id < methodCount) {
- if (!ctxt->engine)
+ QQmlEngine *engine = ctxt->engine;
+ if (!engine)
return -1; // We can't run the method
- QQmlEnginePrivate *ep = QQmlEnginePrivate::get(ctxt->engine);
+ QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine);
+ QV4::ExecutionEngine *v4 = engine->handle();
ep->referenceScarceResources(); // "hold" scarce resources in memory during evaluation.
- QV4::Scope scope(ep->v4engine());
+ QV4::Scope scope(v4);
QV4::ScopedFunctionObject function(scope, method(id));
@@ -951,7 +953,7 @@ int QQmlVMEMetaObject::metaCall(QObject *o, QMetaObject::Call c, int _id, void *
const unsigned int parameterCount = function->formalParameterCount();
QV4::JSCallData jsCallData(scope, parameterCount);
- *jsCallData->thisObject = ep->v8engine()->global();
+ *jsCallData->thisObject = v4->global();
for (uint ii = 0; ii < parameterCount; ++ii)
jsCallData->args[ii] = scope.engine->fromVariant(*(QVariant *)a[ii + 1]);
@@ -1035,7 +1037,7 @@ void QQmlVMEMetaObject::writeVarProperty(int id, const QV4::Value &value)
if (oldVariant)
oldVariant->removeVmePropertyReference();
- QObject *valueObject = 0;
+ QObject *valueObject = nullptr;
QQmlVMEVariantQObjectPtr *guard = getQObjectGuardForProperty(id);
// And, if the new value is a scarce resource, we need to ensure that it does not get
@@ -1058,7 +1060,7 @@ void QQmlVMEMetaObject::writeVarProperty(int id, const QV4::Value &value)
// Write the value and emit change signal as appropriate.
md->set(engine, id, value);
- activate(object, methodOffset() + id, 0);
+ activate(object, methodOffset() + id, nullptr);
}
void QQmlVMEMetaObject::writeProperty(int id, const QVariant &value)
@@ -1086,7 +1088,7 @@ void QQmlVMEMetaObject::writeProperty(int id, const QVariant &value)
QVariant currentValue = readPropertyAsVariant(id);
md->set(engine, id, newv);
if ((currentValue.userType() != value.userType() || currentValue != value))
- activate(object, methodOffset() + id, 0);
+ activate(object, methodOffset() + id, nullptr);
} else {
bool needActivate = false;
if (value.userType() == QMetaType::QObjectStar) {
@@ -1109,7 +1111,7 @@ void QQmlVMEMetaObject::writeProperty(int id, const QVariant &value)
}
if (needActivate)
- activate(object, methodOffset() + id, 0);
+ activate(object, methodOffset() + id, nullptr);
}
}
@@ -1185,7 +1187,7 @@ bool QQmlVMEMetaObject::aliasTarget(int index, QObject **target, int *coreIndex,
{
Q_ASSERT(compiledObject && (index >= propOffset() + int(compiledObject->nProperties)));
- *target = 0;
+ *target = nullptr;
*coreIndex = -1;
*valueTypeIndex = -1;
@@ -1287,7 +1289,7 @@ QQmlVMEVariantQObjectPtr *QQmlVMEMetaObject::getQObjectGuardForProperty(int inde
}
}
- return 0;
+ return nullptr;
}
QT_END_NAMESPACE
diff --git a/src/qml/qml/qqmlvmemetaobject_p.h b/src/qml/qml/qqmlvmemetaobject_p.h
index 27e638ceb4..0c82686d47 100644
--- a/src/qml/qml/qqmlvmemetaobject_p.h
+++ b/src/qml/qml/qqmlvmemetaobject_p.h
@@ -81,7 +81,7 @@ class QQmlVMEVariantQObjectPtr : public QQmlGuard<QObject>
{
public:
inline QQmlVMEVariantQObjectPtr();
- inline ~QQmlVMEVariantQObjectPtr();
+ inline ~QQmlVMEVariantQObjectPtr() override;
inline void objectDestroyed(QObject *) override;
inline void setGuardedValue(QObject *obj, QQmlVMEMetaObject *target, int index);
@@ -95,7 +95,7 @@ class Q_QML_PRIVATE_EXPORT QQmlInterceptorMetaObject : public QAbstractDynamicMe
{
public:
QQmlInterceptorMetaObject(QObject *obj, QQmlPropertyCache *cache);
- ~QQmlInterceptorMetaObject();
+ ~QQmlInterceptorMetaObject() override;
void registerInterceptor(QQmlPropertyIndex index, QQmlPropertyValueInterceptor *interceptor);
@@ -112,7 +112,7 @@ public:
if (it->m_propertyIndex == propertyIndex)
return true;
}
- if (auto parentInterceptor = ((parent.isT1() && parent.flag()) ? static_cast<QQmlInterceptorMetaObject *>(parent.asT1()) : 0))
+ if (auto parentInterceptor = ((parent.isT1() && parent.flag()) ? static_cast<QQmlInterceptorMetaObject *>(parent.asT1()) : nullptr))
return parentInterceptor->intercepts(propertyIndex);
return false;
}
@@ -139,7 +139,7 @@ inline QQmlInterceptorMetaObject *QQmlInterceptorMetaObject::get(QObject *obj)
}
}
- return 0;
+ return nullptr;
}
class QQmlVMEMetaObjectEndpoint;
@@ -147,7 +147,7 @@ class Q_QML_PRIVATE_EXPORT QQmlVMEMetaObject : public QQmlInterceptorMetaObject
{
public:
QQmlVMEMetaObject(QV4::ExecutionEngine *engine, QObject *obj, QQmlPropertyCache *cache, QV4::CompiledData::CompilationUnit *qmlCompilationUnit, int qmlObjectId);
- ~QQmlVMEMetaObject();
+ ~QQmlVMEMetaObject() override;
bool aliasTarget(int index, QObject **target, int *coreIndex, int *valueTypeIndex) const;
QV4::ReturnedValue vmeMethod(int index) const;
@@ -241,7 +241,7 @@ QQmlVMEMetaObject *QQmlVMEMetaObject::get(QObject *obj)
}
}
- return 0;
+ return nullptr;
}
int QQmlVMEMetaObject::propOffset() const
@@ -269,7 +269,7 @@ QQmlVMEMetaObject *QQmlVMEMetaObject::parentVMEMetaObject() const
if (parent.isT1() && parent.flag())
return static_cast<QQmlVMEMetaObject *>(parent.asT1());
- return 0;
+ return nullptr;
}
QT_END_NAMESPACE
diff --git a/src/qml/qml/qqmlxmlhttprequest.cpp b/src/qml/qml/qqmlxmlhttprequest.cpp
index 08842e714c..5673acec89 100644
--- a/src/qml/qml/qqmlxmlhttprequest.cpp
+++ b/src/qml/qml/qqmlxmlhttprequest.cpp
@@ -116,7 +116,7 @@ class DocumentImpl;
class NodeImpl
{
public:
- NodeImpl() : type(Element), document(0), parent(0) {}
+ NodeImpl() : type(Element), document(nullptr), parent(nullptr) {}
virtual ~NodeImpl() {
qDeleteAll(children);
qDeleteAll(attributes);
@@ -157,7 +157,7 @@ public:
class DocumentImpl : public QQmlRefCount, public NodeImpl
{
public:
- DocumentImpl() : root(0) { type = Document; }
+ DocumentImpl() : root(nullptr) { type = Document; }
virtual ~DocumentImpl() {
delete root;
}
@@ -276,25 +276,25 @@ public:
static void initClass(ExecutionEngine *engine);
// JS API
- static ReturnedValue method_get_nodeName(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_nodeValue(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_nodeType(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_namespaceUri(const BuiltinFunction *b, QV4::CallData *callData);
-
- static ReturnedValue method_get_parentNode(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_childNodes(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_firstChild(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_lastChild(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_previousSibling(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_nextSibling(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_attributes(const BuiltinFunction *b, QV4::CallData *callData);
-
- //static ReturnedValue ownerDocument(const BuiltinFunction *b, QV4::CallData *callData);
- //static ReturnedValue namespaceURI(const BuiltinFunction *b, QV4::CallData *callData);
- //static ReturnedValue prefix(const BuiltinFunction *b, QV4::CallData *callData);
- //static ReturnedValue localName(const BuiltinFunction *b, QV4::CallData *callData);
- //static ReturnedValue baseURI(const BuiltinFunction *b, QV4::CallData *callData);
- //static ReturnedValue textContent(const BuiltinFunction *b, QV4::CallData *callData);
+ static ReturnedValue method_get_nodeName(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_nodeValue(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_nodeType(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_namespaceUri(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+
+ static ReturnedValue method_get_parentNode(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_childNodes(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_firstChild(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_lastChild(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_previousSibling(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_nextSibling(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_attributes(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+
+ //static ReturnedValue ownerDocument(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ //static ReturnedValue namespaceURI(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ //static ReturnedValue prefix(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ //static ReturnedValue localName(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ //static ReturnedValue baseURI(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ //static ReturnedValue textContent(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
static ReturnedValue getProto(ExecutionEngine *v4);
@@ -306,18 +306,18 @@ void Heap::NodePrototype::init()
Scope scope(internalClass->engine);
ScopedObject o(scope, this);
- o->defineAccessorProperty(QStringLiteral("nodeName"), QV4::NodePrototype::method_get_nodeName, 0);
- o->defineAccessorProperty(QStringLiteral("nodeValue"), QV4::NodePrototype::method_get_nodeValue, 0);
- o->defineAccessorProperty(QStringLiteral("nodeType"), QV4::NodePrototype::method_get_nodeType, 0);
- o->defineAccessorProperty(QStringLiteral("namespaceUri"), QV4::NodePrototype::method_get_namespaceUri, 0);
+ o->defineAccessorProperty(QStringLiteral("nodeName"), QV4::NodePrototype::method_get_nodeName, nullptr);
+ o->defineAccessorProperty(QStringLiteral("nodeValue"), QV4::NodePrototype::method_get_nodeValue, nullptr);
+ o->defineAccessorProperty(QStringLiteral("nodeType"), QV4::NodePrototype::method_get_nodeType, nullptr);
+ o->defineAccessorProperty(QStringLiteral("namespaceUri"), QV4::NodePrototype::method_get_namespaceUri, nullptr);
- o->defineAccessorProperty(QStringLiteral("parentNode"), QV4::NodePrototype::method_get_parentNode, 0);
- o->defineAccessorProperty(QStringLiteral("childNodes"), QV4::NodePrototype::method_get_childNodes, 0);
- o->defineAccessorProperty(QStringLiteral("firstChild"), QV4::NodePrototype::method_get_firstChild, 0);
- o->defineAccessorProperty(QStringLiteral("lastChild"), QV4::NodePrototype::method_get_lastChild, 0);
- o->defineAccessorProperty(QStringLiteral("previousSibling"), QV4::NodePrototype::method_get_previousSibling, 0);
- o->defineAccessorProperty(QStringLiteral("nextSibling"), QV4::NodePrototype::method_get_nextSibling, 0);
- o->defineAccessorProperty(QStringLiteral("attributes"), QV4::NodePrototype::method_get_attributes, 0);
+ o->defineAccessorProperty(QStringLiteral("parentNode"), QV4::NodePrototype::method_get_parentNode, nullptr);
+ o->defineAccessorProperty(QStringLiteral("childNodes"), QV4::NodePrototype::method_get_childNodes, nullptr);
+ o->defineAccessorProperty(QStringLiteral("firstChild"), QV4::NodePrototype::method_get_firstChild, nullptr);
+ o->defineAccessorProperty(QStringLiteral("lastChild"), QV4::NodePrototype::method_get_lastChild, nullptr);
+ o->defineAccessorProperty(QStringLiteral("previousSibling"), QV4::NodePrototype::method_get_previousSibling, nullptr);
+ o->defineAccessorProperty(QStringLiteral("nextSibling"), QV4::NodePrototype::method_get_nextSibling, nullptr);
+ o->defineAccessorProperty(QStringLiteral("attributes"), QV4::NodePrototype::method_get_attributes, nullptr);
}
@@ -355,10 +355,10 @@ class Attr : public Node
{
public:
// JS API
- static ReturnedValue method_name(const BuiltinFunction *b, QV4::CallData *callData);
+ static ReturnedValue method_name(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
// static void specified(CallContext *);
- static ReturnedValue method_value(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_ownerElement(const BuiltinFunction *b, QV4::CallData *callData);
+ static ReturnedValue method_value(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_ownerElement(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
// static void schemaTypeInfo(CallContext *);
// static void isId(CallContext *c);
@@ -370,7 +370,7 @@ class CharacterData : public Node
{
public:
// JS API
- static ReturnedValue method_length(const BuiltinFunction *b, QV4::CallData *callData);
+ static ReturnedValue method_length(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
// C++ API
static ReturnedValue prototype(ExecutionEngine *v4);
@@ -380,8 +380,8 @@ class Text : public CharacterData
{
public:
// JS API
- static ReturnedValue method_isElementContentWhitespace(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_wholeText(const BuiltinFunction *b, QV4::CallData *callData);
+ static ReturnedValue method_isElementContentWhitespace(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_wholeText(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
// C++ API
static ReturnedValue prototype(ExecutionEngine *);
@@ -398,10 +398,10 @@ class Document : public Node
{
public:
// JS API
- static ReturnedValue method_xmlVersion(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_xmlEncoding(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_xmlStandalone(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_documentElement(const BuiltinFunction *b, QV4::CallData *callData);
+ static ReturnedValue method_xmlVersion(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_xmlEncoding(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_xmlStandalone(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_documentElement(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
// C++ API
static ReturnedValue prototype(ExecutionEngine *);
@@ -420,10 +420,10 @@ void NodeImpl::release()
document->release();
}
-ReturnedValue NodePrototype::method_get_nodeName(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_nodeName(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
@@ -445,10 +445,10 @@ ReturnedValue NodePrototype::method_get_nodeName(const BuiltinFunction *b, QV4::
return Encode(scope.engine->newString(name));
}
-ReturnedValue NodePrototype::method_get_nodeValue(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_nodeValue(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
@@ -464,30 +464,30 @@ ReturnedValue NodePrototype::method_get_nodeValue(const BuiltinFunction *b, QV4:
return Encode(scope.engine->newString(r->d()->d->data));
}
-ReturnedValue NodePrototype::method_get_nodeType(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_nodeType(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
return Encode(r->d()->d->type);
}
-ReturnedValue NodePrototype::method_get_namespaceUri(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_namespaceUri(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
return Encode(scope.engine->newString(r->d()->d->namespaceUri));
}
-ReturnedValue NodePrototype::method_get_parentNode(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_parentNode(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
@@ -497,20 +497,20 @@ ReturnedValue NodePrototype::method_get_parentNode(const BuiltinFunction *b, QV4
return Encode::null();
}
-ReturnedValue NodePrototype::method_get_childNodes(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_childNodes(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
return NodeList::create(scope.engine, r->d()->d);
}
-ReturnedValue NodePrototype::method_get_firstChild(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_firstChild(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
@@ -520,10 +520,10 @@ ReturnedValue NodePrototype::method_get_firstChild(const BuiltinFunction *b, QV4
return Node::create(scope.engine, r->d()->d->children.constFirst());
}
-ReturnedValue NodePrototype::method_get_lastChild(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_lastChild(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
@@ -533,10 +533,10 @@ ReturnedValue NodePrototype::method_get_lastChild(const BuiltinFunction *b, QV4:
return Node::create(scope.engine, r->d()->d->children.constLast());
}
-ReturnedValue NodePrototype::method_get_previousSibling(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_previousSibling(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
@@ -555,10 +555,10 @@ ReturnedValue NodePrototype::method_get_previousSibling(const BuiltinFunction *b
return Encode::null();
}
-ReturnedValue NodePrototype::method_get_nextSibling(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_nextSibling(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
@@ -577,10 +577,10 @@ ReturnedValue NodePrototype::method_get_nextSibling(const BuiltinFunction *b, QV
return Encode::null();
}
-ReturnedValue NodePrototype::method_get_attributes(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue NodePrototype::method_get_attributes(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
THROW_TYPE_ERROR();
@@ -644,7 +644,7 @@ ReturnedValue Element::prototype(ExecutionEngine *engine)
ScopedObject p(scope, engine->newObject());
ScopedObject pp(scope);
p->setPrototype((pp = NodePrototype::getProto(engine)));
- p->defineAccessorProperty(QStringLiteral("tagName"), NodePrototype::method_get_nodeName, 0);
+ p->defineAccessorProperty(QStringLiteral("tagName"), NodePrototype::method_get_nodeName, nullptr);
d->elementPrototype.set(engine, p);
engine->v8Engine->freezeObject(p);
}
@@ -659,49 +659,49 @@ ReturnedValue Attr::prototype(ExecutionEngine *engine)
ScopedObject p(scope, engine->newObject());
ScopedObject pp(scope);
p->setPrototype((pp = NodePrototype::getProto(engine)));
- p->defineAccessorProperty(QStringLiteral("name"), method_name, 0);
- p->defineAccessorProperty(QStringLiteral("value"), method_value, 0);
- p->defineAccessorProperty(QStringLiteral("ownerElement"), method_ownerElement, 0);
+ p->defineAccessorProperty(QStringLiteral("name"), method_name, nullptr);
+ p->defineAccessorProperty(QStringLiteral("value"), method_value, nullptr);
+ p->defineAccessorProperty(QStringLiteral("ownerElement"), method_ownerElement, nullptr);
d->attrPrototype.set(engine, p);
engine->v8Engine->freezeObject(p);
}
return d->attrPrototype.value();
}
-ReturnedValue Attr::method_name(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Attr::method_name(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
RETURN_UNDEFINED();
return Encode(scope.engine->newString(r->d()->d->name));
}
-ReturnedValue Attr::method_value(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Attr::method_value(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
RETURN_UNDEFINED();
return Encode(scope.engine->newString(r->d()->d->data));
}
-ReturnedValue Attr::method_ownerElement(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Attr::method_ownerElement(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
RETURN_UNDEFINED();
return Node::create(scope.engine, r->d()->d->parent);
}
-ReturnedValue CharacterData::method_length(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue CharacterData::method_length(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
RETURN_UNDEFINED();
@@ -716,28 +716,28 @@ ReturnedValue CharacterData::prototype(ExecutionEngine *v4)
ScopedObject p(scope, v4->newObject());
ScopedObject pp(scope);
p->setPrototype((pp = NodePrototype::getProto(v4)));
- p->defineAccessorProperty(QStringLiteral("data"), NodePrototype::method_get_nodeValue, 0);
- p->defineAccessorProperty(QStringLiteral("length"), method_length, 0);
+ p->defineAccessorProperty(QStringLiteral("data"), NodePrototype::method_get_nodeValue, nullptr);
+ p->defineAccessorProperty(QStringLiteral("length"), method_length, nullptr);
d->characterDataPrototype.set(v4, p);
v4->v8Engine->freezeObject(p);
}
return d->characterDataPrototype.value();
}
-ReturnedValue Text::method_isElementContentWhitespace(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Text::method_isElementContentWhitespace(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
RETURN_UNDEFINED();
return Encode(QStringRef(&r->d()->d->data).trimmed().isEmpty());
}
-ReturnedValue Text::method_wholeText(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Text::method_wholeText(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r)
RETURN_UNDEFINED();
@@ -752,8 +752,8 @@ ReturnedValue Text::prototype(ExecutionEngine *v4)
ScopedObject p(scope, v4->newObject());
ScopedObject pp(scope);
p->setPrototype((pp = CharacterData::prototype(v4)));
- p->defineAccessorProperty(QStringLiteral("isElementContentWhitespace"), method_isElementContentWhitespace, 0);
- p->defineAccessorProperty(QStringLiteral("wholeText"), method_wholeText, 0);
+ p->defineAccessorProperty(QStringLiteral("isElementContentWhitespace"), method_isElementContentWhitespace, nullptr);
+ p->defineAccessorProperty(QStringLiteral("wholeText"), method_wholeText, nullptr);
d->textPrototype.set(v4, p);
v4->v8Engine->freezeObject(p);
}
@@ -783,10 +783,10 @@ ReturnedValue Document::prototype(ExecutionEngine *v4)
ScopedObject p(scope, v4->newObject());
ScopedObject pp(scope);
p->setPrototype((pp = NodePrototype::getProto(v4)));
- p->defineAccessorProperty(QStringLiteral("xmlVersion"), method_xmlVersion, 0);
- p->defineAccessorProperty(QStringLiteral("xmlEncoding"), method_xmlEncoding, 0);
- p->defineAccessorProperty(QStringLiteral("xmlStandalone"), method_xmlStandalone, 0);
- p->defineAccessorProperty(QStringLiteral("documentElement"), method_documentElement, 0);
+ p->defineAccessorProperty(QStringLiteral("xmlVersion"), method_xmlVersion, nullptr);
+ p->defineAccessorProperty(QStringLiteral("xmlEncoding"), method_xmlEncoding, nullptr);
+ p->defineAccessorProperty(QStringLiteral("xmlStandalone"), method_xmlStandalone, nullptr);
+ p->defineAccessorProperty(QStringLiteral("documentElement"), method_documentElement, nullptr);
d->documentPrototype.set(v4, p);
v4->v8Engine->freezeObject(p);
}
@@ -797,7 +797,7 @@ ReturnedValue Document::load(ExecutionEngine *v4, const QByteArray &data)
{
Scope scope(v4);
- DocumentImpl *document = 0;
+ DocumentImpl *document = nullptr;
QStack<NodeImpl *> nodeStack;
QXmlStreamReader reader(data);
@@ -885,7 +885,7 @@ ReturnedValue Document::load(ExecutionEngine *v4, const QByteArray &data)
bool Node::isNull() const
{
- return d()->d == 0;
+ return d()->d == nullptr;
}
ReturnedValue NamedNodeMap::getIndexed(const Managed *m, uint index, bool *hasProperty)
@@ -967,40 +967,40 @@ ReturnedValue NodeList::create(ExecutionEngine *v4, NodeImpl *data)
return (v4->memoryManager->allocObject<NodeList>(data))->asReturnedValue();
}
-ReturnedValue Document::method_documentElement(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Document::method_documentElement(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r || r->d()->d->type != NodeImpl::Document)
RETURN_UNDEFINED();
return Node::create(scope.engine, static_cast<DocumentImpl *>(r->d()->d)->root);
}
-ReturnedValue Document::method_xmlStandalone(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Document::method_xmlStandalone(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r || r->d()->d->type != NodeImpl::Document)
RETURN_UNDEFINED();
return Encode(static_cast<DocumentImpl *>(r->d()->d)->isStandalone);
}
-ReturnedValue Document::method_xmlVersion(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Document::method_xmlVersion(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r || r->d()->d->type != NodeImpl::Document)
RETURN_UNDEFINED();
return Encode(scope.engine->newString(static_cast<DocumentImpl *>(r->d()->d)->version));
}
-ReturnedValue Document::method_xmlEncoding(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue Document::method_xmlEncoding(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<Node> r(scope, callData->thisObject.as<Node>());
+ Scoped<Node> r(scope, thisObject->as<Node>());
if (!r || r->d()->d->type != NodeImpl::Document)
RETURN_UNDEFINED();
@@ -1098,7 +1098,7 @@ private:
QQmlXMLHttpRequest::QQmlXMLHttpRequest(QNetworkAccessManager *manager)
: m_state(Unsent), m_errorFlag(false), m_sendFlag(false)
- , m_redirectCount(0), m_gotXml(false), m_textCodec(0), m_network(0), m_nam(manager)
+ , m_redirectCount(0), m_gotXml(false), m_textCodec(nullptr), m_network(nullptr), m_nam(manager)
, m_responseType()
, m_parsedDocument()
{
@@ -1443,7 +1443,7 @@ void QQmlXMLHttpRequest::finished()
dispatchCallback();
m_thisObject.clear();
- m_qmlContext.setContextData(0);
+ m_qmlContext.setContextData(nullptr);
}
@@ -1516,7 +1516,7 @@ QV4::ReturnedValue QQmlXMLHttpRequest::xmlResponseBody(QV4::ExecutionEngine* eng
#if QT_CONFIG(textcodec)
QTextCodec* QQmlXMLHttpRequest::findTextCodec() const
{
- QTextCodec *codec = 0;
+ QTextCodec *codec = nullptr;
if (!m_charset.isEmpty())
codec = QTextCodec::codecForName(m_charset);
@@ -1528,10 +1528,10 @@ QTextCodec* QQmlXMLHttpRequest::findTextCodec() const
}
if (!codec && m_mime == "text/html")
- codec = QTextCodec::codecForHtml(m_responseEntityBody, 0);
+ codec = QTextCodec::codecForHtml(m_responseEntityBody, nullptr);
if (!codec)
- codec = QTextCodec::codecForUtfText(m_responseEntityBody, 0);
+ codec = QTextCodec::codecForUtfText(m_responseEntityBody, nullptr);
if (!codec)
codec = QTextCodec::codecForName("UTF-8");
@@ -1595,7 +1595,7 @@ void QQmlXMLHttpRequest::destroyNetwork()
if (m_network) {
m_network->disconnect();
m_network->deleteLater();
- m_network = 0;
+ m_network = nullptr;
}
}
@@ -1653,21 +1653,21 @@ struct QQmlXMLHttpRequestCtor : public FunctionObject
void setupProto();
- static ReturnedValue method_open(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_setRequestHeader(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_send(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_abort(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_getResponseHeader(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_getAllResponseHeaders(const BuiltinFunction *b, QV4::CallData *callData);
-
- static ReturnedValue method_get_readyState(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_status(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_statusText(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_responseText(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_responseXML(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_response(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_get_responseType(const BuiltinFunction *b, QV4::CallData *callData);
- static ReturnedValue method_set_responseType(const BuiltinFunction *b, QV4::CallData *callData);
+ static ReturnedValue method_open(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_setRequestHeader(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_send(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_abort(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_getResponseHeader(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_getAllResponseHeaders(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+
+ static ReturnedValue method_get_readyState(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_status(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_statusText(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_responseText(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_responseXML(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_response(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_responseType(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_set_responseType(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
};
}
@@ -1709,12 +1709,12 @@ void QQmlXMLHttpRequestCtor::setupProto()
p->defineDefaultProperty(QStringLiteral("getAllResponseHeaders"), method_getAllResponseHeaders);
// Read-only properties
- p->defineAccessorProperty(QStringLiteral("readyState"), method_get_readyState, 0);
- p->defineAccessorProperty(QStringLiteral("status"),method_get_status, 0);
- p->defineAccessorProperty(QStringLiteral("statusText"),method_get_statusText, 0);
- p->defineAccessorProperty(QStringLiteral("responseText"),method_get_responseText, 0);
- p->defineAccessorProperty(QStringLiteral("responseXML"),method_get_responseXML, 0);
- p->defineAccessorProperty(QStringLiteral("response"),method_get_response, 0);
+ p->defineAccessorProperty(QStringLiteral("readyState"), method_get_readyState, nullptr);
+ p->defineAccessorProperty(QStringLiteral("status"),method_get_status, nullptr);
+ p->defineAccessorProperty(QStringLiteral("statusText"),method_get_statusText, nullptr);
+ p->defineAccessorProperty(QStringLiteral("responseText"),method_get_responseText, nullptr);
+ p->defineAccessorProperty(QStringLiteral("responseXML"),method_get_responseXML, nullptr);
+ p->defineAccessorProperty(QStringLiteral("response"),method_get_response, nullptr);
// Read-write properties
p->defineAccessorProperty(QStringLiteral("responseType"), method_get_responseType, method_set_responseType);
@@ -1729,19 +1729,19 @@ void QQmlXMLHttpRequestCtor::setupProto()
// XMLHttpRequest methods
-ReturnedValue QQmlXMLHttpRequestCtor::method_open(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_open(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
- if (callData->argc() < 2 || callData->argc() > 5)
+ if (argc < 2 || argc > 5)
THROW_DOM(DOMEXCEPTION_SYNTAX_ERR, "Incorrect argument count");
// Argument 0 - Method
- QString method = callData->args[0].toQStringNoThrow().toUpper();
+ QString method = argv[0].toQStringNoThrow().toUpper();
if (method != QLatin1String("GET") &&
method != QLatin1String("PUT") &&
method != QLatin1String("HEAD") &&
@@ -1753,23 +1753,23 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_open(const BuiltinFunction *b, QV4:
THROW_DOM(DOMEXCEPTION_SYNTAX_ERR, "Unsupported HTTP method type");
// Argument 1 - URL
- QUrl url = QUrl(callData->args[1].toQStringNoThrow());
+ QUrl url = QUrl(argv[1].toQStringNoThrow());
if (url.isRelative())
url = scope.engine->callingQmlContext()->resolvedUrl(url);
bool async = true;
// Argument 2 - async (optional)
- if (callData->argc() > 2) {
- async = callData->args[2].booleanValue();
+ if (argc > 2) {
+ async = argv[2].booleanValue();
}
// Argument 3/4 - user/pass (optional)
QString username, password;
- if (callData->argc() > 3)
- username = callData->args[3].toQStringNoThrow();
- if (callData->argc() > 4)
- password = callData->args[4].toQStringNoThrow();
+ if (argc > 3)
+ username = argv[3].toQStringNoThrow();
+ if (argc > 4)
+ password = argv[4].toQStringNoThrow();
// Clear the fragment (if any)
url.setFragment(QString());
@@ -1781,22 +1781,22 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_open(const BuiltinFunction *b, QV4:
return r->open(w, scope.engine->callingQmlContext(), method, url, async ? QQmlXMLHttpRequest::AsynchronousLoad : QQmlXMLHttpRequest::SynchronousLoad);
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_setRequestHeader(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_setRequestHeader(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
- if (callData->argc() != 2)
+ if (argc != 2)
THROW_DOM(DOMEXCEPTION_SYNTAX_ERR, "Incorrect argument count");
if (r->readyState() != QQmlXMLHttpRequest::Opened || r->sendFlag())
THROW_DOM(DOMEXCEPTION_INVALID_STATE_ERR, "Invalid state");
- QString name = callData->args[0].toQStringNoThrow();
- QString value = callData->args[1].toQStringNoThrow();
+ QString name = argv[0].toQStringNoThrow();
+ QString value = argv[1].toQStringNoThrow();
// ### Check that name and value are well formed
@@ -1828,10 +1828,10 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_setRequestHeader(const BuiltinFunct
RETURN_UNDEFINED();
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_send(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_send(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
@@ -1841,21 +1841,21 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_send(const BuiltinFunction *b, QV4:
THROW_DOM(DOMEXCEPTION_INVALID_STATE_ERR, "Invalid state");
QByteArray data;
- if (callData->argc() > 0) {
- if (const ArrayBuffer *buffer = callData->args[0].as<ArrayBuffer>()) {
+ if (argc > 0) {
+ if (const ArrayBuffer *buffer = argv[0].as<ArrayBuffer>()) {
data = buffer->asByteArray();
} else {
- data = callData->args[0].toQStringNoThrow().toUtf8();
+ data = argv[0].toQStringNoThrow().toUtf8();
}
}
return r->send(w, scope.engine->callingQmlContext(), data);
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_abort(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_abort(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
@@ -1863,15 +1863,15 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_abort(const BuiltinFunction *b, QV4
return r->abort(w, scope.engine->callingQmlContext());
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_getResponseHeader(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_getResponseHeader(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_DOM(DOMEXCEPTION_SYNTAX_ERR, "Incorrect argument count");
if (r->readyState() != QQmlXMLHttpRequest::Loading &&
@@ -1879,18 +1879,18 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_getResponseHeader(const BuiltinFunc
r->readyState() != QQmlXMLHttpRequest::HeadersReceived)
THROW_DOM(DOMEXCEPTION_INVALID_STATE_ERR, "Invalid state");
- return Encode(scope.engine->newString(r->header(callData->args[0].toQStringNoThrow())));
+ return Encode(scope.engine->newString(r->header(argv[0].toQStringNoThrow())));
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_getAllResponseHeaders(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_getAllResponseHeaders(const FunctionObject *b, const Value *thisObject, const Value *, int argc)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
- if (callData->argc() != 0)
+ if (argc != 0)
THROW_DOM(DOMEXCEPTION_SYNTAX_ERR, "Incorrect argument count");
if (r->readyState() != QQmlXMLHttpRequest::Loading &&
@@ -1902,10 +1902,10 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_getAllResponseHeaders(const Builtin
}
// XMLHttpRequest properties
-ReturnedValue QQmlXMLHttpRequestCtor::method_get_readyState(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_get_readyState(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
@@ -1913,10 +1913,10 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_get_readyState(const BuiltinFunctio
return Encode(r->readyState());
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_get_status(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_get_status(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
@@ -1931,10 +1931,10 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_get_status(const BuiltinFunction *b
return Encode(r->replyStatus());
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_get_statusText(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_get_statusText(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
@@ -1949,10 +1949,10 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_get_statusText(const BuiltinFunctio
return Encode(scope.engine->newString(r->replyStatusText()));
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_get_responseText(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_get_responseText(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
@@ -1964,10 +1964,10 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_get_responseText(const BuiltinFunct
return Encode(scope.engine->newString(r->responseBody()));
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_get_responseXML(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_get_responseXML(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
@@ -1983,10 +1983,10 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_get_responseXML(const BuiltinFuncti
}
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_get_response(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_get_response(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
@@ -2010,29 +2010,29 @@ ReturnedValue QQmlXMLHttpRequestCtor::method_get_response(const BuiltinFunction
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_get_responseType(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_get_responseType(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
return Encode(scope.engine->newString(r->responseType()));
}
-ReturnedValue QQmlXMLHttpRequestCtor::method_set_responseType(const BuiltinFunction *b, QV4::CallData *callData)
+ReturnedValue QQmlXMLHttpRequestCtor::method_set_responseType(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
Scope scope(b);
- Scoped<QQmlXMLHttpRequestWrapper> w(scope, callData->thisObject.as<QQmlXMLHttpRequestWrapper>());
+ Scoped<QQmlXMLHttpRequestWrapper> w(scope, thisObject->as<QQmlXMLHttpRequestWrapper>());
if (!w)
V4THROW_REFERENCE("Not an XMLHttpRequest object");
QQmlXMLHttpRequest *r = w->d()->request;
- if (callData->argc() < 1)
+ if (argc < 1)
THROW_DOM(DOMEXCEPTION_SYNTAX_ERR, "Incorrect argument count");
// Argument 0 - response type
- r->setResponseType(callData->args[0].toQStringNoThrow());
+ r->setResponseType(argv[0].toQStringNoThrow());
return Encode::undefined();
}
diff --git a/src/qml/qml/v8/qqmlbuiltinfunctions.cpp b/src/qml/qml/v8/qqmlbuiltinfunctions.cpp
index 3627f29cb2..1371f1f041 100644
--- a/src/qml/qml/v8/qqmlbuiltinfunctions.cpp
+++ b/src/qml/qml/v8/qqmlbuiltinfunctions.cpp
@@ -151,10 +151,10 @@ void Heap::QtObject::init(QQmlEngine *qmlEngine)
o->defineDefaultProperty(QStringLiteral("createComponent"), QV4::QtObject::method_createComponent);
}
- o->defineAccessorProperty(QStringLiteral("platform"), QV4::QtObject::method_get_platform, 0);
- o->defineAccessorProperty(QStringLiteral("application"), QV4::QtObject::method_get_application, 0);
- o->defineAccessorProperty(QStringLiteral("inputMethod"), QV4::QtObject::method_get_inputMethod, 0);
- o->defineAccessorProperty(QStringLiteral("styleHints"), QV4::QtObject::method_get_styleHints, 0);
+ o->defineAccessorProperty(QStringLiteral("platform"), QV4::QtObject::method_get_platform, nullptr);
+ o->defineAccessorProperty(QStringLiteral("application"), QV4::QtObject::method_get_application, nullptr);
+ o->defineAccessorProperty(QStringLiteral("inputMethod"), QV4::QtObject::method_get_inputMethod, nullptr);
+ o->defineAccessorProperty(QStringLiteral("styleHints"), QV4::QtObject::method_get_styleHints, nullptr);
o->defineDefaultProperty(QStringLiteral("callLater"), QV4::QtObject::method_callLater);
}
@@ -228,12 +228,12 @@ void QtObject::advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint
\qmlmethod bool Qt::isQtObject(object)
Returns true if \c object is a valid reference to a Qt or QML object, otherwise false.
*/
-ReturnedValue QtObject::method_isQtObject(const BuiltinFunction *, CallData *callData)
+ReturnedValue QtObject::method_isQtObject(const FunctionObject *, const Value *, const Value *argv, int argc)
{
- if (callData->argc() == 0)
+ if (argc == 0)
RETURN_RESULT(QV4::Encode(false));
- return QV4::Encode(callData->args[0].as<QV4::QObjectWrapper>() != 0);
+ return QV4::Encode(argv[0].as<QV4::QObjectWrapper>() != nullptr);
}
/*!
@@ -242,17 +242,16 @@ ReturnedValue QtObject::method_isQtObject(const BuiltinFunction *, CallData *cal
Returns a color with the specified \c red, \c green, \c blue and \c alpha components.
All components should be in the range 0-1 inclusive.
*/
-ReturnedValue QtObject::method_rgba(const BuiltinFunction *builtin, CallData *callData)
+ReturnedValue QtObject::method_rgba(const FunctionObject *f, const Value *, const Value *argv, int argc)
{
- QV4::Scope scope(builtin);
- int argCount = callData->argc();
- if (argCount < 3 || argCount > 4)
+ QV4::Scope scope(f);
+ if (argc < 3 || argc > 4)
THROW_GENERIC_ERROR("Qt.rgba(): Invalid arguments");
- double r = callData->args[0].toNumber();
- double g = callData->args[1].toNumber();
- double b = callData->args[2].toNumber();
- double a = (argCount == 4) ? callData->args[3].toNumber() : 1;
+ double r = argv[0].toNumber();
+ double g = argv[1].toNumber();
+ double b = argv[2].toNumber();
+ double a = (argc == 4) ? argv[3].toNumber() : 1;
if (r < 0.0) r=0.0;
if (r > 1.0) r=1.0;
@@ -272,17 +271,17 @@ ReturnedValue QtObject::method_rgba(const BuiltinFunction *builtin, CallData *ca
Returns a color with the specified \c hue, \c saturation, \c lightness and \c alpha components.
All components should be in the range 0-1 inclusive.
*/
-ReturnedValue QtObject::method_hsla(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_hsla(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- int argCount = callData->argc();
+ int argCount = argc;
if (argCount < 3 || argCount > 4)
THROW_GENERIC_ERROR("Qt.hsla(): Invalid arguments");
- double h = callData->args[0].toNumber();
- double s = callData->args[1].toNumber();
- double l = callData->args[2].toNumber();
- double a = (argCount == 4) ? callData->args[3].toNumber() : 1;
+ double h = argv[0].toNumber();
+ double s = argv[1].toNumber();
+ double l = argv[2].toNumber();
+ double a = (argCount == 4) ? argv[3].toNumber() : 1;
if (h < 0.0) h=0.0;
if (h > 1.0) h=1.0;
@@ -304,17 +303,17 @@ All components should be in the range 0-1 inclusive.
\since 5.5
*/
-ReturnedValue QtObject::method_hsva(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_hsva(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- int argCount = callData->argc();
+ int argCount = argc;
if (argCount < 3 || argCount > 4)
THROW_GENERIC_ERROR("Qt.hsva(): Invalid arguments");
- double h = callData->args[0].toNumber();
- double s = callData->args[1].toNumber();
- double v = callData->args[2].toNumber();
- double a = (argCount == 4) ? callData->args[3].toNumber() : 1;
+ double h = argv[0].toNumber();
+ double s = argv[1].toNumber();
+ double v = argv[2].toNumber();
+ double a = (argCount == 4) ? argv[3].toNumber() : 1;
h = qBound(0.0, h, 1.0);
s = qBound(0.0, s, 1.0);
@@ -332,15 +331,15 @@ may be either color values or string values. If a string value is supplied it
must be convertible to a color, as described for the \l{colorbasictypedocs}{color}
basic type.
*/
-ReturnedValue QtObject::method_colorEqual(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_colorEqual(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 2)
+ if (argc != 2)
THROW_GENERIC_ERROR("Qt.colorEqual(): Invalid arguments");
bool ok = false;
- QVariant lhs = scope.engine->toVariant(callData->args[0], -1);
+ QVariant lhs = scope.engine->toVariant(argv[0], -1);
if (lhs.userType() == QVariant::String) {
lhs = QQmlStringConverters::colorFromString(lhs.toString(), &ok);
if (!ok) {
@@ -350,7 +349,7 @@ ReturnedValue QtObject::method_colorEqual(const BuiltinFunction *b, CallData *ca
THROW_GENERIC_ERROR("Qt.colorEqual(): Invalid arguments");
}
- QVariant rhs = scope.engine->toVariant(callData->args[1], -1);
+ QVariant rhs = scope.engine->toVariant(argv[1], -1);
if (rhs.userType() == QVariant::String) {
rhs = QQmlStringConverters::colorFromString(rhs.toString(), &ok);
if (!ok) {
@@ -371,16 +370,16 @@ Returns a \c rect with the top-left corner at \c x, \c y and the specified \c wi
The returned object has \c x, \c y, \c width and \c height attributes with the given values.
*/
-ReturnedValue QtObject::method_rect(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_rect(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 4)
+ if (argc != 4)
THROW_GENERIC_ERROR("Qt.rect(): Invalid arguments");
- double x = callData->args[0].toNumber();
- double y = callData->args[1].toNumber();
- double w = callData->args[2].toNumber();
- double h = callData->args[3].toNumber();
+ double x = argv[0].toNumber();
+ double y = argv[1].toNumber();
+ double w = argv[2].toNumber();
+ double h = argv[3].toNumber();
return scope.engine->fromVariant(QVariant::fromValue(QRectF(x, y, w, h)));
}
@@ -389,14 +388,14 @@ ReturnedValue QtObject::method_rect(const BuiltinFunction *b, CallData *callData
\qmlmethod point Qt::point(int x, int y)
Returns a Point with the specified \c x and \c y coordinates.
*/
-ReturnedValue QtObject::method_point(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_point(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 2)
+ if (argc != 2)
THROW_GENERIC_ERROR("Qt.point(): Invalid arguments");
- double x = callData->args[0].toNumber();
- double y = callData->args[1].toNumber();
+ double x = argv[0].toNumber();
+ double y = argv[1].toNumber();
return scope.engine->fromVariant(QVariant::fromValue(QPointF(x, y)));
}
@@ -405,14 +404,14 @@ ReturnedValue QtObject::method_point(const BuiltinFunction *b, CallData *callDat
\qmlmethod Qt::size(int width, int height)
Returns a Size with the specified \c width and \c height.
*/
-ReturnedValue QtObject::method_size(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_size(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 2)
+ if (argc != 2)
THROW_GENERIC_ERROR("Qt.size(): Invalid arguments");
- double w = callData->args[0].toNumber();
- double h = callData->args[1].toNumber();
+ double w = argv[0].toNumber();
+ double h = argv[1].toNumber();
return scope.engine->fromVariant(QVariant::fromValue(QSizeF(w, h)));
}
@@ -425,15 +424,15 @@ key-value pairs where valid keys are the \l{fontbasictypedocs}{font} type's
subproperty names, and the values are valid values for each subproperty.
Invalid keys will be ignored.
*/
-ReturnedValue QtObject::method_font(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_font(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1 || !callData->args[0].isObject())
+ if (argc != 1 || !argv[0].isObject())
THROW_GENERIC_ERROR("Qt.font(): Invalid arguments");
QV4::ExecutionEngine *v4 = scope.engine;
bool ok = false;
- QVariant v = QQml_valueTypeProvider()->createVariantFromJsObject(QMetaType::QFont, QQmlV4Handle(callData->args[0]), v4, &ok);
+ QVariant v = QQml_valueTypeProvider()->createVariantFromJsObject(QMetaType::QFont, QQmlV4Handle(argv[0]), v4, &ok);
if (!ok)
THROW_GENERIC_ERROR("Qt.font(): Invalid argument: no valid font subproperties specified");
return scope.engine->fromVariant(v);
@@ -445,15 +444,15 @@ ReturnedValue QtObject::method_font(const BuiltinFunction *b, CallData *callData
\qmlmethod Qt::vector2d(real x, real y)
Returns a Vector2D with the specified \c x and \c y.
*/
-ReturnedValue QtObject::method_vector2d(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_vector2d(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 2)
+ if (argc != 2)
THROW_GENERIC_ERROR("Qt.vector2d(): Invalid arguments");
float xy[3]; // qvector2d uses float internally
- xy[0] = callData->args[0].toNumber();
- xy[1] = callData->args[1].toNumber();
+ xy[0] = argv[0].toNumber();
+ xy[1] = argv[1].toNumber();
const void *params[] = { xy };
return scope.engine->fromVariant(QQml_valueTypeProvider()->createValueType(QMetaType::QVector2D, 1, params));
@@ -463,16 +462,16 @@ ReturnedValue QtObject::method_vector2d(const BuiltinFunction *b, CallData *call
\qmlmethod Qt::vector3d(real x, real y, real z)
Returns a Vector3D with the specified \c x, \c y and \c z.
*/
-ReturnedValue QtObject::method_vector3d(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_vector3d(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 3)
+ if (argc != 3)
THROW_GENERIC_ERROR("Qt.vector3d(): Invalid arguments");
float xyz[3]; // qvector3d uses float internally
- xyz[0] = callData->args[0].toNumber();
- xyz[1] = callData->args[1].toNumber();
- xyz[2] = callData->args[2].toNumber();
+ xyz[0] = argv[0].toNumber();
+ xyz[1] = argv[1].toNumber();
+ xyz[2] = argv[2].toNumber();
const void *params[] = { xyz };
return scope.engine->fromVariant(QQml_valueTypeProvider()->createValueType(QMetaType::QVector3D, 1, params));
@@ -482,17 +481,17 @@ ReturnedValue QtObject::method_vector3d(const BuiltinFunction *b, CallData *call
\qmlmethod Qt::vector4d(real x, real y, real z, real w)
Returns a Vector4D with the specified \c x, \c y, \c z and \c w.
*/
-ReturnedValue QtObject::method_vector4d(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_vector4d(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 4)
+ if (argc != 4)
THROW_GENERIC_ERROR("Qt.vector4d(): Invalid arguments");
float xyzw[4]; // qvector4d uses float internally
- xyzw[0] = callData->args[0].toNumber();
- xyzw[1] = callData->args[1].toNumber();
- xyzw[2] = callData->args[2].toNumber();
- xyzw[3] = callData->args[3].toNumber();
+ xyzw[0] = argv[0].toNumber();
+ xyzw[1] = argv[1].toNumber();
+ xyzw[2] = argv[2].toNumber();
+ xyzw[3] = argv[3].toNumber();
const void *params[] = { xyzw };
return scope.engine->fromVariant(QQml_valueTypeProvider()->createValueType(QMetaType::QVector4D, 1, params));
@@ -502,17 +501,17 @@ ReturnedValue QtObject::method_vector4d(const BuiltinFunction *b, CallData *call
\qmlmethod Qt::quaternion(real scalar, real x, real y, real z)
Returns a Quaternion with the specified \c scalar, \c x, \c y, and \c z.
*/
-ReturnedValue QtObject::method_quaternion(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_quaternion(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 4)
+ if (argc != 4)
THROW_GENERIC_ERROR("Qt.quaternion(): Invalid arguments");
qreal sxyz[4]; // qquaternion uses qreal internally
- sxyz[0] = callData->args[0].toNumber();
- sxyz[1] = callData->args[1].toNumber();
- sxyz[2] = callData->args[2].toNumber();
- sxyz[3] = callData->args[3].toNumber();
+ sxyz[0] = argv[0].toNumber();
+ sxyz[1] = argv[1].toNumber();
+ sxyz[2] = argv[2].toNumber();
+ sxyz[3] = argv[3].toNumber();
const void *params[] = { sxyz };
return scope.engine->fromVariant(QQml_valueTypeProvider()->createValueType(QMetaType::QQuaternion, 1, params));
@@ -527,42 +526,42 @@ matrix values.
Finally, the function may be called with no arguments and the resulting
matrix will be the identity matrix.
*/
-ReturnedValue QtObject::method_matrix4x4(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_matrix4x4(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() == 0) {
+ if (argc == 0) {
return scope.engine->fromVariant(QQml_valueTypeProvider()->createValueType(QMetaType::QMatrix4x4, 0, nullptr));
}
- if (callData->argc() == 1 && callData->args[0].isObject()) {
+ if (argc == 1 && argv[0].isObject()) {
bool ok = false;
- QVariant v = QQml_valueTypeProvider()->createVariantFromJsObject(QMetaType::QMatrix4x4, QQmlV4Handle(callData->args[0]), scope.engine, &ok);
+ QVariant v = QQml_valueTypeProvider()->createVariantFromJsObject(QMetaType::QMatrix4x4, QQmlV4Handle(argv[0]), scope.engine, &ok);
if (!ok)
THROW_GENERIC_ERROR("Qt.matrix4x4(): Invalid argument: not a valid matrix4x4 values array");
return scope.engine->fromVariant(v);
}
- if (callData->argc() != 16)
+ if (argc != 16)
THROW_GENERIC_ERROR("Qt.matrix4x4(): Invalid arguments");
qreal vals[16]; // qmatrix4x4 uses qreal internally
- vals[0] = callData->args[0].toNumber();
- vals[1] = callData->args[1].toNumber();
- vals[2] = callData->args[2].toNumber();
- vals[3] = callData->args[3].toNumber();
- vals[4] = callData->args[4].toNumber();
- vals[5] = callData->args[5].toNumber();
- vals[6] = callData->args[6].toNumber();
- vals[7] = callData->args[7].toNumber();
- vals[8] = callData->args[8].toNumber();
- vals[9] = callData->args[9].toNumber();
- vals[10] = callData->args[10].toNumber();
- vals[11] = callData->args[11].toNumber();
- vals[12] = callData->args[12].toNumber();
- vals[13] = callData->args[13].toNumber();
- vals[14] = callData->args[14].toNumber();
- vals[15] = callData->args[15].toNumber();
+ vals[0] = argv[0].toNumber();
+ vals[1] = argv[1].toNumber();
+ vals[2] = argv[2].toNumber();
+ vals[3] = argv[3].toNumber();
+ vals[4] = argv[4].toNumber();
+ vals[5] = argv[5].toNumber();
+ vals[6] = argv[6].toNumber();
+ vals[7] = argv[7].toNumber();
+ vals[8] = argv[8].toNumber();
+ vals[9] = argv[9].toNumber();
+ vals[10] = argv[10].toNumber();
+ vals[11] = argv[11].toNumber();
+ vals[12] = argv[12].toNumber();
+ vals[13] = argv[13].toNumber();
+ vals[14] = argv[14].toNumber();
+ vals[15] = argv[15].toNumber();
const void *params[] = { vals };
return scope.engine->fromVariant(QQml_valueTypeProvider()->createValueType(QMetaType::QMatrix4x4, 1, params));
@@ -582,13 +581,13 @@ by factor and converts the color back to RGB.
If \c factor is not supplied, returns a color 50% lighter than \c baseColor (factor 1.5).
*/
-ReturnedValue QtObject::method_lighter(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_lighter(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1 && callData->argc() != 2)
+ if (argc != 1 && argc != 2)
THROW_GENERIC_ERROR("Qt.lighter(): Invalid arguments");
- QVariant v = scope.engine->toVariant(callData->args[0], -1);
+ QVariant v = scope.engine->toVariant(argv[0], -1);
if (v.userType() == QVariant::String) {
bool ok = false;
v = QQmlStringConverters::colorFromString(v.toString(), &ok);
@@ -600,8 +599,8 @@ ReturnedValue QtObject::method_lighter(const BuiltinFunction *b, CallData *callD
}
qreal factor = 1.5;
- if (callData->argc() == 2)
- factor = callData->args[1].toNumber();
+ if (argc == 2)
+ factor = argv[1].toNumber();
return scope.engine->fromVariant(QQml_colorProvider()->lighter(v, factor));
}
@@ -621,13 +620,13 @@ by factor and converts the color back to RGB.
If \c factor is not supplied, returns a color 50% darker than \c baseColor (factor 2.0).
*/
-ReturnedValue QtObject::method_darker(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_darker(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1 && callData->argc() != 2)
+ if (argc != 1 && argc != 2)
THROW_GENERIC_ERROR("Qt.darker(): Invalid arguments");
- QVariant v = scope.engine->toVariant(callData->args[0], -1);
+ QVariant v = scope.engine->toVariant(argv[0], -1);
if (v.userType() == QVariant::String) {
bool ok = false;
v = QQmlStringConverters::colorFromString(v.toString(), &ok);
@@ -639,8 +638,8 @@ ReturnedValue QtObject::method_darker(const BuiltinFunction *b, CallData *callDa
}
qreal factor = 2.0;
- if (callData->argc() == 2)
- factor = callData->args[1].toNumber();
+ if (argc == 2)
+ factor = argv[1].toNumber();
return scope.engine->fromVariant(QQml_colorProvider()->darker(v, factor));
}
@@ -669,14 +668,14 @@ ReturnedValue QtObject::method_darker(const BuiltinFunction *b, CallData *callDa
Tint is most useful when a subtle change is intended to be conveyed due to some event; you can then use tinting to more effectively tune the visible color.
*/
-ReturnedValue QtObject::method_tint(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_tint(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 2)
+ if (argc != 2)
THROW_GENERIC_ERROR("Qt.tint(): Invalid arguments");
// base color
- QVariant v1 = scope.engine->toVariant(callData->args[0], -1);
+ QVariant v1 = scope.engine->toVariant(argv[0], -1);
if (v1.userType() == QVariant::String) {
bool ok = false;
v1 = QQmlStringConverters::colorFromString(v1.toString(), &ok);
@@ -688,7 +687,7 @@ ReturnedValue QtObject::method_tint(const BuiltinFunction *b, CallData *callData
}
// tint color
- QVariant v2 = scope.engine->toVariant(callData->args[1], -1);
+ QVariant v2 = scope.engine->toVariant(argv[1], -1);
if (v2.userType() == QVariant::String) {
bool ok = false;
v2 = QQmlStringConverters::colorFromString(v2.toString(), &ok);
@@ -718,22 +717,22 @@ If \a format is not specified, \a date is formatted using
\sa Locale
*/
-ReturnedValue QtObject::method_formatDate(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_formatDate(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 1 || callData->argc() > 2)
+ if (argc < 1 || argc > 2)
THROW_GENERIC_ERROR("Qt.formatDate(): Invalid arguments");
Qt::DateFormat enumFormat = Qt::DefaultLocaleShortDate;
- QDate date = scope.engine->toVariant(callData->args[0], -1).toDateTime().date();
+ QDate date = scope.engine->toVariant(argv[0], -1).toDateTime().date();
QString formattedDate;
- if (callData->argc() == 2) {
- QV4::ScopedString s(scope, callData->args[1]);
+ if (argc == 2) {
+ QV4::ScopedString s(scope, argv[1]);
if (s) {
QString format = s->toQString();
formattedDate = date.toString(format);
- } else if (callData->args[1].isNumber()) {
- quint32 intFormat = callData->args[1].asDouble();
+ } else if (argv[1].isNumber()) {
+ quint32 intFormat = argv[1].asDouble();
Qt::DateFormat format = Qt::DateFormat(intFormat);
formattedDate = date.toString(format);
} else {
@@ -761,28 +760,28 @@ If \a format is not specified, \a time is formatted using
\sa Locale
*/
-ReturnedValue QtObject::method_formatTime(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_formatTime(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 1 || callData->argc() > 2)
+ if (argc < 1 || argc > 2)
THROW_GENERIC_ERROR("Qt.formatTime(): Invalid arguments");
- QVariant argVariant = scope.engine->toVariant(callData->args[0], -1);
+ QVariant argVariant = scope.engine->toVariant(argv[0], -1);
QTime time;
- if (callData->args[0].as<DateObject>() || (argVariant.type() == QVariant::String))
+ if (argv[0].as<DateObject>() || (argVariant.type() == QVariant::String))
time = argVariant.toDateTime().time();
else // if (argVariant.type() == QVariant::Time), or invalid.
time = argVariant.toTime();
Qt::DateFormat enumFormat = Qt::DefaultLocaleShortDate;
QString formattedTime;
- if (callData->argc() == 2) {
- QV4::ScopedString s(scope, callData->args[1]);
+ if (argc == 2) {
+ QV4::ScopedString s(scope, argv[1]);
if (s) {
QString format = s->toQString();
formattedTime = time.toString(format);
- } else if (callData->args[1].isNumber()) {
- quint32 intFormat = callData->args[1].asDouble();
+ } else if (argv[1].isNumber()) {
+ quint32 intFormat = argv[1].asDouble();
Qt::DateFormat format = Qt::DateFormat(intFormat);
formattedTime = time.toString(format);
} else {
@@ -887,22 +886,22 @@ with the \a format values below to produce the following results:
\sa Locale
*/
-ReturnedValue QtObject::method_formatDateTime(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_formatDateTime(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 1 || callData->argc() > 2)
+ if (argc < 1 || argc > 2)
THROW_GENERIC_ERROR("Qt.formatDateTime(): Invalid arguments");
Qt::DateFormat enumFormat = Qt::DefaultLocaleShortDate;
- QDateTime dt = scope.engine->toVariant(callData->args[0], -1).toDateTime();
+ QDateTime dt = scope.engine->toVariant(argv[0], -1).toDateTime();
QString formattedDt;
- if (callData->argc() == 2) {
- QV4::ScopedString s(scope, callData->args[1]);
+ if (argc == 2) {
+ QV4::ScopedString s(scope, argv[1]);
if (s) {
QString format = s->toQString();
formattedDt = dt.toString(format);
- } else if (callData->args[1].isNumber()) {
- quint32 intFormat = callData->args[1].asDouble();
+ } else if (argv[1].isNumber()) {
+ quint32 intFormat = argv[1].asDouble();
Qt::DateFormat format = Qt::DateFormat(intFormat);
formattedDt = dt.toString(format);
} else {
@@ -926,14 +925,13 @@ ReturnedValue QtObject::method_formatDateTime(const BuiltinFunction *b, CallData
still fail to launch or fail to open the requested URL. This result will not be reported back
to the application.
*/
-ReturnedValue QtObject::method_openUrlExternally(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_openUrlExternally(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1) {
+ if (argc != 1)
return QV4::Encode(false);
- }
- ScopedValue result(scope, method_resolvedUrl(b, callData));
+ ScopedValue result(scope, method_resolvedUrl(b, thisObject, argv, argc));
QUrl url(result->toQStringNoThrow());
return scope.engine->fromVariant(QQml_guiProvider()->openUrlExternally(url));
}
@@ -942,13 +940,15 @@ ReturnedValue QtObject::method_openUrlExternally(const BuiltinFunction *b, CallD
\qmlmethod url Qt::resolvedUrl(url url)
Returns \a url resolved relative to the URL of the caller.
*/
-ReturnedValue QtObject::method_resolvedUrl(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_resolvedUrl(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
+ if (argc != 1)
+ return Encode::undefined();
- QUrl url = scope.engine->toVariant(callData->args[0], -1).toUrl();
+ QUrl url = scope.engine->toVariant(argv[0], -1).toUrl();
QQmlEngine *e = scope.engine->qmlEngine();
- QQmlEnginePrivate *p = 0;
+ QQmlEnginePrivate *p = nullptr;
if (e) p = QQmlEnginePrivate::get(e);
if (p) {
QQmlContextData *ctxt = scope.engine->callingQmlContext();
@@ -965,10 +965,10 @@ ReturnedValue QtObject::method_resolvedUrl(const BuiltinFunction *b, CallData *c
\qmlmethod list<string> Qt::fontFamilies()
Returns a list of the font families available to the application.
*/
-ReturnedValue QtObject::method_fontFamilies(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_fontFamilies(const FunctionObject *b, const Value *, const Value *, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 0)
+ if (argc != 0)
THROW_GENERIC_ERROR("Qt.fontFamilies(): Invalid arguments");
return scope.engine->fromVariant(QVariant(QQml_guiProvider()->fontFamilies()));
@@ -978,13 +978,13 @@ ReturnedValue QtObject::method_fontFamilies(const BuiltinFunction *b, CallData *
\qmlmethod string Qt::md5(data)
Returns a hex string of the md5 hash of \c data.
*/
-ReturnedValue QtObject::method_md5(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_md5(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_GENERIC_ERROR("Qt.md5(): Invalid arguments");
- QByteArray data = callData->args[0].toQStringNoThrow().toUtf8();
+ QByteArray data = argv[0].toQStringNoThrow().toUtf8();
QByteArray result = QCryptographicHash::hash(data, QCryptographicHash::Md5);
return Encode(scope.engine->newString(QLatin1String(result.toHex())));
}
@@ -993,13 +993,13 @@ ReturnedValue QtObject::method_md5(const BuiltinFunction *b, CallData *callData)
\qmlmethod string Qt::btoa(data)
Binary to ASCII - this function returns a base64 encoding of \c data.
*/
-ReturnedValue QtObject::method_btoa(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_btoa(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_GENERIC_ERROR("Qt.btoa(): Invalid arguments");
- QByteArray data = callData->args[0].toQStringNoThrow().toUtf8();
+ QByteArray data = argv[0].toQStringNoThrow().toUtf8();
return Encode(scope.engine->newString(QLatin1String(data.toBase64())));
}
@@ -1008,13 +1008,13 @@ ReturnedValue QtObject::method_btoa(const BuiltinFunction *b, CallData *callData
\qmlmethod string Qt::atob(data)
ASCII to binary - this function decodes the base64 encoded \a data string and returns it.
*/
-ReturnedValue QtObject::method_atob(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_atob(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_GENERIC_ERROR("Qt.atob(): Invalid arguments");
- QByteArray data = callData->args[0].toQStringNoThrow().toLatin1();
+ QByteArray data = argv[0].toQStringNoThrow().toLatin1();
return Encode(scope.engine->newString(QString::fromUtf8(QByteArray::fromBase64(data))));
}
@@ -1028,7 +1028,7 @@ QQmlEngine::quit() signal to the QCoreApplication::quit() slot.
\sa exit()
*/
-ReturnedValue QtObject::method_quit(const BuiltinFunction *b, CallData *)
+ReturnedValue QtObject::method_quit(const FunctionObject *b, const Value *, const Value *, int)
{
QQmlEnginePrivate::get(b->engine()->qmlEngine())->sendQuit();
return Encode::undefined();
@@ -1045,13 +1045,13 @@ ReturnedValue QtObject::method_quit(const BuiltinFunction *b, CallData *)
\sa quit()
*/
-ReturnedValue QtObject::method_exit(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_exit(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_GENERIC_ERROR("Qt.exit(): Invalid arguments");
- int retCode = callData->args[0].toNumber();
+ int retCode = argv[0].toNumber();
QQmlEnginePrivate::get(scope.engine->qmlEngine())->sendExit(retCode);
return QV4::Encode::undefined();
@@ -1081,10 +1081,10 @@ If this is the case, consider using \l{QtQml::Qt::createComponent()}{Qt.createCo
See \l {Dynamic QML Object Creation from JavaScript} for more information on using this function.
*/
-ReturnedValue QtObject::method_createQmlObject(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_createQmlObject(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 2 || callData->argc() > 3)
+ if (argc < 2 || argc > 3)
THROW_GENERIC_ERROR("Qt.createQmlObject(): Invalid arguments");
struct Error {
@@ -1116,33 +1116,37 @@ ReturnedValue QtObject::method_createQmlObject(const BuiltinFunction *b, CallDat
}
};
- QV8Engine *v8engine = scope.engine->v8Engine;
- QQmlEngine *engine = v8engine->engine();
+ QQmlEngine *engine = scope.engine->qmlEngine();
QQmlContextData *context = scope.engine->callingQmlContext();
+ if (!context) {
+ QQmlEngine *qmlEngine = scope.engine->qmlEngine();
+ if (qmlEngine)
+ context = QQmlContextData::get(QQmlEnginePrivate::get(qmlEngine)->rootContext);
+ }
Q_ASSERT(context);
- QQmlContext *effectiveContext = 0;
+ QQmlContext *effectiveContext = nullptr;
if (context->isPragmaLibraryContext)
effectiveContext = engine->rootContext();
else
effectiveContext = context->asQQmlContext();
Q_ASSERT(effectiveContext);
- QString qml = callData->args[0].toQStringNoThrow();
+ QString qml = argv[0].toQStringNoThrow();
if (qml.isEmpty())
RETURN_RESULT(Encode::null());
QUrl url;
- if (callData->argc() > 2)
- url = QUrl(callData->args[2].toQStringNoThrow());
+ if (argc > 2)
+ url = QUrl(argv[2].toQStringNoThrow());
else
url = QUrl(QLatin1String("inline"));
if (url.isValid() && url.isRelative())
url = context->resolvedUrl(url);
- QObject *parentArg = 0;
- QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, callData->args[1]);
+ QObject *parentArg = nullptr;
+ QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, argv[1]);
if (!!qobjectWrapper)
parentArg = qobjectWrapper->object();
if (!parentArg)
@@ -1238,46 +1242,50 @@ See \l {Dynamic QML Object Creation from JavaScript} for more information on usi
To create a QML object from an arbitrary string of QML (instead of a file),
use \l{QtQml::Qt::createQmlObject()}{Qt.createQmlObject()}.
*/
-ReturnedValue QtObject::method_createComponent(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_createComponent(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 1 || callData->argc() > 3)
+ if (argc < 1 || argc > 3)
THROW_GENERIC_ERROR("Qt.createComponent(): Invalid arguments");
- QV8Engine *v8engine = scope.engine->v8Engine;
- QQmlEngine *engine = v8engine->engine();
+ QQmlEngine *engine = scope.engine->qmlEngine();
QQmlContextData *context = scope.engine->callingQmlContext();
+ if (!context) {
+ QQmlEngine *qmlEngine = scope.engine->qmlEngine();
+ if (qmlEngine)
+ context = QQmlContextData::get(QQmlEnginePrivate::get(qmlEngine)->rootContext);
+ }
Q_ASSERT(context);
QQmlContextData *effectiveContext = context;
if (context->isPragmaLibraryContext)
- effectiveContext = 0;
+ effectiveContext = nullptr;
- QString arg = callData->args[0].toQStringNoThrow();
+ QString arg = argv[0].toQStringNoThrow();
if (arg.isEmpty())
RETURN_RESULT(QV4::Encode::null());
QQmlComponent::CompilationMode compileMode = QQmlComponent::PreferSynchronous;
- QObject *parentArg = 0;
+ QObject *parentArg = nullptr;
int consumedCount = 1;
- if (callData->argc() > 1) {
- ScopedValue lastArg(scope, callData->args[callData->argc()-1]);
+ if (argc > 1) {
+ ScopedValue lastArg(scope, argv[argc-1]);
// The second argument could be the mode enum
- if (callData->args[1].isInteger()) {
- int mode = callData->args[1].integerValue();
+ if (argv[1].isInteger()) {
+ int mode = argv[1].integerValue();
if (mode != int(QQmlComponent::PreferSynchronous) && mode != int(QQmlComponent::Asynchronous))
THROW_GENERIC_ERROR("Qt.createComponent(): Invalid arguments");
compileMode = QQmlComponent::CompilationMode(mode);
consumedCount += 1;
} else {
// The second argument could be the parent only if there are exactly two args
- if ((callData->argc() != 2) || !(lastArg->isObject() || lastArg->isNull()))
+ if ((argc != 2) || !(lastArg->isObject() || lastArg->isNull()))
THROW_GENERIC_ERROR("Qt.createComponent(): Invalid arguments");
}
- if (consumedCount < callData->argc()) {
+ if (consumedCount < argc) {
if (lastArg->isObject()) {
Scoped<QObjectWrapper> qobjectWrapper(scope, lastArg);
if (qobjectWrapper)
@@ -1285,7 +1293,7 @@ ReturnedValue QtObject::method_createComponent(const BuiltinFunction *b, CallDat
if (!parentArg)
THROW_GENERIC_ERROR("Qt.createComponent(): Invalid parent object");
} else if (lastArg->isNull()) {
- parentArg = 0;
+ parentArg = nullptr;
} else {
THROW_GENERIC_ERROR("Qt.createComponent(): Invalid parent object");
}
@@ -1321,17 +1329,17 @@ ReturnedValue QtObject::method_createComponent(const BuiltinFunction *b, CallDat
\sa Locale
*/
-ReturnedValue QtObject::method_locale(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_locale(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
QString code;
- if (callData->argc() > 1)
+ if (argc > 1)
THROW_GENERIC_ERROR("locale() requires 0 or 1 argument");
- if (callData->argc() == 1 && !callData->args[0].isString())
+ if (argc == 1 && !argv[0].isString())
THROW_TYPE_ERROR_WITH_MESSAGE("locale(): argument (locale code) must be a string");
- if (callData->argc() == 1)
- code = callData->args[0].toQStringNoThrow();
+ if (argc == 1)
+ code = argv[0].toQStringNoThrow();
return QQmlLocale::locale(scope.engine, code);
}
@@ -1395,12 +1403,12 @@ DEFINE_OBJECT_VTABLE(QQmlBindingFunction);
\since 5.0
*/
-ReturnedValue QtObject::method_binding(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_binding(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_GENERIC_ERROR("binding() requires 1 argument");
- const QV4::FunctionObject *f = callData->args[0].as<FunctionObject>();
+ const QV4::FunctionObject *f = argv[0].as<FunctionObject>();
if (!f)
THROW_TYPE_ERROR_WITH_MESSAGE("binding(): argument (binding expression) must be a function");
@@ -1408,14 +1416,14 @@ ReturnedValue QtObject::method_binding(const BuiltinFunction *b, CallData *callD
}
-ReturnedValue QtObject::method_get_platform(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_get_platform(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
// ### inefficient. Should be just a value based getter
- Object *o = callData->thisObject.as<Object>();
+ const Object *o = thisObject->as<Object>();
if (!o)
THROW_TYPE_ERROR();
- QtObject *qt = o->as<QtObject>();
+ const QtObject *qt = o->as<QtObject>();
if (!qt)
THROW_TYPE_ERROR();
@@ -1426,14 +1434,14 @@ ReturnedValue QtObject::method_get_platform(const BuiltinFunction *b, CallData *
return QV4::QObjectWrapper::wrap(scope.engine, qt->d()->platform);
}
-ReturnedValue QtObject::method_get_application(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_get_application(const FunctionObject *b, const Value *thisObject, const Value *, int)
{
QV4::Scope scope(b);
// ### inefficient. Should be just a value based getter
- Object *o = callData->thisObject.as<Object>();
+ const Object *o = thisObject->as<Object>();
if (!o)
THROW_TYPE_ERROR();
- QtObject *qt = o->as<QtObject>();
+ const QtObject *qt = o->as<QtObject>();
if (!qt)
THROW_TYPE_ERROR();
@@ -1444,13 +1452,13 @@ ReturnedValue QtObject::method_get_application(const BuiltinFunction *b, CallDat
return QV4::QObjectWrapper::wrap(scope.engine, qt->d()->application);
}
-ReturnedValue QtObject::method_get_inputMethod(const BuiltinFunction *b, CallData *)
+ReturnedValue QtObject::method_get_inputMethod(const FunctionObject *b, const Value *, const Value *, int)
{
QObject *o = QQml_guiProvider()->inputMethod();
return QV4::QObjectWrapper::wrap(b->engine(), o);
}
-ReturnedValue QtObject::method_get_styleHints(const BuiltinFunction *b, CallData *)
+ReturnedValue QtObject::method_get_styleHints(const FunctionObject *b, const Value *, const Value *, int)
{
QObject *o = QQml_guiProvider()->styleHints();
return QV4::QObjectWrapper::wrap(b->engine(), o);
@@ -1513,17 +1521,17 @@ static QString jsStack(QV4::ExecutionEngine *engine) {
return stack;
}
-static ReturnedValue writeToConsole(const BuiltinFunction *b, CallData *callData,
+static ReturnedValue writeToConsole(const FunctionObject *b, const Value *, const Value *argv, int argc,
ConsoleLogTypes logType, bool printStack = false)
{
- QLoggingCategory *loggingCategory = 0;
+ QLoggingCategory *loggingCategory = nullptr;
QString result;
QV4::Scope scope(b);
QV4::ExecutionEngine *v4 = scope.engine;
int start = 0;
- if (callData->argc() > 0) {
- if (const QObjectWrapper* wrapper = callData->args[0].as<QObjectWrapper>()) {
+ if (argc > 0) {
+ if (const QObjectWrapper* wrapper = argv[0].as<QObjectWrapper>()) {
if (QQmlLoggingCategory* category = qobject_cast<QQmlLoggingCategory*>(wrapper->object())) {
if (category->category())
loggingCategory = category->category();
@@ -1535,14 +1543,14 @@ static ReturnedValue writeToConsole(const BuiltinFunction *b, CallData *callData
}
- for (int i = start, ei = callData->argc(); i < ei; ++i) {
+ for (int i = start, ei = argc; i < ei; ++i) {
if (i != start)
result.append(QLatin1Char(' '));
- if (callData->args[i].as<ArrayObject>())
- result += QLatin1Char('[') + callData->args[i].toQStringNoThrow() + QLatin1Char(']');
+ if (argv[i].as<ArrayObject>())
+ result += QLatin1Char('[') + argv[i].toQStringNoThrow() + QLatin1Char(']');
else
- result.append(callData->args[i].toQStringNoThrow());
+ result.append(argv[i].toQStringNoThrow());
}
if (printStack)
@@ -1584,25 +1592,25 @@ static ReturnedValue writeToConsole(const BuiltinFunction *b, CallData *callData
DEFINE_OBJECT_VTABLE(ConsoleObject);
-ReturnedValue ConsoleObject::method_error(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_error(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
- return writeToConsole(b, callData, Error);
+ return writeToConsole(b, thisObject, argv, argc, Error);
}
-ReturnedValue ConsoleObject::method_log(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_log(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
//console.log
//console.debug
//print
- return writeToConsole(b, callData, Log);
+ return writeToConsole(b, thisObject, argv, argc, Log);
}
-ReturnedValue ConsoleObject::method_info(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_info(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
- return writeToConsole(b, callData, Info);
+ return writeToConsole(b, thisObject, argv, argc, Info);
}
-ReturnedValue ConsoleObject::method_profile(const BuiltinFunction *b, CallData *)
+ReturnedValue ConsoleObject::method_profile(const FunctionObject *b, const Value *, const Value *, int)
{
QV4::Scope scope(b);
QV4::ExecutionEngine *v4 = scope.engine;
@@ -1622,7 +1630,7 @@ ReturnedValue ConsoleObject::method_profile(const BuiltinFunction *b, CallData *
return QV4::Encode::undefined();
}
-ReturnedValue ConsoleObject::method_profileEnd(const BuiltinFunction *b, CallData *)
+ReturnedValue ConsoleObject::method_profileEnd(const FunctionObject *b, const Value *, const Value *, int)
{
QV4::Scope scope(b);
QV4::ExecutionEngine *v4 = scope.engine;
@@ -1643,28 +1651,28 @@ ReturnedValue ConsoleObject::method_profileEnd(const BuiltinFunction *b, CallDat
return QV4::Encode::undefined();
}
-ReturnedValue ConsoleObject::method_time(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_time(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_GENERIC_ERROR("console.time(): Invalid arguments");
QV8Engine *v8engine = scope.engine->v8Engine;
- QString name = callData->args[0].toQStringNoThrow();
+ QString name = argv[0].toQStringNoThrow();
v8engine->startTimer(name);
return QV4::Encode::undefined();
}
-ReturnedValue ConsoleObject::method_timeEnd(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_timeEnd(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_GENERIC_ERROR("console.timeEnd(): Invalid arguments");
QV8Engine *v8engine = scope.engine->v8Engine;
- QString name = callData->args[0].toQStringNoThrow();
+ QString name = argv[0].toQStringNoThrow();
bool wasRunning;
qint64 elapsed = v8engine->stopTimer(name, &wasRunning);
if (wasRunning) {
@@ -1673,12 +1681,12 @@ ReturnedValue ConsoleObject::method_timeEnd(const BuiltinFunction *b, CallData *
return QV4::Encode::undefined();
}
-ReturnedValue ConsoleObject::method_count(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_count(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
// first argument: name to print. Ignore any additional arguments
QString name;
- if (callData->argc() > 0)
- name = callData->args[0].toQStringNoThrow();
+ if (argc > 0)
+ name = argv[0].toQStringNoThrow();
Scope scope(b);
QV4::ExecutionEngine *v4 = scope.engine;
@@ -1698,10 +1706,10 @@ ReturnedValue ConsoleObject::method_count(const BuiltinFunction *b, CallData *ca
return QV4::Encode::undefined();
}
-ReturnedValue ConsoleObject::method_trace(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_trace(const FunctionObject *b, const Value *, const Value *, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 0)
+ if (argc != 0)
THROW_GENERIC_ERROR("console.trace(): Invalid arguments");
QV4::ExecutionEngine *v4 = scope.engine;
@@ -1716,26 +1724,26 @@ ReturnedValue ConsoleObject::method_trace(const BuiltinFunction *b, CallData *ca
return QV4::Encode::undefined();
}
-ReturnedValue ConsoleObject::method_warn(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_warn(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
- return writeToConsole(b, callData, Warn);
+ return writeToConsole(b, thisObject, argv, argc, Warn);
}
-ReturnedValue ConsoleObject::method_assert(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_assert(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() == 0)
+ if (argc == 0)
THROW_GENERIC_ERROR("console.assert(): Missing argument");
QV4::ExecutionEngine *v4 = scope.engine;
- if (!callData->args[0].toBoolean()) {
+ if (!argv[0].toBoolean()) {
QString message;
- for (int i = 1, ei = callData->argc(); i < ei; ++i) {
+ for (int i = 1, ei = argc; i < ei; ++i) {
if (i != 1)
message.append(QLatin1Char(' '));
- message.append(callData->args[i].toQStringNoThrow());
+ message.append(argv[i].toQStringNoThrow());
}
QString stack = jsStack(v4);
@@ -1749,13 +1757,13 @@ ReturnedValue ConsoleObject::method_assert(const BuiltinFunction *b, CallData *c
return QV4::Encode::undefined();
}
-ReturnedValue ConsoleObject::method_exception(const BuiltinFunction *b, CallData *callData)
+ReturnedValue ConsoleObject::method_exception(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() == 0)
+ if (argc == 0)
THROW_GENERIC_ERROR("console.exception(): Missing argument");
- return writeToConsole(b, callData, Error, true);
+ return writeToConsole(b, thisObject, argv, argc, Error, true);
}
@@ -1811,32 +1819,32 @@ void QV4::GlobalExtensions::init(Object *globalObject, QJSEngine::Extensions ext
\sa {Internationalization and Localization with Qt Quick}
*/
-ReturnedValue GlobalExtensions::method_qsTranslate(const BuiltinFunction *b, CallData *callData)
+ReturnedValue GlobalExtensions::method_qsTranslate(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 2)
+ if (argc < 2)
THROW_GENERIC_ERROR("qsTranslate() requires at least two arguments");
- if (!callData->args[0].isString())
+ if (!argv[0].isString())
THROW_GENERIC_ERROR("qsTranslate(): first argument (context) must be a string");
- if (!callData->args[1].isString())
+ if (!argv[1].isString())
THROW_GENERIC_ERROR("qsTranslate(): second argument (sourceText) must be a string");
- if ((callData->argc() > 2) && !callData->args[2].isString())
+ if ((argc > 2) && !argv[2].isString())
THROW_GENERIC_ERROR("qsTranslate(): third argument (disambiguation) must be a string");
- QString context = callData->args[0].toQStringNoThrow();
- QString text = callData->args[1].toQStringNoThrow();
+ QString context = argv[0].toQStringNoThrow();
+ QString text = argv[1].toQStringNoThrow();
QString comment;
- if (callData->argc() > 2) comment = callData->args[2].toQStringNoThrow();
+ if (argc > 2) comment = argv[2].toQStringNoThrow();
int i = 3;
- if (callData->argc() > i && callData->args[i].isString()) {
+ if (argc > i && argv[i].isString()) {
qWarning("qsTranslate(): specifying the encoding as fourth argument is deprecated");
++i;
}
int n = -1;
- if (callData->argc() > i)
- n = callData->args[i].toInt32();
+ if (argc > i)
+ n = argv[i].toInt32();
QString result = QCoreApplication::translate(context.toUtf8().constData(),
text.toUtf8().constData(),
@@ -1868,13 +1876,13 @@ ReturnedValue GlobalExtensions::method_qsTranslate(const BuiltinFunction *b, Cal
\sa {Internationalization and Localization with Qt Quick}
*/
-ReturnedValue GlobalExtensions::method_qsTranslateNoOp(const BuiltinFunction *b, CallData *callData)
+ReturnedValue GlobalExtensions::method_qsTranslateNoOp(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 2)
+ if (argc < 2)
return QV4::Encode::undefined();
else
- return callData->args[1].asReturnedValue();
+ return argv[1].asReturnedValue();
}
/*!
@@ -1894,16 +1902,16 @@ ReturnedValue GlobalExtensions::method_qsTranslateNoOp(const BuiltinFunction *b,
\sa {Internationalization and Localization with Qt Quick}
*/
-ReturnedValue GlobalExtensions::method_qsTr(const BuiltinFunction *b, CallData *callData)
+ReturnedValue GlobalExtensions::method_qsTr(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 1)
+ if (argc < 1)
THROW_GENERIC_ERROR("qsTr() requires at least one argument");
- if (!callData->args[0].isString())
+ if (!argv[0].isString())
THROW_GENERIC_ERROR("qsTr(): first argument (sourceText) must be a string");
- if ((callData->argc() > 1) && !callData->args[1].isString())
+ if ((argc > 1) && !argv[1].isString())
THROW_GENERIC_ERROR("qsTr(): second argument (disambiguation) must be a string");
- if ((callData->argc() > 2) && !callData->args[2].isNumber())
+ if ((argc > 2) && !argv[2].isNumber())
THROW_GENERIC_ERROR("qsTr(): third argument (n) must be a number");
QString context;
@@ -1933,13 +1941,13 @@ ReturnedValue GlobalExtensions::method_qsTr(const BuiltinFunction *b, CallData *
}
}
- QString text = callData->args[0].toQStringNoThrow();
+ QString text = argv[0].toQStringNoThrow();
QString comment;
- if (callData->argc() > 1)
- comment = callData->args[1].toQStringNoThrow();
+ if (argc > 1)
+ comment = argv[1].toQStringNoThrow();
int n = -1;
- if (callData->argc() > 2)
- n = callData->args[2].toInt32();
+ if (argc > 2)
+ n = argv[2].toInt32();
QString result = QCoreApplication::translate(context.toUtf8().constData(), text.toUtf8().constData(),
comment.toUtf8().constData(), n);
@@ -1969,12 +1977,12 @@ ReturnedValue GlobalExtensions::method_qsTr(const BuiltinFunction *b, CallData *
\sa {Internationalization and Localization with Qt Quick}
*/
-ReturnedValue GlobalExtensions::method_qsTrNoOp(const BuiltinFunction *, CallData *callData)
+ReturnedValue GlobalExtensions::method_qsTrNoOp(const FunctionObject *, const Value *, const Value *argv, int argc)
{
- if (callData->argc() < 1)
+ if (argc < 1)
return QV4::Encode::undefined();
else
- return callData->args[0].asReturnedValue();
+ return argv[0].asReturnedValue();
}
/*!
@@ -2007,21 +2015,21 @@ ReturnedValue GlobalExtensions::method_qsTrNoOp(const BuiltinFunction *, CallDat
\sa QT_TRID_NOOP(), {Internationalization and Localization with Qt Quick}
*/
-ReturnedValue GlobalExtensions::method_qsTrId(const BuiltinFunction *b, CallData *callData)
+ReturnedValue GlobalExtensions::method_qsTrId(const FunctionObject *b, const Value *, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() < 1)
+ if (argc < 1)
THROW_GENERIC_ERROR("qsTrId() requires at least one argument");
- if (!callData->args[0].isString())
+ if (!argv[0].isString())
THROW_TYPE_ERROR_WITH_MESSAGE("qsTrId(): first argument (id) must be a string");
- if (callData->argc() > 1 && !callData->args[1].isNumber())
+ if (argc > 1 && !argv[1].isNumber())
THROW_TYPE_ERROR_WITH_MESSAGE("qsTrId(): second argument (n) must be a number");
int n = -1;
- if (callData->argc() > 1)
- n = callData->args[1].toInt32();
+ if (argc > 1)
+ n = argv[1].toInt32();
- return Encode(scope.engine->newString(qtTrId(callData->args[0].toQStringNoThrow().toUtf8().constData(), n)));
+ return Encode(scope.engine->newString(qtTrId(argv[0].toQStringNoThrow().toUtf8().constData(), n)));
}
/*!
@@ -2040,17 +2048,17 @@ ReturnedValue GlobalExtensions::method_qsTrId(const BuiltinFunction *b, CallData
\sa qsTrId(), {Internationalization and Localization with Qt Quick}
*/
-ReturnedValue GlobalExtensions::method_qsTrIdNoOp(const BuiltinFunction *, CallData *callData)
+ReturnedValue GlobalExtensions::method_qsTrIdNoOp(const FunctionObject *, const Value *, const Value *argv, int argc)
{
- if (callData->argc() < 1)
+ if (argc < 1)
return QV4::Encode::undefined();
else
- return callData->args[0].asReturnedValue();
+ return argv[0].asReturnedValue();
}
#endif // translation
-ReturnedValue GlobalExtensions::method_gc(const BuiltinFunction *b, CallData *)
+ReturnedValue GlobalExtensions::method_gc(const FunctionObject *b, const Value *, const Value *, int)
{
b->engine()->memoryManager->runGC();
@@ -2059,15 +2067,15 @@ ReturnedValue GlobalExtensions::method_gc(const BuiltinFunction *b, CallData *)
-ReturnedValue GlobalExtensions::method_string_arg(const BuiltinFunction *b, CallData *callData)
+ReturnedValue GlobalExtensions::method_string_arg(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
QV4::Scope scope(b);
- if (callData->argc() != 1)
+ if (argc != 1)
THROW_GENERIC_ERROR("String.arg(): Invalid arguments");
- QString value = callData->thisObject.toQString();
+ QString value = thisObject->toQString();
- QV4::ScopedValue arg(scope, callData->args[0]);
+ QV4::ScopedValue arg(scope, argv[0]);
if (arg->isInteger())
RETURN_RESULT(scope.engine->newString(value.arg(arg->integerValue())));
else if (arg->isDouble())
@@ -2098,10 +2106,10 @@ be passed on to the function invoked. Note that if redundant calls
are eliminated, then only the last set of arguments will be passed to the
function.
*/
-ReturnedValue QtObject::method_callLater(const BuiltinFunction *b, CallData *callData)
+ReturnedValue QtObject::method_callLater(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc)
{
QV8Engine *v8engine = b->engine()->v8Engine;
- return v8engine->delayedCallQueue()->addUniquelyAndExecuteLater(b, callData);
+ return v8engine->delayedCallQueue()->addUniquelyAndExecuteLater(b, thisObject, argv, argc);
}
QT_END_NAMESPACE
diff --git a/src/qml/qml/v8/qqmlbuiltinfunctions_p.h b/src/qml/qml/v8/qqmlbuiltinfunctions_p.h
index 7d61aa0ada..104dae5d79 100644
--- a/src/qml/qml/v8/qqmlbuiltinfunctions_p.h
+++ b/src/qml/qml/v8/qqmlbuiltinfunctions_p.h
@@ -93,45 +93,45 @@ struct QtObject : Object
static ReturnedValue get(const Managed *m, String *name, bool *hasProperty);
static void advanceIterator(Managed *m, ObjectIterator *it, Value *name, uint *index, Property *p, PropertyAttributes *attributes);
- static ReturnedValue method_isQtObject(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_rgba(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_hsla(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_hsva(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_colorEqual(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_font(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_rect(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_point(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_size(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_vector2d(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_vector3d(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_vector4d(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_quaternion(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_matrix4x4(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_lighter(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_darker(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_tint(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_formatDate(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_formatTime(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_formatDateTime(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_openUrlExternally(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_fontFamilies(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_md5(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_btoa(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_atob(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_quit(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_exit(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_resolvedUrl(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_createQmlObject(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_createComponent(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_locale(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_binding(const BuiltinFunction *, CallData *callData);
-
- static ReturnedValue method_get_platform(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_get_application(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_get_inputMethod(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_get_styleHints(const BuiltinFunction *, CallData *callData);
-
- static ReturnedValue method_callLater(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_isQtObject(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_rgba(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_hsla(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_hsva(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_colorEqual(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_font(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_rect(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_point(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_size(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_vector2d(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_vector3d(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_vector4d(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_quaternion(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_matrix4x4(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_lighter(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_darker(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_tint(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_formatDate(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_formatTime(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_formatDateTime(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_openUrlExternally(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_fontFamilies(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_md5(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_btoa(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_atob(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_quit(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_exit(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_resolvedUrl(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_createQmlObject(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_createComponent(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_locale(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_binding(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+
+ static ReturnedValue method_get_platform(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_application(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_inputMethod(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_get_styleHints(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+
+ static ReturnedValue method_callLater(const FunctionObject *, const Value *thisObject, const Value *argv, int argc);
private:
void addAll();
@@ -142,18 +142,18 @@ struct ConsoleObject : Object
{
V4_OBJECT2(ConsoleObject, Object)
- static ReturnedValue method_error(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_log(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_info(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_profile(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_profileEnd(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_time(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_timeEnd(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_count(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_trace(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_warn(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_assert(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_exception(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_error(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_log(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_info(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_profile(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_profileEnd(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_time(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_timeEnd(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_count(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_trace(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_warn(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_assert(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_exception(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
};
@@ -161,17 +161,17 @@ struct Q_QML_PRIVATE_EXPORT GlobalExtensions {
static void init(Object *globalObject, QJSEngine::Extensions extensions);
#if QT_CONFIG(translation)
- static ReturnedValue method_qsTranslate(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_qsTranslateNoOp(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_qsTr(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_qsTrNoOp(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_qsTrId(const BuiltinFunction *, CallData *callData);
- static ReturnedValue method_qsTrIdNoOp(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_qsTranslate(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_qsTranslateNoOp(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_qsTr(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_qsTrNoOp(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_qsTrId(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
+ static ReturnedValue method_qsTrIdNoOp(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
#endif
- static ReturnedValue method_gc(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_gc(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
// on String:prototype
- static ReturnedValue method_string_arg(const BuiltinFunction *, CallData *callData);
+ static ReturnedValue method_string_arg(const FunctionObject *b, const Value *thisObject, const Value *argv, int argc);
};
diff --git a/src/qml/qml/v8/qv8engine.cpp b/src/qml/qml/v8/qv8engine.cpp
index 624e222241..bdb066267a 100644
--- a/src/qml/qml/v8/qv8engine.cpp
+++ b/src/qml/qml/v8/qv8engine.cpp
@@ -123,11 +123,11 @@ static void restoreJSValue(QDataStream &stream, void *data)
}
}
-QV8Engine::QV8Engine(QJSEngine* qq)
+QV8Engine::QV8Engine(QJSEngine *qq, QV4::ExecutionEngine *v4)
: q(qq)
- , m_engine(0)
- , m_xmlHttpRequestData(0)
- , m_listModelData(0)
+ , m_engine(nullptr)
+ , m_v4Engine(v4)
+ , m_xmlHttpRequestData(nullptr)
{
#ifndef Q_OS_HTML5
#ifdef Q_PROCESSOR_X86_32
@@ -149,8 +149,6 @@ QV8Engine::QV8Engine(QJSEngine* qq)
QMetaType::registerConverter<QJSValue, QStringList>(convertJSValueToVariantType<QStringList>);
QMetaType::registerStreamOperators(qMetaTypeId<QJSValue>(), saveJSValue, restoreJSValue);
- m_v4Engine = new QV4::ExecutionEngine;
- m_v4Engine->v8Engine = this;
m_delayedCallQueue.init(m_v4Engine);
QV4::QObjectWrapper::initializeBindings(m_v4Engine);
@@ -163,13 +161,8 @@ QV8Engine::~QV8Engine()
#if QT_CONFIG(xmlstreamreader) && QT_CONFIG(qml_network)
qt_rem_qmlxmlhttprequest(m_v4Engine, m_xmlHttpRequestData);
- m_xmlHttpRequestData = 0;
+ m_xmlHttpRequestData = nullptr;
#endif
-
- delete m_listModelData;
- m_listModelData = 0;
-
- delete m_v4Engine;
}
#if QT_CONFIG(qml_network)
@@ -294,11 +287,6 @@ void QV8Engine::setEngine(QQmlEngine *engine)
initQmlGlobalObject();
}
-QV4::ReturnedValue QV8Engine::global()
-{
- return m_v4Engine->globalObject->asReturnedValue();
-}
-
void QV8Engine::startTimer(const QString &timerName)
{
if (!m_time.isValid())
diff --git a/src/qml/qml/v8/qv8engine_p.h b/src/qml/qml/v8/qv8engine_p.h
index a430fba0e6..b6a378667e 100644
--- a/src/qml/qml/v8/qv8engine_p.h
+++ b/src/qml/qml/v8/qv8engine_p.h
@@ -77,12 +77,6 @@ namespace QV4 {
struct QObjectMethod;
}
-#define V4THROW_ERROR(string) \
- return ctx->engine()->throwError(QString::fromUtf8(string));
-
-#define V4THROW_TYPE(string) \
- return ctx->engine()->throwTypeError(QStringLiteral(string));
-
#define V4_DEFINE_EXTENSION(dataclass, datafunction) \
static inline dataclass *datafunction(QV4::ExecutionEngine *engine) \
{ \
@@ -159,12 +153,11 @@ class Q_QML_PRIVATE_EXPORT QV8Engine
{
friend class QJSEngine;
public:
- static QV8Engine* get(QJSEngine* q) { Q_ASSERT(q); return q->handle(); }
// static QJSEngine* get(QV8Engine* d) { Q_ASSERT(d); return d->q; }
- static QV4::ExecutionEngine *getV4(QJSEngine *q) { return q->handle()->m_v4Engine; }
+ static QV4::ExecutionEngine *getV4(QJSEngine *q) { return q->handle(); }
static QV4::ExecutionEngine *getV4(QV8Engine *d) { return d->m_v4Engine; }
- QV8Engine(QJSEngine* qq);
+ QV8Engine(QJSEngine* qq, QV4::ExecutionEngine *v4);
virtual ~QV8Engine();
// This enum should be in sync with QQmlEngine::ObjectOwnership
@@ -178,14 +171,10 @@ public:
void setEngine(QQmlEngine *engine);
QQmlEngine *engine() { return m_engine; }
QJSEngine *publicEngine() { return q; }
- QV4::ReturnedValue global();
QQmlDelayedCallQueue *delayedCallQueue() { return &m_delayedCallQueue; }
void *xmlHttpRequestData() const { return m_xmlHttpRequestData; }
- Deletable *listModelData() const { return m_listModelData; }
- void setListModelData(Deletable *d) { if (m_listModelData) delete m_listModelData; m_listModelData = d; }
-
void freezeObject(const QV4::Value &value);
#if QT_CONFIG(qml_network)
@@ -222,7 +211,6 @@ protected:
void *m_xmlHttpRequestData;
QVector<Deletable *> m_extensionData;
- Deletable *m_listModelData;
QSet<QString> m_illegalNames;
@@ -242,7 +230,7 @@ inline QV8Engine::Deletable *QV8Engine::extensionData(int index) const
if (index < m_extensionData.count())
return m_extensionData[index];
else
- return 0;
+ return nullptr;
}
diff --git a/src/qml/types/qqmlbind.cpp b/src/qml/types/qqmlbind.cpp
index 91c5a50877..513f7f2997 100644
--- a/src/qml/types/qqmlbind.cpp
+++ b/src/qml/types/qqmlbind.cpp
@@ -60,7 +60,7 @@ QT_BEGIN_NAMESPACE
class QQmlBindPrivate : public QObjectPrivate
{
public:
- QQmlBindPrivate() : obj(0), componentComplete(true), delayed(false), pendingEval(false) {}
+ QQmlBindPrivate() : obj(nullptr), componentComplete(true), delayed(false), pendingEval(false) {}
~QQmlBindPrivate() { }
QQmlNullableValue<bool> when;
@@ -370,7 +370,7 @@ void QQmlBind::eval()
//restore any previous binding
if (d->prevBind) {
QQmlAbstractBinding::Ptr p = d->prevBind;
- d->prevBind = 0;
+ d->prevBind = nullptr;
QQmlPropertyPrivate::setBinding(p.data());
}
return;
diff --git a/src/qml/types/qqmlbind_p.h b/src/qml/types/qqmlbind_p.h
index c9dd14b58a..5bf9ef85c6 100644
--- a/src/qml/types/qqmlbind_p.h
+++ b/src/qml/types/qqmlbind_p.h
@@ -71,7 +71,7 @@ class Q_AUTOTEST_EXPORT QQmlBind : public QObject, public QQmlPropertyValueSourc
Q_PROPERTY(bool delayed READ delayed WRITE setDelayed REVISION 8)
public:
- QQmlBind(QObject *parent=0);
+ QQmlBind(QObject *parent=nullptr);
~QQmlBind();
bool when() const;
diff --git a/src/qml/types/qqmlconnections.cpp b/src/qml/types/qqmlconnections.cpp
index e218cdcfe4..a43562a7b8 100644
--- a/src/qml/types/qqmlconnections.cpp
+++ b/src/qml/types/qqmlconnections.cpp
@@ -56,7 +56,7 @@ QT_BEGIN_NAMESPACE
class QQmlConnectionsPrivate : public QObjectPrivate
{
public:
- QQmlConnectionsPrivate() : target(0), enabled(true), targetSet(false), ignoreUnknownSignals(false), componentcomplete(true) {}
+ QQmlConnectionsPrivate() : target(nullptr), enabled(true), targetSet(false), ignoreUnknownSignals(false), componentcomplete(true) {}
QList<QQmlBoundSignal*> boundsignals;
QObject *target;
@@ -274,7 +274,7 @@ void QQmlConnections::connectSignals()
return;
QObject *target = this->target();
QQmlData *ddata = QQmlData::get(this);
- QQmlContextData *ctxtdata = ddata ? ddata->outerContext : 0;
+ QQmlContextData *ctxtdata = ddata ? ddata->outerContext : nullptr;
const QV4::CompiledData::Unit *qmlUnit = d->compilationUnit->data;
for (const QV4::CompiledData::Binding *binding : qAsConst(d->bindings)) {
@@ -290,7 +290,7 @@ void QQmlConnections::connectSignals()
QQmlBoundSignalExpression *expression = ctxtdata ?
new QQmlBoundSignalExpression(target, signalIndex,
- ctxtdata, this, d->compilationUnit->runtimeFunctions[binding->value.compiledScriptIndex]) : 0;
+ ctxtdata, this, d->compilationUnit->runtimeFunctions[binding->value.compiledScriptIndex]) : nullptr;
signal->takeExpression(expression);
d->boundsignals += signal;
} else {
diff --git a/src/qml/types/qqmlconnections_p.h b/src/qml/types/qqmlconnections_p.h
index 580b6522de..50e2c59ac3 100644
--- a/src/qml/types/qqmlconnections_p.h
+++ b/src/qml/types/qqmlconnections_p.h
@@ -73,7 +73,7 @@ class Q_AUTOTEST_EXPORT QQmlConnections : public QObject, public QQmlParserStatu
Q_PROPERTY(bool ignoreUnknownSignals READ ignoreUnknownSignals WRITE setIgnoreUnknownSignals)
public:
- QQmlConnections(QObject *parent=0);
+ QQmlConnections(QObject *parent=nullptr);
~QQmlConnections();
QObject *target() const;
diff --git a/src/qml/types/qqmldelegatemodel.cpp b/src/qml/types/qqmldelegatemodel.cpp
index 967f89971d..44166e4aa8 100644
--- a/src/qml/types/qqmldelegatemodel.cpp
+++ b/src/qml/types/qqmldelegatemodel.cpp
@@ -128,7 +128,8 @@ public:
QQmlDelegateModelEngineData(QV4::ExecutionEngine *v4);
~QQmlDelegateModelEngineData();
- QV4::ReturnedValue array(QV8Engine *engine, const QVector<QQmlChangeSet::Change> &changes);
+ QV4::ReturnedValue array(QV4::ExecutionEngine *engine,
+ const QVector<QQmlChangeSet::Change> &changes);
QV4::PersistentValue changeProto;
};
@@ -199,10 +200,10 @@ QQmlDelegateModelParts::QQmlDelegateModelParts(QQmlDelegateModel *parent)
*/
QQmlDelegateModelPrivate::QQmlDelegateModelPrivate(QQmlContext *ctxt)
- : m_delegate(0)
- , m_cacheMetaType(0)
+ : m_delegate(nullptr)
+ , m_cacheMetaType(nullptr)
, m_context(ctxt)
- , m_parts(0)
+ , m_parts(nullptr)
, m_filterGroup(QStringLiteral("items"))
, m_count(0)
, m_groupCount(Compositor::MinimumGroupCount)
@@ -213,9 +214,9 @@ QQmlDelegateModelPrivate::QQmlDelegateModelPrivate(QQmlContext *ctxt)
, m_transaction(false)
, m_incubatorCleanupScheduled(false)
, m_waitingToFetchMore(false)
- , m_cacheItems(0)
- , m_items(0)
- , m_persistedItems(0)
+ , m_cacheItems(nullptr)
+ , m_items(nullptr)
+ , m_persistedItems(nullptr)
{
}
@@ -267,10 +268,10 @@ QQmlDelegateModel::~QQmlDelegateModel()
if (cacheItem->object) {
delete cacheItem->object;
- cacheItem->object = 0;
+ cacheItem->object = nullptr;
cacheItem->contextData->invalidate();
Q_ASSERT(cacheItem->contextData->refCount == 1);
- cacheItem->contextData = 0;
+ cacheItem->contextData = nullptr;
cacheItem->scriptRef -= 1;
}
cacheItem->groups &= ~Compositor::UnresolvedFlag;
@@ -278,7 +279,7 @@ QQmlDelegateModel::~QQmlDelegateModel()
if (!cacheItem->isReferenced())
delete cacheItem;
else if (cacheItem->incubationTask)
- cacheItem->incubationTask->vdm = 0;
+ cacheItem->incubationTask->vdm = nullptr;
}
}
@@ -325,7 +326,7 @@ void QQmlDelegateModel::componentComplete()
}
d->m_cacheMetaType = new QQmlDelegateModelItemMetaType(
- QQmlEnginePrivate::getV8Engine(d->m_context->engine()), this, groupNames);
+ d->m_context->engine()->handle(), this, groupNames);
d->m_compositor.setGroupCount(d->m_groupCount);
d->m_compositor.setDefaultGroups(defaultGroups);
@@ -407,7 +408,7 @@ void QQmlDelegateModel::setDelegate(QQmlComponent *delegate)
qmlWarning(this) << tr("The delegate of a DelegateModel cannot be changed within onUpdated.");
return;
}
- bool wasValid = d->m_delegate != 0;
+ bool wasValid = d->m_delegate != nullptr;
d->m_delegate = delegate;
d->m_delegateValidated = false;
if (wasValid && d->m_complete) {
@@ -535,7 +536,7 @@ int QQmlDelegateModel::count() const
QQmlDelegateModel::ReleaseFlags QQmlDelegateModelPrivate::release(QObject *object)
{
- QQmlDelegateModel::ReleaseFlags stat = 0;
+ QQmlDelegateModel::ReleaseFlags stat = nullptr;
if (!object)
return stat;
@@ -545,7 +546,7 @@ QQmlDelegateModel::ReleaseFlags QQmlDelegateModelPrivate::release(QObject *objec
emitDestroyingItem(object);
if (cacheItem->incubationTask) {
releaseIncubator(cacheItem->incubationTask);
- cacheItem->incubationTask = 0;
+ cacheItem->incubationTask = nullptr;
}
cacheItem->Dispose();
stat |= QQmlInstanceModel::Destroyed;
@@ -581,7 +582,7 @@ void QQmlDelegateModel::cancel(int index)
if (cacheItem) {
if (cacheItem->incubationTask && !cacheItem->isObjectReferenced()) {
d->releaseIncubator(cacheItem->incubationTask);
- cacheItem->incubationTask = 0;
+ cacheItem->incubationTask = nullptr;
if (cacheItem->object) {
QObject *object = cacheItem->object;
@@ -630,7 +631,7 @@ QQmlDelegateModelGroup *QQmlDelegateModelPrivate::group_at(
QQmlDelegateModelPrivate *d = static_cast<QQmlDelegateModelPrivate *>(property->data);
return index >= 0 && index < d->m_groupCount - 1
? d->m_groups[index + 1]
- : 0;
+ : nullptr;
}
/*!
@@ -660,7 +661,7 @@ QQmlListProperty<QQmlDelegateModelGroup> QQmlDelegateModel::groups()
QQmlDelegateModelPrivate::group_append,
QQmlDelegateModelPrivate::group_count,
QQmlDelegateModelPrivate::group_at,
- 0);
+ nullptr);
}
/*!
@@ -838,11 +839,11 @@ void QQDMIncubationTask::statusChanged(Status status)
Q_ASSERT(incubating);
// The model was deleted from under our feet, cleanup ourselves
delete incubating->object;
- incubating->object = 0;
+ incubating->object = nullptr;
if (incubating->contextData) {
incubating->contextData->invalidate();
Q_ASSERT(incubating->contextData->refCount == 1);
- incubating->contextData = 0;
+ incubating->contextData = nullptr;
}
incubating->scriptRef = 0;
incubating->deleteLater();
@@ -863,7 +864,7 @@ void QQmlDelegateModelPrivate::releaseIncubator(QQDMIncubationTask *incubationTa
void QQmlDelegateModelPrivate::removeCacheItem(QQmlDelegateModelItem *cacheItem)
{
- int cidx = m_cache.indexOf(cacheItem);
+ int cidx = m_cache.lastIndexOf(cacheItem);
if (cidx >= 0) {
m_compositor.clearFlags(Compositor::Cache, cidx, 1, Compositor::CacheFlag);
m_cache.removeAt(cidx);
@@ -878,8 +879,8 @@ void QQmlDelegateModelPrivate::incubatorStatusChanged(QQDMIncubationTask *incuba
return;
QQmlDelegateModelItem *cacheItem = incubationTask->incubating;
- cacheItem->incubationTask = 0;
- incubationTask->incubating = 0;
+ cacheItem->incubationTask = nullptr;
+ incubationTask->incubating = nullptr;
releaseIncubator(incubationTask);
if (status == QQmlIncubator::Ready) {
@@ -899,13 +900,13 @@ void QQmlDelegateModelPrivate::incubatorStatusChanged(QQDMIncubationTask *incuba
else
emitDestroyingItem(cacheItem->object);
delete cacheItem->object;
- cacheItem->object = 0;
+ cacheItem->object = nullptr;
cacheItem->scriptRef -= 1;
if (cacheItem->contextData) {
cacheItem->contextData->invalidate();
Q_ASSERT(cacheItem->contextData->refCount == 1);
}
- cacheItem->contextData = 0;
+ cacheItem->contextData = nullptr;
if (!cacheItem->isReferenced()) {
removeCacheItem(cacheItem);
@@ -930,13 +931,13 @@ void QQmlDelegateModelPrivate::setInitialState(QQDMIncubationTask *incubationTas
emitInitItem(incubationTask, cacheItem->object);
}
-QObject *QQmlDelegateModelPrivate::object(Compositor::Group group, int index, bool asynchronous)
+QObject *QQmlDelegateModelPrivate::object(Compositor::Group group, int index, QQmlIncubator::IncubationMode incubationMode)
{
if (!m_delegate || index < 0 || index >= m_compositor.count(group)) {
qWarning() << "DelegateModel::item: index out range" << index << m_compositor.count(group);
- return 0;
+ return nullptr;
} else if (!m_context || !m_context->isValid()) {
- return 0;
+ return nullptr;
}
Compositor::iterator it = m_compositor.find(group, index);
@@ -946,7 +947,7 @@ QObject *QQmlDelegateModelPrivate::object(Compositor::Group group, int index, bo
if (!cacheItem) {
cacheItem = m_adaptorModel.createItem(m_cacheMetaType, it.modelIndex());
if (!cacheItem)
- return 0;
+ return nullptr;
cacheItem->groups = it->flags;
@@ -961,7 +962,8 @@ QObject *QQmlDelegateModelPrivate::object(Compositor::Group group, int index, bo
cacheItem->referenceObject();
if (cacheItem->incubationTask) {
- if (!asynchronous && cacheItem->incubationTask->incubationMode() == QQmlIncubator::Asynchronous) {
+ bool sync = (incubationMode == QQmlIncubator::Synchronous || incubationMode == QQmlIncubator::AsynchronousIfNested);
+ if (sync && cacheItem->incubationTask->incubationMode() == QQmlIncubator::Asynchronous) {
// previously requested async - now needed immediately
cacheItem->incubationTask->forceCompletion();
}
@@ -970,7 +972,7 @@ QObject *QQmlDelegateModelPrivate::object(Compositor::Group group, int index, bo
cacheItem->scriptRef += 1;
- cacheItem->incubationTask = new QQDMIncubationTask(this, asynchronous ? QQmlIncubator::Asynchronous : QQmlIncubator::AsynchronousIfNested);
+ cacheItem->incubationTask = new QQDMIncubationTask(this, incubationMode);
cacheItem->incubationTask->incubating = cacheItem;
cacheItem->incubationTask->clear();
@@ -1014,30 +1016,36 @@ QObject *QQmlDelegateModelPrivate::object(Compositor::Group group, int index, bo
delete cacheItem;
}
- return 0;
+ return nullptr;
}
/*
If asynchronous is true or the component is being loaded asynchronously due
- to an ancestor being loaded asynchronously, item() may return 0. In this
- case createdItem() will be emitted when the item is available. The item
- at this stage does not have any references, so item() must be called again
- to ensure a reference is held. Any call to item() which returns a valid item
- must be matched by a call to release() in order to destroy the item.
+ to an ancestor being loaded asynchronously, object() may return 0. In this
+ case createdItem() will be emitted when the object is available. The object
+ at this stage does not have any references, so object() must be called again
+ to ensure a reference is held. Any call to object() which returns a valid object
+ must be matched by a call to release() in order to destroy the object.
*/
-QObject *QQmlDelegateModel::object(int index, bool asynchronous)
+QObject *QQmlDelegateModel::object(int index, QQmlIncubator::IncubationMode incubationMode)
{
Q_D(QQmlDelegateModel);
if (!d->m_delegate || index < 0 || index >= d->m_compositor.count(d->m_compositorGroup)) {
qWarning() << "DelegateModel::item: index out range" << index << d->m_compositor.count(d->m_compositorGroup);
- return 0;
+ return nullptr;
}
- QObject *object = d->object(d->m_compositorGroup, index, asynchronous);
- if (!object)
- return 0;
+ return d->object(d->m_compositorGroup, index, incubationMode);
+}
+
+QQmlIncubator::Status QQmlDelegateModel::incubationStatus(int index)
+{
+ Q_D(QQmlDelegateModel);
+ Compositor::iterator it = d->m_compositor.find(d->m_compositorGroup, index);
+ if (!it->inCache())
+ return QQmlIncubator::Null;
- return object;
+ return d->m_cache.at(it.cacheIndex)->incubationTask->status();
}
QString QQmlDelegateModelPrivate::stringValue(Compositor::Group group, int index, const QString &name)
@@ -1339,7 +1347,7 @@ void QQmlDelegateModelPrivate::itemsRemoved(
if (QQDMIncubationTask *incubationTask = cacheItem->incubationTask) {
if (!cacheItem->isObjectReferenced()) {
releaseIncubator(cacheItem->incubationTask);
- cacheItem->incubationTask = 0;
+ cacheItem->incubationTask = nullptr;
if (cacheItem->object) {
QObject *object = cacheItem->object;
cacheItem->destroyObject();
@@ -1474,7 +1482,7 @@ void QQmlDelegateModelPrivate::emitChanges()
return;
m_transaction = true;
- QV8Engine *engine = QQmlEnginePrivate::getV8Engine(m_context->engine());
+ QV4::ExecutionEngine *engine = m_context->engine()->handle();
for (int i = 1; i < m_groupCount; ++i)
QQmlDelegateModelGroupPrivate::get(m_groups[i])->emitChanges(engine);
m_transaction = false;
@@ -1660,7 +1668,7 @@ bool QQmlDelegateModelPrivate::insert(Compositor::insert_iterator &before, const
// Must be before the new object is inserted into the cache or its indexes will be adjusted too.
itemsInserted(QVector<Compositor::Insert>(1, Compositor::Insert(before, 1, cacheItem->groups & ~Compositor::CacheFlag)));
- before = m_compositor.insert(before, 0, 0, 1, cacheItem->groups);
+ before = m_compositor.insert(before, nullptr, 0, 1, cacheItem->groups);
m_cache.insert(before.cacheIndex, cacheItem);
return true;
@@ -1669,11 +1677,11 @@ bool QQmlDelegateModelPrivate::insert(Compositor::insert_iterator &before, const
//============================================================================
QQmlDelegateModelItemMetaType::QQmlDelegateModelItemMetaType(
- QV8Engine *engine, QQmlDelegateModel *model, const QStringList &groupNames)
+ QV4::ExecutionEngine *engine, QQmlDelegateModel *model, const QStringList &groupNames)
: model(model)
, groupCount(groupNames.count() + 1)
- , v8Engine(engine)
- , metaObject(0)
+ , v4Engine(engine)
+ , metaObject(nullptr)
, groupNames(groupNames)
{
}
@@ -1713,57 +1721,56 @@ void QQmlDelegateModelItemMetaType::initializeMetaObject()
void QQmlDelegateModelItemMetaType::initializePrototype()
{
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(v8Engine);
- QV4::Scope scope(v4);
+ QV4::Scope scope(v4Engine);
- QV4::ScopedObject proto(scope, v4->newObject());
- proto->defineAccessorProperty(QStringLiteral("model"), QQmlDelegateModelItem::get_model, 0);
+ QV4::ScopedObject proto(scope, v4Engine->newObject());
+ proto->defineAccessorProperty(QStringLiteral("model"), QQmlDelegateModelItem::get_model, nullptr);
proto->defineAccessorProperty(QStringLiteral("groups"), QQmlDelegateModelItem::get_groups, QQmlDelegateModelItem::set_groups);
QV4::ScopedString s(scope);
QV4::ScopedProperty p(scope);
- s = v4->newString(QStringLiteral("isUnresolved"));
+ s = v4Engine->newString(QStringLiteral("isUnresolved"));
QV4::ScopedFunctionObject f(scope);
QV4::ExecutionContext *global = scope.engine->rootContext();
p->setGetter((f = QV4::DelegateModelGroupFunction::create(global, 30, QQmlDelegateModelItem::get_member)));
- p->setSetter(0);
+ p->setSetter(nullptr);
proto->insertMember(s, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
- s = v4->newString(QStringLiteral("inItems"));
+ s = v4Engine->newString(QStringLiteral("inItems"));
p->setGetter((f = QV4::DelegateModelGroupFunction::create(global, QQmlListCompositor::Default, QQmlDelegateModelItem::get_member)));
p->setSetter((f = QV4::DelegateModelGroupFunction::create(global, QQmlListCompositor::Default, QQmlDelegateModelItem::set_member)));
proto->insertMember(s, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
- s = v4->newString(QStringLiteral("inPersistedItems"));
+ s = v4Engine->newString(QStringLiteral("inPersistedItems"));
p->setGetter((f = QV4::DelegateModelGroupFunction::create(global, QQmlListCompositor::Persisted, QQmlDelegateModelItem::get_member)));
p->setSetter((f = QV4::DelegateModelGroupFunction::create(global, QQmlListCompositor::Persisted, QQmlDelegateModelItem::set_member)));
proto->insertMember(s, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
- s = v4->newString(QStringLiteral("itemsIndex"));
+ s = v4Engine->newString(QStringLiteral("itemsIndex"));
p->setGetter((f = QV4::DelegateModelGroupFunction::create(global, QQmlListCompositor::Default, QQmlDelegateModelItem::get_index)));
proto->insertMember(s, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
- s = v4->newString(QStringLiteral("persistedItemsIndex"));
+ s = v4Engine->newString(QStringLiteral("persistedItemsIndex"));
p->setGetter((f = QV4::DelegateModelGroupFunction::create(global, QQmlListCompositor::Persisted, QQmlDelegateModelItem::get_index)));
- p->setSetter(0);
+ p->setSetter(nullptr);
proto->insertMember(s, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
for (int i = 2; i < groupNames.count(); ++i) {
QString propertyName = QLatin1String("in") + groupNames.at(i);
propertyName.replace(2, 1, propertyName.at(2).toUpper());
- s = v4->newString(propertyName);
+ s = v4Engine->newString(propertyName);
p->setGetter((f = QV4::DelegateModelGroupFunction::create(global, i + 1, QQmlDelegateModelItem::get_member)));
p->setSetter((f = QV4::DelegateModelGroupFunction::create(global, i + 1, QQmlDelegateModelItem::set_member)));
proto->insertMember(s, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
}
for (int i = 2; i < groupNames.count(); ++i) {
const QString propertyName = groupNames.at(i) + QLatin1String("Index");
- s = v4->newString(propertyName);
+ s = v4Engine->newString(propertyName);
p->setGetter((f = QV4::DelegateModelGroupFunction::create(global, i + 1, QQmlDelegateModelItem::get_index)));
- p->setSetter(0);
+ p->setSetter(nullptr);
proto->insertMember(s, p, QV4::Attr_Accessor|QV4::Attr_NotConfigurable|QV4::Attr_NotEnumerable);
}
- modelItemProto.set(v4, proto);
+ modelItemProto.set(v4Engine, proto);
}
int QQmlDelegateModelItemMetaType::parseGroups(const QStringList &groups) const
@@ -1780,7 +1787,7 @@ int QQmlDelegateModelItemMetaType::parseGroups(const QStringList &groups) const
int QQmlDelegateModelItemMetaType::parseGroups(const QV4::Value &groups) const
{
int groupFlags = 0;
- QV4::Scope scope(QV8Engine::getV4(v8Engine));
+ QV4::Scope scope(v4Engine);
QV4::ScopedString s(scope, groups);
if (s) {
@@ -1806,10 +1813,10 @@ int QQmlDelegateModelItemMetaType::parseGroups(const QV4::Value &groups) const
return groupFlags;
}
-QV4::ReturnedValue QQmlDelegateModelItem::get_model(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQmlDelegateModelItem::get_model(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelItemObject> o(scope, callData->thisObject.as<QQmlDelegateModelItemObject>());
+ QV4::Scoped<QQmlDelegateModelItemObject> o(scope, thisObject->as<QQmlDelegateModelItemObject>());
if (!o)
return b->engine()->throwTypeError(QStringLiteral("Not a valid VisualData object"));
if (!o->d()->item->metaType->model)
@@ -1818,10 +1825,10 @@ QV4::ReturnedValue QQmlDelegateModelItem::get_model(const QV4::BuiltinFunction *
return o->d()->item->get();
}
-QV4::ReturnedValue QQmlDelegateModelItem::get_groups(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQmlDelegateModelItem::get_groups(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelItemObject> o(scope, callData->thisObject.as<QQmlDelegateModelItemObject>());
+ QV4::Scoped<QQmlDelegateModelItemObject> o(scope, thisObject->as<QQmlDelegateModelItemObject>());
if (!o)
return scope.engine->throwTypeError(QStringLiteral("Not a valid VisualData object"));
@@ -1834,21 +1841,21 @@ QV4::ReturnedValue QQmlDelegateModelItem::get_groups(const QV4::BuiltinFunction
return scope.engine->fromVariant(groups);
}
-QV4::ReturnedValue QQmlDelegateModelItem::set_groups(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQmlDelegateModelItem::set_groups(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelItemObject> o(scope, callData->thisObject.as<QQmlDelegateModelItemObject>());
+ QV4::Scoped<QQmlDelegateModelItemObject> o(scope, thisObject->as<QQmlDelegateModelItemObject>());
if (!o)
return scope.engine->throwTypeError(QStringLiteral("Not a valid VisualData object"));
- if (!callData->argc())
+ if (!argc)
THROW_TYPE_ERROR();
if (!o->d()->item->metaType->model)
RETURN_UNDEFINED();
QQmlDelegateModelPrivate *model = QQmlDelegateModelPrivate::get(o->d()->item->metaType->model);
- const int groupFlags = model->m_cacheMetaType->parseGroups(callData->args[0]);
+ const int groupFlags = model->m_cacheMetaType->parseGroups(argv[0]);
const int cacheIndex = model->m_cache.indexOf(o->d()->item);
Compositor::iterator it = model->m_compositor.find(Compositor::Cache, cacheIndex);
model->setGroups(it, 1, Compositor::Cache, groupFlags);
@@ -1900,12 +1907,12 @@ void QV4::Heap::QQmlDelegateModelItemObject::destroy()
QQmlDelegateModelItem::QQmlDelegateModelItem(
QQmlDelegateModelItemMetaType *metaType, int modelIndex)
- : v4(QV8Engine::getV4(metaType->v8Engine))
+ : v4(metaType->v4Engine)
, metaType(metaType)
- , contextData(0)
- , object(0)
- , attached(0)
- , incubationTask(0)
+ , contextData(nullptr)
+ , object(nullptr)
+ , attached(nullptr)
+ , incubationTask(nullptr)
, objectRef(0)
, scriptRef(0)
, groups(0)
@@ -1953,39 +1960,41 @@ void QQmlDelegateModelItem::destroyObject()
Q_ASSERT(data);
if (data->ownContext) {
data->ownContext->clearContext();
- data->ownContext = 0;
- data->context = 0;
+ if (data->ownContext->contextObject == object)
+ data->ownContext->contextObject = nullptr;
+ data->ownContext = nullptr;
+ data->context = nullptr;
}
object->deleteLater();
if (attached) {
- attached->m_cacheItem = 0;
- attached = 0;
+ attached->m_cacheItem = nullptr;
+ attached = nullptr;
}
contextData->invalidate();
- contextData = 0;
- object = 0;
+ contextData = nullptr;
+ object = nullptr;
}
QQmlDelegateModelItem *QQmlDelegateModelItem::dataForObject(QObject *object)
{
QQmlData *d = QQmlData::get(object);
- QQmlContextData *context = d ? d->context : 0;
- for (context = context ? context->parent : 0; context; context = context->parent) {
+ QQmlContextData *context = d ? d->context : nullptr;
+ for (context = context ? context->parent : nullptr; context; context = context->parent) {
if (QQmlDelegateModelItem *cacheItem = qobject_cast<QQmlDelegateModelItem *>(
context->contextObject)) {
return cacheItem;
}
}
- return 0;
+ return nullptr;
}
int QQmlDelegateModelItem::groupIndex(Compositor::Group group)
{
if (QQmlDelegateModelPrivate * const model = metaType->model
? QQmlDelegateModelPrivate::get(metaType->model)
- : 0) {
+ : nullptr) {
return model->m_compositor.find(Compositor::Cache, model->m_cache.indexOf(this)).index[group];
}
return -1;
@@ -2058,7 +2067,7 @@ int QQmlDelegateModelAttachedMetaObject::metaCall(QObject *object, QMetaObject::
}
QQmlDelegateModelAttached::QQmlDelegateModelAttached(QObject *parent)
- : m_cacheItem(0)
+ : m_cacheItem(nullptr)
, m_previousGroups(0)
{
QQml_setParent_noEvent(this, parent);
@@ -2098,7 +2107,7 @@ QQmlDelegateModelAttached::QQmlDelegateModelAttached(
QQmlDelegateModel *QQmlDelegateModelAttached::model() const
{
- return m_cacheItem ? m_cacheItem->metaType->model : 0;
+ return m_cacheItem ? m_cacheItem->metaType->model : nullptr;
}
/*!
@@ -2210,11 +2219,11 @@ void QQmlDelegateModelAttached::emitChanges()
const QMetaObject *meta = metaObject();
for (int i = 1; i < m_cacheItem->metaType->groupCount; ++i, ++notifierId) {
if (groupChanges & (1 << i))
- QMetaObject::activate(this, meta, notifierId, 0);
+ QMetaObject::activate(this, meta, notifierId, nullptr);
}
for (int i = 1; i < m_cacheItem->metaType->groupCount; ++i, ++notifierId) {
if (indexChanges & (1 << i))
- QMetaObject::activate(this, meta, notifierId, 0);
+ QMetaObject::activate(this, meta, notifierId, nullptr);
}
if (groupChanges)
@@ -2236,13 +2245,13 @@ bool QQmlDelegateModelGroupPrivate::isChangedConnected()
IS_SIGNAL_CONNECTED(q, QQmlDelegateModelGroup, changed, (const QQmlV4Handle &,const QQmlV4Handle &));
}
-void QQmlDelegateModelGroupPrivate::emitChanges(QV8Engine *engine)
+void QQmlDelegateModelGroupPrivate::emitChanges(QV4::ExecutionEngine *v4)
{
Q_Q(QQmlDelegateModelGroup);
if (isChangedConnected() && !changeSet.isEmpty()) {
- QV4::Scope scope(QV8Engine::getV4(engine));
- QV4::ScopedValue removed(scope, engineData(scope.engine)->array(engine, changeSet.removes()));
- QV4::ScopedValue inserted(scope, engineData(scope.engine)->array(engine, changeSet.inserts()));
+ QV4::Scope scope(v4);
+ QV4::ScopedValue removed(scope, engineData(scope.engine)->array(v4, changeSet.removes()));
+ QV4::ScopedValue inserted(scope, engineData(scope.engine)->array(v4, changeSet.inserts()));
emit q->changed(QQmlV4Handle(removed), QQmlV4Handle(inserted));
}
if (changeSet.difference() != 0)
@@ -2471,8 +2480,7 @@ QQmlV4Handle QQmlDelegateModelGroup::get(int index)
if (model->m_cacheMetaType->modelItemProto.isUndefined())
model->m_cacheMetaType->initializePrototype();
- QV8Engine *v8 = model->m_cacheMetaType->v8Engine;
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(v8);
+ QV4::ExecutionEngine *v4 = model->m_cacheMetaType->v4Engine;
QV4::Scope scope(v4);
QV4::ScopedObject o(scope, v4->memoryManager->allocObject<QQmlDelegateModelItemObject>(cacheItem));
QV4::ScopedObject p(scope, model->m_cacheMetaType->modelItemProto.value());
@@ -2500,7 +2508,7 @@ bool QQmlDelegateModelGroupPrivate::parseIndex(const QV4::Value &value, int *ind
QQmlDelegateModelItem * const cacheItem = object->d()->item;
if (QQmlDelegateModelPrivate *model = cacheItem->metaType->model
? QQmlDelegateModelPrivate::get(cacheItem->metaType->model)
- : 0) {
+ : nullptr) {
*index = model->m_cache.indexOf(cacheItem);
*group = Compositor::Cache;
return true;
@@ -2631,7 +2639,7 @@ void QQmlDelegateModelGroup::create(QQmlV4Function *args)
return;
}
- QObject *object = model->object(group, index, false);
+ QObject *object = model->object(group, index, QQmlIncubator::AsynchronousIfNested);
if (object) {
QVector<Compositor::Insert> inserts;
Compositor::iterator it = model->m_compositor.find(group, index);
@@ -3119,21 +3127,21 @@ bool QQmlPartsModel::isValid() const
return m_model->isValid();
}
-QObject *QQmlPartsModel::object(int index, bool asynchronous)
+QObject *QQmlPartsModel::object(int index, QQmlIncubator::IncubationMode incubationMode)
{
QQmlDelegateModelPrivate *model = QQmlDelegateModelPrivate::get(m_model);
if (!model->m_delegate || index < 0 || index >= model->m_compositor.count(m_compositorGroup)) {
qWarning() << "DelegateModel::item: index out range" << index << model->m_compositor.count(m_compositorGroup);
- return 0;
+ return nullptr;
}
- QObject *object = model->object(m_compositorGroup, index, asynchronous);
+ QObject *object = model->object(m_compositorGroup, index, incubationMode);
if (QQuickPackage *package = qmlobject_cast<QQuickPackage *>(object)) {
QObject *part = package->part(m_part);
if (!part)
- return 0;
+ return nullptr;
m_packaged.insertMulti(part, package);
return part;
}
@@ -3145,12 +3153,12 @@ QObject *QQmlPartsModel::object(int index, bool asynchronous)
model->m_delegateValidated = true;
}
- return 0;
+ return nullptr;
}
QQmlInstanceModel::ReleaseFlags QQmlPartsModel::release(QObject *item)
{
- QQmlInstanceModel::ReleaseFlags flags = 0;
+ QQmlInstanceModel::ReleaseFlags flags = nullptr;
QHash<QObject *, QQuickPackage *>::iterator it = m_packaged.find(item);
if (it != m_packaged.end()) {
@@ -3178,6 +3186,16 @@ void QQmlPartsModel::setWatchedRoles(const QList<QByteArray> &roles)
m_watchedRoles = roles;
}
+QQmlIncubator::Status QQmlPartsModel::incubationStatus(int index)
+{
+ QQmlDelegateModelPrivate *model = QQmlDelegateModelPrivate::get(m_model);
+ Compositor::iterator it = model->m_compositor.find(model->m_compositorGroup, index);
+ if (!it->inCache())
+ return QQmlIncubator::Null;
+
+ return model->m_cache.at(it.cacheIndex)->incubationTask->status();
+}
+
int QQmlPartsModel::indexOf(QObject *item, QObject *) const
{
QHash<QObject *, QQuickPackage *>::const_iterator it = m_packaged.find(item);
@@ -3222,23 +3240,23 @@ struct QQmlDelegateModelGroupChange : QV4::Object
return e->memoryManager->allocObject<QQmlDelegateModelGroupChange>();
}
- static QV4::ReturnedValue method_get_index(const QV4::BuiltinFunction *b, QV4::CallData *callData) {
+ static QV4::ReturnedValue method_get_index(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int) {
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelGroupChange> that(scope, callData->thisObject.as<QQmlDelegateModelGroupChange>());
+ QV4::Scoped<QQmlDelegateModelGroupChange> that(scope, thisObject->as<QQmlDelegateModelGroupChange>());
if (!that)
THROW_TYPE_ERROR();
return QV4::Encode(that->d()->change.index);
}
- static QV4::ReturnedValue method_get_count(const QV4::BuiltinFunction *b, QV4::CallData *callData) {
+ static QV4::ReturnedValue method_get_count(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int) {
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelGroupChange> that(scope, callData->thisObject.as<QQmlDelegateModelGroupChange>());
+ QV4::Scoped<QQmlDelegateModelGroupChange> that(scope, thisObject->as<QQmlDelegateModelGroupChange>());
if (!that)
THROW_TYPE_ERROR();
return QV4::Encode(that->d()->change.count);
}
- static QV4::ReturnedValue method_get_moveId(const QV4::BuiltinFunction *b, QV4::CallData *callData) {
+ static QV4::ReturnedValue method_get_moveId(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int) {
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelGroupChange> that(scope, callData->thisObject.as<QQmlDelegateModelGroupChange>());
+ QV4::Scoped<QQmlDelegateModelGroupChange> that(scope, thisObject->as<QQmlDelegateModelGroupChange>());
if (!that)
THROW_TYPE_ERROR();
if (that->d()->change.moveId < 0)
@@ -3318,9 +3336,9 @@ QQmlDelegateModelEngineData::QQmlDelegateModelEngineData(QV4::ExecutionEngine *v
QV4::Scope scope(v4);
QV4::ScopedObject proto(scope, v4->newObject());
- proto->defineAccessorProperty(QStringLiteral("index"), QQmlDelegateModelGroupChange::method_get_index, 0);
- proto->defineAccessorProperty(QStringLiteral("count"), QQmlDelegateModelGroupChange::method_get_count, 0);
- proto->defineAccessorProperty(QStringLiteral("moveId"), QQmlDelegateModelGroupChange::method_get_moveId, 0);
+ proto->defineAccessorProperty(QStringLiteral("index"), QQmlDelegateModelGroupChange::method_get_index, nullptr);
+ proto->defineAccessorProperty(QStringLiteral("count"), QQmlDelegateModelGroupChange::method_get_count, nullptr);
+ proto->defineAccessorProperty(QStringLiteral("moveId"), QQmlDelegateModelGroupChange::method_get_moveId, nullptr);
changeProto.set(v4, proto);
}
@@ -3328,9 +3346,9 @@ QQmlDelegateModelEngineData::~QQmlDelegateModelEngineData()
{
}
-QV4::ReturnedValue QQmlDelegateModelEngineData::array(QV8Engine *engine, const QVector<QQmlChangeSet::Change> &changes)
+QV4::ReturnedValue QQmlDelegateModelEngineData::array(QV4::ExecutionEngine *v4,
+ const QVector<QQmlChangeSet::Change> &changes)
{
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine);
QV4::Scope scope(v4);
QV4::ScopedObject o(scope, QQmlDelegateModelGroupChangeArray::create(v4, changes));
return o.asReturnedValue();
diff --git a/src/qml/types/qqmldelegatemodel_p.h b/src/qml/types/qqmldelegatemodel_p.h
index 186144d107..b894df8f82 100644
--- a/src/qml/types/qqmldelegatemodel_p.h
+++ b/src/qml/types/qqmldelegatemodel_p.h
@@ -54,6 +54,7 @@
#include <private/qtqmlglobal_p.h>
#include <private/qqmllistcompositor_p.h>
#include <private/qqmlobjectmodel_p.h>
+#include <private/qqmlincubator_p.h>
#include <QtCore/qabstractitemmodel.h>
#include <QtCore/qstringlist.h>
@@ -89,7 +90,7 @@ class Q_QML_PRIVATE_EXPORT QQmlDelegateModel : public QQmlInstanceModel, public
Q_INTERFACES(QQmlParserStatus)
public:
QQmlDelegateModel();
- QQmlDelegateModel(QQmlContext *, QObject *parent=0);
+ QQmlDelegateModel(QQmlContext *, QObject *parent=nullptr);
~QQmlDelegateModel();
void classBegin() override;
@@ -108,12 +109,13 @@ public:
Q_INVOKABLE QVariant parentModelIndex() const;
int count() const override;
- bool isValid() const override { return delegate() != 0; }
- QObject *object(int index, bool asynchronous = false) override;
+ bool isValid() const override { return delegate() != nullptr; }
+ QObject *object(int index, QQmlIncubator::IncubationMode incubationMode = QQmlIncubator::AsynchronousIfNested) override;
ReleaseFlags release(QObject *object) override;
void cancel(int index) override;
QString stringValue(int index, const QString &role) override;
void setWatchedRoles(const QList<QByteArray> &roles) override;
+ QQmlIncubator::Status incubationStatus(int index) override;
int indexOf(QObject *object, QObject *objectContext) const override;
@@ -162,8 +164,8 @@ class Q_QML_PRIVATE_EXPORT QQmlDelegateModelGroup : public QObject
Q_PROPERTY(QString name READ name WRITE setName NOTIFY nameChanged)
Q_PROPERTY(bool includeByDefault READ defaultInclude WRITE setDefaultInclude NOTIFY defaultIncludeChanged)
public:
- QQmlDelegateModelGroup(QObject *parent = 0);
- QQmlDelegateModelGroup(const QString &name, QQmlDelegateModel *model, int compositorType, QObject *parent = 0);
+ QQmlDelegateModelGroup(QObject *parent = nullptr);
+ QQmlDelegateModelGroup(const QString &name, QQmlDelegateModel *model, int compositorType, QObject *parent = nullptr);
~QQmlDelegateModelGroup();
QString name() const;
diff --git a/src/qml/types/qqmldelegatemodel_p_p.h b/src/qml/types/qqmldelegatemodel_p_p.h
index e0416e93ee..68b987a5fa 100644
--- a/src/qml/types/qqmldelegatemodel_p_p.h
+++ b/src/qml/types/qqmldelegatemodel_p_p.h
@@ -69,7 +69,7 @@ class QQmlDelegateModelAttachedMetaObject;
class QQmlDelegateModelItemMetaType : public QQmlRefCount
{
public:
- QQmlDelegateModelItemMetaType(QV8Engine *engine, QQmlDelegateModel *model, const QStringList &groupNames);
+ QQmlDelegateModelItemMetaType(QV4::ExecutionEngine *engine, QQmlDelegateModel *model, const QStringList &groupNames);
~QQmlDelegateModelItemMetaType();
void initializeMetaObject();
@@ -80,7 +80,7 @@ public:
QPointer<QQmlDelegateModel> model;
const int groupCount;
- QV8Engine * const v8Engine;
+ QV4::ExecutionEngine * const v4Engine;
QQmlDelegateModelAttachedMetaObject *metaObject;
const QStringList groupNames;
QV4::PersistentValue modelItemProto;
@@ -126,9 +126,9 @@ public:
virtual void setValue(const QString &role, const QVariant &value) { Q_UNUSED(role); Q_UNUSED(value); }
virtual bool resolveIndex(const QQmlAdaptorModel &, int) { return false; }
- static QV4::ReturnedValue get_model(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue get_groups(const QV4::BuiltinFunction *, QV4::CallData *callData);
- static QV4::ReturnedValue set_groups(const QV4::BuiltinFunction *, QV4::CallData *callData);
+ static QV4::ReturnedValue get_model(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue get_groups(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue set_groups(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
static QV4::ReturnedValue get_member(QQmlDelegateModelItem *thisItem, uint flag, const QV4::Value &);
static QV4::ReturnedValue set_member(QQmlDelegateModelItem *thisItem, uint flag, const QV4::Value &arg);
static QV4::ReturnedValue get_index(QQmlDelegateModelItem *thisItem, uint flag, const QV4::Value &arg);
@@ -182,7 +182,7 @@ class QQDMIncubationTask : public QQmlIncubator
public:
QQDMIncubationTask(QQmlDelegateModelPrivate *l, IncubationMode mode)
: QQmlIncubator(mode)
- , incubating(0)
+ , incubating(nullptr)
, vdm(l) {}
void statusChanged(Status) override;
@@ -220,7 +220,7 @@ public:
void setModel(QQmlDelegateModel *model, Compositor::Group group);
bool isChangedConnected();
- void emitChanges(QV8Engine *engine);
+ void emitChanges(QV4::ExecutionEngine *engine);
void emitModelUpdated(bool reset);
void createdPackage(int index, QQuickPackage *package);
@@ -256,7 +256,7 @@ public:
void connectModel(QQmlAdaptorModel *model);
void requestMoreIfNecessary();
- QObject *object(Compositor::Group group, int index, bool asynchronous);
+ QObject *object(Compositor::Group group, int index, QQmlIncubator::IncubationMode incubationMode);
QQmlDelegateModel::ReleaseFlags release(QObject *object);
QString stringValue(Compositor::Group group, int index, const QString &name);
void emitCreatedPackage(QQDMIncubationTask *incubationTask, QQuickPackage *package);
@@ -278,12 +278,12 @@ public:
void itemsInserted(
const QVector<Compositor::Insert> &inserts,
QVarLengthArray<QVector<QQmlChangeSet::Change>, Compositor::MaximumGroupCount> *translatedInserts,
- QHash<int, QList<QQmlDelegateModelItem *> > *movedItems = 0);
+ QHash<int, QList<QQmlDelegateModelItem *> > *movedItems = nullptr);
void itemsInserted(const QVector<Compositor::Insert> &inserts);
void itemsRemoved(
const QVector<Compositor::Remove> &removes,
QVarLengthArray<QVector<QQmlChangeSet::Change>, Compositor::MaximumGroupCount> *translatedRemoves,
- QHash<int, QList<QQmlDelegateModelItem *> > *movedItems = 0);
+ QHash<int, QList<QQmlDelegateModelItem *> > *movedItems = nullptr);
void itemsRemoved(const QVector<Compositor::Remove> &removes);
void itemsMoved(
const QVector<Compositor::Remove> &removes, const QVector<Compositor::Insert> &inserts);
@@ -341,7 +341,7 @@ class QQmlPartsModel : public QQmlInstanceModel, public QQmlDelegateModelGroupEm
Q_OBJECT
Q_PROPERTY(QString filterOnGroup READ filterGroup WRITE setFilterGroup NOTIFY filterGroupChanged RESET resetFilterGroup)
public:
- QQmlPartsModel(QQmlDelegateModel *model, const QString &part, QObject *parent = 0);
+ QQmlPartsModel(QQmlDelegateModel *model, const QString &part, QObject *parent = nullptr);
~QQmlPartsModel();
QString filterGroup() const;
@@ -352,11 +352,12 @@ public:
int count() const override;
bool isValid() const override;
- QObject *object(int index, bool asynchronous = false) override;
+ QObject *object(int index, QQmlIncubator::IncubationMode incubationMode = QQmlIncubator::AsynchronousIfNested) override;
ReleaseFlags release(QObject *item) override;
QString stringValue(int index, const QString &role) override;
QList<QByteArray> watchedRoles() const { return m_watchedRoles; }
void setWatchedRoles(const QList<QByteArray> &roles) override;
+ QQmlIncubator::Status incubationStatus(int index) override;
int indexOf(QObject *item, QObject *objectContext) const override;
diff --git a/src/qml/types/qqmlinstantiator.cpp b/src/qml/types/qqmlinstantiator.cpp
index 2de5875deb..213bef7879 100644
--- a/src/qml/types/qqmlinstantiator.cpp
+++ b/src/qml/types/qqmlinstantiator.cpp
@@ -56,8 +56,8 @@ QQmlInstantiatorPrivate::QQmlInstantiatorPrivate()
, ownModel(false)
, requestedIndex(-1)
, model(QVariant(1))
- , instanceModel(0)
- , delegate(0)
+ , instanceModel(nullptr)
+ , delegate(nullptr)
{
}
@@ -85,7 +85,7 @@ void QQmlInstantiatorPrivate::clear()
QObject *QQmlInstantiatorPrivate::modelObject(int index, bool async)
{
requestedIndex = index;
- QObject *o = instanceModel->object(index, async);
+ QObject *o = instanceModel->object(index, async ? QQmlIncubator::Asynchronous : QQmlIncubator::AsynchronousIfNested);
requestedIndex = -1;
return o;
}
@@ -123,7 +123,7 @@ void QQmlInstantiatorPrivate::_q_createdItem(int idx, QObject* item)
if (objects.contains(item)) //Case when it was created synchronously in regenerate
return;
if (requestedIndex != idx) // Asynchronous creation, reference the object
- (void)instanceModel->object(idx, false);
+ (void)instanceModel->object(idx);
item->setParent(q);
if (objects.size() < idx + 1) {
int modelCount = instanceModel->count();
@@ -183,7 +183,7 @@ void QQmlInstantiatorPrivate::_q_modelUpdated(const QQmlChangeSet &changeSet, bo
objects = objects.mid(0, index) + movedObjects + objects.mid(index);
} else {
if (insert.index <= objects.size())
- objects.insert(insert.index, insert.count, 0);
+ objects.insert(insert.index, insert.count, nullptr);
for (int i = 0; i < insert.count; ++i) {
int modelIndex = index + i;
QObject* obj = modelObject(modelIndex, async);
@@ -396,11 +396,11 @@ void QQmlInstantiator::setModel(const QVariant &v)
QQmlInstanceModel *prevModel = d->instanceModel;
QObject *object = qvariant_cast<QObject*>(v);
- QQmlInstanceModel *vim = 0;
+ QQmlInstanceModel *vim = nullptr;
if (object && (vim = qobject_cast<QQmlInstanceModel *>(object))) {
if (d->ownModel) {
delete d->instanceModel;
- prevModel = 0;
+ prevModel = nullptr;
d->ownModel = false;
}
d->instanceModel = vim;
@@ -444,7 +444,7 @@ QObject *QQmlInstantiator::object() const
Q_D(const QQmlInstantiator);
if (d->objects.count())
return d->objects[0];
- return 0;
+ return nullptr;
}
/*!
@@ -457,7 +457,7 @@ QObject *QQmlInstantiator::objectAt(int index) const
Q_D(const QQmlInstantiator);
if (index >= 0 && index < d->objects.count())
return d->objects[index];
- return 0;
+ return nullptr;
}
/*!
diff --git a/src/qml/types/qqmlinstantiator_p.h b/src/qml/types/qqmlinstantiator_p.h
index ee18daa48c..5727c4d1e1 100644
--- a/src/qml/types/qqmlinstantiator_p.h
+++ b/src/qml/types/qqmlinstantiator_p.h
@@ -71,7 +71,7 @@ class Q_AUTOTEST_EXPORT QQmlInstantiator : public QObject, public QQmlParserStat
Q_CLASSINFO("DefaultProperty", "delegate")
public:
- QQmlInstantiator(QObject *parent = 0);
+ QQmlInstantiator(QObject *parent = nullptr);
~QQmlInstantiator();
bool isActive() const;
diff --git a/src/qml/types/qqmllistmodel.cpp b/src/qml/types/qqmllistmodel.cpp
index e32e0c75f3..d4fc02cd3e 100644
--- a/src/qml/types/qqmllistmodel.cpp
+++ b/src/qml/types/qqmllistmodel.cpp
@@ -100,7 +100,7 @@ const ListLayout::Role &ListLayout::getRoleOrCreate(const QString &key, Role::Da
if (node) {
const Role &r = *node->value;
if (type != r.type)
- qmlWarning(0) << QStringLiteral("Can't assign to existing role '%1' of different type [%2 -> %3]").arg(r.name).arg(roleTypeName(type)).arg(roleTypeName(r.type));
+ qmlWarning(nullptr) << QStringLiteral("Can't assign to existing role '%1' of different type [%2 -> %3]").arg(r.name).arg(roleTypeName(type)).arg(roleTypeName(r.type));
return r;
}
@@ -113,7 +113,7 @@ const ListLayout::Role &ListLayout::getRoleOrCreate(QV4::String *key, Role::Data
if (node) {
const Role &r = *node->value;
if (type != r.type)
- qmlWarning(0) << QStringLiteral("Can't assign to existing role '%1' of different type [%2 -> %3]").arg(r.name).arg(roleTypeName(type)).arg(roleTypeName(r.type));
+ qmlWarning(nullptr) << QStringLiteral("Can't assign to existing role '%1' of different type [%2 -> %3]").arg(r.name).arg(roleTypeName(type)).arg(roleTypeName(r.type));
return r;
}
@@ -134,7 +134,7 @@ const ListLayout::Role &ListLayout::createRole(const QString &key, ListLayout::R
if (type == Role::List) {
r->subLayout = new ListLayout;
} else {
- r->subLayout = 0;
+ r->subLayout = nullptr;
}
int dataSize = dataSizes[type];
@@ -203,7 +203,7 @@ ListLayout::Role::Role(const Role *other)
if (other->subLayout)
subLayout = new ListLayout(other->subLayout);
else
- subLayout = 0;
+ subLayout = nullptr;
}
ListLayout::Role::~Role()
@@ -236,8 +236,8 @@ const ListLayout::Role *ListLayout::getRoleOrCreate(const QString &key, const QV
}
if (type == Role::Invalid) {
- qmlWarning(0) << "Can't create role for unsupported data type";
- return 0;
+ qmlWarning(nullptr) << "Can't create role for unsupported data type";
+ return nullptr;
}
return &getRoleOrCreate(key, type);
@@ -245,7 +245,7 @@ const ListLayout::Role *ListLayout::getRoleOrCreate(const QString &key, const QV
const ListLayout::Role *ListLayout::getExistingRole(const QString &key) const
{
- Role *r = 0;
+ Role *r = nullptr;
QStringHash<Role *>::Node *node = roleHash.findNode(key);
if (node)
r = node->value;
@@ -254,7 +254,7 @@ const ListLayout::Role *ListLayout::getExistingRole(const QString &key) const
const ListLayout::Role *ListLayout::getExistingRole(QV4::String *key) const
{
- Role *r = 0;
+ Role *r = nullptr;
QStringHash<Role *>::Node *node = roleHash.findNode(key);
if (node)
r = node->value;
@@ -264,30 +264,35 @@ const ListLayout::Role *ListLayout::getExistingRole(QV4::String *key) const
QObject *ListModel::getOrCreateModelObject(QQmlListModel *model, int elementIndex)
{
ListElement *e = elements[elementIndex];
- if (e->m_objectCache == 0) {
- e->m_objectCache = new QObject;
+ if (e->m_objectCache == nullptr) {
+ void *memory = operator new(sizeof(QObject) + sizeof(QQmlData));
+ void *ddataMemory = ((char *)memory) + sizeof(QObject);
+ e->m_objectCache = new (memory) QObject;
+ QQmlData *ddata = new (ddataMemory) QQmlData;
+ ddata->ownMemory = false;
+ QObjectPrivate::get(e->m_objectCache)->declarativeData = ddata;
(void)new ModelNodeMetaObject(e->m_objectCache, model, elementIndex);
}
return e->m_objectCache;
}
-void ListModel::sync(ListModel *src, ListModel *target, QHash<int, ListModel *> *targetModelHash)
+bool ListModel::sync(ListModel *src, ListModel *target)
{
// Sanity check
- target->m_uid = src->m_uid;
- if (targetModelHash)
- targetModelHash->insert(target->m_uid, target);
+
+ bool hasChanges = false;
// Build hash of elements <-> uid for each of the lists
QHash<int, ElementSync> elementHash;
- for (int i=0 ; i < target->elements.count() ; ++i) {
+ for (int i = 0; i < target->elements.count(); ++i) {
ListElement *e = target->elements.at(i);
int uid = e->getUid();
ElementSync sync;
sync.target = e;
+ sync.targetIndex = i;
elementHash.insert(uid, sync);
}
- for (int i=0 ; i < src->elements.count() ; ++i) {
+ for (int i = 0; i < src->elements.count(); ++i) {
ListElement *e = src->elements.at(i);
int uid = e->getUid();
@@ -295,24 +300,39 @@ void ListModel::sync(ListModel *src, ListModel *target, QHash<int, ListModel *>
if (it == elementHash.end()) {
ElementSync sync;
sync.src = e;
+ sync.srcIndex = i;
elementHash.insert(uid, sync);
} else {
ElementSync &sync = it.value();
sync.src = e;
+ sync.srcIndex = i;
}
}
+ QQmlListModel *targetModel = target->m_modelCache;
+
// Get list of elements that are in the target but no longer in the source. These get deleted first.
- QHash<int, ElementSync>::iterator it = elementHash.begin();
- QHash<int, ElementSync>::iterator end = elementHash.end();
- while (it != end) {
- const ElementSync &s = it.value();
- if (s.src == 0) {
+ int rowsRemoved = 0;
+ for (int i = 0 ; i < target->elements.count() ; ++i) {
+ ListElement *element = target->elements.at(i);
+ ElementSync &s = elementHash.find(element->getUid()).value();
+ Q_ASSERT(s.targetIndex >= 0);
+ // need to update the targetIndex, to keep it correct after removals
+ s.targetIndex -= rowsRemoved;
+ if (s.src == nullptr) {
+ Q_ASSERT(s.targetIndex == i);
+ hasChanges = true;
+ if (targetModel)
+ targetModel->beginRemoveRows(QModelIndex(), i, i);
s.target->destroy(target->m_layout);
target->elements.removeOne(s.target);
delete s.target;
+ if (targetModel)
+ targetModel->endRemoveRows();
+ ++rowsRemoved;
+ --i;
+ continue;
}
- ++it;
}
// Sync the layouts
@@ -320,15 +340,15 @@ void ListModel::sync(ListModel *src, ListModel *target, QHash<int, ListModel *>
// Clear the target list, and append in correct order from the source
target->elements.clear();
- for (int i=0 ; i < src->elements.count() ; ++i) {
+ for (int i = 0; i < src->elements.count(); ++i) {
ListElement *srcElement = src->elements.at(i);
- it = elementHash.find(srcElement->getUid());
- const ElementSync &s = it.value();
+ ElementSync &s = elementHash.find(srcElement->getUid()).value();
+ Q_ASSERT(s.srcIndex >= 0);
ListElement *targetElement = s.target;
- if (targetElement == 0) {
+ if (targetElement == nullptr) {
targetElement = new ListElement(srcElement->getUid());
}
- ListElement::sync(srcElement, src->m_layout, targetElement, target->m_layout, targetModelHash);
+ s.changedRoles = ListElement::sync(srcElement, src->m_layout, targetElement, target->m_layout);
target->elements.append(targetElement);
}
@@ -340,13 +360,43 @@ void ListModel::sync(ListModel *src, ListModel *target, QHash<int, ListModel *>
if (ModelNodeMetaObject *mo = e->objectCache())
mo->updateValues();
}
+
+ // now emit the change notifications required. This can be safely done, as we're only emitting changes, moves and inserts,
+ // so the model indices can't be out of bounds
+ //
+ // to ensure things are kept in the correct order, emit inserts and moves first. This shouls ensure all persistent
+ // model indices are updated correctly
+ int rowsInserted = 0;
+ for (int i = 0 ; i < target->elements.count() ; ++i) {
+ ListElement *element = target->elements.at(i);
+ ElementSync &s = elementHash.find(element->getUid()).value();
+ Q_ASSERT(s.srcIndex >= 0);
+ s.srcIndex += rowsInserted;
+ if (s.srcIndex != s.targetIndex) {
+ if (targetModel) {
+ if (s.targetIndex == -1) {
+ targetModel->beginInsertRows(QModelIndex(), i, i);
+ targetModel->endInsertRows();
+ } else {
+ targetModel->beginMoveRows(QModelIndex(), i, i, QModelIndex(), s.srcIndex);
+ targetModel->endMoveRows();
+ }
+ }
+ hasChanges = true;
+ ++rowsInserted;
+ }
+ if (s.targetIndex != -1 && !s.changedRoles.isEmpty()) {
+ QModelIndex idx = targetModel->createIndex(i, 0);
+ if (targetModel)
+ targetModel->dataChanged(idx, idx, s.changedRoles);
+ hasChanges = true;
+ }
+ }
+ return hasChanges;
}
-ListModel::ListModel(ListLayout *layout, QQmlListModel *modelCache, int uid) : m_layout(layout), m_modelCache(modelCache)
+ListModel::ListModel(ListLayout *layout, QQmlListModel *modelCache) : m_layout(layout), m_modelCache(modelCache)
{
- if (uid == -1)
- uid = uidCounter.fetchAndAddOrdered(1);
- m_uid = uid;
}
void ListModel::destroy()
@@ -354,11 +404,10 @@ void ListModel::destroy()
for (const auto &destroyer : remove(0, elements.count()))
destroyer();
- m_uid = -1;
- m_layout = 0;
+ m_layout = nullptr;
if (m_modelCache && m_modelCache->m_primary == false)
delete m_modelCache;
- m_modelCache = 0;
+ m_modelCache = nullptr;
}
int ListModel::appendElement()
@@ -459,7 +508,7 @@ void ListModel::set(int elementIndex, QV4::Object *object, QVector<int> *roles)
roleIndex = e->setDoubleProperty(r, propertyValue->asDouble());
} else if (QV4::ArrayObject *a = propertyValue->as<QV4::ArrayObject>()) {
const ListLayout::Role &r = m_layout->getRoleOrCreate(propertyName, ListLayout::Role::List);
- ListModel *subModel = new ListModel(r.subLayout, 0, -1);
+ ListModel *subModel = new ListModel(r.subLayout, nullptr);
int arrayLength = a->getLength();
for (int j=0 ; j < arrayLength ; ++j) {
@@ -540,7 +589,7 @@ void ListModel::set(int elementIndex, QV4::Object *object)
} else if (QV4::ArrayObject *a = propertyValue->as<QV4::ArrayObject>()) {
const ListLayout::Role &r = m_layout->getRoleOrCreate(propertyName, ListLayout::Role::List);
if (r.type == ListLayout::Role::List) {
- ListModel *subModel = new ListModel(r.subLayout, 0, -1);
+ ListModel *subModel = new ListModel(r.subLayout, nullptr);
int arrayLength = a->getLength();
for (int j=0 ; j < arrayLength ; ++j) {
@@ -649,7 +698,7 @@ inline char *ListElement::getPropertyMemory(const ListLayout::Role &role)
ListElement *e = this;
int blockIndex = 0;
while (blockIndex < role.blockIndex) {
- if (e->next == 0) {
+ if (e->next == nullptr) {
e->next = new ListElement;
e->next->uid = uid;
}
@@ -664,7 +713,7 @@ inline char *ListElement::getPropertyMemory(const ListLayout::Role &role)
ModelNodeMetaObject *ListElement::objectCache()
{
if (!m_objectCache)
- return 0;
+ return nullptr;
return ModelNodeMetaObject::get(m_objectCache);
}
@@ -672,7 +721,7 @@ QString *ListElement::getStringProperty(const ListLayout::Role &role)
{
char *mem = getPropertyMemory(role);
QString *s = reinterpret_cast<QString *>(mem);
- return s->data_ptr() ? s : 0;
+ return s->data_ptr() ? s : nullptr;
}
QObject *ListElement::getQObjectProperty(const ListLayout::Role &role)
@@ -684,7 +733,7 @@ QObject *ListElement::getQObjectProperty(const ListLayout::Role &role)
QVariantMap *ListElement::getVariantMapProperty(const ListLayout::Role &role)
{
- QVariantMap *map = 0;
+ QVariantMap *map = nullptr;
char *mem = getPropertyMemory(role);
if (isMemoryUsed<QVariantMap>(mem))
@@ -695,7 +744,7 @@ QVariantMap *ListElement::getVariantMapProperty(const ListLayout::Role &role)
QDateTime *ListElement::getDateTimeProperty(const ListLayout::Role &role)
{
- QDateTime *dt = 0;
+ QDateTime *dt = nullptr;
char *mem = getPropertyMemory(role);
if (isMemoryUsed<QDateTime>(mem))
@@ -706,7 +755,7 @@ QDateTime *ListElement::getDateTimeProperty(const ListLayout::Role &role)
QJSValue *ListElement::getFunctionProperty(const ListLayout::Role &role)
{
- QJSValue *f = 0;
+ QJSValue *f = nullptr;
char *mem = getPropertyMemory(role);
if (isMemoryUsed<QJSValue>(mem))
@@ -727,7 +776,7 @@ QPointer<QObject> *ListElement::getGuardProperty(const ListLayout::Role &role)
}
}
- QPointer<QObject> *o = 0;
+ QPointer<QObject> *o = nullptr;
if (existingGuard)
o = reinterpret_cast<QPointer<QObject> *>(mem);
@@ -758,7 +807,7 @@ QVariant ListElement::getProperty(const ListLayout::Role &role, const QQmlListMo
case ListLayout::Role::String:
{
QString *value = reinterpret_cast<QString *>(mem);
- if (value->data_ptr() != 0)
+ if (value->data_ptr() != nullptr)
data = *value;
}
break;
@@ -774,7 +823,7 @@ QVariant ListElement::getProperty(const ListLayout::Role &role, const QQmlListMo
ListModel *model = *value;
if (model) {
- if (model->m_modelCache == 0) {
+ if (model->m_modelCache == nullptr) {
model->m_modelCache = new QQmlListModel(owner, model, eng);
QQmlEngine::setContextForObject(model->m_modelCache, QQmlEngine::contextForObject(owner));
}
@@ -831,7 +880,7 @@ int ListElement::setStringProperty(const ListLayout::Role &role, const QString &
char *mem = getPropertyMemory(role);
QString *c = reinterpret_cast<QString *>(mem);
bool changed;
- if (c->data_ptr() == 0) {
+ if (c->data_ptr() == nullptr) {
new (mem) QString(s);
changed = true;
} else {
@@ -949,7 +998,11 @@ int ListElement::setVariantMapProperty(const ListLayout::Role &role, QVariantMap
char *mem = getPropertyMemory(role);
if (isMemoryUsed<QVariantMap>(mem)) {
QVariantMap *map = reinterpret_cast<QVariantMap *>(mem);
+ if (m && map->isSharedWith(*m))
+ return roleIndex;
map->~QMap();
+ } else if (!m) {
+ return roleIndex;
}
if (m)
new (mem) QVariantMap(*m);
@@ -1061,16 +1114,16 @@ void ListElement::clearProperty(const ListLayout::Role &role)
setBoolProperty(role, false);
break;
case ListLayout::Role::List:
- setListProperty(role, 0);
+ setListProperty(role, nullptr);
break;
case ListLayout::Role::QObject:
- setQObjectProperty(role, 0);
+ setQObjectProperty(role, nullptr);
break;
case ListLayout::Role::DateTime:
setDateTimeProperty(role, QDateTime());
break;
case ListLayout::Role::VariantMap:
- setVariantMapProperty(role, (QVariantMap *)0);
+ setVariantMapProperty(role, (QVariantMap *)nullptr);
break;
case ListLayout::Role::Function:
setFunctionProperty(role, QJSValue());
@@ -1082,17 +1135,17 @@ void ListElement::clearProperty(const ListLayout::Role &role)
ListElement::ListElement()
{
- m_objectCache = 0;
+ m_objectCache = nullptr;
uid = uidCounter.fetchAndAddOrdered(1);
- next = 0;
+ next = nullptr;
memset(data, 0, sizeof(data));
}
ListElement::ListElement(int existingUid)
{
- m_objectCache = 0;
+ m_objectCache = nullptr;
uid = existingUid;
- next = 0;
+ next = nullptr;
memset(data, 0, sizeof(data));
}
@@ -1101,12 +1154,14 @@ ListElement::~ListElement()
delete next;
}
-void ListElement::sync(ListElement *src, ListLayout *srcLayout, ListElement *target, ListLayout *targetLayout, QHash<int, ListModel *> *targetModelHash)
+QVector<int> ListElement::sync(ListElement *src, ListLayout *srcLayout, ListElement *target, ListLayout *targetLayout)
{
+ QVector<int> changedRoles;
for (int i=0 ; i < srcLayout->roleCount() ; ++i) {
const ListLayout::Role &srcRole = srcLayout->getExistingRole(i);
const ListLayout::Role &targetRole = targetLayout->getExistingRole(i);
+ int roleIndex = -1;
switch (srcRole.type) {
case ListLayout::Role::List:
{
@@ -1114,18 +1169,19 @@ void ListElement::sync(ListElement *src, ListLayout *srcLayout, ListElement *tar
ListModel *targetSubModel = target->getListProperty(targetRole);
if (srcSubModel) {
- if (targetSubModel == 0) {
- targetSubModel = new ListModel(targetRole.subLayout, 0, srcSubModel->getUid());
+ if (targetSubModel == nullptr) {
+ targetSubModel = new ListModel(targetRole.subLayout, nullptr);
target->setListPropertyFast(targetRole, targetSubModel);
}
- ListModel::sync(srcSubModel, targetSubModel, targetModelHash);
+ if (ListModel::sync(srcSubModel, targetSubModel))
+ roleIndex = targetRole.index;
}
}
break;
case ListLayout::Role::QObject:
{
QObject *object = src->getQObjectProperty(srcRole);
- target->setQObjectProperty(targetRole, object);
+ roleIndex = target->setQObjectProperty(targetRole, object);
}
break;
case ListLayout::Role::String:
@@ -1134,21 +1190,24 @@ void ListElement::sync(ListElement *src, ListLayout *srcLayout, ListElement *tar
case ListLayout::Role::DateTime:
case ListLayout::Role::Function:
{
- QVariant v = src->getProperty(srcRole, 0, 0);
- target->setVariantProperty(targetRole, v);
+ QVariant v = src->getProperty(srcRole, nullptr, nullptr);
+ roleIndex = target->setVariantProperty(targetRole, v);
}
break;
case ListLayout::Role::VariantMap:
{
QVariantMap *map = src->getVariantMapProperty(srcRole);
- target->setVariantMapProperty(targetRole, map);
+ roleIndex = target->setVariantMapProperty(targetRole, map);
}
break;
default:
break;
}
+ if (roleIndex >= 0)
+ changedRoles << roleIndex;
}
+ return changedRoles;
}
void ListElement::destroy(ListLayout *layout)
@@ -1212,7 +1271,7 @@ void ListElement::destroy(ListLayout *layout)
}
if (next)
- next->destroy(0);
+ next->destroy(nullptr);
uid = -1;
}
@@ -1270,7 +1329,7 @@ int ListElement::setJsProperty(const ListLayout::Role &role, const QV4::Value &d
QV4::Scope scope(a->engine());
QV4::ScopedObject o(scope);
- ListModel *subModel = new ListModel(role.subLayout, 0, -1);
+ ListModel *subModel = new ListModel(role.subLayout, nullptr);
int arrayLength = a->getLength();
for (int j=0 ; j < arrayLength ; ++j) {
o = a->getIndexed(j);
@@ -1278,7 +1337,7 @@ int ListElement::setJsProperty(const ListLayout::Role &role, const QV4::Value &d
}
roleIndex = setListProperty(role, subModel);
} else {
- qmlWarning(0) << QStringLiteral("Can't assign to existing role '%1' of different type [%2 -> %3]").arg(role.name).arg(roleTypeName(role.type)).arg(roleTypeName(ListLayout::Role::List));
+ qmlWarning(nullptr) << QStringLiteral("Can't assign to existing role '%1' of different type [%2 -> %3]").arg(role.name).arg(roleTypeName(role.type)).arg(roleTypeName(ListLayout::Role::List));
}
} else if (d.isBoolean()) {
roleIndex = setBoolProperty(role, d.booleanValue());
@@ -1420,7 +1479,7 @@ bool ModelObject::put(Managed *m, String *name, const Value &value)
ModelObject *that = static_cast<ModelObject*>(m);
ExecutionEngine *eng = that->engine();
- const int elementIndex = that->d()->m_elementIndex;
+ const int elementIndex = that->d()->elementIndex();
const QString propName = name->toQString();
int roleIndex = that->d()->m_model->m_listModel->setExistingProperty(elementIndex, propName, value, eng);
if (roleIndex != -1)
@@ -1448,7 +1507,7 @@ ReturnedValue ModelObject::get(const Managed *m, String *name, bool *hasProperty
QQmlPropertyCapture::OnlyOnce, false);
}
- const int elementIndex = that->d()->m_elementIndex;
+ const int elementIndex = that->d()->elementIndex();
QVariant value = that->d()->m_model->data(elementIndex, role->index);
return that->engine()->fromVariant(value);
}
@@ -1457,7 +1516,7 @@ void ModelObject::advanceIterator(Managed *m, ObjectIterator *it, Value *name, u
{
ModelObject *that = static_cast<ModelObject*>(m);
ExecutionEngine *v4 = that->engine();
- name->setM(0);
+ name->setM(nullptr);
*index = UINT_MAX;
if (it->arrayIndex < uint(that->d()->m_model->m_listModel->roleCount())) {
Scope scope(that->engine());
@@ -1466,7 +1525,7 @@ void ModelObject::advanceIterator(Managed *m, ObjectIterator *it, Value *name, u
ScopedString roleName(scope, v4->newString(role.name));
name->setM(roleName->d());
*attributes = QV4::Attr_Data;
- QVariant value = that->d()->m_model->data(that->d()->m_elementIndex, role.index);
+ QVariant value = that->d()->m_model->data(that->d()->elementIndex(), role.index);
p->value = v4->fromVariant(value);
return;
}
@@ -1493,20 +1552,22 @@ DynamicRoleModelNode *DynamicRoleModelNode::create(const QVariantMap &obj, QQmlL
return object;
}
-void DynamicRoleModelNode::sync(DynamicRoleModelNode *src, DynamicRoleModelNode *target, QHash<int, QQmlListModel *> *targetModelHash)
+QVector<int> DynamicRoleModelNode::sync(DynamicRoleModelNode *src, DynamicRoleModelNode *target)
{
- for (int i=0 ; i < src->m_meta->count() ; ++i) {
+ QVector<int> changedRoles;
+ for (int i = 0; i < src->m_meta->count(); ++i) {
const QByteArray &name = src->m_meta->name(i);
QVariant value = src->m_meta->value(i);
QQmlListModel *srcModel = qobject_cast<QQmlListModel *>(value.value<QObject *>());
QQmlListModel *targetModel = qobject_cast<QQmlListModel *>(target->m_meta->value(i).value<QObject *>());
+ bool modelHasChanges = false;
if (srcModel) {
- if (targetModel == 0)
+ if (targetModel == nullptr)
targetModel = QQmlListModel::createWithOwner(target->m_owner);
- QQmlListModel::sync(srcModel, targetModel, targetModelHash);
+ modelHasChanges = QQmlListModel::sync(srcModel, targetModel);
QObject *targetModelObject = targetModel;
value = QVariant::fromValue(targetModelObject);
@@ -1514,8 +1575,10 @@ void DynamicRoleModelNode::sync(DynamicRoleModelNode *src, DynamicRoleModelNode
delete targetModel;
}
- target->setValue(name, value);
+ if (target->setValue(name, value) || modelHasChanges)
+ changedRoles << target->m_owner->m_roles.indexOf(QString::fromUtf8(name));
}
+ return changedRoles;
}
void DynamicRoleModelNode::updateValues(const QVariantMap &object, QVector<int> &roles)
@@ -1724,14 +1787,13 @@ QQmlListModel::QQmlListModel(QObject *parent)
{
m_mainThread = true;
m_primary = true;
- m_agent = 0;
- m_uid = uidCounter.fetchAndAddOrdered(1);
+ m_agent = nullptr;
m_dynamicRoles = false;
m_layout = new ListLayout;
- m_listModel = new ListModel(m_layout, this, -1);
+ m_listModel = new ListModel(m_layout, this);
- m_engine = 0;
+ m_engine = nullptr;
}
QQmlListModel::QQmlListModel(const QQmlListModel *owner, ListModel *data, QV4::ExecutionEngine *engine, QObject *parent)
@@ -1743,7 +1805,7 @@ QQmlListModel::QQmlListModel(const QQmlListModel *owner, ListModel *data, QV4::E
Q_ASSERT(owner->m_dynamicRoles == false);
m_dynamicRoles = false;
- m_layout = 0;
+ m_layout = nullptr;
m_listModel = data;
m_engine = engine;
@@ -1758,14 +1820,14 @@ QQmlListModel::QQmlListModel(QQmlListModel *orig, QQmlListModelWorkerAgent *agen
m_dynamicRoles = orig->m_dynamicRoles;
m_layout = new ListLayout(orig->m_layout);
- m_listModel = new ListModel(m_layout, this, orig->m_listModel->getUid());
+ m_listModel = new ListModel(m_layout, this);
if (m_dynamicRoles)
- sync(orig, this, 0);
+ sync(orig, this);
else
- ListModel::sync(orig->m_listModel, m_listModel, 0);
+ ListModel::sync(orig->m_listModel, m_listModel);
- m_engine = 0;
+ m_engine = nullptr;
}
QQmlListModel::~QQmlListModel()
@@ -1782,10 +1844,10 @@ QQmlListModel::~QQmlListModel()
}
}
- m_listModel = 0;
+ m_listModel = nullptr;
delete m_layout;
- m_layout = 0;
+ m_layout = nullptr;
}
QQmlListModel *QQmlListModel::createWithOwner(QQmlListModel *newOwner)
@@ -1807,32 +1869,32 @@ QQmlListModel *QQmlListModel::createWithOwner(QQmlListModel *newOwner)
QV4::ExecutionEngine *QQmlListModel::engine() const
{
- if (m_engine == 0) {
- m_engine = QQmlEnginePrivate::get(qmlEngine(this))->v4engine();
+ if (m_engine == nullptr) {
+ m_engine = qmlEngine(this)->handle();
}
return m_engine;
}
-void QQmlListModel::sync(QQmlListModel *src, QQmlListModel *target, QHash<int, QQmlListModel *> *targetModelHash)
+bool QQmlListModel::sync(QQmlListModel *src, QQmlListModel *target)
{
Q_ASSERT(src->m_dynamicRoles && target->m_dynamicRoles);
- target->m_uid = src->m_uid;
- if (targetModelHash)
- targetModelHash->insert(target->m_uid, target);
+ bool hasChanges = false;
+
target->m_roles = src->m_roles;
// Build hash of elements <-> uid for each of the lists
QHash<int, ElementSync> elementHash;
- for (int i=0 ; i < target->m_modelObjects.count() ; ++i) {
+ for (int i = 0 ; i < target->m_modelObjects.count(); ++i) {
DynamicRoleModelNode *e = target->m_modelObjects.at(i);
int uid = e->getUid();
ElementSync sync;
sync.target = e;
+ sync.targetIndex = i;
elementHash.insert(uid, sync);
}
- for (int i=0 ; i < src->m_modelObjects.count() ; ++i) {
+ for (int i = 0 ; i < src->m_modelObjects.count(); ++i) {
DynamicRoleModelNode *e = src->m_modelObjects.at(i);
int uid = e->getUid();
@@ -1840,118 +1902,102 @@ void QQmlListModel::sync(QQmlListModel *src, QQmlListModel *target, QHash<int, Q
if (it == elementHash.end()) {
ElementSync sync;
sync.src = e;
+ sync.srcIndex = i;
elementHash.insert(uid, sync);
} else {
ElementSync &sync = it.value();
sync.src = e;
+ sync.srcIndex = i;
}
}
// Get list of elements that are in the target but no longer in the source. These get deleted first.
- QHash<int, ElementSync>::iterator it = elementHash.begin();
- QHash<int, ElementSync>::iterator end = elementHash.end();
- while (it != end) {
- const ElementSync &s = it.value();
- if (s.src == 0) {
- int targetIndex = target->m_modelObjects.indexOf(s.target);
- target->m_modelObjects.remove(targetIndex, 1);
+ int rowsRemoved = 0;
+ for (int i = 0 ; i < target->m_modelObjects.count() ; ++i) {
+ DynamicRoleModelNode *element = target->m_modelObjects.at(i);
+ ElementSync &s = elementHash.find(element->getUid()).value();
+ Q_ASSERT(s.targetIndex >= 0);
+ // need to update the targetIndex, to keep it correct after removals
+ s.targetIndex -= rowsRemoved;
+ if (s.src == nullptr) {
+ Q_ASSERT(s.targetIndex == i);
+ hasChanges = true;
+ target->beginRemoveRows(QModelIndex(), i, i);
+ target->m_modelObjects.remove(i, 1);
+ target->endRemoveRows();
delete s.target;
+ ++rowsRemoved;
+ --i;
+ continue;
}
- ++it;
}
// Clear the target list, and append in correct order from the source
target->m_modelObjects.clear();
- for (int i=0 ; i < src->m_modelObjects.count() ; ++i) {
- DynamicRoleModelNode *srcElement = src->m_modelObjects.at(i);
- it = elementHash.find(srcElement->getUid());
- const ElementSync &s = it.value();
+ for (int i = 0 ; i < src->m_modelObjects.count() ; ++i) {
+ DynamicRoleModelNode *element = src->m_modelObjects.at(i);
+ ElementSync &s = elementHash.find(element->getUid()).value();
+ Q_ASSERT(s.srcIndex >= 0);
DynamicRoleModelNode *targetElement = s.target;
- if (targetElement == 0) {
- targetElement = new DynamicRoleModelNode(target, srcElement->getUid());
+ if (targetElement == nullptr) {
+ targetElement = new DynamicRoleModelNode(target, element->getUid());
}
- DynamicRoleModelNode::sync(srcElement, targetElement, targetModelHash);
+ s.changedRoles = DynamicRoleModelNode::sync(element, targetElement);
target->m_modelObjects.append(targetElement);
}
-}
-void QQmlListModel::emitItemsChanged(int index, int count, const QVector<int> &roles)
-{
- if (count <= 0)
- return;
-
- if (m_mainThread) {
- emit dataChanged(createIndex(index, 0), createIndex(index + count - 1, 0), roles);;
- } else {
- int uid = m_dynamicRoles ? getUid() : m_listModel->getUid();
- m_agent->data.changedChange(uid, index, count, roles);
+ // now emit the change notifications required. This can be safely done, as we're only emitting changes, moves and inserts,
+ // so the model indices can't be out of bounds
+ //
+ // to ensure things are kept in the correct order, emit inserts and moves first. This shouls ensure all persistent
+ // model indices are updated correctly
+ int rowsInserted = 0;
+ for (int i = 0 ; i < target->m_modelObjects.count() ; ++i) {
+ DynamicRoleModelNode *element = target->m_modelObjects.at(i);
+ ElementSync &s = elementHash.find(element->getUid()).value();
+ Q_ASSERT(s.srcIndex >= 0);
+ s.srcIndex += rowsInserted;
+ if (s.srcIndex != s.targetIndex) {
+ if (s.targetIndex == -1) {
+ target->beginInsertRows(QModelIndex(), i, i);
+ target->endInsertRows();
+ } else {
+ target->beginMoveRows(QModelIndex(), i, i, QModelIndex(), s.srcIndex);
+ target->endMoveRows();
+ }
+ hasChanges = true;
+ ++rowsInserted;
+ }
+ if (s.targetIndex != -1 && !s.changedRoles.isEmpty()) {
+ QModelIndex idx = target->createIndex(i, 0);
+ emit target->dataChanged(idx, idx, s.changedRoles);
+ hasChanges = true;
+ }
}
+ return hasChanges;
}
-void QQmlListModel::emitItemsAboutToBeRemoved(int index, int count)
-{
- if (count <= 0 || !m_mainThread)
- return;
-
- beginRemoveRows(QModelIndex(), index, index + count - 1);
-}
-
-void QQmlListModel::emitItemsRemoved(int index, int count)
+void QQmlListModel::emitItemsChanged(int index, int count, const QVector<int> &roles)
{
if (count <= 0)
return;
- if (m_mainThread) {
- endRemoveRows();
- emit countChanged();
- } else {
- int uid = m_dynamicRoles ? getUid() : m_listModel->getUid();
- if (index == 0 && count == this->count())
- m_agent->data.clearChange(uid);
- m_agent->data.removeChange(uid, index, count);
- }
+ if (m_mainThread)
+ emit dataChanged(createIndex(index, 0), createIndex(index + count - 1, 0), roles);;
}
void QQmlListModel::emitItemsAboutToBeInserted(int index, int count)
{
- if (count <= 0 || !m_mainThread)
- return;
-
- beginInsertRows(QModelIndex(), index, index + count - 1);
+ Q_ASSERT(index >= 0 && count >= 0);
+ if (m_mainThread)
+ beginInsertRows(QModelIndex(), index, index + count - 1);
}
-void QQmlListModel::emitItemsInserted(int index, int count)
+void QQmlListModel::emitItemsInserted()
{
- if (count <= 0)
- return;
-
if (m_mainThread) {
endInsertRows();
emit countChanged();
- } else {
- int uid = m_dynamicRoles ? getUid() : m_listModel->getUid();
- m_agent->data.insertChange(uid, index, count);
- }
-}
-
-void QQmlListModel::emitItemsAboutToBeMoved(int from, int to, int n)
-{
- if (n <= 0 || !m_mainThread)
- return;
-
- beginMoveRows(QModelIndex(), from, from + n - 1, QModelIndex(), to > from ? to + n : to);
-}
-
-void QQmlListModel::emitItemsMoved(int from, int to, int n)
-{
- if (n <= 0)
- return;
-
- if (m_mainThread) {
- endMoveRows();
- } else {
- int uid = m_dynamicRoles ? getUid() : m_listModel->getUid();
- m_agent->data.moveChange(uid, from, n, to);
}
}
@@ -2065,7 +2111,7 @@ QHash<int, QByteArray> QQmlListModel::roleNames() const
*/
void QQmlListModel::setDynamicRoles(bool enableDynamicRoles)
{
- if (m_mainThread && m_agent == 0) {
+ if (m_mainThread && m_agent == nullptr) {
if (enableDynamicRoles) {
if (m_layout->roleCount())
qmlWarning(this) << tr("unable to enable dynamic roles as this model is not empty");
@@ -2133,7 +2179,13 @@ void QQmlListModel::remove(QQmlV4Function *args)
void QQmlListModel::removeElements(int index, int removeCount)
{
- emitItemsAboutToBeRemoved(index, removeCount);
+ Q_ASSERT(index >= 0 && removeCount >= 0);
+
+ if (!removeCount)
+ return;
+
+ if (m_mainThread)
+ beginRemoveRows(QModelIndex(), index, index + removeCount - 1);
QVector<std::function<void()>> toDestroy;
if (m_dynamicRoles) {
@@ -2148,7 +2200,10 @@ void QQmlListModel::removeElements(int index, int removeCount)
toDestroy = m_listModel->remove(index, removeCount);
}
- emitItemsRemoved(index, removeCount);
+ if (m_mainThread) {
+ endRemoveRows();
+ emit countChanged();
+ }
for (const auto &destroyer : toDestroy)
destroyer();
}
@@ -2197,7 +2252,7 @@ void QQmlListModel::insert(QQmlV4Function *args)
m_listModel->insert(index+i, argObject);
}
}
- emitItemsInserted(index, objectArrayLength);
+ emitItemsInserted();
} else if (argObject) {
emitItemsAboutToBeInserted(index, 1);
@@ -2207,7 +2262,7 @@ void QQmlListModel::insert(QQmlV4Function *args)
m_listModel->insert(index, argObject);
}
- emitItemsInserted(index, 1);
+ emitItemsInserted();
} else {
qmlWarning(this) << tr("insert: value is not an object");
}
@@ -2232,14 +2287,15 @@ void QQmlListModel::insert(QQmlV4Function *args)
*/
void QQmlListModel::move(int from, int to, int n)
{
- if (n==0 || from==to)
+ if (n == 0 || from == to)
return;
if (!canMove(from, to, n)) {
qmlWarning(this) << tr("move: out of range");
return;
}
- emitItemsAboutToBeMoved(from, to, n);
+ if (m_mainThread)
+ beginMoveRows(QModelIndex(), from, from + n - 1, QModelIndex(), to > from ? to + n : to);
if (m_dynamicRoles) {
@@ -2268,7 +2324,8 @@ void QQmlListModel::move(int from, int to, int n)
m_listModel->move(from, to, n);
}
- emitItemsMoved(from, to, n);
+ if (m_mainThread)
+ endMoveRows();
}
/*!
@@ -2308,7 +2365,7 @@ void QQmlListModel::append(QQmlV4Function *args)
}
}
- emitItemsInserted(index, objectArrayLength);
+ emitItemsInserted();
} else if (argObject) {
int index;
@@ -2322,7 +2379,7 @@ void QQmlListModel::append(QQmlV4Function *args)
m_listModel->append(argObject);
}
- emitItemsInserted(index, 1);
+ emitItemsInserted();
} else {
qmlWarning(this) << tr("append: value is not an object");
}
@@ -2374,10 +2431,14 @@ QQmlV4Handle QQmlListModel::get(int index) const
result = QV4::QObjectWrapper::wrap(scope.engine, object);
} else {
QObject *object = m_listModel->getOrCreateModelObject(const_cast<QQmlListModel *>(this), index);
- result = scope.engine->memoryManager->allocObject<QV4::ModelObject>(object, const_cast<QQmlListModel *>(this), index);
- // Keep track of the QObjectWrapper in persistent value storage
- QV4::Value *val = scope.engine->memoryManager->m_weakValues->allocate();
- *val = result;
+ QQmlData *ddata = QQmlData::get(object);
+ if (ddata->jsWrapper.isNullOrUndefined()) {
+ result = scope.engine->memoryManager->allocObject<QV4::ModelObject>(object, const_cast<QQmlListModel *>(this));
+ // Keep track of the QObjectWrapper in persistent value storage
+ ddata->jsWrapper.set(scope.engine, result);
+ } else {
+ result = ddata->jsWrapper.value();
+ }
}
}
@@ -2424,7 +2485,7 @@ void QQmlListModel::set(int index, const QQmlV4Handle &handle)
m_listModel->insert(index, object);
}
- emitItemsInserted(index, 1);
+ emitItemsInserted();
} else {
QVector<int> roles;
@@ -2544,15 +2605,15 @@ bool QQmlListModelParser::applyProperty(QV4::CompiledData::CompilationUnit *comp
const quint32 targetObjectIndex = binding->value.objectIndex;
const QV4::CompiledData::Object *target = qmlUnit->objectAt(targetObjectIndex);
- ListModel *subModel = 0;
+ ListModel *subModel = nullptr;
if (outterElementIndex == -1) {
subModel = model;
} else {
const ListLayout::Role &role = model->getOrCreateListRole(elementName);
if (role.type == ListLayout::Role::List) {
subModel = model->getListProperty(outterElementIndex, role);
- if (subModel == 0) {
- subModel = new ListModel(role.subLayout, 0, -1);
+ if (subModel == nullptr) {
+ subModel = new ListModel(role.subLayout, nullptr);
QVariant vModel = QVariant::fromValue(subModel);
model->setOrCreateProperty(outterElementIndex, elementName, vModel);
}
@@ -2579,7 +2640,7 @@ bool QQmlListModelParser::applyProperty(QV4::CompiledData::CompilationUnit *comp
QString scriptStr = binding->valueAsScriptString(qmlUnit);
if (definesEmptyList(scriptStr)) {
const ListLayout::Role &role = model->getOrCreateListRole(elementName);
- ListModel *emptyModel = new ListModel(role.subLayout, 0, -1);
+ ListModel *emptyModel = new ListModel(role.subLayout, nullptr);
value = QVariant::fromValue(emptyModel);
} else if (binding->isFunctionExpression()) {
QQmlBinding::Identifier id = binding->value.compiledScriptIndex;
@@ -2630,7 +2691,7 @@ void QQmlListModelParser::applyBindings(QObject *obj, QV4::CompiledData::Compila
{
QQmlListModel *rv = static_cast<QQmlListModel *>(obj);
- rv->m_engine = QV8Engine::getV4(qmlEngine(rv));
+ rv->m_engine = qmlEngine(rv)->handle();
const QV4::CompiledData::Unit *qmlUnit = compilationUnit->data;
diff --git a/src/qml/types/qqmllistmodel_p.h b/src/qml/types/qqmllistmodel_p.h
index 499a113504..0c0859dc80 100644
--- a/src/qml/types/qqmllistmodel_p.h
+++ b/src/qml/types/qqmllistmodel_p.h
@@ -82,7 +82,7 @@ class Q_QML_PRIVATE_EXPORT QQmlListModel : public QAbstractListModel
Q_PROPERTY(bool dynamicRoles READ dynamicRoles WRITE setDynamicRoles)
public:
- QQmlListModel(QObject *parent=0);
+ QQmlListModel(QObject *parent=nullptr);
~QQmlListModel();
QModelIndex index(int row, int column, const QModelIndex &parent) const override;
@@ -125,7 +125,7 @@ private:
// Constructs a flat list model for a worker agent
QQmlListModel(QQmlListModel *orig, QQmlListModelWorkerAgent *agent);
- QQmlListModel(const QQmlListModel *owner, ListModel *data, QV4::ExecutionEngine *engine, QObject *parent=0);
+ QQmlListModel(const QQmlListModel *owner, ListModel *data, QV4::ExecutionEngine *engine, QObject *parent=nullptr);
QV4::ExecutionEngine *engine() const;
@@ -143,28 +143,22 @@ private:
QVector<class DynamicRoleModelNode *> m_modelObjects;
QVector<QString> m_roles;
- int m_uid;
struct ElementSync
{
- ElementSync() : src(0), target(0) {}
-
- DynamicRoleModelNode *src;
- DynamicRoleModelNode *target;
+ DynamicRoleModelNode *src = nullptr;
+ DynamicRoleModelNode *target = nullptr;
+ int srcIndex = -1;
+ int targetIndex = -1;
+ QVector<int> changedRoles;
};
- int getUid() const { return m_uid; }
-
- static void sync(QQmlListModel *src, QQmlListModel *target, QHash<int, QQmlListModel *> *targetModelHash);
+ static bool sync(QQmlListModel *src, QQmlListModel *target);
static QQmlListModel *createWithOwner(QQmlListModel *newOwner);
void emitItemsChanged(int index, int count, const QVector<int> &roles);
- void emitItemsAboutToBeRemoved(int index, int count);
- void emitItemsRemoved(int index, int count);
void emitItemsAboutToBeInserted(int index, int count);
- void emitItemsInserted(int index, int count);
- void emitItemsAboutToBeMoved(int from, int to, int n);
- void emitItemsMoved(int from, int to, int n);
+ void emitItemsInserted();
void removeElements(int index, int removeCount);
};
diff --git a/src/qml/types/qqmllistmodel_p_p.h b/src/qml/types/qqmllistmodel_p_p.h
index dea1ef2eb3..ad5e94c909 100644
--- a/src/qml/types/qqmllistmodel_p_p.h
+++ b/src/qml/types/qqmllistmodel_p_p.h
@@ -108,7 +108,7 @@ public:
return m_uid;
}
- static void sync(DynamicRoleModelNode *src, DynamicRoleModelNode *target, QHash<int, QQmlListModel *> *targetModelHash);
+ static QVector<int> sync(DynamicRoleModelNode *src, DynamicRoleModelNode *target);
private:
QQmlListModel *m_owner;
@@ -164,15 +164,17 @@ namespace QV4 {
namespace Heap {
struct ModelObject : public QObjectWrapper {
- void init(QObject *object, QQmlListModel *model, int elementIndex)
+ void init(QObject *object, QQmlListModel *model)
{
QObjectWrapper::init(object);
m_model = model;
- m_elementIndex = elementIndex;
+ QObjectPrivate *op = QObjectPrivate::get(object);
+ m_nodeModelMetaObject = static_cast<ModelNodeMetaObject *>(op->metaObject);
}
void destroy() { QObjectWrapper::destroy(); }
+ int elementIndex() const { return m_nodeModelMetaObject->m_elementIndex; }
QQmlListModel *m_model;
- int m_elementIndex;
+ ModelNodeMetaObject *m_nodeModelMetaObject;
};
}
@@ -261,7 +263,7 @@ public:
ListElement(int existingUid);
~ListElement();
- static void sync(ListElement *src, ListLayout *srcLayout, ListElement *target, ListLayout *targetLayout, QHash<int, ListModel *> *targetModelHash);
+ static QVector<int> sync(ListElement *src, ListLayout *srcLayout, ListElement *target, ListLayout *targetLayout);
enum
{
@@ -328,7 +330,7 @@ class ListModel
{
public:
- ListModel(ListLayout *layout, QQmlListModel *modelCache, int uid);
+ ListModel(ListLayout *layout, QQmlListModel *modelCache);
~ListModel() {}
void destroy();
@@ -377,25 +379,23 @@ public:
void move(int from, int to, int n);
- int getUid() const { return m_uid; }
-
- static void sync(ListModel *src, ListModel *target, QHash<int, ListModel *> *srcModelHash);
+ static bool sync(ListModel *src, ListModel *target);
QObject *getOrCreateModelObject(QQmlListModel *model, int elementIndex);
private:
QPODVector<ListElement *, 4> elements;
ListLayout *m_layout;
- int m_uid;
QQmlListModel *m_modelCache;
struct ElementSync
{
- ElementSync() : src(0), target(0) {}
-
- ListElement *src;
- ListElement *target;
+ ListElement *src = nullptr;
+ ListElement *target = nullptr;
+ int srcIndex = -1;
+ int targetIndex = -1;
+ QVector<int> changedRoles;
};
void newElement(int index);
diff --git a/src/qml/types/qqmllistmodelworkeragent.cpp b/src/qml/types/qqmllistmodelworkeragent.cpp
index 0a5adbf292..fe3eaa3198 100644
--- a/src/qml/types/qqmllistmodelworkeragent.cpp
+++ b/src/qml/types/qqmllistmodelworkeragent.cpp
@@ -50,39 +50,8 @@
QT_BEGIN_NAMESPACE
-
-void QQmlListModelWorkerAgent::Data::clearChange(int uid)
-{
- for (int i=0 ; i < changes.count() ; ++i) {
- if (changes[i].modelUid == uid) {
- changes.removeAt(i);
- --i;
- }
- }
-}
-
-void QQmlListModelWorkerAgent::Data::insertChange(int uid, int index, int count)
+QQmlListModelWorkerAgent::Sync::~Sync()
{
- Change c = { uid, Change::Inserted, index, count, 0, QVector<int>() };
- changes << c;
-}
-
-void QQmlListModelWorkerAgent::Data::removeChange(int uid, int index, int count)
-{
- Change c = { uid, Change::Removed, index, count, 0, QVector<int>() };
- changes << c;
-}
-
-void QQmlListModelWorkerAgent::Data::moveChange(int uid, int index, int count, int to)
-{
- Change c = { uid, Change::Moved, index, count, to, QVector<int>() };
- changes << c;
-}
-
-void QQmlListModelWorkerAgent::Data::changedChange(int uid, int index, int count, const QVector<int> &roles)
-{
- Change c = { uid, Change::Changed, index, count, 0, roles };
- changes << c;
}
QQmlListModelWorkerAgent::QQmlListModelWorkerAgent(QQmlListModel *model)
@@ -117,7 +86,7 @@ void QQmlListModelWorkerAgent::release()
void QQmlListModelWorkerAgent::modelDestroyed()
{
- m_orig = 0;
+ m_orig = nullptr;
}
int QQmlListModelWorkerAgent::count() const
@@ -167,8 +136,7 @@ void QQmlListModelWorkerAgent::move(int from, int to, int count)
void QQmlListModelWorkerAgent::sync()
{
- Sync *s = new Sync(data, m_copy);
- data.changes.clear();
+ Sync *s = new Sync(m_copy);
mutex.lock();
QCoreApplication::postEvent(this, s);
@@ -183,61 +151,14 @@ bool QQmlListModelWorkerAgent::event(QEvent *e)
QMutexLocker locker(&mutex);
if (m_orig) {
Sync *s = static_cast<Sync *>(e);
- const QList<Change> &changes = s->data.changes;
- cc = m_orig->count() != s->list->count();
-
- QHash<int, QQmlListModel *> targetModelDynamicHash;
- QHash<int, ListModel *> targetModelStaticHash;
+ cc = (m_orig->count() != s->list->count());
Q_ASSERT(m_orig->m_dynamicRoles == s->list->m_dynamicRoles);
if (m_orig->m_dynamicRoles)
- QQmlListModel::sync(s->list, m_orig, &targetModelDynamicHash);
+ QQmlListModel::sync(s->list, m_orig);
else
- ListModel::sync(s->list->m_listModel, m_orig->m_listModel, &targetModelStaticHash);
-
- for (int ii = 0; ii < changes.count(); ++ii) {
- const Change &change = changes.at(ii);
-
- QQmlListModel *model = 0;
- if (m_orig->m_dynamicRoles) {
- model = targetModelDynamicHash.value(change.modelUid);
- } else {
- ListModel *lm = targetModelStaticHash.value(change.modelUid);
- if (lm)
- model = lm->m_modelCache;
- }
-
- if (model) {
- switch (change.type) {
- case Change::Inserted:
- model->beginInsertRows(
- QModelIndex(), change.index, change.index + change.count - 1);
- model->endInsertRows();
- break;
- case Change::Removed:
- model->beginRemoveRows(
- QModelIndex(), change.index, change.index + change.count - 1);
- model->endRemoveRows();
- break;
- case Change::Moved:
- model->beginMoveRows(
- QModelIndex(),
- change.index,
- change.index + change.count - 1,
- QModelIndex(),
- change.to > change.index ? change.to + change.count : change.to);
- model->endMoveRows();
- break;
- case Change::Changed:
- emit model->dataChanged(
- model->createIndex(change.index, 0),
- model->createIndex(change.index + change.count - 1, 0),
- change.roles);
- break;
- }
- }
- }
+ ListModel::sync(s->list->m_listModel, m_orig->m_listModel);
}
syncDone.wakeAll();
diff --git a/src/qml/types/qqmllistmodelworkeragent_p.h b/src/qml/types/qqmllistmodelworkeragent_p.h
index 5a39651bf7..2120f25744 100644
--- a/src/qml/types/qqmllistmodelworkeragent_p.h
+++ b/src/qml/types/qqmllistmodelworkeragent_p.h
@@ -91,7 +91,7 @@ public:
struct VariantRef
{
- VariantRef() : a(0) {}
+ VariantRef() : a(nullptr) {}
VariantRef(const VariantRef &r) : a(r.a) { if (a) a->addref(); }
VariantRef(QQmlListModelWorkerAgent *_a) : a(_a) { if (a) a->addref(); }
~VariantRef() { if (a) a->release(); }
@@ -114,35 +114,12 @@ private:
friend class QQuickWorkerScriptEnginePrivate;
friend class QQmlListModel;
- struct Change
- {
- int modelUid;
- enum { Inserted, Removed, Moved, Changed } type;
- int index; // Inserted/Removed/Moved/Changed
- int count; // Inserted/Removed/Moved/Changed
- int to; // Moved
- QVector<int> roles;
- };
-
- struct Data
- {
- QList<Change> changes;
-
- void clearChange(int uid);
- void insertChange(int uid, int index, int count);
- void removeChange(int uid, int index, int count);
- void moveChange(int uid, int index, int count, int to);
- void changedChange(int uid, int index, int count, const QVector<int> &roles);
- };
- Data data;
-
struct Sync : public QEvent {
- Sync(const Data &d, QQmlListModel *l)
+ Sync(QQmlListModel *l)
: QEvent(QEvent::User)
- , data(d)
, list(l)
{}
- Data data;
+ ~Sync();
QQmlListModel *list;
};
diff --git a/src/qml/types/qqmlobjectmodel.cpp b/src/qml/types/qqmlobjectmodel.cpp
index dcd0360199..08740b4a6f 100644
--- a/src/qml/types/qqmlobjectmodel.cpp
+++ b/src/qml/types/qqmlobjectmodel.cpp
@@ -267,7 +267,7 @@ bool QQmlObjectModel::isValid() const
return true;
}
-QObject *QQmlObjectModel::object(int index, bool)
+QObject *QQmlObjectModel::object(int index, QQmlIncubator::IncubationMode)
{
Q_D(QQmlObjectModel);
QQmlObjectModelPrivate::Item &item = d->children[index];
@@ -287,7 +287,7 @@ QQmlInstanceModel::ReleaseFlags QQmlObjectModel::release(QObject *item)
if (!d->children[idx].deref())
return QQmlInstanceModel::Referenced;
}
- return 0;
+ return nullptr;
}
QString QQmlObjectModel::stringValue(int index, const QString &name)
@@ -298,6 +298,11 @@ QString QQmlObjectModel::stringValue(int index, const QString &name)
return QQmlEngine::contextForObject(d->children.at(index).item)->contextProperty(name).toString();
}
+QQmlIncubator::Status QQmlObjectModel::incubationStatus(int)
+{
+ return QQmlIncubator::Ready;
+}
+
int QQmlObjectModel::indexOf(QObject *item, QObject *) const
{
Q_D(const QQmlObjectModel);
@@ -332,7 +337,7 @@ QObject *QQmlObjectModel::get(int index) const
{
Q_D(const QQmlObjectModel);
if (index < 0 || index >= d->children.count())
- return 0;
+ return nullptr;
return d->children.at(index).item;
}
diff --git a/src/qml/types/qqmlobjectmodel_p.h b/src/qml/types/qqmlobjectmodel_p.h
index fc4c03874f..267828dcdd 100644
--- a/src/qml/types/qqmlobjectmodel_p.h
+++ b/src/qml/types/qqmlobjectmodel_p.h
@@ -52,6 +52,7 @@
//
#include <private/qtqmlglobal_p.h>
+#include <private/qqmlincubator_p.h>
#include <QtQml/qqml.h>
#include <QtCore/qobject.h>
@@ -74,11 +75,12 @@ public:
virtual int count() const = 0;
virtual bool isValid() const = 0;
- virtual QObject *object(int index, bool asynchronous=false) = 0;
+ virtual QObject *object(int index, QQmlIncubator::IncubationMode incubationMode = QQmlIncubator::AsynchronousIfNested) = 0;
virtual ReleaseFlags release(QObject *object) = 0;
virtual void cancel(int) {}
virtual QString stringValue(int, const QString &) = 0;
virtual void setWatchedRoles(const QList<QByteArray> &roles) = 0;
+ virtual QQmlIncubator::Status incubationStatus(int index) = 0;
virtual int indexOf(QObject *object, QObject *objectContext) const = 0;
@@ -90,7 +92,7 @@ Q_SIGNALS:
void destroyingItem(QObject *object);
protected:
- QQmlInstanceModel(QObjectPrivate &dd, QObject *parent = 0)
+ QQmlInstanceModel(QObjectPrivate &dd, QObject *parent = nullptr)
: QObject(dd, parent) {}
private:
@@ -108,15 +110,16 @@ class Q_QML_PRIVATE_EXPORT QQmlObjectModel : public QQmlInstanceModel
Q_CLASSINFO("DefaultProperty", "children")
public:
- QQmlObjectModel(QObject *parent=0);
+ QQmlObjectModel(QObject *parent=nullptr);
~QQmlObjectModel() {}
int count() const override;
bool isValid() const override;
- QObject *object(int index, bool asynchronous = false) override;
+ QObject *object(int index, QQmlIncubator::IncubationMode incubationMode = QQmlIncubator::AsynchronousIfNested) override;
ReleaseFlags release(QObject *object) override;
QString stringValue(int index, const QString &role) override;
void setWatchedRoles(const QList<QByteArray> &) override {}
+ QQmlIncubator::Status incubationStatus(int index) override;
int indexOf(QObject *object, QObject *objectContext) const override;
diff --git a/src/qml/types/qqmltimer.cpp b/src/qml/types/qqmltimer.cpp
index 2037c4f6cd..6554010f36 100644
--- a/src/qml/types/qqmltimer.cpp
+++ b/src/qml/types/qqmltimer.cpp
@@ -57,7 +57,7 @@ class QQmlTimerPrivate : public QObjectPrivate, public QAnimationJobChangeListen
Q_DECLARE_PUBLIC(QQmlTimer)
public:
QQmlTimerPrivate()
- : interval(1000), running(false), repeating(false), triggeredOnStart(false)
+ : running(false), repeating(false), triggeredOnStart(false)
, classBegun(false), componentComplete(false), firstTick(true), awaitingTick(false) {}
void animationFinished(QAbstractAnimationJob *) override;
@@ -71,7 +71,7 @@ public:
}
}
- int interval;
+ int interval = 1000;
QPauseAnimationJob pause;
bool running : 1;
bool repeating : 1;
diff --git a/src/qml/types/qqmltimer_p.h b/src/qml/types/qqmltimer_p.h
index 7739dad2a6..d597869994 100644
--- a/src/qml/types/qqmltimer_p.h
+++ b/src/qml/types/qqmltimer_p.h
@@ -72,7 +72,7 @@ class Q_QML_PRIVATE_EXPORT QQmlTimer : public QObject, public QQmlParserStatus
Q_PROPERTY(QObject *parent READ parent CONSTANT)
public:
- QQmlTimer(QObject *parent=0);
+ QQmlTimer(QObject *parent=nullptr);
void setInterval(int interval);
int interval() const;
diff --git a/src/qml/types/qquickpackage.cpp b/src/qml/types/qquickpackage.cpp
index e0d1888f33..e8e897bab9 100644
--- a/src/qml/types/qquickpackage.cpp
+++ b/src/qml/types/qquickpackage.cpp
@@ -183,7 +183,7 @@ QObject *QQuickPackage::part(const QString &name)
if (name == QLatin1String("default") && !d->dataList.isEmpty())
return d->dataList.at(0);
- return 0;
+ return nullptr;
}
QQuickPackageAttached *QQuickPackage::qmlAttachedProperties(QObject *o)
diff --git a/src/qml/types/qquickpackage_p.h b/src/qml/types/qquickpackage_p.h
index ca383bfdcb..122c7fcb30 100644
--- a/src/qml/types/qquickpackage_p.h
+++ b/src/qml/types/qquickpackage_p.h
@@ -66,7 +66,7 @@ class Q_AUTOTEST_EXPORT QQuickPackage : public QObject
Q_PROPERTY(QQmlListProperty<QObject> data READ data)
public:
- QQuickPackage(QObject *parent=0);
+ QQuickPackage(QObject *parent=nullptr);
virtual ~QQuickPackage();
QQmlListProperty<QObject> data();
diff --git a/src/qml/types/qquickworkerscript.cpp b/src/qml/types/qquickworkerscript.cpp
index 346f2e6a61..80c2d3a4bc 100644
--- a/src/qml/types/qquickworkerscript.cpp
+++ b/src/qml/types/qquickworkerscript.cpp
@@ -186,7 +186,7 @@ public:
int m_nextId;
- static QV4::ReturnedValue method_sendMessage(const QV4::BuiltinFunction *, QV4::CallData *callData);
+ static QV4::ReturnedValue method_sendMessage(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
signals:
void stopThread();
@@ -201,9 +201,9 @@ private:
};
QQuickWorkerScriptEnginePrivate::WorkerEngine::WorkerEngine(QQuickWorkerScriptEnginePrivate *parent)
-: QV8Engine(0), p(parent)
+ : QV8Engine(nullptr, new QV4::ExecutionEngine), p(parent)
#if QT_CONFIG(qml_network)
-, accessManager(0)
+, accessManager(nullptr)
#endif
{
m_v4Engine->v8Engine = this;
@@ -214,6 +214,7 @@ QQuickWorkerScriptEnginePrivate::WorkerEngine::~WorkerEngine()
#if QT_CONFIG(qml_network)
delete accessManager;
#endif
+ delete m_v4Engine;
}
void QQuickWorkerScriptEnginePrivate::WorkerEngine::init()
@@ -246,11 +247,11 @@ void QQuickWorkerScriptEnginePrivate::WorkerEngine::init()
QV4::ScopedFunctionObject createsendconstructor(scope, createsendscript.run());
Q_ASSERT(!scope.engine->hasException);
QV4::ScopedString name(scope, m_v4Engine->newString(QStringLiteral("sendMessage")));
- QV4::ScopedValue function(scope, QV4::BuiltinFunction::create(globalContext, name,
- QQuickWorkerScriptEnginePrivate::method_sendMessage));
+ QV4::ScopedValue function(scope, QV4::FunctionObject::createBuiltinFunction(globalContext, name,
+ QQuickWorkerScriptEnginePrivate::method_sendMessage));
QV4::JSCallData jsCallData(scope, 1);
jsCallData->args[0] = function;
- *jsCallData->thisObject = global();
+ *jsCallData->thisObject = m_v4Engine->global();
createsend.set(scope.engine, createsendconstructor->call(jsCallData));
}
@@ -267,7 +268,7 @@ QV4::ReturnedValue QQuickWorkerScriptEnginePrivate::WorkerEngine::sendFunction(i
QV4::ScopedValue v(scope);
QV4::JSCallData jsCallData(scope, 1);
jsCallData->args[0] = QV4::Primitive::fromInt32(id);
- *jsCallData->thisObject = global();
+ *jsCallData->thisObject = m_v4Engine->global();
v = f->call(jsCallData);
if (scope.hasException())
v = scope.engine->catchException();
@@ -289,19 +290,19 @@ QNetworkAccessManager *QQuickWorkerScriptEnginePrivate::WorkerEngine::networkAcc
#endif
QQuickWorkerScriptEnginePrivate::QQuickWorkerScriptEnginePrivate(QQmlEngine *engine)
-: workerEngine(0), qmlengine(engine), m_nextId(0)
+: workerEngine(nullptr), qmlengine(engine), m_nextId(0)
{
}
-QV4::ReturnedValue QQuickWorkerScriptEnginePrivate::method_sendMessage(const QV4::BuiltinFunction *b,
- QV4::CallData *callData)
+QV4::ReturnedValue QQuickWorkerScriptEnginePrivate::method_sendMessage(const QV4::FunctionObject *b,
+ const QV4::Value *, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- WorkerEngine *engine = (WorkerEngine*)scope.engine->v8Engine;
+ WorkerEngine *engine = static_cast<WorkerEngine *>(scope.engine->v8Engine);
- int id = callData->argc() > 1 ? callData->args[1].toInt32() : 0;
+ int id = argc > 1 ? argv[1].toInt32() : 0;
- QV4::ScopedValue v(scope, callData->argument(2));
+ QV4::ScopedValue v(scope, argc > 2 ? argv[2] : QV4::Primitive::undefinedValue());
QByteArray data = QV4::Serialize::serialize(v, scope.engine);
QMutexLocker locker(&engine->p->m_lock);
@@ -367,7 +368,7 @@ void QQuickWorkerScriptEnginePrivate::processMessage(int id, const QByteArray &d
Q_ASSERT(!!qmlContext);
QV4::JSCallData jsCallData(scope, 2);
- *jsCallData->thisObject = workerEngine->global();
+ *jsCallData->thisObject = v4->global();
jsCallData->args[0] = qmlContext->d()->qml(); // ###
jsCallData->args[1] = value;
f->call(jsCallData);
@@ -396,22 +397,10 @@ void QQuickWorkerScriptEnginePrivate::processLoad(int id, const QUrl &url)
QV4::Scoped<QV4::QmlContext> qmlContext(scope, getWorker(script));
Q_ASSERT(!!qmlContext);
- if (const QQmlPrivate::CachedQmlUnit *cachedUnit = QQmlMetaType::findCachedCompilationUnit(url)) {
- QV4::CompiledData::CompilationUnit *jsUnit = cachedUnit->createCompilationUnit();
- program.reset(new QV4::Script(v4, qmlContext, jsUnit));
- } else {
- QFile f(fileName);
- if (!f.open(QIODevice::ReadOnly)) {
- qWarning().nospace() << "WorkerScript: Cannot find source file " << url.toString();
- return;
- }
-
- QByteArray data = f.readAll();
- QString sourceCode = QString::fromUtf8(data);
- QmlIR::Document::removeScriptPragmas(sourceCode);
-
- program.reset(new QV4::Script(v4, qmlContext, sourceCode, url.toString()));
- program->parse();
+ program.reset(QV4::Script::createFromFileOrCache(v4, qmlContext, fileName, url));
+ if (program.isNull()) {
+ qWarning().nospace() << "WorkerScript: Cannot find source file " << url.toString();
+ return;
}
if (!v4->hasException)
@@ -518,7 +507,7 @@ QQuickWorkerScriptEngine::~QQuickWorkerScriptEngine()
}
QQuickWorkerScriptEnginePrivate::WorkerScript::WorkerScript()
-: id(-1), initialized(false), owner(0)
+: id(-1), initialized(false), owner(nullptr)
{
}
@@ -545,7 +534,7 @@ void QQuickWorkerScriptEngine::removeWorkerScript(int id)
{
QQuickWorkerScriptEnginePrivate::WorkerScript* script = d->workers.value(id);
if (script) {
- script->owner = 0;
+ script->owner = nullptr;
QCoreApplication::postEvent(d, new WorkerRemoveEvent(id));
}
}
@@ -576,7 +565,7 @@ void QQuickWorkerScriptEngine::run()
qDeleteAll(d->workers);
d->workers.clear();
- delete d->workerEngine; d->workerEngine = 0;
+ delete d->workerEngine; d->workerEngine = nullptr;
}
@@ -627,7 +616,7 @@ void QQuickWorkerScriptEngine::run()
{Threaded ListModel Example}
*/
QQuickWorkerScript::QQuickWorkerScript(QObject *parent)
-: QObject(parent), m_engine(0), m_scriptId(-1), m_componentComplete(true)
+: QObject(parent), m_engine(nullptr), m_scriptId(-1), m_componentComplete(true)
{
}
@@ -707,7 +696,7 @@ QQuickWorkerScriptEngine *QQuickWorkerScript::engine()
QQmlEngine *engine = qmlEngine(this);
if (!engine) {
qWarning("QQuickWorkerScript: engine() called without qmlEngine() set");
- return 0;
+ return nullptr;
}
m_engine = QQmlEnginePrivate::get(engine)->getWorkerScriptEngine();
@@ -718,7 +707,7 @@ QQuickWorkerScriptEngine *QQuickWorkerScript::engine()
return m_engine;
}
- return 0;
+ return nullptr;
}
void QQuickWorkerScript::componentComplete()
@@ -742,8 +731,7 @@ bool QQuickWorkerScript::event(QEvent *event)
QQmlEngine *engine = qmlEngine(this);
if (engine) {
WorkerDataEvent *workerEvent = static_cast<WorkerDataEvent *>(event);
- QV8Engine *v8engine = QQmlEnginePrivate::get(engine)->v8engine();
- QV4::Scope scope(QV8Engine::getV4(v8engine));
+ QV4::Scope scope(engine->handle());
QV4::ScopedValue value(scope, QV4::Serialize::deserialize(workerEvent->data(), scope.engine));
emit message(QQmlV4Handle(value));
}
diff --git a/src/qml/types/qquickworkerscript_p.h b/src/qml/types/qquickworkerscript_p.h
index 8ea630c685..1a8d2ab076 100644
--- a/src/qml/types/qquickworkerscript_p.h
+++ b/src/qml/types/qquickworkerscript_p.h
@@ -67,7 +67,7 @@ class QQuickWorkerScriptEngine : public QThread
{
Q_OBJECT
public:
- QQuickWorkerScriptEngine(QQmlEngine *parent = 0);
+ QQuickWorkerScriptEngine(QQmlEngine *parent = nullptr);
~QQuickWorkerScriptEngine();
int registerWorkerScript(QQuickWorkerScript *);
@@ -91,7 +91,7 @@ class Q_AUTOTEST_EXPORT QQuickWorkerScript : public QObject, public QQmlParserSt
Q_INTERFACES(QQmlParserStatus)
public:
- QQuickWorkerScript(QObject *parent = 0);
+ QQuickWorkerScript(QObject *parent = nullptr);
~QQuickWorkerScript();
QUrl source() const;
diff --git a/src/qml/util/qqmladaptormodel.cpp b/src/qml/util/qqmladaptormodel.cpp
index d5b38f6d3e..b4bebb9d5d 100644
--- a/src/qml/util/qqmladaptormodel.cpp
+++ b/src/qml/util/qqmladaptormodel.cpp
@@ -61,10 +61,10 @@ public:
V4_DEFINE_EXTENSION(QQmlAdaptorModelEngineData, engineData)
-static QV4::ReturnedValue get_index(const QV4::BuiltinFunction *f, QV4::CallData *callData)
+static QV4::ReturnedValue get_index(const QV4::FunctionObject *f, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(f);
- QV4::Scoped<QQmlDelegateModelItemObject> o(scope, callData->thisObject.as<QQmlDelegateModelItemObject>());
+ QV4::Scoped<QQmlDelegateModelItemObject> o(scope, thisObject->as<QQmlDelegateModelItemObject>());
if (!o)
RETURN_RESULT(scope.engine->throwTypeError(QStringLiteral("Not a valid VisualData object")));
@@ -106,8 +106,8 @@ public:
void setValue(const QString &role, const QVariant &value) override;
bool resolveIndex(const QQmlAdaptorModel &model, int idx) override;
- static QV4::ReturnedValue get_property(const QV4::BuiltinFunction *, QV4::CallData *);
- static QV4::ReturnedValue set_property(const QV4::BuiltinFunction *, QV4::CallData *);
+ static QV4::ReturnedValue get_property(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue set_property(const QV4::FunctionObject *, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
VDMModelDelegateDataType *type;
QVector<QVariant> cachedData;
@@ -121,8 +121,8 @@ class VDMModelDelegateDataType
public:
VDMModelDelegateDataType(QQmlAdaptorModel *model)
: model(model)
- , metaObject(0)
- , propertyCache(0)
+ , metaObject(nullptr)
+ , propertyCache(nullptr)
, propertyOffset(0)
, signalOffset(0)
, hasModelData(false)
@@ -176,7 +176,7 @@ public:
const int idx = item->modelIndex();
if (idx >= index && idx < index + count) {
for (int i = 0; i < signalIndexes.count(); ++i)
- QMetaObject::activate(item, signalIndexes.at(i), 0);
+ QMetaObject::activate(item, signalIndexes.at(i), nullptr);
}
}
return changed;
@@ -195,10 +195,10 @@ public:
dataType->watchedRoles += newRoles;
}
- static QV4::ReturnedValue get_hasModelChildren(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+ static QV4::ReturnedValue get_hasModelChildren(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelItemObject> o(scope, callData->thisObject.as<QQmlDelegateModelItemObject>());
+ QV4::Scoped<QQmlDelegateModelItemObject> o(scope, thisObject->as<QQmlDelegateModelItemObject>());
if (!o)
RETURN_RESULT(scope.engine->throwTypeError(QStringLiteral("Not a valid VisualData object")));
@@ -217,8 +217,8 @@ public:
QV4::ExecutionEngine *v4 = data->v4;
QV4::Scope scope(v4);
QV4::ScopedObject proto(scope, v4->newObject());
- proto->defineAccessorProperty(QStringLiteral("index"), get_index, 0);
- proto->defineAccessorProperty(QStringLiteral("hasModelChildren"), get_hasModelChildren, 0);
+ proto->defineAccessorProperty(QStringLiteral("index"), get_index, nullptr);
+ proto->defineAccessorProperty(QStringLiteral("hasModelChildren"), get_hasModelChildren, nullptr);
QV4::ScopedProperty p(scope);
typedef QHash<QByteArray, int>::const_iterator iterator;
@@ -298,11 +298,11 @@ int QQmlDMCachedModelData::metaCall(QMetaObject::Call call, int id, void **argum
const QMetaObject *meta = metaObject();
if (cachedData.count() > 1) {
cachedData[propertyIndex] = *static_cast<QVariant *>(arguments[0]);
- QMetaObject::activate(this, meta, propertyIndex, 0);
+ QMetaObject::activate(this, meta, propertyIndex, nullptr);
} else if (cachedData.count() == 1) {
cachedData[0] = *static_cast<QVariant *>(arguments[0]);
- QMetaObject::activate(this, meta, 0, 0);
- QMetaObject::activate(this, meta, 1, 0);
+ QMetaObject::activate(this, meta, 0, nullptr);
+ QMetaObject::activate(this, meta, 1, nullptr);
}
} else if (*type->model) {
setValue(type->propertyRoles.at(propertyIndex), *static_cast<QVariant *>(arguments[0]));
@@ -336,17 +336,17 @@ bool QQmlDMCachedModelData::resolveIndex(const QQmlAdaptorModel &, int idx)
const QMetaObject *meta = metaObject();
const int propertyCount = type->propertyRoles.count();
for (int i = 0; i < propertyCount; ++i)
- QMetaObject::activate(this, meta, i, 0);
+ QMetaObject::activate(this, meta, i, nullptr);
return true;
} else {
return false;
}
}
-QV4::ReturnedValue QQmlDMCachedModelData::get_property(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQmlDMCachedModelData::get_property(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelItemObject> o(scope, callData->thisObject.as<QQmlDelegateModelItemObject>());
+ QV4::Scoped<QQmlDelegateModelItemObject> o(scope, thisObject->as<QQmlDelegateModelItemObject>());
if (!o)
return scope.engine->throwTypeError(QStringLiteral("Not a valid VisualData object"));
@@ -365,13 +365,13 @@ QV4::ReturnedValue QQmlDMCachedModelData::get_property(const QV4::BuiltinFunctio
return QV4::Encode::undefined();
}
-QV4::ReturnedValue QQmlDMCachedModelData::set_property(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQmlDMCachedModelData::set_property(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQmlDelegateModelItemObject> o(scope, callData->thisObject.as<QQmlDelegateModelItemObject>());
+ QV4::Scoped<QQmlDelegateModelItemObject> o(scope, thisObject->as<QQmlDelegateModelItemObject>());
if (!o)
return scope.engine->throwTypeError(QStringLiteral("Not a valid VisualData object"));
- if (!callData->argc())
+ if (!argc)
return scope.engine->throwTypeError();
uint propertyId = static_cast<const QV4::IndexedBuiltinFunction *>(b)->d()->index;
@@ -380,12 +380,12 @@ QV4::ReturnedValue QQmlDMCachedModelData::set_property(const QV4::BuiltinFunctio
QQmlDMCachedModelData *modelData = static_cast<QQmlDMCachedModelData *>(o->d()->item);
if (!modelData->cachedData.isEmpty()) {
if (modelData->cachedData.count() > 1) {
- modelData->cachedData[propertyId] = scope.engine->toVariant(callData->args[0], QVariant::Invalid);
- QMetaObject::activate(o->d()->item, o->d()->item->metaObject(), propertyId, 0);
+ modelData->cachedData[propertyId] = scope.engine->toVariant(argv[0], QVariant::Invalid);
+ QMetaObject::activate(o->d()->item, o->d()->item->metaObject(), propertyId, nullptr);
} else if (modelData->cachedData.count() == 1) {
- modelData->cachedData[0] = scope.engine->toVariant(callData->args[0], QVariant::Invalid);
- QMetaObject::activate(o->d()->item, o->d()->item->metaObject(), 0, 0);
- QMetaObject::activate(o->d()->item, o->d()->item->metaObject(), 1, 0);
+ modelData->cachedData[0] = scope.engine->toVariant(argv[0], QVariant::Invalid);
+ QMetaObject::activate(o->d()->item, o->d()->item->metaObject(), 0, nullptr);
+ QMetaObject::activate(o->d()->item, o->d()->item->metaObject(), 1, nullptr);
}
}
}
@@ -586,26 +586,26 @@ public:
}
}
- static QV4::ReturnedValue get_modelData(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+ static QV4::ReturnedValue get_modelData(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::ExecutionEngine *v4 = b->engine();
- QQmlDelegateModelItemObject *o = callData->thisObject.as<QQmlDelegateModelItemObject>();
+ const QQmlDelegateModelItemObject *o = thisObject->as<QQmlDelegateModelItemObject>();
if (!o)
return v4->throwTypeError(QStringLiteral("Not a valid VisualData object"));
return v4->fromVariant(static_cast<QQmlDMListAccessorData *>(o->d()->item)->cachedData);
}
- static QV4::ReturnedValue set_modelData(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+ static QV4::ReturnedValue set_modelData(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::ExecutionEngine *v4 = b->engine();
- QQmlDelegateModelItemObject *o = callData->thisObject.as<QQmlDelegateModelItemObject>();
+ const QQmlDelegateModelItemObject *o = thisObject->as<QQmlDelegateModelItemObject>();
if (!o)
return v4->throwTypeError(QStringLiteral("Not a valid VisualData object"));
- if (!callData->argc())
+ if (!argc)
return v4->throwTypeError();
- static_cast<QQmlDMListAccessorData *>(o->d()->item)->setModelData(v4->toVariant(callData->args[0], QVariant::Invalid));
+ static_cast<QQmlDMListAccessorData *>(o->d()->item)->setModelData(v4->toVariant(argv[0], QVariant::Invalid));
return QV4::Encode::undefined();
}
@@ -710,7 +710,7 @@ public:
QMetaObjectBuilder builder;
VDMObjectDelegateDataType()
- : metaObject(0)
+ : metaObject(nullptr)
, propertyOffset(0)
, signalOffset(0)
, shared(true)
@@ -720,7 +720,7 @@ public:
VDMObjectDelegateDataType(const VDMObjectDelegateDataType &type)
: QQmlRefCount()
, QQmlAdaptorModel::Accessors()
- , metaObject(0)
+ , metaObject(nullptr)
, propertyOffset(type.propertyOffset)
, signalOffset(type.signalOffset)
, shared(false)
@@ -759,7 +759,7 @@ public:
dataType->initializeMetaType(model);
return index >= 0 && index < model.list.count()
? new QQmlDMObjectData(metaType, dataType, index, qvariant_cast<QObject *>(model.list.at(index)))
- : 0;
+ : nullptr;
}
void initializeMetaType(QQmlAdaptorModel &)
@@ -807,7 +807,7 @@ public:
QMetaObject::metacall(m_data->object, call, id - m_type->propertyOffset + objectPropertyOffset, arguments);
return -1;
} else if (id >= m_type->signalOffset && call == QMetaObject::InvokeMetaMethod) {
- QMetaObject::activate(m_data, this, id - m_type->signalOffset, 0);
+ QMetaObject::activate(m_data, this, id - m_type->signalOffset, nullptr);
return -1;
} else {
return m_data->qt_metacall(call, id, arguments);
@@ -937,10 +937,10 @@ void QQmlAdaptorModel::setModel(const QVariant &variant, QQmlDelegateModel *vdm,
accessors = new VDMObjectDelegateDataType;
} else if (list.type() != QQmlListAccessor::Invalid
&& list.type() != QQmlListAccessor::Instance) { // Null QObject
- setObject(0);
+ setObject(nullptr);
accessors = &qt_vdm_list_accessors;
} else {
- setObject(0);
+ setObject(nullptr);
accessors = &qt_vdm_null_accessors;
}
}
@@ -960,7 +960,7 @@ bool QQmlAdaptorModel::isValid() const
void QQmlAdaptorModel::objectDestroyed(QObject *)
{
- setModel(QVariant(), 0, 0);
+ setModel(QVariant(), nullptr, nullptr);
}
QQmlAdaptorModelEngineData::QQmlAdaptorModelEngineData(QV4::ExecutionEngine *v4)
@@ -968,7 +968,7 @@ QQmlAdaptorModelEngineData::QQmlAdaptorModelEngineData(QV4::ExecutionEngine *v4)
{
QV4::Scope scope(v4);
QV4::ScopedObject proto(scope, v4->newObject());
- proto->defineAccessorProperty(QStringLiteral("index"), get_index, 0);
+ proto->defineAccessorProperty(QStringLiteral("index"), get_index, nullptr);
proto->defineAccessorProperty(QStringLiteral("modelData"),
QQmlDMListAccessorData::get_modelData, QQmlDMListAccessorData::set_modelData);
listItemProto.set(v4, proto);
diff --git a/src/qml/util/qqmladaptormodel_p.h b/src/qml/util/qqmladaptormodel_p.h
index 7bbddcff07..8f773efa20 100644
--- a/src/qml/util/qqmladaptormodel_p.h
+++ b/src/qml/util/qqmladaptormodel_p.h
@@ -74,7 +74,7 @@ public:
inline Accessors() {}
virtual ~Accessors();
virtual int count(const QQmlAdaptorModel &) const { return 0; }
- virtual void cleanup(QQmlAdaptorModel &, QQmlDelegateModel * = 0) const {}
+ virtual void cleanup(QQmlAdaptorModel &, QQmlDelegateModel * = nullptr) const {}
virtual QVariant value(const QQmlAdaptorModel &, int, const QString &) const {
return QVariant(); }
@@ -82,7 +82,7 @@ public:
virtual QQmlDelegateModelItem *createItem(
QQmlAdaptorModel &,
QQmlDelegateModelItemMetaType *,
- int) const { return 0; }
+ int) const { return nullptr; }
virtual bool notify(
const QQmlAdaptorModel &,
diff --git a/src/qml/util/qqmlchangeset.cpp b/src/qml/util/qqmlchangeset.cpp
index ccfd34161f..561bde7d0c 100644
--- a/src/qml/util/qqmlchangeset.cpp
+++ b/src/qml/util/qqmlchangeset.cpp
@@ -122,7 +122,7 @@ void QQmlChangeSet::remove(int index, int count)
{
QVector<Change> removes;
removes.append(Change(index, count));
- remove(&removes, 0);
+ remove(&removes, nullptr);
}
/*!
diff --git a/src/qml/util/qqmlchangeset_p.h b/src/qml/util/qqmlchangeset_p.h
index 8e1fa3f9f2..8347a3ff19 100644
--- a/src/qml/util/qqmlchangeset_p.h
+++ b/src/qml/util/qqmlchangeset_p.h
@@ -62,10 +62,10 @@ class Q_QML_PRIVATE_EXPORT QQmlChangeSet
public:
struct MoveKey
{
- MoveKey() : moveId(-1), offset(0) {}
+ MoveKey() {}
MoveKey(int moveId, int offset) : moveId(moveId), offset(offset) {}
- int moveId;
- int offset;
+ int moveId = -1;
+ int offset = 0;
};
// The storrage for Change (below). This struct is trivial, which it has to be in order to store
@@ -119,7 +119,7 @@ public:
void change(int index, int count);
void insert(const QVector<Change> &inserts);
- void remove(const QVector<Change> &removes, QVector<Change> *inserts = 0);
+ void remove(const QVector<Change> &removes, QVector<Change> *inserts = nullptr);
void move(const QVector<Change> &removes, const QVector<Change> &inserts);
void change(const QVector<Change> &changes);
void apply(const QQmlChangeSet &changeSet);
diff --git a/src/qml/util/qqmllistaccessor.cpp b/src/qml/util/qqmllistaccessor.cpp
index 356584abdc..ad55519ad3 100644
--- a/src/qml/util/qqmllistaccessor.cpp
+++ b/src/qml/util/qqmllistaccessor.cpp
@@ -72,7 +72,7 @@ void QQmlListAccessor::setList(const QVariant &v, QQmlEngine *engine)
if (d.userType() == qMetaTypeId<QJSValue>())
d = d.value<QJSValue>().toVariant();
- QQmlEnginePrivate *enginePrivate = engine?QQmlEnginePrivate::get(engine):0;
+ QQmlEnginePrivate *enginePrivate = engine?QQmlEnginePrivate::get(engine):nullptr;
if (!d.isValid()) {
m_type = Invalid;
diff --git a/src/qml/util/qqmllistaccessor_p.h b/src/qml/util/qqmllistaccessor_p.h
index bad5a5803c..bcd079adef 100644
--- a/src/qml/util/qqmllistaccessor_p.h
+++ b/src/qml/util/qqmllistaccessor_p.h
@@ -63,7 +63,7 @@ public:
~QQmlListAccessor();
QVariant list() const;
- void setList(const QVariant &, QQmlEngine * = 0);
+ void setList(const QVariant &, QQmlEngine * = nullptr);
bool isValid() const;
diff --git a/src/qml/util/qqmllistcompositor.cpp b/src/qml/util/qqmllistcompositor.cpp
index 05a4eaac39..8b0b8f48f0 100644
--- a/src/qml/util/qqmllistcompositor.cpp
+++ b/src/qml/util/qqmllistcompositor.cpp
@@ -1253,7 +1253,7 @@ void QQmlListCompositor::listItemsRemoved(
QVector<QQmlChangeSet::Change> removals;
removals.append(QQmlChangeSet::Change(index, count));
- listItemsRemoved(translatedRemovals, list, &removals, 0, 0);
+ listItemsRemoved(translatedRemovals, list, &removals, nullptr, nullptr);
}
/*!
diff --git a/src/qml/util/qqmllistcompositor_p.h b/src/qml/util/qqmllistcompositor_p.h
index 6ae9c47df3..172040559c 100644
--- a/src/qml/util/qqmllistcompositor_p.h
+++ b/src/qml/util/qqmllistcompositor_p.h
@@ -87,17 +87,17 @@ public:
class Range
{
public:
- Range() : next(this), previous(this), list(0), index(0), count(0), flags(0) {}
+ Range() : next(this), previous(this) {}
Range(Range *next, void *list, int index, int count, uint flags)
: next(next), previous(next->previous), list(list), index(index), count(count), flags(flags) {
next->previous = this; previous->next = this; }
Range *next;
Range *previous;
- void *list;
- int index;
- int count;
- uint flags;
+ void *list = nullptr;
+ int index = 0;
+ int count = 0;
+ uint flags = 0;
inline int start() const { return index; }
inline int end() const { return index + count; }
@@ -145,11 +145,11 @@ public:
void setGroup(Group g) { group = g; groupFlag = 1 << g; }
- Range *range;
- int offset;
- Group group;
+ Range *range = nullptr;
+ int offset = 0;
+ Group group = Default;
int groupFlag;
- int groupCount;
+ int groupCount = 0;
union {
struct {
int cacheIndex;
@@ -222,22 +222,22 @@ public:
const iterator &end() { return m_end; }
- void append(void *list, int index, int count, uint flags, QVector<Insert> *inserts = 0);
- void insert(Group group, int before, void *list, int index, int count, uint flags, QVector<Insert> *inserts = 0);
- iterator insert(iterator before, void *list, int index, int count, uint flags, QVector<Insert> *inserts = 0);
+ void append(void *list, int index, int count, uint flags, QVector<Insert> *inserts = nullptr);
+ void insert(Group group, int before, void *list, int index, int count, uint flags, QVector<Insert> *inserts = nullptr);
+ iterator insert(iterator before, void *list, int index, int count, uint flags, QVector<Insert> *inserts = nullptr);
- void setFlags(Group fromGroup, int from, int count, Group group, int flags, QVector<Insert> *inserts = 0);
- void setFlags(iterator from, int count, Group group, uint flags, QVector<Insert> *inserts = 0);
- void setFlags(Group fromGroup, int from, int count, uint flags, QVector<Insert> *inserts = 0) {
+ void setFlags(Group fromGroup, int from, int count, Group group, int flags, QVector<Insert> *inserts = nullptr);
+ void setFlags(iterator from, int count, Group group, uint flags, QVector<Insert> *inserts = nullptr);
+ void setFlags(Group fromGroup, int from, int count, uint flags, QVector<Insert> *inserts = nullptr) {
setFlags(fromGroup, from, count, fromGroup, flags, inserts); }
- void setFlags(const iterator from, int count, uint flags, QVector<Insert> *inserts = 0) {
+ void setFlags(const iterator from, int count, uint flags, QVector<Insert> *inserts = nullptr) {
setFlags(from, count, from.group, flags, inserts); }
- void clearFlags(Group fromGroup, int from, int count, Group group, uint flags, QVector<Remove> *removals = 0);
- void clearFlags(iterator from, int count, Group group, uint flags, QVector<Remove> *removals = 0);
- void clearFlags(Group fromGroup, int from, int count, uint flags, QVector<Remove> *removals = 0) {
+ void clearFlags(Group fromGroup, int from, int count, Group group, uint flags, QVector<Remove> *removals = nullptr);
+ void clearFlags(iterator from, int count, Group group, uint flags, QVector<Remove> *removals = nullptr);
+ void clearFlags(Group fromGroup, int from, int count, uint flags, QVector<Remove> *removals = nullptr) {
clearFlags(fromGroup, from, count, fromGroup, flags, removals); }
- void clearFlags(const iterator &from, int count, uint flags, QVector<Remove> *removals = 0) {
+ void clearFlags(const iterator &from, int count, uint flags, QVector<Remove> *removals = nullptr) {
clearFlags(from, count, from.group, flags, removals); }
bool verifyMoveTo(Group fromGroup, int from, Group toGroup, int to, int count, Group group) const;
@@ -249,8 +249,8 @@ public:
int to,
int count,
Group group,
- QVector<Remove> *removals = 0,
- QVector<Insert> *inserts = 0);
+ QVector<Remove> *removals = nullptr,
+ QVector<Insert> *inserts = nullptr);
void clear();
void listItemsInserted(void *list, int index, int count, QVector<Insert> *inserts);
@@ -289,13 +289,13 @@ private:
QVector<Remove> *translatedRemovals,
void *list,
QVector<QQmlChangeSet::Change> *removals,
- QVector<QQmlChangeSet::Change> *insertions = 0,
- QVector<MovedFlags> *movedFlags = 0);
+ QVector<QQmlChangeSet::Change> *insertions = nullptr,
+ QVector<MovedFlags> *movedFlags = nullptr);
void listItemsInserted(
QVector<Insert> *translatedInsertions,
void *list,
const QVector<QQmlChangeSet::Change> &insertions,
- const QVector<MovedFlags> *movedFlags = 0);
+ const QVector<MovedFlags> *movedFlags = nullptr);
void listItemsChanged(
QVector<Change> *translatedChanges,
void *list,
@@ -308,8 +308,7 @@ Q_DECLARE_TYPEINFO(QQmlListCompositor::Change, Q_PRIMITIVE_TYPE);
Q_DECLARE_TYPEINFO(QQmlListCompositor::Remove, Q_PRIMITIVE_TYPE);
Q_DECLARE_TYPEINFO(QQmlListCompositor::Insert, Q_PRIMITIVE_TYPE);
-inline QQmlListCompositor::iterator::iterator()
- : range(0), offset(0), group(Default), groupCount(0) {}
+inline QQmlListCompositor::iterator::iterator() {}
inline QQmlListCompositor::iterator::iterator(const iterator &it)
: range(it.range)
, offset(it.offset)
diff --git a/src/qml/util/qqmlpropertymap.cpp b/src/qml/util/qqmlpropertymap.cpp
index b54e8d901a..578c05086f 100644
--- a/src/qml/util/qqmlpropertymap.cpp
+++ b/src/qml/util/qqmlpropertymap.cpp
@@ -355,7 +355,7 @@ QQmlPropertyMap::QQmlPropertyMap(const QMetaObject *staticMetaObject, QObject *p
*/
/*!
- \fn QQmlPropertyMap::QQmlPropertyMap(DerivedType *derived, QObject *parent)
+ \fn template<class DerivedType> QQmlPropertyMap::QQmlPropertyMap(DerivedType *derived, QObject *parent)
Constructs a bindable map with parent object \a parent. Use this constructor
in classes derived from QQmlPropertyMap.
diff --git a/src/qml/util/qqmlpropertymap.h b/src/qml/util/qqmlpropertymap.h
index 3930ac00a8..cb7ada3d79 100644
--- a/src/qml/util/qqmlpropertymap.h
+++ b/src/qml/util/qqmlpropertymap.h
@@ -56,7 +56,7 @@ class Q_QML_EXPORT QQmlPropertyMap : public QObject
Q_OBJECT
public:
explicit QQmlPropertyMap(QObject *parent = nullptr);
- virtual ~QQmlPropertyMap();
+ ~QQmlPropertyMap() override;
QVariant value(const QString &key) const;
void insert(const QString &key, const QVariant &value);
diff --git a/src/qmldebug/qmldebug.pro b/src/qmldebug/qmldebug.pro
index e5f6de3314..2539414d8f 100644
--- a/src/qmldebug/qmldebug.pro
+++ b/src/qmldebug/qmldebug.pro
@@ -7,15 +7,25 @@ load(qt_module)
SOURCES += \
qqmldebugclient.cpp \
qqmldebugconnection.cpp \
+ qqmldebugmessageclient.cpp \
qqmlenginecontrolclient.cpp \
- qqmlprofilerclient.cpp
+ qqmlprofilerclient.cpp \
+ qqmlprofilerevent.cpp \
+ qqmlprofilereventlocation.cpp \
+ qqmlprofilereventtype.cpp \
+ qqmlprofilertypedevent.cpp
HEADERS += \
qqmldebugclient_p.h \
qqmldebugclient_p_p.h \
qqmldebugconnection_p.h \
+ qqmldebugmessageclient_p.h \
qqmlenginecontrolclient_p.h \
qqmlenginecontrolclient_p_p.h \
- qqmleventlocation_p.h \
qqmlprofilerclient_p.h \
- qqmlprofilerclient_p_p.h
+ qqmlprofilerclient_p_p.h \
+ qqmlprofilerevent_p.h \
+ qqmlprofilereventlocation_p.h \
+ qqmlprofilereventreceiver_p.h \
+ qqmlprofilereventtype_p.h \
+ qqmlprofilertypedevent_p.h
diff --git a/src/qmldebug/qqmldebugclient.cpp b/src/qmldebug/qqmldebugclient.cpp
index 7f1e8c637c..d412b7b267 100644
--- a/src/qmldebug/qqmldebugclient.cpp
+++ b/src/qmldebug/qqmldebugclient.cpp
@@ -77,7 +77,7 @@ void QQmlDebugClientPrivate::addToConnection()
Q_Q(QQmlDebugClient);
if (connection && !connection->addClient(name, q)) {
qWarning() << "QQmlDebugClient: Conflicting plugin name" << name;
- connection = 0;
+ connection = nullptr;
}
}
diff --git a/src/qmldebug/qqmldebugconnection.cpp b/src/qmldebug/qqmldebugconnection.cpp
index 73ccd7c854..67bad8d812 100644
--- a/src/qmldebug/qqmldebugconnection.cpp
+++ b/src/qmldebug/qqmldebugconnection.cpp
@@ -63,15 +63,15 @@ class QQmlDebugConnectionPrivate : public QObjectPrivate
public:
QQmlDebugConnectionPrivate();
- QPacketProtocol *protocol;
- QIODevice *device;
- QLocalServer *server;
+ QPacketProtocol *protocol = nullptr;
+ QIODevice *device = nullptr;
+ QLocalServer *server = nullptr;
QEventLoop handshakeEventLoop;
QTimer handshakeTimer;
- bool gotHello;
- int currentDataStreamVersion;
- int maximumDataStreamVersion;
+ bool gotHello = false;
+ int currentDataStreamVersion = QDataStream::Qt_4_7;
+ int maximumDataStreamVersion = QDataStream::Qt_DefaultCompiledVersion;
QHash <QString, float> serverPlugins;
QHash<QString, QQmlDebugClient *> plugins;
QStringList removedPlugins;
@@ -81,10 +81,7 @@ public:
void flush();
};
-QQmlDebugConnectionPrivate::QQmlDebugConnectionPrivate() :
- protocol(0), device(0), server(0), gotHello(false),
- currentDataStreamVersion(QDataStream::Qt_4_7),
- maximumDataStreamVersion(QDataStream::Qt_DefaultCompiledVersion)
+QQmlDebugConnectionPrivate::QQmlDebugConnectionPrivate()
{
handshakeTimer.setSingleShot(true);
handshakeTimer.setInterval(3000);
@@ -303,7 +300,7 @@ void QQmlDebugConnection::close()
if (d->device) {
d->device->deleteLater();
- d->device = 0;
+ d->device = nullptr;
}
}
diff --git a/src/qmldebug/qqmldebugconnection_p.h b/src/qmldebug/qqmldebugconnection_p.h
index be425b6cbf..ad9376886c 100644
--- a/src/qmldebug/qqmldebugconnection_p.h
+++ b/src/qmldebug/qqmldebugconnection_p.h
@@ -64,7 +64,7 @@ class QQmlDebugConnection : public QObject
Q_DISABLE_COPY(QQmlDebugConnection)
Q_DECLARE_PRIVATE(QQmlDebugConnection)
public:
- QQmlDebugConnection(QObject *parent = 0);
+ QQmlDebugConnection(QObject *parent = nullptr);
~QQmlDebugConnection();
void connectToHost(const QString &hostName, quint16 port);
diff --git a/src/qmldebug/qqmldebugmessageclient.cpp b/src/qmldebug/qqmldebugmessageclient.cpp
new file mode 100644
index 0000000000..a03c1f8af2
--- /dev/null
+++ b/src/qmldebug/qqmldebugmessageclient.cpp
@@ -0,0 +1,95 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qqmldebugmessageclient_p.h"
+
+#include <QtCore/qdatastream.h>
+
+QT_BEGIN_NAMESPACE
+
+/*!
+ \class QQmlDebugMessageClient
+ \internal
+
+ \brief Client for the debug message service
+
+ The QQmlDebugMessageClient receives debug messages routed through the QML
+ debug connection via QDebugMessageService.
+ */
+
+QQmlDebugMessageClient::QQmlDebugMessageClient(QQmlDebugConnection *client)
+ : QQmlDebugClient(QLatin1String("DebugMessages"), client)
+{
+}
+
+void QQmlDebugMessageClient::stateChanged(State state)
+{
+ emit newState(state);
+}
+
+void QQmlDebugMessageClient::messageReceived(const QByteArray &data)
+{
+ QDataStream ds(data);
+ QByteArray command;
+ ds >> command;
+
+ if (command == "MESSAGE") {
+ int type;
+ int line;
+ QByteArray debugMessage;
+ QByteArray file;
+ QByteArray function;
+ ds >> type >> debugMessage >> file >> line >> function;
+ QQmlDebugContextInfo info;
+ info.line = line;
+ info.file = QString::fromUtf8(file);
+ info.function = QString::fromUtf8(function);
+ info.timestamp = -1;
+ if (!ds.atEnd()) {
+ QByteArray category;
+ ds >> category;
+ info.category = QString::fromUtf8(category);
+ if (!ds.atEnd())
+ ds >> info.timestamp;
+ }
+ emit message(QtMsgType(type), QString::fromUtf8(debugMessage), info);
+ }
+}
+
+QT_END_NAMESPACE
diff --git a/src/qmldebug/qqmldebugmessageclient_p.h b/src/qmldebug/qqmldebugmessageclient_p.h
new file mode 100644
index 0000000000..75c70044e4
--- /dev/null
+++ b/src/qmldebug/qqmldebugmessageclient_p.h
@@ -0,0 +1,87 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QQMLDEBUGMESSAGECLIENT_P_H
+#define QQMLDEBUGMESSAGECLIENT_P_H
+
+#include "qqmldebugclient_p.h"
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+QT_BEGIN_NAMESPACE
+
+struct QQmlDebugContextInfo
+{
+ int line;
+ QString file;
+ QString function;
+ QString category;
+ qint64 timestamp;
+};
+
+class QQmlDebugMessageClient : public QQmlDebugClient
+{
+ Q_OBJECT
+
+public:
+ explicit QQmlDebugMessageClient(QQmlDebugConnection *client);
+
+ virtual void stateChanged(State state) override;
+ virtual void messageReceived(const QByteArray &) override;
+
+signals:
+ void newState(QQmlDebugClient::State);
+ void message(QtMsgType, const QString &, const QQmlDebugContextInfo &);
+
+private:
+ Q_DISABLE_COPY(QQmlDebugMessageClient)
+};
+
+QT_END_NAMESPACE
+
+#endif // QQMLDEBUGMESSAGECLIENT_P_H
diff --git a/src/qmldebug/qqmlenginecontrolclient.cpp b/src/qmldebug/qqmlenginecontrolclient.cpp
index 3f75298e51..13f216ce38 100644
--- a/src/qmldebug/qqmlenginecontrolclient.cpp
+++ b/src/qmldebug/qqmlenginecontrolclient.cpp
@@ -108,32 +108,37 @@ void QQmlEngineControlClient::messageReceived(const QByteArray &data)
if (!stream.atEnd())
stream >> name;
- QQmlEngineControlClientPrivate::EngineState &state = d->blockedEngines[id];
- Q_ASSERT(state.blockers == 0);
- Q_ASSERT(state.releaseCommand == QQmlEngineControlClientPrivate::InvalidCommand);
+ auto handleWaiting = [&](
+ QQmlEngineControlClientPrivate::CommandType command, std::function<void()> emitter) {
+ QQmlEngineControlClientPrivate::EngineState &state = d->blockedEngines[id];
+ Q_ASSERT(state.blockers == 0);
+ Q_ASSERT(state.releaseCommand == QQmlEngineControlClientPrivate::InvalidCommand);
+ state.releaseCommand = command;
+ emitter();
+ if (state.blockers == 0) {
+ d->sendCommand(state.releaseCommand, id);
+ d->blockedEngines.remove(id);
+ }
+ };
switch (message) {
case QQmlEngineControlClientPrivate::EngineAboutToBeAdded:
- state.releaseCommand = QQmlEngineControlClientPrivate::StartWaitingEngine;
- emit engineAboutToBeAdded(id, name);
+ handleWaiting(QQmlEngineControlClientPrivate::StartWaitingEngine, [&](){
+ emit engineAboutToBeAdded(id, name);
+ });
break;
case QQmlEngineControlClientPrivate::EngineAdded:
emit engineAdded(id, name);
break;
case QQmlEngineControlClientPrivate::EngineAboutToBeRemoved:
- state.releaseCommand = QQmlEngineControlClientPrivate::StopWaitingEngine;
- emit engineAboutToBeRemoved(id, name);
+ handleWaiting(QQmlEngineControlClientPrivate::StopWaitingEngine, [&](){
+ emit engineAboutToBeRemoved(id, name);
+ });
break;
case QQmlEngineControlClientPrivate::EngineRemoved:
emit engineRemoved(id, name);
break;
}
-
- if (state.blockers == 0 &&
- state.releaseCommand != QQmlEngineControlClientPrivate::InvalidCommand) {
- d->sendCommand(state.releaseCommand, id);
- d->blockedEngines.remove(id);
- }
}
QQmlEngineControlClientPrivate::QQmlEngineControlClientPrivate(QQmlDebugConnection *connection) :
diff --git a/src/qmldebug/qqmlprofilerclient.cpp b/src/qmldebug/qqmlprofilerclient.cpp
index 3676bd933c..d2a2d24f13 100644
--- a/src/qmldebug/qqmlprofilerclient.cpp
+++ b/src/qmldebug/qqmlprofilerclient.cpp
@@ -43,337 +43,316 @@
QT_BEGIN_NAMESPACE
-QQmlProfilerClient::QQmlProfilerClient(QQmlDebugConnection *connection) :
- QQmlDebugClient(*(new QQmlProfilerClientPrivate(connection)))
+int QQmlProfilerClientPrivate::resolveType(const QQmlProfilerTypedEvent &event)
{
-}
+ int typeIndex = -1;
+ if (event.serverTypeId != 0) {
+ QHash<qint64, int>::ConstIterator it = serverTypeIds.constFind(event.serverTypeId);
-QQmlProfilerClient::QQmlProfilerClient(QQmlProfilerClientPrivate &dd) :
- QQmlDebugClient(dd)
-{
+ if (it != serverTypeIds.constEnd()) {
+ typeIndex = it.value();
+ } else {
+ typeIndex = eventReceiver->numLoadedEventTypes();
+ eventReceiver->addEventType(event.type);
+ serverTypeIds[event.serverTypeId] = typeIndex;
+ }
+ } else {
+ QHash<QQmlProfilerEventType, int>::ConstIterator it = eventTypeIds.constFind(event.type);
+
+ if (it != eventTypeIds.constEnd()) {
+ typeIndex = it.value();
+ } else {
+ typeIndex = eventReceiver->numLoadedEventTypes();
+ eventReceiver->addEventType(event.type);
+ eventTypeIds[event.type] = typeIndex;
+ }
+ }
+ return typeIndex;
}
-QQmlProfilerClientPrivate::QQmlProfilerClientPrivate(QQmlDebugConnection *connection) :
- QQmlDebugClientPrivate(QQmlProfilerService::s_key, connection),
- features(std::numeric_limits<quint64>::max())
+int QQmlProfilerClientPrivate::resolveStackTop()
{
+ if (rangesInProgress.isEmpty())
+ return -1;
+
+ QQmlProfilerTypedEvent &typedEvent = rangesInProgress.top();
+ int typeIndex = typedEvent.event.typeIndex();
+ if (typeIndex >= 0)
+ return typeIndex;
+
+ typeIndex = resolveType(typedEvent);
+ typedEvent.event.setTypeIndex(typeIndex);
+ while (!pendingMessages.isEmpty()
+ && pendingMessages.head().timestamp() < typedEvent.event.timestamp()) {
+ forwardEvents(pendingMessages.dequeue());
+ }
+ forwardEvents(typedEvent.event);
+ return typeIndex;
}
-void QQmlProfilerClient::setFeatures(quint64 features)
+void QQmlProfilerClientPrivate::forwardEvents(const QQmlProfilerEvent &last)
{
- Q_D(QQmlProfilerClient);
- d->features = features;
+ while (!pendingDebugMessages.isEmpty()
+ && pendingDebugMessages.front().timestamp() <= last.timestamp()) {
+ eventReceiver->addEvent(pendingDebugMessages.dequeue());
+ }
+ eventReceiver->addEvent(last);
}
-void QQmlProfilerClient::sendRecordingStatus(bool record, int engineId, quint32 flushInterval)
+void QQmlProfilerClientPrivate::processCurrentEvent()
{
- Q_D(const QQmlProfilerClient);
-
- QPacket stream(d->connection->currentDataStreamVersion());
- stream << record << engineId << d->features << flushInterval << true;
- sendMessage(stream.data());
+ // RangeData and RangeLocation always apply to the range on the top of the stack. Furthermore,
+ // all ranges are perfectly nested. This is why we can defer the type resolution until either
+ // the range ends or a child range starts. With only the information in RangeStart we wouldn't
+ // be able to uniquely identify the event type.
+ Message rangeStage = currentEvent.type.rangeType() == MaximumRangeType ?
+ currentEvent.type.message() : currentEvent.event.rangeStage();
+ switch (rangeStage) {
+ case RangeStart:
+ resolveStackTop();
+ rangesInProgress.push(currentEvent);
+ break;
+ case RangeEnd: {
+ int typeIndex = resolveStackTop();
+ if (typeIndex == -1)
+ break;
+ currentEvent.event.setTypeIndex(typeIndex);
+ while (!pendingMessages.isEmpty())
+ forwardEvents(pendingMessages.dequeue());
+ forwardEvents(currentEvent.event);
+ rangesInProgress.pop();
+ break;
+ }
+ case RangeData:
+ if (!rangesInProgress.isEmpty())
+ rangesInProgress.top().type.setData(currentEvent.type.data());
+ break;
+ case RangeLocation:
+ if (!rangesInProgress.isEmpty())
+ rangesInProgress.top().type.setLocation(currentEvent.type.location());
+ break;
+ case DebugMessage:
+ currentEvent.event.setTypeIndex(resolveType(currentEvent));
+ pendingDebugMessages.enqueue(currentEvent.event);
+ break;
+ default: {
+ int typeIndex = resolveType(currentEvent);
+ currentEvent.event.setTypeIndex(typeIndex);
+ if (rangesInProgress.isEmpty())
+ eventReceiver->addEvent(currentEvent.event);
+ else
+ pendingMessages.enqueue(currentEvent.event);
+ break;
+ }
+ }
}
-void QQmlProfilerClient::traceStarted(qint64 time, int engineId)
+void QQmlProfilerClientPrivate::sendRecordingStatus(int engineId)
{
- Q_UNUSED(time);
- Q_UNUSED(engineId);
+ Q_Q(QQmlProfilerClient);
+ QPacket stream(connection->currentDataStreamVersion());
+ stream << recording << engineId; // engineId -1 is OK. It means "all of them"
+ if (recording) {
+ stream << requestedFeatures << flushInterval;
+ stream << true; // yes, we support type IDs
+ }
+ q->sendMessage(stream.data());
}
-void QQmlProfilerClient::traceFinished(qint64 time, int engineId)
+QQmlProfilerClient::QQmlProfilerClient(QQmlDebugConnection *connection,
+ QQmlProfilerEventReceiver *eventReceiver,
+ quint64 features)
+ : QQmlDebugClient(*(new QQmlProfilerClientPrivate(connection, eventReceiver)))
{
- Q_UNUSED(time);
- Q_UNUSED(engineId);
+ Q_D(QQmlProfilerClient);
+ setRequestedFeatures(features);
+ connect(d->engineControl.data(), &QQmlEngineControlClient::engineAboutToBeAdded,
+ this, &QQmlProfilerClient::sendRecordingStatus);
+ connect(d->engineControl.data(), &QQmlEngineControlClient::engineAboutToBeRemoved,
+ this, [d](int engineId) {
+ // We may already be done with that engine. Then we don't need to block it.
+ if (d->trackedEngines.contains(engineId))
+ d->engineControl->blockEngine(engineId);
+ });
+ connect(this, &QQmlProfilerClient::traceFinished,
+ d->engineControl.data(), [d](qint64 timestamp, const QList<int> &engineIds) {
+ Q_UNUSED(timestamp);
+ // The engines might not be blocked because the trace can get finished before engine control
+ // sees them.
+ for (int blocked : d->engineControl->blockedEngines()) {
+ if (engineIds.contains(blocked))
+ d->engineControl->releaseEngine(blocked);
+ }
+ });
}
-void QQmlProfilerClient::rangeStart(QQmlProfilerDefinitions::RangeType type, qint64 startTime)
+QQmlProfilerClient::~QQmlProfilerClient()
{
- Q_UNUSED(type);
- Q_UNUSED(startTime);
+ //Disable profiling if started by client
+ //Profiling data will be lost!!
+ if (isRecording())
+ setRecording(false);
}
-void QQmlProfilerClient::rangeData(QQmlProfilerDefinitions::RangeType type, qint64 time,
- const QString &data)
+void QQmlProfilerClient::clearEvents()
{
- Q_UNUSED(type);
- Q_UNUSED(time);
- Q_UNUSED(data);
+ Q_D(QQmlProfilerClient);
+ d->rangesInProgress.clear();
+ d->pendingMessages.clear();
+ d->pendingDebugMessages.clear();
+ if (d->recordedFeatures != 0) {
+ d->recordedFeatures = 0;
+ emit recordedFeaturesChanged(0);
+ }
+ emit cleared();
}
-void QQmlProfilerClient::rangeLocation(QQmlProfilerDefinitions::RangeType type, qint64 time,
- const QQmlEventLocation &location)
+void QQmlProfilerClient::clearAll()
{
- Q_UNUSED(type);
- Q_UNUSED(time);
- Q_UNUSED(location);
+ Q_D(QQmlProfilerClient);
+ d->serverTypeIds.clear();
+ d->eventTypeIds.clear();
+ d->trackedEngines.clear();
+ clearEvents();
}
-void QQmlProfilerClient::rangeEnd(QQmlProfilerDefinitions::RangeType type, qint64 endTime)
+void QQmlProfilerClientPrivate::finalize()
{
- Q_UNUSED(type);
- Q_UNUSED(endTime);
+ while (!rangesInProgress.isEmpty()) {
+ currentEvent = rangesInProgress.top();
+ currentEvent.event.setRangeStage(RangeEnd);
+ currentEvent.event.setTimestamp(maximumTime);
+ processCurrentEvent();
+ }
+ while (!pendingDebugMessages.isEmpty())
+ eventReceiver->addEvent(pendingDebugMessages.dequeue());
}
-void QQmlProfilerClient::animationFrame(qint64 time, int frameRate, int animationCount,
- int threadId)
+
+void QQmlProfilerClient::sendRecordingStatus(int engineId)
{
- Q_UNUSED(time);
- Q_UNUSED(frameRate);
- Q_UNUSED(animationCount);
- Q_UNUSED(threadId);
+ Q_D(QQmlProfilerClient);
+ d->sendRecordingStatus(engineId);
}
-void QQmlProfilerClient::sceneGraphEvent(QQmlProfilerDefinitions::SceneGraphFrameType type,
- qint64 time, qint64 numericData1, qint64 numericData2,
- qint64 numericData3, qint64 numericData4,
- qint64 numericData5)
+bool QQmlProfilerClient::isRecording() const
{
- Q_UNUSED(type);
- Q_UNUSED(time);
- Q_UNUSED(numericData1);
- Q_UNUSED(numericData2);
- Q_UNUSED(numericData3);
- Q_UNUSED(numericData4);
- Q_UNUSED(numericData5);
+ Q_D(const QQmlProfilerClient);
+ return d->recording;
}
-void QQmlProfilerClient::pixmapCacheEvent(QQmlProfilerDefinitions::PixmapEventType type,
- qint64 time, const QString &url, int numericData1,
- int numericData2)
+void QQmlProfilerClient::setRecording(bool v)
{
- Q_UNUSED(type);
- Q_UNUSED(time);
- Q_UNUSED(url);
- Q_UNUSED(numericData1);
- Q_UNUSED(numericData2);
+ Q_D(QQmlProfilerClient);
+ if (v == d->recording)
+ return;
+
+ d->recording = v;
+
+ if (state() == Enabled)
+ sendRecordingStatus();
+
+ emit recordingChanged(v);
}
-void QQmlProfilerClient::memoryAllocation(QQmlProfilerDefinitions::MemoryType type, qint64 time,
- qint64 amount)
+quint64 QQmlProfilerClient::recordedFeatures() const
{
- Q_UNUSED(type);
- Q_UNUSED(time);
- Q_UNUSED(amount);
+ Q_D(const QQmlProfilerClient);
+ return d->recordedFeatures;
}
-void QQmlProfilerClient::inputEvent(QQmlProfilerDefinitions::InputEventType type, qint64 time,
- int a, int b)
+void QQmlProfilerClient::setRequestedFeatures(quint64 features)
{
- Q_UNUSED(type);
- Q_UNUSED(time);
- Q_UNUSED(a);
- Q_UNUSED(b);
+ Q_D(QQmlProfilerClient);
+ d->requestedFeatures = features;
+ if (features & static_cast<quint64>(1) << ProfileDebugMessages) {
+ if (d->messageClient.isNull()) {
+ d->messageClient.reset(new QQmlDebugMessageClient(connection()));
+ connect(d->messageClient.data(), &QQmlDebugMessageClient::message, this,
+ [this](QtMsgType type, const QString &text, const QQmlDebugContextInfo &context)
+ {
+ Q_D(QQmlProfilerClient);
+ d->updateFeatures(ProfileDebugMessages);
+ d->currentEvent.event.setTimestamp(context.timestamp > 0 ? context.timestamp : 0);
+ d->currentEvent.event.setTypeIndex(-1);
+ d->currentEvent.event.setString(text);
+ d->currentEvent.type = QQmlProfilerEventType(
+ DebugMessage, MaximumRangeType, type,
+ QQmlProfilerEventLocation(context.file, context.line, 1));
+ d->currentEvent.serverTypeId = 0;
+ d->processCurrentEvent();
+ });
+ }
+ } else {
+ d->messageClient.reset();
+ }
}
-void QQmlProfilerClient::complete()
+void QQmlProfilerClient::setFlushInterval(quint32 flushInterval)
{
+ Q_D(QQmlProfilerClient);
+ d->flushInterval = flushInterval;
}
-void QQmlProfilerClient::unknownEvent(QQmlProfilerDefinitions::Message messageType, qint64 time,
- int detailType)
+QQmlProfilerClient::QQmlProfilerClient(QQmlProfilerClientPrivate &dd) :
+ QQmlDebugClient(dd)
{
- Q_UNUSED(messageType);
- Q_UNUSED(time);
- Q_UNUSED(detailType);
+ Q_D(QQmlProfilerClient);
+ connect(d->engineControl.data(), &QQmlEngineControlClient::engineAboutToBeAdded,
+ this, &QQmlProfilerClient::sendRecordingStatus);
}
-void QQmlProfilerClient::unknownData(QPacket &stream)
+bool QQmlProfilerClientPrivate::updateFeatures(ProfileFeature feature)
{
- Q_UNUSED(stream);
+ Q_Q(QQmlProfilerClient);
+ quint64 flag = 1ULL << feature;
+ if (!(requestedFeatures & flag))
+ return false;
+ if (!(recordedFeatures & flag)) {
+ recordedFeatures |= flag;
+ emit q->recordedFeaturesChanged(recordedFeatures);
+ }
+ return true;
}
-inline QQmlProfilerDefinitions::ProfileFeature featureFromRangeType(
- QQmlProfilerDefinitions::RangeType range)
+void QQmlProfilerClient::stateChanged(State status)
{
- switch (range) {
- case QQmlProfilerDefinitions::Painting:
- return QQmlProfilerDefinitions::ProfilePainting;
- case QQmlProfilerDefinitions::Compiling:
- return QQmlProfilerDefinitions::ProfileCompiling;
- case QQmlProfilerDefinitions::Creating:
- return QQmlProfilerDefinitions::ProfileCreating;
- case QQmlProfilerDefinitions::Binding:
- return QQmlProfilerDefinitions::ProfileBinding;
- case QQmlProfilerDefinitions::HandlingSignal:
- return QQmlProfilerDefinitions::ProfileHandlingSignal;
- case QQmlProfilerDefinitions::Javascript:
- return QQmlProfilerDefinitions::ProfileJavaScript;
- default:
- return QQmlProfilerDefinitions::MaximumProfileFeature;
+ if (status == Enabled) {
+ sendRecordingStatus(-1);
+ } else {
+ Q_D(QQmlProfilerClient);
+ d->finalize();
}
+
}
void QQmlProfilerClient::messageReceived(const QByteArray &data)
{
Q_D(QQmlProfilerClient);
-
QPacket stream(d->connection->currentDataStreamVersion(), data);
- // Force all the 1 << <FLAG> expressions to be done in 64 bit, to silence some warnings
- const quint64 one = static_cast<quint64>(1);
-
- qint64 time;
- int messageType;
-
- stream >> time >> messageType;
-
- if (messageType >= QQmlProfilerDefinitions::MaximumMessage) {
- unknownEvent(static_cast<QQmlProfilerDefinitions::Message>(messageType), time, -1);
- return;
+ stream >> d->currentEvent;
+
+ d->maximumTime = qMax(d->currentEvent.event.timestamp(), d->maximumTime);
+ if (d->currentEvent.type.message() == Complete) {
+ d->finalize();
+ emit complete(d->maximumTime);
+ } else if (d->currentEvent.type.message() == Event
+ && d->currentEvent.type.detailType() == StartTrace) {
+ const QList<int> engineIds = d->currentEvent.event.numbers<QList<int>, qint32>();
+ d->trackedEngines.append(engineIds);
+ emit traceStarted(d->currentEvent.event.timestamp(), engineIds);
+ } else if (d->currentEvent.type.message() == Event
+ && d->currentEvent.type.detailType() == EndTrace) {
+ const QList<int> engineIds = d->currentEvent.event.numbers<QList<int>, qint32>();
+ for (int engineId : engineIds)
+ d->trackedEngines.removeAll(engineId);
+ emit traceFinished(d->currentEvent.event.timestamp(), engineIds);
+ } else if (d->updateFeatures(d->currentEvent.type.feature())) {
+ d->processCurrentEvent();
}
-
- if (messageType == QQmlProfilerDefinitions::Event) {
- int type;
- stream >> type;
-
- QQmlProfilerDefinitions::EventType eventType =
- static_cast<QQmlProfilerDefinitions::EventType>(type);
-
- if (eventType == QQmlProfilerDefinitions::EndTrace) {
- int engineId = -1;
- if (!stream.atEnd())
- stream >> engineId;
- traceFinished(time, engineId);
- } else if (eventType == QQmlProfilerDefinitions::AnimationFrame) {
- if (!(d->features & one << QQmlProfilerDefinitions::ProfileAnimations))
- return;
-
- int frameRate, animationCount;
- int threadId = 0;
- stream >> frameRate >> animationCount;
- if (!stream.atEnd())
- stream >> threadId;
-
- animationFrame(time, frameRate, animationCount, threadId);
- } else if (type == QQmlProfilerDefinitions::StartTrace) {
- int engineId = -1;
- if (!stream.atEnd())
- stream >> engineId;
- traceStarted(time, engineId);
- } else if (eventType == QQmlProfilerDefinitions::Key ||
- eventType == QQmlProfilerDefinitions::Mouse) {
-
- if (!(d->features & one << QQmlProfilerDefinitions::ProfileInputEvents))
- return;
-
- int type;
- if (!stream.atEnd()) {
- stream >> type;
- } else {
- type = (eventType == QQmlProfilerDefinitions::Key) ?
- QQmlProfilerDefinitions::InputKeyUnknown :
- QQmlProfilerDefinitions::InputMouseUnknown;
- }
-
- int a = 0;
- if (!stream.atEnd())
- stream >> a;
-
- int b = 0;
- if (!stream.atEnd())
- stream >> b;
-
- inputEvent(static_cast<QQmlProfilerDefinitions::InputEventType>(type), time, a, b);
- } else {
- unknownEvent(QQmlProfilerDefinitions::Event, time, type);
- }
- } else if (messageType == QQmlProfilerDefinitions::Complete) {
- complete();
- } else if (messageType == QQmlProfilerDefinitions::SceneGraphFrame) {
- if (!(d->features & one << QQmlProfilerDefinitions::ProfileSceneGraph))
- return;
-
- int type;
- int count = 0;
- qint64 params[5];
-
- stream >> type;
- while (!stream.atEnd())
- stream >> params[count++];
-
- while (count < 5)
- params[count++] = 0;
-
- sceneGraphEvent(static_cast<QQmlProfilerDefinitions::SceneGraphFrameType>(type), time,
- params[0], params[1], params[2], params[3], params[4]);
- } else if (messageType == QQmlProfilerDefinitions::PixmapCacheEvent) {
- if (!(d->features & one << QQmlProfilerDefinitions::ProfilePixmapCache))
- return;
-
- int type, param1 = 0, param2 = 0;
- QString pixUrl;
- stream >> type >> pixUrl;
-
- QQmlProfilerDefinitions::PixmapEventType pixmapEventType =
- static_cast<QQmlProfilerDefinitions::PixmapEventType>(type);
-
- if (pixmapEventType == QQmlProfilerDefinitions::PixmapReferenceCountChanged ||
- pixmapEventType == QQmlProfilerDefinitions::PixmapCacheCountChanged) {
- stream >> param1;
- } else if (pixmapEventType == QQmlProfilerDefinitions::PixmapSizeKnown) {
- stream >> param1 >> param2;
- }
-
- pixmapCacheEvent(pixmapEventType, time, pixUrl, param1, param2);
- } else if (messageType == QQmlProfilerDefinitions::MemoryAllocation) {
- if (!(d->features & one << QQmlProfilerDefinitions::ProfileMemory))
- return;
- int type;
- qint64 delta;
- stream >> type >> delta;
- memoryAllocation((QQmlProfilerDefinitions::MemoryType)type, time, delta);
- } else {
- int range;
- stream >> range;
-
- QQmlProfilerDefinitions::RangeType rangeType =
- static_cast<QQmlProfilerDefinitions::RangeType>(range);
-
- if (range >= QQmlProfilerDefinitions::MaximumRangeType ||
- !(d->features & one << featureFromRangeType(rangeType)))
- return;
-
- qint64 typeId = 0;
- if (messageType == QQmlProfilerDefinitions::RangeStart) {
- rangeStart(rangeType, time);
- if (!stream.atEnd()) {
- stream >> typeId;
- auto i = d->types.constFind(typeId);
- if (i != d->types.constEnd()) {
- rangeLocation(rangeType, time, i->location);
- rangeData(rangeType, time, i->name);
- }
- }
- } else if (messageType == QQmlProfilerDefinitions::RangeData) {
- QString data;
- stream >> data;
- rangeData(rangeType, time, data);
- if (!stream.atEnd()) {
- stream >> typeId;
- d->types[typeId].name = data;
- }
- } else if (messageType == QQmlProfilerDefinitions::RangeLocation) {
- QQmlEventLocation location;
- stream >> location.filename >> location.line;
-
- if (!stream.atEnd())
- stream >> location.column;
-
- rangeLocation(rangeType, time, location);
- if (!stream.atEnd()) {
- stream >> typeId;
- d->types[typeId].location = location;
- }
- } else if (messageType == QQmlProfilerDefinitions::RangeEnd) {
- rangeEnd(rangeType, time);
- } else {
- unknownEvent(static_cast<QQmlProfilerDefinitions::Message>(messageType), time, range);
- }
- }
-
- if (!stream.atEnd())
- unknownData(stream);
}
+
QT_END_NAMESPACE
#include "moc_qqmlprofilerclient_p.cpp"
diff --git a/src/qmldebug/qqmlprofilerclient_p.h b/src/qmldebug/qqmlprofilerclient_p.h
index a328cad26c..68a32a1a5a 100644
--- a/src/qmldebug/qqmlprofilerclient_p.h
+++ b/src/qmldebug/qqmlprofilerclient_p.h
@@ -41,7 +41,9 @@
#define QQMLPROFILERCLIENT_P_H
#include "qqmldebugclient_p.h"
-#include "qqmleventlocation_p.h"
+#include "qqmlprofilereventlocation_p.h"
+#include "qqmlprofilereventreceiver_p.h"
+
#include <private/qqmlprofilerdefinitions_p.h>
#include <private/qpacket_p.h>
@@ -59,52 +61,42 @@
QT_BEGIN_NAMESPACE
class QQmlProfilerClientPrivate;
-class QQmlProfilerClient : public QQmlDebugClient
+class QQmlProfilerClient : public QQmlDebugClient, public QQmlProfilerDefinitions
{
Q_OBJECT
Q_DECLARE_PRIVATE(QQmlProfilerClient)
+ Q_PROPERTY(bool recording READ isRecording WRITE setRecording NOTIFY recordingChanged)
public:
- QQmlProfilerClient(QQmlDebugConnection *connection);
- void setFeatures(quint64 features);
- void sendRecordingStatus(bool record, int engineId = -1, quint32 flushInterval = 0);
-
-protected:
- QQmlProfilerClient(QQmlProfilerClientPrivate &dd);
-
-private:
- void messageReceived(const QByteArray &message) override;
+ QQmlProfilerClient(QQmlDebugConnection *connection, QQmlProfilerEventReceiver *eventReceiver,
+ quint64 features = std::numeric_limits<quint64>::max());
+ ~QQmlProfilerClient();
- virtual void traceStarted(qint64 time, int engineId);
- virtual void traceFinished(qint64 time, int engineId);
+ bool isRecording() const;
+ void setRecording(bool);
+ quint64 recordedFeatures() const;
+ virtual void messageReceived(const QByteArray &) override;
+ virtual void stateChanged(State status) override;
- virtual void rangeStart(QQmlProfilerDefinitions::RangeType type, qint64 startTime);
- virtual void rangeData(QQmlProfilerDefinitions::RangeType type, qint64 time,
- const QString &data);
- virtual void rangeLocation(QQmlProfilerDefinitions::RangeType type, qint64 time,
- const QQmlEventLocation &location);
- virtual void rangeEnd(QQmlProfilerDefinitions::RangeType type, qint64 endTime);
+ void clearEvents();
+ void clearAll();
- virtual void animationFrame(qint64 time, int frameRate, int animationCount, int threadId);
+ void sendRecordingStatus(int engineId = -1);
+ void setRequestedFeatures(quint64 features);
+ void setFlushInterval(quint32 flushInterval);
- virtual void sceneGraphEvent(QQmlProfilerDefinitions::SceneGraphFrameType type, qint64 time,
- qint64 numericData1, qint64 numericData2, qint64 numericData3,
- qint64 numericData4, qint64 numericData5);
-
- virtual void pixmapCacheEvent(QQmlProfilerDefinitions::PixmapEventType type, qint64 time,
- const QString &url, int numericData1, int numericData2);
-
- virtual void memoryAllocation(QQmlProfilerDefinitions::MemoryType type, qint64 time,
- qint64 amount);
+protected:
+ QQmlProfilerClient(QQmlProfilerClientPrivate &dd);
- virtual void inputEvent(QQmlProfilerDefinitions::InputEventType type, qint64 time, int a,
- int b);
+signals:
+ void complete(qint64 maximumTime);
+ void traceFinished(qint64 timestamp, const QList<int> &engineIds);
+ void traceStarted(qint64 timestamp, const QList<int> &engineIds);
- virtual void complete();
+ void recordingChanged(bool arg);
+ void recordedFeaturesChanged(quint64 features);
- virtual void unknownEvent(QQmlProfilerDefinitions::Message messageType, qint64 time,
- int detailType);
- virtual void unknownData(QPacket &stream);
+ void cleared();
};
QT_END_NAMESPACE
diff --git a/src/qmldebug/qqmlprofilerclient_p_p.h b/src/qmldebug/qqmlprofilerclient_p_p.h
index 9c44113aa8..0caef8e448 100644
--- a/src/qmldebug/qqmlprofilerclient_p_p.h
+++ b/src/qmldebug/qqmlprofilerclient_p_p.h
@@ -40,8 +40,15 @@
#ifndef QQMLPROFILERCLIENT_P_P_H
#define QQMLPROFILERCLIENT_P_P_H
-#include "qqmlprofilerclient_p.h"
#include "qqmldebugclient_p_p.h"
+#include "qqmldebugmessageclient_p.h"
+#include "qqmlenginecontrolclient_p.h"
+#include "qqmlprofilerclient_p.h"
+#include "qqmlprofilertypedevent_p.h"
+
+#include <private/qqmlprofilerdefinitions_p.h>
+
+#include <QtCore/qqueue.h>
//
// W A R N I N G
@@ -56,20 +63,50 @@
QT_BEGIN_NAMESPACE
-struct QQmlProfilerRangeType
-{
- QQmlEventLocation location;
- QString name;
-};
-
-class QQmlProfilerClientPrivate : public QQmlDebugClientPrivate
-{
+class QQmlProfilerClientPrivate : public QQmlDebugClientPrivate, public QQmlProfilerDefinitions {
Q_DECLARE_PUBLIC(QQmlProfilerClient)
public:
- QQmlProfilerClientPrivate(QQmlDebugConnection *connection);
- quint64 features;
+ QQmlProfilerClientPrivate(QQmlDebugConnection *connection,
+ QQmlProfilerEventReceiver *eventReceiver)
+ : QQmlDebugClientPrivate(QLatin1String("CanvasFrameRate"), connection)
+ , eventReceiver(eventReceiver)
+ , engineControl(new QQmlEngineControlClient(connection))
+ , maximumTime(0)
+ , recording(false)
+ , requestedFeatures(0)
+ , recordedFeatures(0)
+ , flushInterval(0)
+ {
+ }
+
+ virtual ~QQmlProfilerClientPrivate() override {}
+
+ void sendRecordingStatus(int engineId);
+ bool updateFeatures(ProfileFeature feature);
+ int resolveType(const QQmlProfilerTypedEvent &type);
+ int resolveStackTop();
+ void forwardEvents(const QQmlProfilerEvent &last);
+ void processCurrentEvent();
+ void finalize();
+
+ QQmlProfilerEventReceiver *eventReceiver;
+ QScopedPointer<QQmlEngineControlClient> engineControl;
+ QScopedPointer<QQmlDebugMessageClient> messageClient;
+ qint64 maximumTime;
+ bool recording;
+ quint64 requestedFeatures;
+ quint64 recordedFeatures;
+ quint32 flushInterval;
+
+ // Reuse the same event, so that we don't have to constantly reallocate all the data.
+ QQmlProfilerTypedEvent currentEvent;
+ QHash<QQmlProfilerEventType, int> eventTypeIds;
+ QHash<qint64, int> serverTypeIds;
+ QStack<QQmlProfilerTypedEvent> rangesInProgress;
+ QQueue<QQmlProfilerEvent> pendingMessages;
+ QQueue<QQmlProfilerEvent> pendingDebugMessages;
- QHash<qint64, QQmlProfilerRangeType> types;
+ QList<int> trackedEngines;
};
QT_END_NAMESPACE
diff --git a/src/qmldebug/qqmlprofilerevent.cpp b/src/qmldebug/qqmlprofilerevent.cpp
new file mode 100644
index 0000000000..30ae1c79a1
--- /dev/null
+++ b/src/qmldebug/qqmlprofilerevent.cpp
@@ -0,0 +1,273 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qqmlprofilerevent_p.h"
+#include <QtCore/qdatastream.h>
+
+QT_BEGIN_NAMESPACE
+
+bool operator==(const QQmlProfilerEvent &event1, const QQmlProfilerEvent &event2)
+{
+ if (event1.timestamp() != event2.timestamp() || event1.typeIndex() != event2.typeIndex())
+ return false;
+
+ // This is not particularly efficient, but we also don't need to do this very often.
+ return event1.numbers<QVarLengthArray<qint64>>() == event2.numbers<QVarLengthArray<qint64>>();
+}
+
+bool operator!=(const QQmlProfilerEvent &event1, const QQmlProfilerEvent &event2)
+{
+ return !(event1 == event2);
+}
+
+enum SerializationType {
+ OneByte = 0,
+ TwoByte = 1,
+ FourByte = 2,
+ EightByte = 3,
+ TypeMask = 0x3
+};
+
+enum SerializationTypeOffset {
+ TimestampOffset = 0,
+ TypeIndexOffset = 2,
+ DataLengthOffset = 4,
+ DataOffset = 6
+};
+
+template<typename Number>
+static inline void readNumbers(QDataStream &stream, Number *data, quint16 length)
+{
+ for (quint16 i = 0; i != length; ++i)
+ stream >> data[i];
+}
+
+template<typename Number>
+static inline Number readNumber(QDataStream &stream, qint8 type)
+{
+ switch (type) {
+ case OneByte: {
+ qint8 value;
+ stream >> value;
+ return static_cast<Number>(value);
+ }
+ case TwoByte: {
+ qint16 value;
+ stream >> value;
+ return static_cast<Number>(value);
+ }
+ case FourByte: {
+ qint32 value;
+ stream >> value;
+ return static_cast<Number>(value);
+ }
+ case EightByte: {
+ qint64 value;
+ stream >> value;
+ return static_cast<Number>(value);
+ }
+ default:
+ Q_UNREACHABLE();
+ return 0;
+ }
+}
+
+QDataStream &operator>>(QDataStream &stream, QQmlProfilerEvent &event)
+{
+ qint8 type;
+ stream >> type;
+
+ event.m_timestamp = readNumber<qint64>(stream, (type >> TimestampOffset) & TypeMask);
+ event.m_typeIndex = readNumber<qint32>(stream, (type >> TypeIndexOffset) & TypeMask);
+ event.m_dataLength = readNumber<quint16>(stream, (type >> DataLengthOffset) & TypeMask);
+
+ uint bytesPerNumber = 1 << ((type >> DataOffset) & TypeMask);
+
+ if (event.m_dataLength * bytesPerNumber > sizeof(event.m_data)) {
+ event.m_dataType = static_cast<QQmlProfilerEvent::Type>((bytesPerNumber * 8)
+ | QQmlProfilerEvent::External);
+ event.m_data.external = malloc(event.m_dataLength * bytesPerNumber);
+ } else {
+ event.m_dataType = static_cast<QQmlProfilerEvent::Type>(bytesPerNumber * 8);
+ }
+
+ switch (event.m_dataType) {
+ case QQmlProfilerEvent::Inline8Bit:
+ readNumbers<qint8>(stream, event.m_data.internal8bit, event.m_dataLength);
+ break;
+ case QQmlProfilerEvent::External8Bit:
+ readNumbers<qint8>(stream, static_cast<qint8 *>(event.m_data.external),
+ event.m_dataLength);
+ break;
+ case QQmlProfilerEvent::Inline16Bit:
+ readNumbers<qint16>(stream, event.m_data.internal16bit, event.m_dataLength);
+ break;
+ case QQmlProfilerEvent::External16Bit:
+ readNumbers<qint16>(stream, static_cast<qint16 *>(event.m_data.external),
+ event.m_dataLength);
+ break;
+ case QQmlProfilerEvent::Inline32Bit:
+ readNumbers<qint32>(stream, event.m_data.internal32bit, event.m_dataLength);
+ break;
+ case QQmlProfilerEvent::External32Bit:
+ readNumbers<qint32>(stream, static_cast<qint32 *>(event.m_data.external),
+ event.m_dataLength);
+ break;
+ case QQmlProfilerEvent::Inline64Bit:
+ readNumbers<qint64>(stream, event.m_data.internal64bit, event.m_dataLength);
+ break;
+ case QQmlProfilerEvent::External64Bit:
+ readNumbers<qint64>(stream, static_cast<qint64 *>(event.m_data.external),
+ event.m_dataLength);
+ break;
+ default:
+ Q_UNREACHABLE();
+ break;
+ }
+
+ return stream;
+}
+
+static inline qint8 minimumType(const QQmlProfilerEvent &event, quint16 length,
+ quint16 origBitsPerNumber)
+{
+ qint8 type = OneByte;
+ bool ok = true;
+ for (quint16 i = 0; i < length;) {
+ if ((1 << type) == origBitsPerNumber / 8)
+ return type;
+ switch (type) {
+ case OneByte:
+ ok = (event.number<qint8>(i) == event.number<qint64>(i));
+ break;
+ case TwoByte:
+ ok = (event.number<qint16>(i) == event.number<qint64>(i));
+ break;
+ case FourByte:
+ ok = (event.number<qint32>(i) == event.number<qint64>(i));
+ break;
+ default:
+ // EightByte isn't possible, as (1 << type) == origBitsPerNumber / 8 then.
+ Q_UNREACHABLE();
+ break;
+ }
+
+ if (ok)
+ ++i;
+ else
+ ++type;
+ }
+ return type;
+}
+
+template<typename Number>
+static inline qint8 minimumType(Number number)
+{
+ if (static_cast<qint8>(number) == number)
+ return OneByte;
+ if (static_cast<qint16>(number) == number)
+ return TwoByte;
+ if (static_cast<qint32>(number) == number)
+ return FourByte;
+ return EightByte;
+}
+
+template<typename Number>
+static inline void writeNumbers(QDataStream &stream, const QQmlProfilerEvent &event, quint16 length)
+{
+ for (quint16 i = 0; i != length; ++i)
+ stream << event.number<Number>(i);
+}
+
+template<typename Number>
+static inline void writeNumber(QDataStream &stream, Number number, qint8 type)
+{
+ switch (type) {
+ case OneByte:
+ stream << static_cast<qint8>(number);
+ break;
+ case TwoByte:
+ stream << static_cast<qint16>(number);
+ break;
+ case FourByte:
+ stream << static_cast<qint32>(number);
+ break;
+ case EightByte:
+ stream << static_cast<qint64>(number);
+ break;
+ default:
+ Q_UNREACHABLE();
+ break;
+ }
+}
+
+QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEvent &event)
+{
+ qint8 type = minimumType(event.m_timestamp); // << TimestampOffset;
+ type |= minimumType(event.m_typeIndex) << TypeIndexOffset;
+ type |= minimumType(event.m_dataLength) << DataLengthOffset;
+ type |= minimumType(event, event.m_dataLength, event.m_dataType) << DataOffset;
+ stream << type;
+
+ writeNumber(stream, event.m_timestamp, (type >> TimestampOffset) & TypeMask);
+ writeNumber(stream, event.m_typeIndex, (type >> TypeIndexOffset) & TypeMask);
+ writeNumber(stream, event.m_dataLength, (type >> DataLengthOffset) & TypeMask);
+
+ switch ((type >> DataOffset) & TypeMask) {
+ case OneByte:
+ writeNumbers<qint8>(stream, event, event.m_dataLength);
+ break;
+ case TwoByte:
+ writeNumbers<qint16>(stream, event, event.m_dataLength);
+ break;
+ case FourByte:
+ writeNumbers<qint32>(stream, event, event.m_dataLength);
+ break;
+ case EightByte:
+ writeNumbers<qint64>(stream, event, event.m_dataLength);
+ break;
+ default:
+ Q_UNREACHABLE();
+ break;
+ }
+
+ return stream;
+}
+
+QT_END_NAMESPACE
diff --git a/src/qmldebug/qqmlprofilerevent_p.h b/src/qmldebug/qqmlprofilerevent_p.h
new file mode 100644
index 0000000000..49a0c9e347
--- /dev/null
+++ b/src/qmldebug/qqmlprofilerevent_p.h
@@ -0,0 +1,355 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QQMLPROFILEREVENT_P_H
+#define QQMLPROFILEREVENT_P_H
+
+#include <private/qqmlprofilerdefinitions_p.h>
+
+#include <QtCore/qstring.h>
+#include <QtCore/qbytearray.h>
+#include <QtCore/qvarlengtharray.h>
+#include <QtCore/qmetatype.h>
+
+#include <initializer_list>
+#include <type_traits>
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+QT_BEGIN_NAMESPACE
+
+struct QQmlProfilerEvent : public QQmlProfilerDefinitions {
+ QQmlProfilerEvent() :
+ m_timestamp(-1), m_typeIndex(-1), m_dataType(Inline8Bit), m_dataLength(0)
+ {}
+
+ template<typename Number>
+ QQmlProfilerEvent(qint64 timestamp, int typeIndex, std::initializer_list<Number> list)
+ : m_timestamp(timestamp), m_typeIndex(typeIndex)
+ {
+ assignNumbers<std::initializer_list<Number>, Number>(list);
+ }
+
+ QQmlProfilerEvent(qint64 timestamp, int typeIndex, const QString &data)
+ : m_timestamp(timestamp), m_typeIndex(typeIndex)
+ {
+ assignNumbers<QByteArray, qint8>(data.toUtf8());
+ }
+
+ template<typename Number>
+ QQmlProfilerEvent(qint64 timestamp, int typeIndex, const QVector<Number> &data)
+ : m_timestamp(timestamp), m_typeIndex(typeIndex)
+ {
+ assignNumbers<QVector<Number>, Number>(data);
+ }
+
+ QQmlProfilerEvent(const QQmlProfilerEvent &other)
+ : m_timestamp(other.m_timestamp), m_typeIndex(other.m_typeIndex),
+ m_dataType(other.m_dataType), m_dataLength(other.m_dataLength)
+ {
+ assignData(other);
+ }
+
+ QQmlProfilerEvent(QQmlProfilerEvent &&other)
+ {
+ memcpy(static_cast<void *>(this), static_cast<const void *>(&other), sizeof(QQmlProfilerEvent));
+ other.m_dataType = Inline8Bit; // prevent dtor from deleting the pointer
+ }
+
+ QQmlProfilerEvent &operator=(const QQmlProfilerEvent &other)
+ {
+ if (this != &other) {
+ clearPointer();
+ m_timestamp = other.m_timestamp;
+ m_typeIndex = other.m_typeIndex;
+ m_dataType = other.m_dataType;
+ m_dataLength = other.m_dataLength;
+ assignData(other);
+ }
+ return *this;
+ }
+
+ QQmlProfilerEvent &operator=(QQmlProfilerEvent &&other)
+ {
+ if (this != &other) {
+ memcpy(static_cast<void *>(this), static_cast<const void *>(&other), sizeof(QQmlProfilerEvent));
+ other.m_dataType = Inline8Bit;
+ }
+ return *this;
+ }
+
+ ~QQmlProfilerEvent()
+ {
+ clearPointer();
+ }
+
+ qint64 timestamp() const { return m_timestamp; }
+ void setTimestamp(qint64 timestamp) { m_timestamp = timestamp; }
+
+ int typeIndex() const { return m_typeIndex; }
+ void setTypeIndex(int typeIndex) { m_typeIndex = typeIndex; }
+
+ template<typename Number>
+ Number number(int i) const
+ {
+ // Trailing zeroes can be omitted, for example for SceneGraph events
+ if (i >= m_dataLength)
+ return 0;
+ switch (m_dataType) {
+ case Inline8Bit:
+ return m_data.internal8bit[i];
+QT_WARNING_PUSH
+QT_WARNING_DISABLE_GCC("-Warray-bounds") // Mingw 5.3 gcc doesn't get the type/length logic.
+ case Inline16Bit:
+ return m_data.internal16bit[i];
+ case Inline32Bit:
+ return m_data.internal32bit[i];
+ case Inline64Bit:
+ return m_data.internal64bit[i];
+QT_WARNING_POP
+ case External8Bit:
+ return static_cast<const qint8 *>(m_data.external)[i];
+ case External16Bit:
+ return static_cast<const qint16 *>(m_data.external)[i];
+ case External32Bit:
+ return static_cast<const qint32 *>(m_data.external)[i];
+ case External64Bit:
+ return static_cast<const qint64 *>(m_data.external)[i];
+ default:
+ return 0;
+ }
+ }
+
+ template<typename Number>
+ void setNumber(int i, Number number)
+ {
+ QVarLengthArray<Number> nums = numbers<QVarLengthArray<Number>, Number>();
+ int prevSize = nums.size();
+ if (i >= prevSize) {
+ nums.resize(i + 1);
+ // Fill with zeroes. We don't want to accidentally prevent squeezing.
+ while (prevSize < i)
+ nums[prevSize++] = 0;
+ }
+ nums[i] = number;
+ setNumbers<QVarLengthArray<Number>, Number>(nums);
+ }
+
+ template<typename Container, typename Number>
+ void setNumbers(const Container &numbers)
+ {
+ clearPointer();
+ assignNumbers<Container, Number>(numbers);
+ }
+
+ template<typename Number>
+ void setNumbers(std::initializer_list<Number> numbers)
+ {
+ setNumbers<std::initializer_list<Number>, Number>(numbers);
+ }
+
+ template<typename Container, typename Number = qint64>
+ Container numbers() const
+ {
+ Container container;
+ for (int i = 0; i < m_dataLength; ++i)
+ container.append(number<Number>(i));
+ return container;
+ }
+
+ QString string() const
+ {
+ switch (m_dataType) {
+ case External8Bit:
+ return QString::fromUtf8(static_cast<const char *>(m_data.external), m_dataLength);
+ case Inline8Bit:
+ return QString::fromUtf8(m_data.internalChar, m_dataLength);
+ default:
+ Q_UNREACHABLE();
+ return QString();
+ }
+ }
+
+ void setString(const QString &data)
+ {
+ clearPointer();
+ assignNumbers<QByteArray, char>(data.toUtf8());
+ }
+
+ Message rangeStage() const
+ {
+ Q_ASSERT(m_dataType == Inline8Bit);
+ return static_cast<Message>(m_data.internal8bit[0]);
+ }
+
+ void setRangeStage(Message stage)
+ {
+ clearPointer();
+ m_dataType = Inline8Bit;
+ m_dataLength = 1;
+ m_data.internal8bit[0] = stage;
+ }
+
+ bool isValid() const
+ {
+ return m_timestamp != -1;
+ }
+
+private:
+ enum Type: quint16 {
+ External = 1,
+ Inline8Bit = 8,
+ External8Bit = Inline8Bit | External,
+ Inline16Bit = 16,
+ External16Bit = Inline16Bit | External,
+ Inline32Bit = 32,
+ External32Bit = Inline32Bit | External,
+ Inline64Bit = 64,
+ External64Bit = Inline64Bit | External
+ };
+
+ qint64 m_timestamp;
+
+ static const int s_internalDataLength = 8;
+ union {
+ void *external;
+ char internalChar [s_internalDataLength];
+ qint8 internal8bit [s_internalDataLength];
+ qint16 internal16bit[s_internalDataLength / 2];
+ qint32 internal32bit[s_internalDataLength / 4];
+ qint64 internal64bit[s_internalDataLength / 8];
+ } m_data;
+
+ qint32 m_typeIndex;
+ Type m_dataType;
+ quint16 m_dataLength;
+
+ void assignData(const QQmlProfilerEvent &other)
+ {
+ if (m_dataType & External) {
+ uint length = m_dataLength * (other.m_dataType / 8);
+ m_data.external = malloc(length);
+ memcpy(m_data.external, other.m_data.external, length);
+ } else {
+ memcpy(&m_data, &other.m_data, sizeof(m_data));
+ }
+ }
+
+ template<typename Big, typename Small>
+ bool squeezable(Big source)
+ {
+ return static_cast<Small>(source) == source;
+ }
+
+ template<typename Container, typename Number>
+ typename std::enable_if<(sizeof(Number) > 1), bool>::type
+ squeeze(const Container &numbers)
+ {
+ typedef typename QIntegerForSize<sizeof(Number) / 2>::Signed Small;
+ foreach (Number item, numbers) {
+ if (!squeezable<Number, Small>(item))
+ return false;
+ }
+ assignNumbers<Container, Small>(numbers);
+ return true;
+ }
+
+ template<typename Container, typename Number>
+ typename std::enable_if<(sizeof(Number) <= 1), bool>::type
+ squeeze(const Container &)
+ {
+ return false;
+ }
+
+ template<typename Container, typename Number>
+ void assignNumbers(const Container &numbers)
+ {
+ Number *data;
+ m_dataLength = squeezable<size_t, quint16>(static_cast<size_t>(numbers.size())) ?
+ static_cast<quint16>(numbers.size()) : std::numeric_limits<quint16>::max();
+ if (m_dataLength > sizeof(m_data) / sizeof(Number)) {
+ if (squeeze<Container, Number>(numbers))
+ return;
+ m_dataType = static_cast<Type>((sizeof(Number) * 8) | External);
+ m_data.external = malloc(m_dataLength * sizeof(Number));
+ data = static_cast<Number *>(m_data.external);
+ } else {
+ m_dataType = static_cast<Type>(sizeof(Number) * 8);
+ data = static_cast<Number *>(m_dataType & External ? m_data.external : &m_data);
+ }
+ quint16 i = 0;
+ for (Number item : numbers) {
+ if (i >= m_dataLength)
+ break;
+ data[i++] = item;
+ }
+ }
+
+ void clearPointer()
+ {
+ if (m_dataType & External)
+ free(m_data.external);
+ }
+
+ friend QDataStream &operator>>(QDataStream &stream, QQmlProfilerEvent &event);
+ friend QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEvent &event);
+};
+
+bool operator==(const QQmlProfilerEvent &event1, const QQmlProfilerEvent &event2);
+bool operator!=(const QQmlProfilerEvent &event1, const QQmlProfilerEvent &event2);
+
+QDataStream &operator>>(QDataStream &stream, QQmlProfilerEvent &event);
+QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEvent &event);
+
+Q_DECLARE_TYPEINFO(QQmlProfilerEvent, Q_MOVABLE_TYPE);
+
+QT_END_NAMESPACE
+
+Q_DECLARE_METATYPE(QQmlProfilerEvent)
+
+#endif // QQMLPROFILEREVENT_P_H
diff --git a/src/qmldebug/qqmlprofilereventlocation.cpp b/src/qmldebug/qqmlprofilereventlocation.cpp
new file mode 100644
index 0000000000..8be44c17a3
--- /dev/null
+++ b/src/qmldebug/qqmlprofilereventlocation.cpp
@@ -0,0 +1,56 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qqmlprofilereventlocation_p.h"
+
+#include <QtCore/qdatastream.h>
+
+QT_BEGIN_NAMESPACE
+
+QDataStream &operator>>(QDataStream &stream, QQmlProfilerEventLocation &location)
+{
+ return stream >> location.m_filename >> location.m_line >> location.m_column;
+}
+
+QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEventLocation &location)
+{
+ return stream << location.m_filename << location.m_line << location.m_column;
+}
+
+QT_END_NAMESPACE
diff --git a/src/qmldebug/qqmlprofilereventlocation_p.h b/src/qmldebug/qqmlprofilereventlocation_p.h
new file mode 100644
index 0000000000..6f37eab14b
--- /dev/null
+++ b/src/qmldebug/qqmlprofilereventlocation_p.h
@@ -0,0 +1,121 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QQMLPROFILEREVENTLOCATION_P_H
+#define QQMLPROFILEREVENTLOCATION_P_H
+
+#include <QtCore/qstring.h>
+#include <QtCore/qhash.h>
+#include <QtCore/qdatastream.h>
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+QT_BEGIN_NAMESPACE
+
+class QQmlProfilerEventLocation
+{
+public:
+ QQmlProfilerEventLocation() : m_line(-1),m_column(-1) {}
+ QQmlProfilerEventLocation(const QString &file, int lineNumber, int columnNumber) :
+ m_filename(file), m_line(lineNumber), m_column(columnNumber)
+ {}
+
+ void clear()
+ {
+ m_filename.clear();
+ m_line = m_column = -1;
+ }
+
+ bool isValid() const
+ {
+ return !m_filename.isEmpty();
+ }
+
+ QString filename() const { return m_filename; }
+ int line() const { return m_line; }
+ int column() const { return m_column; }
+
+private:
+ friend QDataStream &operator>>(QDataStream &stream, QQmlProfilerEventLocation &location);
+ friend QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEventLocation &location);
+
+ QString m_filename;
+ int m_line;
+ int m_column;
+};
+
+inline bool operator==(const QQmlProfilerEventLocation &location1,
+ const QQmlProfilerEventLocation &location2)
+{
+ // compare filename last as it's expensive.
+ return location1.line() == location2.line() && location1.column() == location2.column()
+ && location1.filename() == location2.filename();
+}
+
+inline bool operator!=(const QQmlProfilerEventLocation &location1,
+ const QQmlProfilerEventLocation &location2)
+{
+ return !(location1 == location2);
+}
+
+inline uint qHash(const QQmlProfilerEventLocation &location)
+{
+ return qHash(location.filename())
+ ^ ((location.line() & 0xfff) // 12 bits of line number
+ | ((location.column() << 16) & 0xff0000)); // 8 bits of column
+
+}
+
+QDataStream &operator>>(QDataStream &stream, QQmlProfilerEventLocation &location);
+QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEventLocation &location);
+
+Q_DECLARE_TYPEINFO(QQmlProfilerEventLocation, Q_MOVABLE_TYPE);
+
+QT_END_NAMESPACE
+
+#endif // QQMLPROFILEREVENTLOCATION_P_H
diff --git a/src/qmldebug/qqmlprofilereventreceiver_p.h b/src/qmldebug/qqmlprofilereventreceiver_p.h
new file mode 100644
index 0000000000..defe64a42e
--- /dev/null
+++ b/src/qmldebug/qqmlprofilereventreceiver_p.h
@@ -0,0 +1,74 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QQMLPROFILEREVENTRECEIVER_P_H
+#define QQMLPROFILEREVENTRECEIVER_P_H
+
+#include "qqmlprofilerevent_p.h"
+#include "qqmlprofilereventtype_p.h"
+
+#include <QtCore/qobject.h>
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+QT_BEGIN_NAMESPACE
+
+class QQmlProfilerEventReceiver : public QObject
+{
+ Q_OBJECT
+public:
+ QQmlProfilerEventReceiver(QObject *parent = nullptr) : QObject(parent) {}
+
+ virtual int numLoadedEventTypes() const = 0;
+ virtual void addEventType(const QQmlProfilerEventType &type) = 0;
+ virtual void addEvent(const QQmlProfilerEvent &event) = 0;
+};
+
+QT_END_NAMESPACE
+
+#endif // QQMLPROFILEREVENTRECEIVER_P_H
diff --git a/src/qmldebug/qqmlprofilereventtype.cpp b/src/qmldebug/qqmlprofilereventtype.cpp
new file mode 100644
index 0000000000..b0aad3fc5b
--- /dev/null
+++ b/src/qmldebug/qqmlprofilereventtype.cpp
@@ -0,0 +1,92 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qqmlprofilereventtype_p.h"
+
+#include <QtCore/qdatastream.h>
+
+QT_BEGIN_NAMESPACE
+
+QDataStream &operator>>(QDataStream &stream, QQmlProfilerEventType &type)
+{
+ quint8 message;
+ quint8 rangeType;
+ stream >> type.m_displayName >> type.m_data >> type.m_location >> message >> rangeType
+ >> type.m_detailType;
+ type.m_message = static_cast<QQmlProfilerDefinitions::Message>(message);
+ type.m_rangeType = static_cast<QQmlProfilerDefinitions::RangeType>(rangeType);
+ return stream;
+}
+
+QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEventType &type)
+{
+ return stream << type.m_displayName << type.m_data << type.m_location
+ << static_cast<quint8>(type.m_message) << static_cast<quint8>(type.m_rangeType)
+ << type.m_detailType;
+}
+
+QQmlProfilerDefinitions::ProfileFeature QQmlProfilerEventType::feature() const
+{
+ switch (m_message) {
+ case Event: {
+ switch (m_detailType) {
+ case Mouse:
+ case Key:
+ return ProfileInputEvents;
+ case AnimationFrame:
+ return ProfileAnimations;
+ default:
+ return MaximumProfileFeature;
+ }
+ }
+ case PixmapCacheEvent:
+ return ProfilePixmapCache;
+ case SceneGraphFrame:
+ return ProfileSceneGraph;
+ case MemoryAllocation:
+ return ProfileMemory;
+ case DebugMessage:
+ return ProfileDebugMessages;
+ default:
+ return featureFromRangeType(m_rangeType);
+ }
+}
+
+
+QT_END_NAMESPACE
diff --git a/src/qmldebug/qqmlprofilereventtype_p.h b/src/qmldebug/qqmlprofilereventtype_p.h
new file mode 100644
index 0000000000..7bd67f9ca8
--- /dev/null
+++ b/src/qmldebug/qqmlprofilereventtype_p.h
@@ -0,0 +1,126 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QQMLPROFILEREVENTTYPE_P_H
+#define QQMLPROFILEREVENTTYPE_P_H
+
+#include "qqmlprofilereventlocation_p.h"
+
+#include <private/qqmlprofilerdefinitions_p.h>
+
+#include <QtCore/qstring.h>
+#include <QtCore/qmetatype.h>
+#include <QtCore/qhash.h>
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+QT_BEGIN_NAMESPACE
+
+class QQmlProfilerEventType : public QQmlProfilerDefinitions {
+public:
+ QQmlProfilerEventType(Message message = MaximumMessage, RangeType rangeType = MaximumRangeType,
+ int detailType = -1,
+ const QQmlProfilerEventLocation &location = QQmlProfilerEventLocation(),
+ const QString &data = QString(), const QString displayName = QString()) :
+ m_displayName(displayName), m_data(data), m_location(location), m_message(message),
+ m_rangeType(rangeType), m_detailType(detailType)
+ {}
+
+ void setDisplayName(const QString &displayName) { m_displayName = displayName; }
+ void setData(const QString &data) { m_data = data; }
+ void setLocation(const QQmlProfilerEventLocation &location) { m_location = location; }
+
+ ProfileFeature feature() const;
+ QString displayName() const { return m_displayName; }
+ QString data() const { return m_data; }
+ QQmlProfilerEventLocation location() const { return m_location; }
+ Message message() const { return m_message; }
+ RangeType rangeType() const { return m_rangeType; }
+ int detailType() const { return m_detailType; }
+
+private:
+ friend QDataStream &operator>>(QDataStream &stream, QQmlProfilerEventType &type);
+ friend QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEventType &type);
+
+ QString m_displayName;
+ QString m_data;
+ QQmlProfilerEventLocation m_location;
+ Message m_message;
+ RangeType m_rangeType;
+ int m_detailType; // can be EventType, BindingType, PixmapEventType or SceneGraphFrameType
+};
+
+QDataStream &operator>>(QDataStream &stream, QQmlProfilerEventType &type);
+QDataStream &operator<<(QDataStream &stream, const QQmlProfilerEventType &type);
+
+inline uint qHash(const QQmlProfilerEventType &type)
+{
+ return qHash(type.location())
+ ^ (((type.message() << 12) & 0xf000) // 4 bits message
+ | ((type.rangeType() << 24) & 0xf000000) // 4 bits rangeType
+ | ((static_cast<uint>(type.detailType()) << 28) & 0xf0000000)); // 4 bits detailType
+}
+
+inline bool operator==(const QQmlProfilerEventType &type1, const QQmlProfilerEventType &type2)
+{
+ return type1.message() == type2.message() && type1.rangeType() == type2.rangeType()
+ && type1.detailType() == type2.detailType() && type1.location() == type2.location();
+}
+
+inline bool operator!=(const QQmlProfilerEventType &type1, const QQmlProfilerEventType &type2)
+{
+ return !(type1 == type2);
+}
+
+Q_DECLARE_TYPEINFO(QQmlProfilerEventType, Q_MOVABLE_TYPE);
+
+QT_END_NAMESPACE
+
+Q_DECLARE_METATYPE(QQmlProfilerEventType)
+
+#endif // QQMLPROFILEREVENTTYPE_P_H
diff --git a/src/qmldebug/qqmlprofilertypedevent.cpp b/src/qmldebug/qqmlprofilertypedevent.cpp
new file mode 100644
index 0000000000..9b00481e17
--- /dev/null
+++ b/src/qmldebug/qqmlprofilertypedevent.cpp
@@ -0,0 +1,226 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQml module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qqmlprofilertypedevent_p.h"
+#include <QtCore/qvarlengtharray.h>
+
+QT_BEGIN_NAMESPACE
+
+QDataStream &operator>>(QDataStream &stream, QQmlProfilerTypedEvent &event)
+{
+ qint64 time;
+ qint32 messageType;
+ qint32 subtype;
+
+ stream >> time >> messageType;
+
+ if (messageType < 0 || messageType > QQmlProfilerDefinitions::MaximumMessage)
+ messageType = QQmlProfilerDefinitions::MaximumMessage;
+
+ QQmlProfilerDefinitions::RangeType rangeType = QQmlProfilerDefinitions::MaximumRangeType;
+ if (!stream.atEnd()) {
+ stream >> subtype;
+ rangeType = static_cast<QQmlProfilerDefinitions::RangeType>(subtype);
+ if (rangeType < 0 || rangeType > QQmlProfilerDefinitions::MaximumRangeType)
+ rangeType = QQmlProfilerDefinitions::MaximumRangeType;
+ } else {
+ subtype = -1;
+ }
+
+ event.event.setTimestamp(time > 0 ? time : 0);
+ event.event.setTypeIndex(-1);
+ event.serverTypeId = 0;
+
+ switch (messageType) {
+ case QQmlProfilerDefinitions::Event: {
+ event.type = QQmlProfilerEventType(
+ static_cast<QQmlProfilerDefinitions::Message>(messageType),
+ QQmlProfilerDefinitions::MaximumRangeType, subtype);
+ switch (subtype) {
+ case QQmlProfilerDefinitions::StartTrace:
+ case QQmlProfilerDefinitions::EndTrace: {
+ QVarLengthArray<qint32> engineIds;
+ while (!stream.atEnd()) {
+ qint32 id;
+ stream >> id;
+ engineIds << id;
+ }
+ event.event.setNumbers<QVarLengthArray<qint32>, qint32>(engineIds);
+ break;
+ }
+ case QQmlProfilerDefinitions::AnimationFrame: {
+ qint32 frameRate, animationCount;
+ qint32 threadId;
+ stream >> frameRate >> animationCount;
+ if (!stream.atEnd())
+ stream >> threadId;
+ else
+ threadId = 0;
+
+ event.event.setNumbers<qint32>({frameRate, animationCount, threadId});
+ break;
+ }
+ case QQmlProfilerDefinitions::Mouse:
+ case QQmlProfilerDefinitions::Key:
+ int inputType = (subtype == QQmlProfilerDefinitions::Key
+ ? QQmlProfilerDefinitions::InputKeyUnknown
+ : QQmlProfilerDefinitions::InputMouseUnknown);
+ if (!stream.atEnd())
+ stream >> inputType;
+ qint32 a = -1;
+ if (!stream.atEnd())
+ stream >> a;
+ qint32 b = -1;
+ if (!stream.atEnd())
+ stream >> b;
+
+ event.event.setNumbers<qint32>({inputType, a, b});
+ break;
+ }
+
+ break;
+ }
+ case QQmlProfilerDefinitions::Complete: {
+ event.type = QQmlProfilerEventType(
+ static_cast<QQmlProfilerDefinitions::Message>(messageType),
+ QQmlProfilerDefinitions::MaximumRangeType, subtype);
+ break;
+ }
+ case QQmlProfilerDefinitions::SceneGraphFrame: {
+ QVarLengthArray<qint64> params;
+ qint64 param;
+
+ while (!stream.atEnd()) {
+ stream >> param;
+ params.push_back(param);
+ }
+
+ event.type = QQmlProfilerEventType(
+ static_cast<QQmlProfilerDefinitions::Message>(messageType),
+ QQmlProfilerDefinitions::MaximumRangeType, subtype);
+ event.event.setNumbers<QVarLengthArray<qint64>, qint64>(params);
+ break;
+ }
+ case QQmlProfilerDefinitions::PixmapCacheEvent: {
+ qint32 width = 0, height = 0, refcount = 0;
+ QString filename;
+ stream >> filename;
+ if (subtype == QQmlProfilerDefinitions::PixmapReferenceCountChanged
+ || subtype == QQmlProfilerDefinitions::PixmapCacheCountChanged) {
+ stream >> refcount;
+ } else if (subtype == QQmlProfilerDefinitions::PixmapSizeKnown) {
+ stream >> width >> height;
+ refcount = 1;
+ }
+
+ event.type = QQmlProfilerEventType(
+ static_cast<QQmlProfilerDefinitions::Message>(messageType),
+ QQmlProfilerDefinitions::MaximumRangeType, subtype,
+ QQmlProfilerEventLocation(filename, 0, 0));
+ event.event.setNumbers<qint32>({width, height, refcount});
+ break;
+ }
+ case QQmlProfilerDefinitions::MemoryAllocation: {
+ qint64 delta;
+ stream >> delta;
+
+ event.type = QQmlProfilerEventType(
+ static_cast<QQmlProfilerDefinitions::Message>(messageType),
+ QQmlProfilerDefinitions::MaximumRangeType, subtype);
+ event.event.setNumbers<qint64>({delta});
+ break;
+ }
+ case QQmlProfilerDefinitions::RangeStart: {
+ if (!stream.atEnd()) {
+ qint64 typeId;
+ stream >> typeId;
+ if (stream.status() == QDataStream::Ok)
+ event.serverTypeId = typeId;
+ // otherwise it's the old binding type of 4 bytes
+ }
+
+ event.type = QQmlProfilerEventType(QQmlProfilerDefinitions::MaximumMessage, rangeType, -1);
+ event.event.setRangeStage(QQmlProfilerDefinitions::RangeStart);
+ break;
+ }
+ case QQmlProfilerDefinitions::RangeData: {
+ QString data;
+ stream >> data;
+
+ event.type = QQmlProfilerEventType(QQmlProfilerDefinitions::MaximumMessage, rangeType, -1,
+ QQmlProfilerEventLocation(), data);
+ event.event.setRangeStage(QQmlProfilerDefinitions::RangeData);
+ if (!stream.atEnd())
+ stream >> event.serverTypeId;
+ break;
+ }
+ case QQmlProfilerDefinitions::RangeLocation: {
+ QString filename;
+ qint32 line = 0;
+ qint32 column = 0;
+ stream >> filename >> line;
+
+ if (!stream.atEnd()) {
+ stream >> column;
+ if (!stream.atEnd())
+ stream >> event.serverTypeId;
+ }
+
+ event.type = QQmlProfilerEventType(QQmlProfilerDefinitions::MaximumMessage, rangeType, -1,
+ QQmlProfilerEventLocation(filename, line, column));
+ event.event.setRangeStage(QQmlProfilerDefinitions::RangeLocation);
+ break;
+ }
+ case QQmlProfilerDefinitions::RangeEnd: {
+ event.type = QQmlProfilerEventType(QQmlProfilerDefinitions::MaximumMessage, rangeType, -1);
+ event.event.setRangeStage(QQmlProfilerDefinitions::RangeEnd);
+ break;
+ }
+ default:
+ event.event.setNumbers<char>({});
+ event.type = QQmlProfilerEventType(
+ static_cast<QQmlProfilerDefinitions::Message>(messageType),
+ QQmlProfilerDefinitions::MaximumRangeType, subtype);
+ break;
+ }
+
+ return stream;
+}
+
+QT_END_NAMESPACE
diff --git a/src/qmldebug/qqmleventlocation_p.h b/src/qmldebug/qqmlprofilertypedevent_p.h
index c3a2b93f0f..e7e947f2ef 100644
--- a/src/qmldebug/qqmleventlocation_p.h
+++ b/src/qmldebug/qqmlprofilertypedevent_p.h
@@ -1,6 +1,6 @@
/****************************************************************************
**
-** Copyright (C) 2016 The Qt Company Ltd.
+** Copyright (C) 2017 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
** This file is part of the QtQml module of the Qt Toolkit.
@@ -37,10 +37,13 @@
**
****************************************************************************/
-#ifndef QQMLEVENTLOCATION_P_H
-#define QQMLEVENTLOCATION_P_H
+#ifndef QQMLPROFILERTYPEDEVENT_P_H
+#define QQMLPROFILERTYPEDEVENT_P_H
-#include <QtCore/qstring.h>
+#include "qqmlprofilerevent_p.h"
+#include "qqmlprofilereventtype_p.h"
+
+#include <QtCore/qdatastream.h>
//
// W A R N I N G
@@ -55,19 +58,19 @@
QT_BEGIN_NAMESPACE
-struct QQmlEventLocation
+struct QQmlProfilerTypedEvent
{
- QQmlEventLocation() : line(-1), column(-1) {}
- QQmlEventLocation(const QString &file, int lineNumber, int columnNumber) :
- filename(file), line(lineNumber), column(columnNumber) {}
-
- QString filename;
- int line;
- int column;
+ QQmlProfilerEvent event;
+ QQmlProfilerEventType type;
+ qint64 serverTypeId = 0;
};
-Q_DECLARE_TYPEINFO(QQmlEventLocation, Q_MOVABLE_TYPE);
+QDataStream &operator>>(QDataStream &stream, QQmlProfilerTypedEvent &event);
+
+Q_DECLARE_TYPEINFO(QQmlProfilerTypedEvent, Q_MOVABLE_TYPE);
QT_END_NAMESPACE
-#endif // QQMLEVENTLOCATION_P_H
+Q_DECLARE_METATYPE(QQmlProfilerTypedEvent)
+
+#endif // QQMLPROFILERTYPEDEVENT_P_H
diff --git a/src/qmldevtools/qmldevtools.pro b/src/qmldevtools/qmldevtools.pro
index 5ee97776b8..23b7cf651e 100644
--- a/src/qmldevtools/qmldevtools.pro
+++ b/src/qmldevtools/qmldevtools.pro
@@ -4,6 +4,7 @@ QT = core-private
CONFIG += minimal_syncqt internal_module qmldevtools_build
MODULE_INCNAME = QtQml
+INCLUDEPATH += $$OUT_PWD/../qml
# 2415: variable "xx" of static storage duration was declared but never referenced
# unused variable 'xx' [-Werror,-Wunused-const-variable]
diff --git a/src/qmltest/doc/qtqmltest.qdocconf b/src/qmltest/doc/qtqmltest.qdocconf
new file mode 100644
index 0000000000..33e8ae334c
--- /dev/null
+++ b/src/qmltest/doc/qtqmltest.qdocconf
@@ -0,0 +1,42 @@
+include($QT_INSTALL_DOCS/global/qt-module-defaults.qdocconf)
+
+project = QtQmlTest
+description = Qt Quick Test Reference Documentation
+version = $QT_VERSION
+moduleheader = QtQuickTest
+qhp.projects = QtQmlTest
+
+qhp.QtQmlTest.file = qtqmltest.qhp
+qhp.QtQmlTest.namespace = org.qt-project.qtqmltest.$QT_VERSION_TAG
+qhp.QtQmlTest.virtualFolder = qtqmltest
+qhp.QtQmlTest.indexTitle = Qt Quick Test
+qhp.QtQmlTest.indexRoot =
+
+qhp.QtQmlTest.filterAttributes = qtqmltest $QT_VERSION qtrefdoc
+qhp.QtQmlTest.customFilters.Qt.name = QtQmlTest $QT_VERSION
+qhp.QtQmlTest.customFilters.Qt.filterAttributes = qtqmltest $QT_VERSION
+qhp.QtQmlTest.subprojects = qmltypes classes examples
+qhp.QtQmlTest.subprojects.classes.title = C++ Classes
+qhp.QtQmlTest.subprojects.classes.indexTitle = Qt Quick Test C++ Classes
+qhp.QtQmlTest.subprojects.classes.selectors = class doc:headerfile
+qhp.QtQmlTest.subprojects.classes.sortPages = true
+qhp.QtQmlTest.subprojects.examples.title = Examples
+qhp.QtQmlTest.subprojects.examples.indexTitle = Qt Quick Test Examples
+qhp.QtQmlTest.subprojects.examples.selectors = doc:example
+qhp.QtQmlTest.subprojects.qmltypes.title = QML Types
+qhp.QtQmlTest.subprojects.qmltypes.indexTitle = Qt Quick Test QML Types
+qhp.QtQmlTest.subprojects.qmltypes.selectors = qmlclass
+qhp.QtQmlTest.subprojects.qmltypes.sortPages = true
+
+
+tagfile = ../../../doc/qtqmltest/qtqmltest.tags
+
+depends += qtcore qtxmlpatterns qtgui qttestlib qtqml qtquick qtdoc
+
+headerdirs += ..
+
+sourcedirs += ..
+
+navigation.landingpage = "Qt Quick Test"
+navigation.cppclassespage = "Qt Quick Test C++ Classes"
+navigation.qmltypespage = "Qt Quick Test QML Types"
diff --git a/src/qmltest/doc/src/qtquicktest-index.qdoc b/src/qmltest/doc/src/qtquicktest-index.qdoc
new file mode 100644
index 0000000000..6b5f8fdf4c
--- /dev/null
+++ b/src/qmltest/doc/src/qtquicktest-index.qdoc
@@ -0,0 +1,185 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the documentation of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:FDL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Free Documentation License Usage
+** Alternatively, this file may be used under the terms of the GNU Free
+** Documentation License version 1.3 as published by the Free Software
+** Foundation and appearing in the file included in the packaging of
+** this file. Please review the following information to ensure
+** the GNU Free Documentation License version 1.3 requirements
+** will be met: https://www.gnu.org/licenses/fdl-1.3.html.
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+/*!
+ \page qtquicktest-index.html
+ \title Qt Quick Test
+ \brief Unit testing framework for QML.
+
+ \section1 Introduction
+
+ \l {Qt Quick Test QML Types}{Qt Quick Test} is a unit test framework for QML applications.
+ Test cases are written as JavaScript functions within a \l [QML] TestCase
+ type:
+
+ \qml
+ import QtQuick 2.3
+ import QtTest 1.0
+
+ TestCase {
+ name: "MathTests"
+
+ function test_math() {
+ compare(2 + 2, 4, "2 + 2 = 4")
+ }
+
+ function test_fail() {
+ compare(2 + 2, 5, "2 + 2 = 5")
+ }
+ }
+ \endqml
+
+ Functions whose names start with \c{test_} are treated as test cases
+ to be executed. See the documentation for the \l [QML] TestCase and
+ \l [QML] SignalSpy types for more information on writing test cases.
+
+ \section1 Running Tests
+
+ Test cases are launched by a C++ harness that consists of
+ the following code:
+
+ \code
+ #include <QtQuickTest/quicktest.h>
+ QUICK_TEST_MAIN(example)
+ \endcode
+
+ Where "example" is the identifier to use to uniquely identify
+ this set of tests. Finally, add \c{CONFIG += qmltestcase} to the project
+ file:
+
+ \badcode
+ TEMPLATE = app
+ TARGET = tst_example
+ CONFIG += warn_on qmltestcase
+ SOURCES += tst_example.cpp
+ \endcode
+
+ The test harness scans the specified source directory recursively
+ for "tst_*.qml" files. If \c{QUICK_TEST_SOURCE_DIR} is not defined,
+ then the current directory will be scanned when the harness is run.
+ Other *.qml files may appear for auxillary QML components that are
+ used by the test.
+
+ The \c{-input} command-line option can be set at runtime to run
+ test cases from a different directory. This may be needed to run
+ tests on a target device where the compiled-in directory name refers
+ to a host. For example:
+
+ \badcode
+ tst_example -input /mnt/SDCard/qmltests
+ \endcode
+
+ It is also possible to run a single file using the \c{-input} option.
+ For example:
+
+ \badcode
+ tst_example -input data/test.qml
+ \endcode
+
+ \badcode
+ tst_example -input <full_path>/test.qml
+ \endcode
+
+ \note Specifying the full path to the qml test file is for example
+ needed for shadow builds.
+
+ If your test case needs QML imports, then you can add them as
+ \c{-import} options to the test program command-line.
+
+ If \c IMPORTPATH is specified in your .pro file, each import path added to \c IMPORTPATH
+ will be passed as a command-line argument when the test is run using "make check":
+
+ \badcode
+ IMPORTPATH += $$PWD/../imports/my_module1 $$PWD/../imports/my_module2
+ \endcode
+
+ The \c{-functions} command-line option will return a list of the current
+ tests functions. It is possible to run a single test function using the name
+ of the test function as an argument. For example:
+
+ \badcode
+ tst_example Test_Name::function1
+ \endcode
+
+ The \c{-help} command-line option will return all the options available.
+
+ \badcode
+ tst_example -help
+ \endcode
+
+ \section1 Executing C++ Before QML Tests
+
+ To execute C++ code before any of the QML tests are run, the
+ \c QUICK_TEST_MAIN_WITH_SETUP macro can be used. This can be useful for
+ setting context properties on the QML engine, amongst other things.
+
+ The macro is identical to \l QUICK_TEST_MAIN, except that it takes an
+ additional \c QObject* argument. The test framework will call slots and
+ invokable functions with the following names:
+
+ \table
+ \header
+ \li Name
+ \li Purpose
+ \row
+ \li void qmlEngineAvailable(QQmlEngine*)
+ \li Called when the QML engine is available.
+ Any \l {QQmlEngine::addImportPath}{import paths},
+ \l {QQmlEngine::addPluginPath}{plugin paths},
+ and \l {QQmlFileSelector::setExtraSelectors}{extra file selectors}
+ will have been set on the engine by this point.
+ \endtable
+
+ Each function will be called once for each \c tst_*.qml file, so any
+ arguments are unique to that test. For example, this means that each QML
+ test file will have its own QML engine.
+
+ The following example demonstrates how the macro can be used to set context
+ properties on the QML engine:
+
+ \code
+ #include <QtQuickTest>
+ #include <QQmlEngine>
+ #include <QQmlContext>
+
+ class Setup : public QObject
+ {
+ public:
+ Setup() {}
+
+ public slots:
+ void qmlEngineAvailable(QQmlEngine *engine)
+ {
+ engine->rootContext()->setContextProperty("myContextProperty", QVariant(true));
+ }
+ };
+
+ QUICK_TEST_MAIN_WITH_SETUP(mytest, Setup)
+
+ #include "tst_mytest.moc"
+ \endcode
+*/
diff --git a/src/qmltest/qmltest.pro b/src/qmltest/qmltest.pro
index 48546d5f64..e2200e5abb 100644
--- a/src/qmltest/qmltest.pro
+++ b/src/qmltest/qmltest.pro
@@ -1,5 +1,7 @@
TARGET = QtQuickTest
+QMAKE_DOCS = $$PWD/doc/qtqmltest.qdocconf
+
DEFINES += QT_NO_URL_CAST_FROM_STRING QT_NO_FOREACH
QT = core testlib-private
QT_PRIVATE = quick qml-private gui core-private gui-private
@@ -13,12 +15,6 @@ qtHaveModule(widgets) {
DEFINES += QT_QMLTEST_WITH_WIDGETS
}
-# Install qmltestcase.prf into the Qt mkspecs so that "CONFIG += qmltestcase"
-# can be used in customer applications to build against QtQuickTest.
-feature.path = $$[QT_INSTALL_DATA]/mkspecs/features
-feature.files = $$PWD/features/qmltestcase.prf
-INSTALLS += feature
-
SOURCES += \
$$PWD/quicktest.cpp \
$$PWD/quicktestevent.cpp \
diff --git a/src/qmltest/quicktest.cpp b/src/qmltest/quicktest.cpp
index 3cd1694dd0..a02a0a806d 100644
--- a/src/qmltest/quicktest.cpp
+++ b/src/qmltest/quicktest.cpp
@@ -62,6 +62,7 @@
#include <QtGui/QGuiApplication>
#include <QtCore/QTranslator>
#include <QtTest/QSignalSpy>
+#include <QtQml/QQmlFileSelector>
#include <private/qqmlcomponent_p.h>
@@ -78,7 +79,7 @@ class QTestRootObject : public QObject
Q_PROPERTY(bool hasTestCase READ hasTestCase WRITE setHasTestCase NOTIFY hasTestCaseChanged)
Q_PROPERTY(QObject *defined READ defined)
public:
- QTestRootObject(QObject *parent = 0)
+ QTestRootObject(QObject *parent = nullptr)
: QObject(parent), hasQuit(false), m_windowShown(false), m_hasTestCase(false) {
m_defined = new QQmlPropertyMap(this);
#if defined(QT_OPENGL_ES_2_ANGLE)
@@ -190,7 +191,7 @@ bool qWaitForSignal(QObject *obj, const char* signal, int timeout = 5000)
if (remaining <= 0)
break;
QCoreApplication::processEvents(QEventLoop::AllEvents, remaining);
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
+ QCoreApplication::sendPostedEvents(nullptr, QEvent::DeferredDelete);
QTest::qSleep(10);
}
@@ -326,6 +327,11 @@ private:
int quick_test_main(int argc, char **argv, const char *name, const char *sourceDir)
{
+ return quick_test_main_with_setup(argc, argv, name, sourceDir, nullptr);
+}
+
+int quick_test_main_with_setup(int argc, char **argv, const char *name, const char *sourceDir, QObject *setup)
+{
// Peek at arguments to check for '-widgets' argument
#ifdef QT_QMLTEST_WITH_WIDGETS
bool withWidgets = false;
@@ -337,7 +343,7 @@ int quick_test_main(int argc, char **argv, const char *name, const char *sourceD
}
#endif
- QCoreApplication *app = 0;
+ QCoreApplication *app = nullptr;
if (!QCoreApplication::instance()) {
#ifdef QT_QMLTEST_WITH_WIDGETS
if (withWidgets)
@@ -354,10 +360,12 @@ int quick_test_main(int argc, char **argv, const char *name, const char *sourceD
// -plugins dir Specify a directory where to search for plugins.
// -input dir Specify the input directory for test cases.
// -translation file Specify the translation file.
+ // -file-selector Specify a file selector
QStringList imports;
QStringList pluginPaths;
QString testPath;
QString translationFile;
+ QStringList fileSelectors;
int index = 1;
QScopedArrayPointer<char *> testArgV(new char *[argc + 1]);
testArgV[0] = argv[0];
@@ -382,6 +390,9 @@ int quick_test_main(int argc, char **argv, const char *name, const char *sourceD
} else if (strcmp(argv[index], "-translation") == 0 && (index + 1) < argc) {
translationFile = stripQuotes(QString::fromLocal8Bit(argv[index + 1]));
index += 2;
+ } else if (strcmp(argv[index], "-file-selector") == 0 && (index + 1) < argc) {
+ fileSelectors += stripQuotes(QString::fromLocal8Bit(argv[index + 1]));
+ index += 2;
} else {
testArgV[testArgC++] = argv[index++];
}
@@ -474,6 +485,11 @@ int quick_test_main(int argc, char **argv, const char *name, const char *sourceD
for (const QString &path : qAsConst(pluginPaths))
engine.addPluginPath(path);
+ if (!fileSelectors.isEmpty()) {
+ QQmlFileSelector* const qmlFileSelector = new QQmlFileSelector(&engine, &engine);
+ qmlFileSelector->setExtraSelectors(fileSelectors);
+ }
+
TestCaseCollector testCaseCollector(fi, &engine);
if (!testCaseCollector.errors().isEmpty()) {
for (const QQmlError &error : testCaseCollector.errors())
@@ -505,6 +521,14 @@ int quick_test_main(int argc, char **argv, const char *name, const char *sourceD
view.rootContext()->setContextProperty
(QLatin1String("qtest"), QTestRootObject::instance()); // Deprecated. Use QTestRootObject from Qt.test.qtestroot instead
+ // Do this down here so that import paths, plugin paths,
+ // file selectors, etc. are available in case the user needs access to them.
+ if (setup) {
+ // Don't check the return value; it's OK if it doesn't exist.
+ // If we add more callbacks in the future, it makes sense if the user only implements one of them.
+ QMetaObject::invokeMethod(setup, "qmlEngineAvailable", Q_ARG(QQmlEngine*, view.engine()));
+ }
+
view.setObjectName(fi.baseName());
view.setTitle(view.objectName());
QTestRootObject::instance()->init();
@@ -553,7 +577,7 @@ int quick_test_main(int argc, char **argv, const char *name, const char *sourceD
}
// Flush the current logging stream.
- QuickTestResult::setProgramName(0);
+ QuickTestResult::setProgramName(nullptr);
delete app;
// Return the number of failures as the exit code.
diff --git a/src/qmltest/quicktest.h b/src/qmltest/quicktest.h
index 6486accb9e..62ed749722 100644
--- a/src/qmltest/quicktest.h
+++ b/src/qmltest/quicktest.h
@@ -48,6 +48,7 @@ QT_BEGIN_NAMESPACE
QTEST_ADD_GPU_BLACKLIST_SUPPORT_DEFS
Q_QUICK_TEST_EXPORT int quick_test_main(int argc, char **argv, const char *name, const char *sourceDir);
+Q_QUICK_TEST_EXPORT int quick_test_main_with_setup(int argc, char **argv, const char *name, const char *sourceDir, QObject *setup);
#ifdef QUICK_TEST_SOURCE_DIR
@@ -67,6 +68,15 @@ Q_QUICK_TEST_EXPORT int quick_test_main(int argc, char **argv, const char *name,
return quick_test_main(argc, argv, #name, QUICK_TEST_SOURCE_DIR); \
}
+#define QUICK_TEST_MAIN_WITH_SETUP(name, QuickTestSetupClass) \
+ int main(int argc, char **argv) \
+ { \
+ QTEST_ADD_GPU_BLACKLIST_SUPPORT \
+ QTEST_SET_MAIN_SOURCE_PATH \
+ QuickTestSetupClass setup; \
+ return quick_test_main_with_setup(argc, argv, #name, QUICK_TEST_SOURCE_DIR, &setup); \
+ }
+
#else
#define QUICK_TEST_MAIN(name) \
@@ -74,7 +84,7 @@ Q_QUICK_TEST_EXPORT int quick_test_main(int argc, char **argv, const char *name,
{ \
QTEST_ADD_GPU_BLACKLIST_SUPPORT \
QTEST_SET_MAIN_SOURCE_PATH \
- return quick_test_main(argc, argv, #name, 0); \
+ return quick_test_main(argc, argv, #name, nullptr); \
}
#define QUICK_TEST_OPENGL_MAIN(name) \
@@ -82,7 +92,16 @@ Q_QUICK_TEST_EXPORT int quick_test_main(int argc, char **argv, const char *name,
{ \
QTEST_ADD_GPU_BLACKLIST_SUPPORT \
QTEST_SET_MAIN_SOURCE_PATH \
- return quick_test_main(argc, argv, #name, 0); \
+ return quick_test_main(argc, argv, #name, nullptr); \
+ }
+
+#define QUICK_TEST_MAIN_WITH_SETUP(name, QuickTestSetupClass) \
+ int main(int argc, char **argv) \
+ { \
+ QTEST_ADD_GPU_BLACKLIST_SUPPORT \
+ QTEST_SET_MAIN_SOURCE_PATH \
+ QuickTestSetupClass setup; \
+ return quick_test_main_with_setup(argc, argv, #name, nullptr, &setup); \
}
#endif
diff --git a/src/qmltest/quicktestevent.cpp b/src/qmltest/quicktestevent.cpp
index 663d3c64e1..ee375a896c 100644
--- a/src/qmltest/quicktestevent.cpp
+++ b/src/qmltest/quicktestevent.cpp
@@ -121,6 +121,23 @@ bool QuickTestEvent::keyClickChar(const QString &character, int modifiers, int d
return true;
}
+// valueToKeySequence() is copied from qquickshortcut.cpp
+static QKeySequence valueToKeySequence(const QVariant &value)
+{
+ if (value.type() == QVariant::Int)
+ return QKeySequence(static_cast<QKeySequence::StandardKey>(value.toInt()));
+ return QKeySequence::fromString(value.toString());
+}
+
+bool QuickTestEvent::keySequence(const QVariant &keySequence)
+{
+ QWindow *window = activeWindow();
+ if (!window)
+ return false;
+ QTest::keySequence(window, valueToKeySequence(keySequence));
+ return true;
+}
+
namespace QtQuickTest
{
enum MouseAction { MousePress, MouseRelease, MouseClick, MouseDoubleClick, MouseMove, MouseDoubleClickSequence };
@@ -173,7 +190,7 @@ namespace QtQuickTest
me.setTimestamp(++lastMouseTimestamp);
break;
case MouseRelease:
- me = QMouseEvent(QEvent::MouseButtonRelease, pos, window->mapToGlobal(pos), button, 0, stateKey);
+ me = QMouseEvent(QEvent::MouseButtonRelease, pos, window->mapToGlobal(pos), button, nullptr, stateKey);
me.setTimestamp(++lastMouseTimestamp);
lastMouseTimestamp += 500; // avoid double clicks being generated
break;
@@ -338,7 +355,7 @@ QWindow *QuickTestEvent::eventWindow(QObject *item)
QQuickItem *testParentitem = qobject_cast<QQuickItem *>(parent());
if (testParentitem)
return testParentitem->window();
- return 0;
+ return nullptr;
}
QWindow *QuickTestEvent::activeWindow()
diff --git a/src/qmltest/quicktestevent_p.h b/src/qmltest/quicktestevent_p.h
index 89065b8880..f33f339cdd 100644
--- a/src/qmltest/quicktestevent_p.h
+++ b/src/qmltest/quicktestevent_p.h
@@ -81,8 +81,8 @@ class Q_QUICK_TEST_EXPORT QuickTestEvent : public QObject
Q_OBJECT
Q_PROPERTY(int defaultMouseDelay READ defaultMouseDelay FINAL)
public:
- QuickTestEvent(QObject *parent = 0);
- ~QuickTestEvent();
+ QuickTestEvent(QObject *parent = nullptr);
+ ~QuickTestEvent() override;
int defaultMouseDelay() const;
public Q_SLOTS:
@@ -94,6 +94,8 @@ public Q_SLOTS:
bool keyReleaseChar(const QString &character, int modifiers, int delay);
bool keyClickChar(const QString &character, int modifiers, int delay);
+ Q_REVISION(2) bool keySequence(const QVariant &keySequence);
+
bool mousePress(QObject *item, qreal x, qreal y, int button,
int modifiers, int delay);
bool mouseRelease(QObject *item, qreal x, qreal y, int button,
@@ -113,7 +115,7 @@ public Q_SLOTS:
QQuickTouchEventSequence *touchEvent(QObject *item = nullptr);
private:
- QWindow *eventWindow(QObject *item = 0);
+ QWindow *eventWindow(QObject *item = nullptr);
QWindow *activeWindow();
QTouchDevice *touchDevice();
diff --git a/src/qmltest/quicktestresult.cpp b/src/qmltest/quicktestresult.cpp
index 8a2282f5c6..c4a3280cf6 100644
--- a/src/qmltest/quicktestresult.cpp
+++ b/src/qmltest/quicktestresult.cpp
@@ -73,7 +73,7 @@
QT_BEGIN_NAMESPACE
-static const char *globalProgramName = 0;
+static const char *globalProgramName = nullptr;
static bool loggingStarted = false;
static QBenchmarkGlobalData globalBenchmarkData;
@@ -88,7 +88,7 @@ class Q_QUICK_TEST_EXPORT QuickTestImageObject : public QObject
Q_PROPERTY(QSize size READ size CONSTANT)
public:
- QuickTestImageObject(const QImage& img, QObject *parent = 0)
+ QuickTestImageObject(const QImage& img, QObject *parent = nullptr)
: QObject(parent)
, m_image(img)
{
@@ -143,7 +143,7 @@ public Q_SLOTS:
QImageWriter writer(filePath);
if (!writer.write(m_image)) {
QQmlEngine *engine = qmlContext(this)->engine();
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine->handle());
+ QV4::ExecutionEngine *v4 = engine->handle();
v4->throwError(QStringLiteral("Can't save to %1: %2").arg(filePath, writer.errorString()));
}
}
@@ -172,9 +172,9 @@ class QuickTestResultPrivate
{
public:
QuickTestResultPrivate()
- : table(0)
- , benchmarkIter(0)
- , benchmarkData(0)
+ : table(nullptr)
+ , benchmarkIter(nullptr)
+ , benchmarkData(nullptr)
, iterCount(0)
{
}
@@ -261,10 +261,10 @@ void QuickTestResult::setFunctionName(const QString &name)
QString fullName = d->testCaseName + QLatin1String("::") + name;
QTestResult::setCurrentTestFunction
(d->intern(fullName).constData());
- QTestPrivate::checkBlackLists(fullName.toUtf8().constData(), 0);
+ QTestPrivate::checkBlackLists(fullName.toUtf8().constData(), nullptr);
}
} else {
- QTestResult::setCurrentTestFunction(0);
+ QTestResult::setCurrentTestFunction(nullptr);
}
d->functionName = name;
emit functionNameChanged();
@@ -293,7 +293,7 @@ void QuickTestResult::setDataTag(const QString &tag)
QTestPrivate::checkBlackLists((testCaseName() + QLatin1String("::") + functionName()).toUtf8().constData(), tag.toUtf8().constData());
emit dataTagChanged();
} else {
- QTestResult::setCurrentTestData(0);
+ QTestResult::setCurrentTestData(nullptr);
}
}
@@ -438,7 +438,7 @@ void QuickTestResult::clearTestTable()
{
Q_D(QuickTestResult);
delete d->table;
- d->table = 0;
+ d->table = nullptr;
}
void QuickTestResult::finishTestData()
@@ -745,7 +745,7 @@ void QuickTestResult::stopBenchmark()
{
Q_D(QuickTestResult);
delete d->benchmarkIter;
- d->benchmarkIter = 0;
+ d->benchmarkIter = nullptr;
}
QObject *QuickTestResult::grabImage(QQuickItem *item)
@@ -759,7 +759,7 @@ QObject *QuickTestResult::grabImage(QQuickItem *item)
QQmlEngine::setContextForObject(o, qmlContext(this));
return o;
}
- return 0;
+ return nullptr;
}
QObject *QuickTestResult::findChild(QObject *parent, const QString &objectName)
@@ -787,7 +787,7 @@ void QuickTestResult::setProgramName(const char *name)
} else if (!name && loggingStarted) {
QTestResult::setCurrentTestObject(globalProgramName);
QTestLog::stopLogging();
- QTestResult::setCurrentTestObject(0);
+ QTestResult::setCurrentTestObject(nullptr);
}
globalProgramName = name;
QTestResult::setCurrentTestObject(globalProgramName);
diff --git a/src/qmltest/quicktestresult_p.h b/src/qmltest/quicktestresult_p.h
index af13299ee5..6e7b72830e 100644
--- a/src/qmltest/quicktestresult_p.h
+++ b/src/qmltest/quicktestresult_p.h
@@ -77,8 +77,8 @@ class Q_QUICK_TEST_EXPORT QuickTestResult : public QObject
Q_PROPERTY(int skipCount READ skipCount)
Q_PROPERTY(QStringList functionsToRun READ functionsToRun)
public:
- QuickTestResult(QObject *parent = 0);
- ~QuickTestResult();
+ QuickTestResult(QObject *parent = nullptr);
+ ~QuickTestResult() override;
// Values must match QBenchmarkIterationController::RunMode.
enum RunMode
diff --git a/src/quick/accessible/qaccessiblequickitem.cpp b/src/quick/accessible/qaccessiblequickitem.cpp
index 2d6bb02af4..87e581384b 100644
--- a/src/quick/accessible/qaccessiblequickitem.cpp
+++ b/src/quick/accessible/qaccessiblequickitem.cpp
@@ -92,7 +92,7 @@ QAccessibleInterface *QAccessibleQuickItem::childAt(int x, int y) const
{
if (item()->clip()) {
if (!rect().contains(x, y))
- return 0;
+ return nullptr;
}
const QList<QQuickItem*> kids = accessibleUnignoredChildren(item(), true);
@@ -106,14 +106,14 @@ QAccessibleInterface *QAccessibleQuickItem::childAt(int x, int y) const
}
}
- return 0;
+ return nullptr;
}
QAccessibleInterface *QAccessibleQuickItem::parent() const
{
QQuickItem *parent = item()->parentItem();
QQuickWindow *window = item()->window();
- QQuickItem *ci = window ? window->contentItem() : 0;
+ QQuickItem *ci = window ? window->contentItem() : nullptr;
while (parent && !QQuickItemPrivate::get(parent)->isAccessible && parent != ci)
parent = parent->parentItem();
@@ -131,7 +131,7 @@ QAccessibleInterface *QAccessibleQuickItem::parent() const
return QAccessible::queryAccessibleInterface(parent);
}
}
- return 0;
+ return nullptr;
}
QAccessibleInterface *QAccessibleQuickItem::child(int index) const
@@ -139,7 +139,7 @@ QAccessibleInterface *QAccessibleQuickItem::child(int index) const
QList<QQuickItem *> children = childItems();
if (index < 0 || index >= children.count())
- return 0;
+ return nullptr;
QQuickItem *child = children.at(index);
return QAccessible::queryAccessibleInterface(child);
@@ -458,7 +458,7 @@ QTextDocument *QAccessibleQuickItem::textDocument() const
QQuickTextDocument *qqdoc = docVariant.value<QQuickTextDocument*>();
return qqdoc->textDocument();
}
- return 0;
+ return nullptr;
}
int QAccessibleQuickItem::characterCount() const
diff --git a/src/quick/accessible/qaccessiblequickview.cpp b/src/quick/accessible/qaccessiblequickview.cpp
index b3d1b6fc0f..3bb40546be 100644
--- a/src/quick/accessible/qaccessiblequickview.cpp
+++ b/src/quick/accessible/qaccessiblequickview.cpp
@@ -78,7 +78,7 @@ QAccessibleInterface *QAccessibleQuickWindow::child(int index) const
const QList<QQuickItem*> &kids = rootItems();
if (index >= 0 && index < kids.count())
return QAccessible::queryAccessibleInterface(kids.at(index));
- return 0;
+ return nullptr;
}
QAccessibleInterface *QAccessibleQuickWindow::focusChild() const
@@ -133,7 +133,7 @@ QAccessibleInterface *QAccessibleQuickWindow::childAt(int x, int y) const
return childIface;
}
}
- return 0;
+ return nullptr;
}
int QAccessibleQuickWindow::indexOfChild(const QAccessibleInterface *iface) const
diff --git a/src/quick/accessible/qquickaccessiblefactory.cpp b/src/quick/accessible/qquickaccessiblefactory.cpp
index a1fa695e5a..1aacf8e8bd 100644
--- a/src/quick/accessible/qquickaccessiblefactory.cpp
+++ b/src/quick/accessible/qquickaccessiblefactory.cpp
@@ -55,11 +55,11 @@ QAccessibleInterface *qQuickAccessibleFactory(const QString &classname, QObject
Q_ASSERT(item);
QQuickItemPrivate *itemPrivate = QQuickItemPrivate::get(item);
if (!itemPrivate->isAccessible)
- return 0;
+ return nullptr;
return new QAccessibleQuickItem(item);
}
- return 0;
+ return nullptr;
}
#endif
diff --git a/src/quick/configure.json b/src/quick/configure.json
index 65ad5b810b..7004ea7f7b 100644
--- a/src/quick/configure.json
+++ b/src/quick/configure.json
@@ -139,6 +139,14 @@
"privateFeature"
]
},
+ "quick-repeater": {
+ "label": "Repeater item",
+ "purpose": "Provides the Repeater item.",
+ "section": "Qt Quick",
+ "output": [
+ "privateFeature"
+ ]
+ },
"quick-shadereffect": {
"label": "ShaderEffect item",
"purpose": "Provides Shader effects.",
@@ -171,6 +179,7 @@
"quick-path",
"quick-pathview",
"quick-positioners",
+ "quick-repeater",
"quick-shadereffect",
"quick-sprite"
]
diff --git a/src/quick/designer/qqmldesignermetaobject.cpp b/src/quick/designer/qqmldesignermetaobject.cpp
index 33ea442b76..09493c30d6 100644
--- a/src/quick/designer/qqmldesignermetaobject.cpp
+++ b/src/quick/designer/qqmldesignermetaobject.cpp
@@ -50,7 +50,7 @@
QT_BEGIN_NAMESPACE
static QHash<QDynamicMetaObjectData *, bool> nodeInstanceMetaObjectList;
-static void (*notifyPropertyChangeCallBack)(QObject*, const QQuickDesignerSupport::PropertyName &propertyName) = 0;
+static void (*notifyPropertyChangeCallBack)(QObject*, const QQuickDesignerSupport::PropertyName &propertyName) = nullptr;
struct MetaPropertyData {
inline QPair<QVariant, bool> &getDataRef(int idx) {
@@ -127,7 +127,7 @@ void QQmlDesignerMetaObject::init(QObject *object, QQmlEngine *engine)
}
QQmlDesignerMetaObject::QQmlDesignerMetaObject(QObject *object, QQmlEngine *engine)
- : QQmlVMEMetaObject(QQmlEnginePrivate::getV4Engine(engine), object, cacheForObject(object, engine), /*qml compilation unit*/nullptr, /*qmlObjectId*/-1),
+ : QQmlVMEMetaObject(engine->handle(), object, cacheForObject(object, engine), /*qml compilation unit*/nullptr, /*qmlObjectId*/-1),
m_context(engine->contextForObject(object)),
m_data(new MetaPropertyData)
{
@@ -174,7 +174,7 @@ void QQmlDesignerMetaObject::setValue(int id, const QVariant &value)
QPair<QVariant, bool> &prop = m_data->getDataRef(id);
prop.first = propertyWriteValue(id, value);
prop.second = true;
- QMetaObject::activate(myObject(), id + m_type->signalOffset(), 0);
+ QMetaObject::activate(myObject(), id + m_type->signalOffset(), nullptr);
}
QVariant QQmlDesignerMetaObject::propertyWriteValue(int, const QVariant &value)
@@ -187,7 +187,7 @@ const QAbstractDynamicMetaObject *QQmlDesignerMetaObject::dynamicMetaObjectParen
if (QQmlVMEMetaObject::parent.isT1())
return QQmlVMEMetaObject::parent.asT1()->toDynamicMetaObject(QQmlVMEMetaObject::object);
else
- return 0;
+ return nullptr;
}
const QMetaObject *QQmlDesignerMetaObject::metaObjectParent() const
@@ -218,7 +218,7 @@ int QQmlDesignerMetaObject::openMetaCall(QObject *o, QMetaObject::Call call, int
prop.first = propertyWriteValue(propId, *reinterpret_cast<QVariant *>(a[0]));
prop.second = true;
//propertyWritten(propId);
- activate(myObject(), m_type->signalOffset() + propId, 0);
+ activate(myObject(), m_type->signalOffset() + propId, nullptr);
}
}
return -1;
diff --git a/src/quick/designer/qquickdesignercustomobjectdata.cpp b/src/quick/designer/qquickdesignercustomobjectdata.cpp
index ca9c1259fd..59e086b5a3 100644
--- a/src/quick/designer/qquickdesignercustomobjectdata.cpp
+++ b/src/quick/designer/qquickdesignercustomobjectdata.cpp
@@ -180,7 +180,7 @@ void QQuickDesignerCustomObjectData::doResetProperty(QQmlContext *context, const
QQmlAbstractBinding *binding = QQmlPropertyPrivate::binding(property);
if (binding && !(hasValidResetBinding(propertyName) && getResetBinding(propertyName) == binding)) {
- binding->setEnabled(false, 0);
+ binding->setEnabled(false, nullptr);
}
diff --git a/src/quick/designer/qquickdesignersupport.cpp b/src/quick/designer/qquickdesignersupport.cpp
index 88971e3172..1851c25a77 100644
--- a/src/quick/designer/qquickdesignersupport.cpp
+++ b/src/quick/designer/qquickdesignersupport.cpp
@@ -78,7 +78,7 @@ QQuickDesignerSupport::~QQuickDesignerSupport()
void QQuickDesignerSupport::refFromEffectItem(QQuickItem *referencedItem, bool hide)
{
- if (referencedItem == 0)
+ if (referencedItem == nullptr)
return;
QQuickItemPrivate::get(referencedItem)->refFromEffectItem(hide);
@@ -114,7 +114,7 @@ void QQuickDesignerSupport::refFromEffectItem(QQuickItem *referencedItem, bool h
void QQuickDesignerSupport::derefFromEffectItem(QQuickItem *referencedItem, bool unhide)
{
- if (referencedItem == 0)
+ if (referencedItem == nullptr)
return;
delete m_itemTextureHash.take(referencedItem);
@@ -123,7 +123,7 @@ void QQuickDesignerSupport::derefFromEffectItem(QQuickItem *referencedItem, bool
QImage QQuickDesignerSupport::renderImageForItem(QQuickItem *referencedItem, const QRectF &boundingRect, const QSize &imageSize)
{
- if (referencedItem == 0 || referencedItem->parentItem() == 0) {
+ if (referencedItem == nullptr || referencedItem->parentItem() == nullptr) {
qDebug() << __FILE__ << __LINE__ << "Warning: Item can be rendered.";
return QImage();
}
@@ -131,7 +131,7 @@ QImage QQuickDesignerSupport::renderImageForItem(QQuickItem *referencedItem, con
QSGLayer *renderTexture = m_itemTextureHash.value(referencedItem);
Q_ASSERT(renderTexture);
- if (renderTexture == 0)
+ if (renderTexture == nullptr)
return QImage();
renderTexture->setRect(boundingRect);
renderTexture->setSize(imageSize);
@@ -150,7 +150,7 @@ QImage QQuickDesignerSupport::renderImageForItem(QQuickItem *referencedItem, con
bool QQuickDesignerSupport::isDirty(QQuickItem *referencedItem, DirtyType dirtyType)
{
- if (referencedItem == 0)
+ if (referencedItem == nullptr)
return false;
return QQuickItemPrivate::get(referencedItem)->dirtyAttributes & dirtyType;
@@ -158,7 +158,7 @@ bool QQuickDesignerSupport::isDirty(QQuickItem *referencedItem, DirtyType dirtyT
void QQuickDesignerSupport::addDirty(QQuickItem *referencedItem, QQuickDesignerSupport::DirtyType dirtyType)
{
- if (referencedItem == 0)
+ if (referencedItem == nullptr)
return;
QQuickItemPrivate::get(referencedItem)->dirtyAttributes |= dirtyType;
@@ -166,7 +166,7 @@ void QQuickDesignerSupport::addDirty(QQuickItem *referencedItem, QQuickDesignerS
void QQuickDesignerSupport::resetDirty(QQuickItem *referencedItem)
{
- if (referencedItem == 0)
+ if (referencedItem == nullptr)
return;
QQuickItemPrivate::get(referencedItem)->dirtyAttributes = 0x0;
@@ -175,7 +175,7 @@ void QQuickDesignerSupport::resetDirty(QQuickItem *referencedItem)
QTransform QQuickDesignerSupport::windowTransform(QQuickItem *referencedItem)
{
- if (referencedItem == 0)
+ if (referencedItem == nullptr)
return QTransform();
return QQuickItemPrivate::get(referencedItem)->itemToWindowTransform();
@@ -183,7 +183,7 @@ QTransform QQuickDesignerSupport::windowTransform(QQuickItem *referencedItem)
QTransform QQuickDesignerSupport::parentTransform(QQuickItem *referencedItem)
{
- if (referencedItem == 0)
+ if (referencedItem == nullptr)
return QTransform();
QTransform parentTransform;
@@ -294,31 +294,31 @@ bool QQuickDesignerSupport::hasAnchor(QQuickItem *item, const QString &name)
return false;
if (name == QLatin1String("anchors.fill"))
- return anchors(item)->fill() != 0;
+ return anchors(item)->fill() != nullptr;
if (name == QLatin1String("anchors.centerIn"))
- return anchors(item)->centerIn() != 0;
+ return anchors(item)->centerIn() != nullptr;
if (name == QLatin1String("anchors.right"))
- return anchors(item)->right().item != 0;
+ return anchors(item)->right().item != nullptr;
if (name == QLatin1String("anchors.top"))
- return anchors(item)->top().item != 0;
+ return anchors(item)->top().item != nullptr;
if (name == QLatin1String("anchors.left"))
- return anchors(item)->left().item != 0;
+ return anchors(item)->left().item != nullptr;
if (name == QLatin1String("anchors.bottom"))
- return anchors(item)->bottom().item != 0;
+ return anchors(item)->bottom().item != nullptr;
if (name == QLatin1String("anchors.horizontalCenter"))
- return anchors(item)->horizontalCenter().item != 0;
+ return anchors(item)->horizontalCenter().item != nullptr;
if (name == QLatin1String("anchors.verticalCenter"))
- return anchors(item)->verticalCenter().item != 0;
+ return anchors(item)->verticalCenter().item != nullptr;
if (name == QLatin1String("anchors.baseline"))
- return anchors(item)->baseline().item != 0;
+ return anchors(item)->baseline().item != nullptr;
return anchors(item)->usedAnchors().testFlag(anchorLineFlagForName(name));
}
@@ -337,7 +337,7 @@ QQuickItem *QQuickDesignerSupport::anchorCenterInTargetItem(QQuickItem *item)
QPair<QString, QObject*> QQuickDesignerSupport::anchorLineTarget(QQuickItem *item, const QString &name, QQmlContext *context)
{
- QObject *targetObject = 0;
+ QObject *targetObject = nullptr;
QString targetName;
if (name == QLatin1String("anchors.fill")) {
diff --git a/src/quick/designer/qquickdesignersupportitems.cpp b/src/quick/designer/qquickdesignersupportitems.cpp
index 38ba46e702..9fadbb2122 100644
--- a/src/quick/designer/qquickdesignersupportitems.cpp
+++ b/src/quick/designer/qquickdesignersupportitems.cpp
@@ -55,11 +55,11 @@
QT_BEGIN_NAMESPACE
-static void (*fixResourcePathsForObjectCallBack)(QObject*) = 0;
+static void (*fixResourcePathsForObjectCallBack)(QObject*) = nullptr;
static void stopAnimation(QObject *object)
{
- if (object == 0)
+ if (object == nullptr)
return;
QQuickTransition *transition = qobject_cast<QQuickTransition*>(object);
@@ -203,7 +203,7 @@ QObject *QQuickDesignerSupportItems::createPrimitive(const QString &typeName, in
Q_UNUSED(disableComponentComplete)
- QObject *object = 0;
+ QObject *object = nullptr;
QQmlType type = QQmlMetaType::qmlType(typeName, majorNumber, minorNumber);
if (isCrashingType(type)) {
@@ -214,7 +214,7 @@ QObject *QQuickDesignerSupportItems::createPrimitive(const QString &typeName, in
} else
{
if (type.typeName() == "QQmlComponent") {
- object = new QQmlComponent(context->engine(), 0);
+ object = new QQmlComponent(context->engine(), nullptr);
} else {
object = type.create();
}
@@ -235,7 +235,7 @@ QObject *QQuickDesignerSupportItems::createPrimitive(const QString &typeName, in
tweakObjects(object);
- if (object && QQmlEngine::contextForObject(object) == 0)
+ if (object && QQmlEngine::contextForObject(object) == nullptr)
QQmlEngine::setContextForObject(object, context);
QQmlEngine::setObjectOwnership(object, QQmlEngine::CppOwnership);
diff --git a/src/quick/designer/qquickdesignersupportmetainfo.cpp b/src/quick/designer/qquickdesignersupportmetainfo.cpp
index b398bae55d..9c8a642837 100644
--- a/src/quick/designer/qquickdesignersupportmetainfo.cpp
+++ b/src/quick/designer/qquickdesignersupportmetainfo.cpp
@@ -47,7 +47,7 @@ QT_BEGIN_NAMESPACE
bool QQuickDesignerSupportMetaInfo::isSubclassOf(QObject *object, const QByteArray &superTypeName)
{
- if (object == 0)
+ if (object == nullptr)
return false;
const QMetaObject *metaObject = object->metaObject();
diff --git a/src/quick/designer/qquickdesignersupportproperties.cpp b/src/quick/designer/qquickdesignersupportproperties.cpp
index a4d1fd0dc1..674f811f8f 100644
--- a/src/quick/designer/qquickdesignersupportproperties.cpp
+++ b/src/quick/designer/qquickdesignersupportproperties.cpp
@@ -134,7 +134,7 @@ QQuickDesignerSupport::PropertyNameList QQuickDesignerSupportProperties::propert
QObjectList localObjectList;
- if (inspectedObjects == 0)
+ if (inspectedObjects == nullptr)
inspectedObjects = &localObjectList;
@@ -191,7 +191,7 @@ QQuickDesignerSupport::PropertyNameList QQuickDesignerSupportProperties::allProp
QObjectList localObjectList;
- if (inspectedObjects == 0)
+ if (inspectedObjects == nullptr)
inspectedObjects = &localObjectList;
diff --git a/src/quick/designer/qquickdesignersupportproperties_p.h b/src/quick/designer/qquickdesignersupportproperties_p.h
index a2872be060..02e75ea886 100644
--- a/src/quick/designer/qquickdesignersupportproperties_p.h
+++ b/src/quick/designer/qquickdesignersupportproperties_p.h
@@ -92,10 +92,10 @@ public:
static bool isPropertyBlackListed(const QQuickDesignerSupport::PropertyName &propertyName);
static QQuickDesignerSupport::PropertyNameList propertyNameListForWritableProperties(QObject *object,
const QQuickDesignerSupport::PropertyName &baseName = QQuickDesignerSupport::PropertyName(),
- QObjectList *inspectedObjects = 0);
+ QObjectList *inspectedObjects = nullptr);
static QQuickDesignerSupport::PropertyNameList allPropertyNames(QObject *object,
const QQuickDesignerSupport::PropertyName &baseName = QQuickDesignerSupport::PropertyName(),
- QObjectList *inspectedObjects = 0);
+ QObjectList *inspectedObjects = nullptr);
static bool hasFullImplementedListInterface(const QQmlListReference &list);
};
diff --git a/src/quick/designer/qquickdesignersupportpropertychanges.cpp b/src/quick/designer/qquickdesignersupportpropertychanges.cpp
index 5cafcfc360..0ee8857325 100644
--- a/src/quick/designer/qquickdesignersupportpropertychanges.cpp
+++ b/src/quick/designer/qquickdesignersupportpropertychanges.cpp
@@ -59,7 +59,7 @@ QObject *QQuickDesignerSupportPropertyChanges::targetObject(QObject *propertyCha
QQuickPropertyChanges *propertyChange = qobject_cast<QQuickPropertyChanges*>(propertyChanges);
if (!propertyChange)
- return 0;
+ return nullptr;
return propertyChange->object();
}
@@ -114,7 +114,7 @@ QObject *QQuickDesignerSupportPropertyChanges::stateObject(QObject *propertyChan
QQuickPropertyChanges *propertyChange = qobject_cast<QQuickPropertyChanges*>(propertyChanges);
if (!propertyChange)
- return 0;
+ return nullptr;
return propertyChange->state();
}
diff --git a/src/quick/doc/images/animatedsprite-loading-frames.png b/src/quick/doc/images/animatedsprite-loading-frames.png
new file mode 100644
index 0000000000..924e7f0bac
--- /dev/null
+++ b/src/quick/doc/images/animatedsprite-loading-frames.png
Binary files differ
diff --git a/src/quick/doc/images/animatedsprite-loading-interpolated.gif b/src/quick/doc/images/animatedsprite-loading-interpolated.gif
new file mode 100644
index 0000000000..e4512cd3be
--- /dev/null
+++ b/src/quick/doc/images/animatedsprite-loading-interpolated.gif
Binary files differ
diff --git a/src/quick/doc/images/animatedsprite-loading.gif b/src/quick/doc/images/animatedsprite-loading.gif
new file mode 100644
index 0000000000..1eaf7ad892
--- /dev/null
+++ b/src/quick/doc/images/animatedsprite-loading.gif
Binary files differ
diff --git a/src/quick/doc/images/animatedsprite-loading.png b/src/quick/doc/images/animatedsprite-loading.png
new file mode 100644
index 0000000000..ff2bbbd140
--- /dev/null
+++ b/src/quick/doc/images/animatedsprite-loading.png
Binary files differ
diff --git a/src/quick/doc/qtquick.qdocconf b/src/quick/doc/qtquick.qdocconf
index 028b30dba1..7ce0dfcf09 100644
--- a/src/quick/doc/qtquick.qdocconf
+++ b/src/quick/doc/qtquick.qdocconf
@@ -33,7 +33,7 @@ qhp.QtQuick.subprojects.examples.selectors = fake:example
tagfile = ../../../doc/qtquick/qtquick.tags
-depends += qtcore qtxmlpatterns qtqml qtgui qtlinguist qtquickcontrols qtdoc qtquickdialogs qtsensors qtwidgets qmake qtmultimedia qtgraphicaleffects
+depends += qtcore qtxmlpatterns qtqml qtqmltest qtgui qtlinguist qtquickcontrols qtquickcontrols2 qtdoc qtquickdialogs qtsensors qtwidgets qmake qtmultimedia qtgraphicaleffects qtsql
headerdirs += ..\
../../quickwidgets
diff --git a/src/quick/doc/snippets/pointerHandlers/dragHandler.qml b/src/quick/doc/snippets/pointerHandlers/dragHandler.qml
index 349cdcb95f..78a7db5b0c 100644
--- a/src/quick/doc/snippets/pointerHandlers/dragHandler.qml
+++ b/src/quick/doc/snippets/pointerHandlers/dragHandler.qml
@@ -1,12 +1,22 @@
/****************************************************************************
**
** Copyright (C) 2017 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
+** Contact: https://www.qt.io/licensing/
**
** This file is part of the documentation of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
-** You may use this file under the terms of the BSD license as follows:
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
diff --git a/src/quick/doc/snippets/pointerHandlers/dragHandlerDifferentTarget.qml b/src/quick/doc/snippets/pointerHandlers/dragHandlerDifferentTarget.qml
index e8f2a04e6a..4c4168de83 100644
--- a/src/quick/doc/snippets/pointerHandlers/dragHandlerDifferentTarget.qml
+++ b/src/quick/doc/snippets/pointerHandlers/dragHandlerDifferentTarget.qml
@@ -1,12 +1,22 @@
/****************************************************************************
**
** Copyright (C) 2017 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
+** Contact: https://www.qt.io/licensing/
**
** This file is part of the documentation of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
-** You may use this file under the terms of the BSD license as follows:
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
diff --git a/src/quick/doc/snippets/pointerHandlers/dragHandlerNullTarget.qml b/src/quick/doc/snippets/pointerHandlers/dragHandlerNullTarget.qml
index e210ce0952..09429ec1d2 100644
--- a/src/quick/doc/snippets/pointerHandlers/dragHandlerNullTarget.qml
+++ b/src/quick/doc/snippets/pointerHandlers/dragHandlerNullTarget.qml
@@ -1,12 +1,22 @@
/****************************************************************************
**
** Copyright (C) 2017 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
+** Contact: https://www.qt.io/licensing/
**
** This file is part of the documentation of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
-** You may use this file under the terms of the BSD license as follows:
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
diff --git a/src/quick/doc/snippets/pointerHandlers/pinchHandler.qml b/src/quick/doc/snippets/pointerHandlers/pinchHandler.qml
index 841e401da1..955047d115 100644
--- a/src/quick/doc/snippets/pointerHandlers/pinchHandler.qml
+++ b/src/quick/doc/snippets/pointerHandlers/pinchHandler.qml
@@ -1,12 +1,22 @@
/****************************************************************************
**
** Copyright (C) 2017 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
+** Contact: https://www.qt.io/licensing/
**
** This file is part of the documentation of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
-** You may use this file under the terms of the BSD license as follows:
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
diff --git a/src/quick/doc/snippets/pointerHandlers/pinchHandlerDifferentTarget.qml b/src/quick/doc/snippets/pointerHandlers/pinchHandlerDifferentTarget.qml
index 211c370da6..a5255a64e3 100644
--- a/src/quick/doc/snippets/pointerHandlers/pinchHandlerDifferentTarget.qml
+++ b/src/quick/doc/snippets/pointerHandlers/pinchHandlerDifferentTarget.qml
@@ -1,12 +1,22 @@
/****************************************************************************
**
** Copyright (C) 2017 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
+** Contact: https://www.qt.io/licensing/
**
** This file is part of the documentation of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
-** You may use this file under the terms of the BSD license as follows:
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
diff --git a/src/quick/doc/snippets/pointerHandlers/pinchHandlerNullTarget.qml b/src/quick/doc/snippets/pointerHandlers/pinchHandlerNullTarget.qml
index b0139d7194..7d21efcb84 100644
--- a/src/quick/doc/snippets/pointerHandlers/pinchHandlerNullTarget.qml
+++ b/src/quick/doc/snippets/pointerHandlers/pinchHandlerNullTarget.qml
@@ -1,12 +1,22 @@
/****************************************************************************
**
** Copyright (C) 2017 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
+** Contact: https://www.qt.io/licensing/
**
** This file is part of the documentation of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
-** You may use this file under the terms of the BSD license as follows:
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
diff --git a/src/quick/doc/snippets/qml/localstorage/dbtransaction.js b/src/quick/doc/snippets/pointerHandlers/pointHandler.qml
index aafe10c5f1..262eb607b6 100644
--- a/src/quick/doc/snippets/qml/localstorage/dbtransaction.js
+++ b/src/quick/doc/snippets/pointerHandlers/pointHandler.qml
@@ -1,9 +1,9 @@
- /****************************************************************************
+/****************************************************************************
**
** Copyright (C) 2017 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
-** This file is part of the examples of the Qt Toolkit.
+** This file is part of the documentation of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
** Commercial License Usage
@@ -47,61 +47,33 @@
** $QT_END_LICENSE$
**
****************************************************************************/
-
-//![0]
-var db = LocalStorage.openDatabaseSync("ActivityTrackDB", "", "Database tracking sports activities", 1000000);
-db.transaction(
- try {
- function(tx) {
- tx.executeSql("INSERT INTO trip_log VALUES(?, ?, ?)",
- [ "01/10/2016","Sylling - Vikersund", "53" ]);
- }
- } catch (err) {
- console.log("Error inserting into table trip_log: " + err);
- }
-)
//![0]
+import QtQuick 2.10
+import QtQuick.Window 2.2
+import Qt.labs.handlers 1.0
+
+Window {
+ width: 480
+ height: 320
+ visible: true
-//![1]
-// Retrieve activity date, description and distance based on minimum
-// distance parameter Pdistance
-function db_distance_select(Pdistance)
-{
-var db = LocalStorage.openDatabaseSync("ActivityTrackDB", "", "Database tracking sports activities", 1000000);
-db.transaction(
- function(tx) {
- var results = tx.executeSql("SELECT rowid,
- date,
- trip_desc,
- distance FROM trip_log
- where distance >= ?",[Pdistance]);
- for (var i = 0; i < results.rows.length; i++) {
- listModel.append({"id": results.rows.item(i).rowid,
- "date": results.rows.item(i).date,
- "trip_desc": results.rows.item(i).trip_desc,
- "distance": results.rows.item(i).distance});
+ Item {
+ id: glassPane
+ z: 10000
+ anchors.fill: parent
+
+ PointHandler {
+ id: handler
+ acceptedDevices: PointerDevice.TouchScreen | PointerDevice.TouchPad
+ target: Rectangle {
+ parent: glassPane
+ color: "red"
+ visible: handler.active
+ x: handler.point.position.x - width / 2
+ y: handler.point.position.y - height / 2
+ width: 20; height: width; radius: width / 2
+ }
}
}
}
-//![1]
-//![2]
-var db = LocalStorage.openDatabaseSync("ActivityTrackDB", "", "Database tracking sports activities", 1000000);
-if (db.version == "0.1") {
- db.changeVersion("0.1", "0.2", function(tx) {
- tx.executeSql("INSERT INTO trip_log VALUES(?, ?, ?)",
- [ "01/10/2016","Sylling - Vikersund", "53" ]);
- }
-});
-//![2]
-//![3]
-create table trip_log(date text, data text)
-//![3]
-//![4]
-var obj = {description = "Vikersund - Noresund", distance = "60"}
-//![4]
-//![5]
-db.transaction(function(tx) {
- result = tx.executeSQL("insert into trip_log values (?,?)",
- ["01/11/2016", JSON.stringify(obj)])
-}
-//![5]
+//![0]
diff --git a/src/quick/doc/snippets/qml/layout-simple.qml b/src/quick/doc/snippets/qml/layout-simple.qml
new file mode 100644
index 0000000000..6afdbe3ec9
--- /dev/null
+++ b/src/quick/doc/snippets/qml/layout-simple.qml
@@ -0,0 +1,74 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the documentation of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of The Qt Company Ltd nor the names of its
+** contributors may be used to endorse or promote products derived
+** from this software without specific prior written permission.
+**
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.9
+import QtQuick.Layouts 1.2
+import QtQuick.Window 2.2
+
+//! [1]
+Window {
+ RowLayout {
+ anchors.fill: parent
+ //! [spacing]
+ spacing: 6
+ //! [spacing]
+ Rectangle {
+ color: 'azure'
+ Layout.preferredWidth: 100
+ Layout.preferredHeight: 150
+ }
+ Rectangle {
+ color: "plum"
+ Layout.fillWidth: true
+ Layout.fillHeight: true
+ }
+ }
+}
+//! [1]
diff --git a/src/quick/doc/snippets/qml/path/arcrotation.qml b/src/quick/doc/snippets/qml/path/arcrotation.qml
index c73d67ff17..985ac51d8a 100644
--- a/src/quick/doc/snippets/qml/path/arcrotation.qml
+++ b/src/quick/doc/snippets/qml/path/arcrotation.qml
@@ -1,12 +1,22 @@
/****************************************************************************
**
** Copyright (C) 2016 The Qt Company Ltd.
-** Contact: http://www.qt.io/licensing/
+** Contact: https://www.qt.io/licensing/
**
** This file is part of the documentation of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
-** You may use this file under the terms of the BSD license as follows:
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
diff --git a/src/quick/doc/src/concepts/layouts/qtquicklayouts-overview.qdoc b/src/quick/doc/src/concepts/layouts/qtquicklayouts-overview.qdoc
index 05e4465f2a..06ebe2d3d1 100644
--- a/src/quick/doc/src/concepts/layouts/qtquicklayouts-overview.qdoc
+++ b/src/quick/doc/src/concepts/layouts/qtquicklayouts-overview.qdoc
@@ -74,8 +74,31 @@
\endlist
+ \section1 A Simple Layout
+
+ \snippet qml/layout-simple.qml 1
+
+ As the intention of using a layout is to rearrange its children whenever the layout changes
+ size, the application should make sure that the layout gets resized. In the above snippet the
+ RowLayout ensures that by specifying \c{anchors.fill: parent}. However, it can also be by other
+ means, such as directly specifying \l{Item::width}{width} and \l{Item::height}{height}
+ properties. In the same snippet, the \c azure Rectangle has a fixed size of \c{(100, 150)}
+ pixels, and the \c plum Rectangle will expand to occupy all the space it gets allocated.
+
+ \note A layout is responsible for its children's geometry. You should
+ therefore not specify \l{Item::width}{width}, \l{Item::height}{height}, \l{Item::x}{x},
+ \l{Item::y}{y} or any other properties that might influence those properties (such as
+ \l{Item::anchors}{anchors}) on those items. Otherwise there would be a conflict of interest,
+ and the result is undefined. This is also the case if the child item is a layout. Therefore,
+ only layouts with no parent layout can have \c{anchors.fill: parent}.
+
+ All items in the layout will have 6 pixels of spacing between them:
+
+ \snippet qml/layout-simple.qml spacing
+
+
+ \section2 Size Constraints
- \section1 Size Constraints
Since an item can be resized by its layout, the layout needs to know the
\l{Layout::minimumWidth}{minimum}, \l{Layout::preferredWidth}{preferred},
and \l{Layout::maximumWidth}{maximum} sizes of all items where \l{Layout::fillWidth}{Layout.fillWidth} or
diff --git a/src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc b/src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc
index 27c8e51381..2705ca5e34 100644
--- a/src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc
+++ b/src/quick/doc/src/concepts/modelviewsdata/cppmodels.qdoc
@@ -41,6 +41,10 @@ QObjectList or a \l QAbstractItemModel. The first three are useful for exposing
simpler datasets, while QAbstractItemModel provides a more flexible solution for
more complex models.
+For a video tutorial that takes you through the whole process of exposing a C++
+model to QML, see the
+\l {https://youtu.be/9BcAYDlpuT8}{Using C++ Models in QML Tutorial}.
+
\section2 QStringList-based Model
A model may be a simple \l QStringList, which provides the contents of the list
diff --git a/src/quick/doc/src/concepts/pointerhandlers/qtquickhandlers-index.qdoc b/src/quick/doc/src/concepts/pointerhandlers/qtquickhandlers-index.qdoc
index b17c5ab728..fc1fd5fbc1 100644
--- a/src/quick/doc/src/concepts/pointerhandlers/qtquickhandlers-index.qdoc
+++ b/src/quick/doc/src/concepts/pointerhandlers/qtquickhandlers-index.qdoc
@@ -67,7 +67,7 @@
\list
\li \l{Qt Quick}
- \li \l{Qt Quick Pointer Handlers Overview}
+ \li \l{Qt Quick Pointer Handlers}
\li \l{Qt Quick Pointer Handlers QML Types}{Qt Quick Pointer Handlers QML Types}
\endlist
*/
diff --git a/src/quick/doc/src/concepts/visualcanvas/scenegraph.qdoc b/src/quick/doc/src/concepts/visualcanvas/scenegraph.qdoc
index 27576d488c..99175ab94e 100644
--- a/src/quick/doc/src/concepts/visualcanvas/scenegraph.qdoc
+++ b/src/quick/doc/src/concepts/visualcanvas/scenegraph.qdoc
@@ -1,6 +1,6 @@
/****************************************************************************
**
-** Copyright (C) 2017 The Qt Company Ltd.
+** Copyright (C) 2018 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
** This file is part of the documentation of the Qt Toolkit.
@@ -176,8 +176,8 @@ attach application code. This can be used to add custom scene graph
content or render raw OpenGL content. The integration points are
defined by the render loop.
-For detailed description of how the scene graph renderer works, see
-\l {Qt Quick Scene Graph Renderer}.
+For detailed description of how the scene graph renderer for OpenGL
+works, see \l {Qt Quick Scene Graph OpenGL Renderer}.
There are three render loop variants available: \c basic, \c windows,
and \c threaded. Out of these, \c basic and \c windows are
@@ -413,10 +413,11 @@ with multiple windows.
*/
/*!
- \title Qt Quick Scene Graph Renderer
+ \title Qt Quick Scene Graph OpenGL Renderer
\page qtquick-visualcanvas-scenegraph-renderer.html
- This document explains how the scene graph renderer works internally
+ This document explains how the scene graph renderer for OpenGL
+ works internally
so that one can write code that uses it in an optimal fashion, both
performance-wise and feature-wise.
@@ -428,7 +429,7 @@ with multiple windows.
\note Even in the case where every frame is unique and everything is
uploaded from scratch, the default renderer will perform well.
- The Qt Quick items in a QML scene populates a tree of QSGNode
+ The Qt Quick items in a QML scene populate a tree of QSGNode
instances. Once created, this tree is a complete description of how
a certain frame should be rendered. It does not contain any
references back to the Qt Quick items at all and will on most
@@ -441,11 +442,11 @@ with multiple windows.
If needed, the renderer can be completely replaced using the
internal scene graph back-end API. This is mostly interesting for
platform vendors who wish to take advantage of non-standard hardware
- features. For majority of use cases, the default renderer will be
+ features. For the majority of use cases, the default renderer will be
sufficient.
The default renderer focuses on two primary strategies to optimize
- the rendering. Batching of draw calls and retention of geometry on
+ the rendering: Batching of draw calls, and retention of geometry on
the GPU.
\section1 Batching
@@ -458,7 +459,7 @@ with multiple windows.
\image visualcanvas_list.png
- The simplest way of drawing this list is on a cell-by-cell basis. First
+ The simplest way of drawing this list is on a cell-by-cell basis. First,
the background is drawn. This is a rectangle of a specific color. In
OpenGL terms this means selecting a shader program to do solid color
fills, setting up the fill color, setting the transformation matrix
@@ -495,8 +496,8 @@ with multiple windows.
batches. From Qt Quick core item set, this includes Rectangle items
with opaque colors and fully opaque images, such as JPEGs or BMPs.
- Another benefit of using opaque primitives, is that opaque
- primitives does not require \c GL_BLEND to be enabled which can be
+ Another benefit of using opaque primitives is that opaque
+ primitives do not require \c GL_BLEND to be enabled, which can be
quite costly, especially on mobile and embedded GPUs.
Opaque primitives are rendered in a front-to-back manner with
@@ -533,7 +534,7 @@ with multiple windows.
and the two text elements in another call, as the texts only overlap
a background which they are stacked in front of. In the right-most
case, the background of "Item 4" overlaps the text of "Item 3" so in
- this case, each of backgrounds and texts need to be drawn using
+ this case, each of backgrounds and texts needs to be drawn using
separate calls.
Z-wise, the alpha primitives are interleaved with the opaque nodes
@@ -550,7 +551,7 @@ with multiple windows.
The renderer modifies the vertex shader returned from
QSGMaterialShader::vertexShader() and compresses the z values of the
- vertex after the model-view and projection matrices has been applied
+ vertex after the model-view and projection matrices have been applied
and then adds a small translation on the z to position it the
correct z position.
@@ -561,7 +562,7 @@ with multiple windows.
The active texture is a unique OpenGL state, which means that
multiple primitives using different OpenGL textures cannot be
- batched. The Qt Quick scene graph for this reason allows multiple
+ batched. The Qt Quick scene graph, for this reason, allows multiple
QSGTexture instances to be allocated as smaller sub-regions of a
larger texture; a texture atlas.
@@ -603,10 +604,10 @@ with multiple windows.
Each Qt Quick Item inserts a QSGTransformNode into the scene graph
tree to manage its x, y, scale or rotation. Child items will be
populated under this transform node. The default renderer tracks
- the state of transform nodes between frames, and will look at
+ the state of transform nodes between frames and will look at
subtrees to decide if a transform node is a good candidate to become
a root for a set of batches. A transform node which changes between
- frames and which has a fairly complex subtree, can become a batch
+ frames and which has a fairly complex subtree can become a batch
root.
QSGGeometryNodes in the subtree of a batch root are pre-transformed
@@ -621,7 +622,7 @@ with multiple windows.
removed nodes when panning through a grid or list.
Another benefit of identifying transform nodes as batch roots is
- that it allows the renderer to retain the parts of the tree that has
+ that it allows the renderer to retain the parts of the tree that have
not changed. For instance, say a UI consists of a list and a button
row. When the list is being scrolled and delegates are being added
and removed, the rest of the UI, the button row, is unchanged and
@@ -684,7 +685,7 @@ with multiple windows.
to either \c vertex or \c {msaa}.
Vertex antialiasing can produce seams between edges of adjacent
- primitives, even when the two edges are mathmatically the same.
+ primitives, even when the two edges are mathematically the same.
Multisample antialiasing does not.
@@ -722,7 +723,7 @@ with multiple windows.
job when creating batches and can rely on early-z to avoid overdraw.
When multisample antialiasing is used, content rendered into
- framebuffer objects, need additional extensions to support multisampling
+ framebuffer objects need additional extensions to support multisampling
of framebuffers. Typically \c GL_EXT_framebuffer_multisample and
\c GL_EXT_framebuffer_blit. Most desktop chips have these extensions
present, but they are less common in embedded chips. When framebuffer
@@ -736,7 +737,7 @@ with multiple windows.
As stated in the beginning, understanding the finer details of the
renderer is not required to get good performance. It is written to
optimize for common use cases and will perform quite well under
- almost any circumstance.
+ almost any circumstances.
\list
@@ -744,7 +745,7 @@ with multiple windows.
as possible of the geometry being uploaded again and again. By
setting the environment variable \c {QSG_RENDERER_DEBUG=render}, the
renderer will output statistics on how well the batching goes, how
- many batches, which batches are retained and which are opaque and
+ many batches are used, which batches are retained and which are opaque and
not. When striving for optimal performance, uploads should happen
only when really needed, batches should be fewer than 10 and at
least 3-4 of them should be opaque.
@@ -772,16 +773,16 @@ with multiple windows.
QQuickWindow::createTextureFromImage(), let the image have
QImage::Format_RGB32, when possible.
- \li Be aware of that overlapping compond items, like in the
- illustration above, can not be batched.
+ \li Be aware of that overlapping compound items, like in the
+ illustration above, cannot be batched.
\li Clipping breaks batching. Never use on a per-item basis, inside
- tables cells, item delegates or similar. Instead of clipping text,
+ table cells, item delegates or similar. Instead of clipping text,
use eliding. Instead of clipping an image, create a
QQuickImageProvider that returns a cropped image.
\li Batching only works for 16-bit indices. All built-in items use
- 16-bit indices, but custom geometry is free to also use 32-bit
+ 16-bit indices, but a custom geometry is free to also use 32-bit
indices.
\li Some material flags prevent batching, the most limiting one
@@ -792,7 +793,7 @@ with multiple windows.
QQuickWindow::setColor() will be used in a call to \c glClear(),
which is potentially faster.
- \li Mipmapped Image items are not placed in global atlas and will
+ \li Mipmapped Image items are not placed in the global atlas and will
not be batched.
\endlist
diff --git a/src/quick/doc/src/qmltypereference.qdoc b/src/quick/doc/src/qmltypereference.qdoc
index 16bb4e2a30..f5b189c580 100644
--- a/src/quick/doc/src/qmltypereference.qdoc
+++ b/src/quick/doc/src/qmltypereference.qdoc
@@ -894,5 +894,5 @@ import QtTest 1.1
\endcode
For more information about how to use these types, see
-\l{Qt Quick Test Reference Documentation}.
+\l{Qt Quick Test}.
*/
diff --git a/src/quick/doc/src/qtquick.qdoc b/src/quick/doc/src/qtquick.qdoc
index e2d4f16dae..ece66cb589 100644
--- a/src/quick/doc/src/qtquick.qdoc
+++ b/src/quick/doc/src/qtquick.qdoc
@@ -89,7 +89,8 @@ To find out more about using the QML language, see the \l{Qt QML} module documen
\section1 Licenses and Attributions
Qt Quick is available under commercial licenses from \l{The Qt Company}.
-In addition, it is available under the
+In addition, it is available under free software licenses. Since Qt 5.4,
+these free software licenses are
\l{GNU Lesser General Public License, version 3}, or
the \l{GNU General Public License, version 2}.
See \l{Qt Licensing} for further details.
diff --git a/src/quick/handlers/handlers.pri b/src/quick/handlers/handlers.pri
index 9e32b9278c..8bd74d95da 100644
--- a/src/quick/handlers/handlers.pri
+++ b/src/quick/handlers/handlers.pri
@@ -5,6 +5,7 @@ HEADERS += \
$$PWD/qquickpinchhandler_p.h \
$$PWD/qquickpointerdevicehandler_p.h \
$$PWD/qquickpointerhandler_p.h \
+ $$PWD/qquickpointhandler_p.h \
$$PWD/qquicksinglepointhandler_p.h \
$$PWD/qquicktaphandler_p.h \
@@ -15,6 +16,7 @@ SOURCES += \
$$PWD/qquickpinchhandler.cpp \
$$PWD/qquickpointerdevicehandler.cpp \
$$PWD/qquickpointerhandler.cpp \
+ $$PWD/qquickpointhandler.cpp \
$$PWD/qquicksinglepointhandler.cpp \
$$PWD/qquicktaphandler.cpp \
diff --git a/src/quick/handlers/qquickdraghandler.cpp b/src/quick/handlers/qquickdraghandler.cpp
index 12f1a29bca..041780257a 100644
--- a/src/quick/handlers/qquickdraghandler.cpp
+++ b/src/quick/handlers/qquickdraghandler.cpp
@@ -53,20 +53,21 @@ QT_BEGIN_NAMESPACE
DragHandler is a handler that is used to interactively move an Item.
Like other Pointer Handlers, by default it is fully functional, and
- manipulates its \l target.
+ manipulates its \l {PointerHandler::target} {target}.
\snippet pointerHandlers/dragHandler.qml 0
It has properties to restrict the range of dragging.
- If it is declared within one Item but is assigned a different \l target,
- then it handles events within the bounds of the \l parent Item but
+ If it is declared within one Item but is assigned a different
+ \l {PointerHandler::target} {target}, then it handles events within the
+ bounds of the \l {PointerHandler::parent} {parent} Item but
manipulates the \c target Item instead:
\snippet pointerHandlers/dragHandlerDifferentTarget.qml 0
- A third way to use it is to set \l target to \c null and react to property
- changes in some other way:
+ A third way to use it is to set \l {PointerHandler::target} {target} to
+ \c null and react to property changes in some other way:
\snippet pointerHandlers/dragHandlerNullTarget.qml 0
@@ -91,19 +92,44 @@ bool QQuickDragHandler::wantsEventPoint(QQuickEventPoint *point)
|| QQuickSinglePointHandler::wantsEventPoint(point));
}
+bool QQuickDragHandler::targetContains(QQuickEventPoint *point)
+{
+ Q_ASSERT(parentItem() && target());
+ return target()->contains(localTargetPosition(point));
+}
+
+QPointF QQuickDragHandler::localTargetPosition(QQuickEventPoint *point)
+{
+ QPointF pos = point->position();
+ if (target() != parentItem())
+ pos = parentItem()->mapToItem(target(), pos);
+ return pos;
+}
+
void QQuickDragHandler::onGrabChanged(QQuickPointerHandler *grabber, QQuickEventPoint::GrabState stateChange, QQuickEventPoint *point)
{
- if (grabber == this && stateChange == QQuickEventPoint::GrabExclusive)
- // In case the grab got handled over from another grabber, we might not get the Press
- initializeTargetStartPos(point);
- enforceConstraints();
+ if (grabber == this && stateChange == QQuickEventPoint::GrabExclusive) {
+ // In case the grab got handed over from another grabber, we might not get the Press.
+ if (!m_pressedInsideTarget) {
+ if (target())
+ m_pressTargetPos = QPointF(target()->width(), target()->height()) / 2;
+ m_pressScenePos = point->scenePosition();
+ } else if (m_pressTargetPos.isNull()) {
+ if (target())
+ m_pressTargetPos = localTargetPosition(point);
+ m_pressScenePos = point->scenePosition();
+ }
+ }
QQuickSinglePointHandler::onGrabChanged(grabber, stateChange, point);
}
void QQuickDragHandler::onActiveChanged()
{
- if (!active())
- m_targetStartPos = QPointF();
+ if (!active()) {
+ m_pressTargetPos = QPointF();
+ m_pressScenePos = m_pressTargetPos;
+ m_pressedInsideTarget = false;
+ }
}
void QQuickDragHandler::handleEventPoint(QQuickEventPoint *point)
@@ -111,25 +137,40 @@ void QQuickDragHandler::handleEventPoint(QQuickEventPoint *point)
point->setAccepted();
switch (point->state()) {
case QQuickEventPoint::Pressed:
- initializeTargetStartPos(point);
+ if (target()) {
+ m_pressedInsideTarget = targetContains(point);
+ m_pressTargetPos = localTargetPosition(point);
+ }
+ m_pressScenePos = point->scenePosition();
setPassiveGrab(point);
break;
case QQuickEventPoint::Updated: {
- QPointF delta = point->scenePosition() - point->scenePressPosition();
- if (!m_xAxis.enabled())
- delta.setX(0);
- if (!m_yAxis.enabled())
- delta.setY(0);
+ QVector2D accumulatedDragDelta = QVector2D(point->scenePosition() - m_pressScenePos);
if (active()) {
- setTranslation(QVector2D(delta));
+ // update translation property. Make sure axis is respected for it.
+ if (!m_xAxis.enabled())
+ accumulatedDragDelta.setX(0);
+ if (!m_yAxis.enabled())
+ accumulatedDragDelta.setY(0);
+ setTranslation(accumulatedDragDelta);
+
if (target() && target()->parentItem()) {
- QPointF pos = target()->parentItem()->mapFromScene(m_targetStartPos + delta);
+ const QPointF newTargetTopLeft = localTargetPosition(point) - m_pressTargetPos;
+ const QPointF xformOrigin = target()->transformOriginPoint();
+ const QPointF targetXformOrigin = newTargetTopLeft + xformOrigin;
+ QPointF pos = target()->parentItem()->mapFromItem(target(), targetXformOrigin);
+ pos -= xformOrigin;
+ QPointF targetItemPos = target()->position();
+ if (!m_xAxis.enabled())
+ pos.setX(targetItemPos.x());
+ if (!m_yAxis.enabled())
+ pos.setY(targetItemPos.y());
enforceAxisConstraints(&pos);
moveTarget(pos, point);
}
} else if (!point->exclusiveGrabber() &&
- ((m_xAxis.enabled() && QQuickWindowPrivate::dragOverThreshold(delta.x(), Qt::XAxis, point)) ||
- (m_yAxis.enabled() && QQuickWindowPrivate::dragOverThreshold(delta.y(), Qt::YAxis, point)))) {
+ ((m_xAxis.enabled() && QQuickWindowPrivate::dragOverThreshold(accumulatedDragDelta.x(), Qt::XAxis, point)) ||
+ (m_yAxis.enabled() && QQuickWindowPrivate::dragOverThreshold(accumulatedDragDelta.y(), Qt::YAxis, point)))) {
setExclusiveGrab(point);
if (auto parent = parentItem()) {
if (point->pointerEvent()->asPointerTouchEvent())
@@ -165,23 +206,6 @@ void QQuickDragHandler::enforceAxisConstraints(QPointF *localPos)
localPos->setY(qBound(m_yAxis.minimum(), localPos->y(), m_yAxis.maximum()));
}
-void QQuickDragHandler::initializeTargetStartPos(QQuickEventPoint *point)
-{
- if (target() && target()->parentItem() && m_targetStartPos.isNull()) { // prefer the m_targetStartPos we got when it got Pressed.
- m_targetStartPos = target()->parentItem()->mapToScene(target()->position());
- if (!target()->contains(point->position())) {
- // If pressed outside of target item, move the target item so that the touchpoint is in its center,
- // while still respecting the axis constraints.
- const QPointF center = target()->parentItem()->mapFromScene(point->scenePosition());
- const QPointF pointCenteredInItemPos = target()->parentItem()->mapToScene(center - QPointF(target()->width(), target()->height())/2);
- if (m_xAxis.enabled())
- m_targetStartPos.setX(pointCenteredInItemPos.x());
- if (m_yAxis.enabled())
- m_targetStartPos.setY(pointCenteredInItemPos.y());
- }
- }
-}
-
void QQuickDragHandler::setTranslation(const QVector2D &trans)
{
if (trans == m_translation) // fuzzy compare?
@@ -192,23 +216,33 @@ void QQuickDragHandler::setTranslation(const QVector2D &trans)
/*!
\qmlpropertygroup QtQuick::DragHandler::xAxis
+ \qmlproperty real QtQuick::DragHandler::xAxis.minimum
+ \qmlproperty real QtQuick::DragHandler::xAxis.maximum
+ \qmlproperty bool QtQuick::DragHandler::xAxis.enabled
+
+ \c xAxis controls the constraints for horizontal dragging.
+
+ \c minimum is the minimum acceptable value of \l {Item::x}{x} to be
+ applied to the \l {PointerHandler::target} {target}.
+ \c maximum is the maximum acceptable value of \l {Item::x}{x} to be
+ applied to the \l {PointerHandler::target} {target}.
+ If \c enabled is true, horizontal dragging is allowed.
+ */
+
+/*!
\qmlpropertygroup QtQuick::DragHandler::yAxis
- \qmlproperty real QtQuick::DragHandler::DragAxis::minimum
- \qmlproperty real QtQuick::DragHandler::DragAxis::maximum
- \qmlproperty real QtQuick::DragHandler::DragAxis::enabled
-
- \c xAxis and yAxis control the constraints for horizontal and vertical
- dragging, respectively.
-
- \value minimum
- The minimum acceptable value of \l {Item::x}{x} or \l {Item::y}{y}
- to be applied to the \l target
- \value maximum
- The maximum acceptable value of \l {Item::x}{x} or \l {Item::y}{y}
- to be applied to the \l target
- \value enabled
- Whether dragging in this direction is allowed at all
-*/
+ \qmlproperty real QtQuick::DragHandler::yAxis.minimum
+ \qmlproperty real QtQuick::DragHandler::yAxis.maximum
+ \qmlproperty bool QtQuick::DragHandler::yAxis.enabled
+
+ \c yAxis controls the constraints for vertical dragging.
+
+ \c minimum is the minimum acceptable value of \l {Item::y}{y} to be
+ applied to the \l {PointerHandler::target} {target}.
+ \c maximum is the maximum acceptable value of \l {Item::y}{y} to be
+ applied to the \l {PointerHandler::target} {target}.
+ If \c enabled is true, vertical dragging is allowed.
+ */
QQuickDragAxis::QQuickDragAxis()
: m_minimum(-DBL_MAX)
, m_maximum(DBL_MAX)
diff --git a/src/quick/handlers/qquickdraghandler_p.h b/src/quick/handlers/qquickdraghandler_p.h
index d10084c654..363df31a64 100644
--- a/src/quick/handlers/qquickdraghandler_p.h
+++ b/src/quick/handlers/qquickdraghandler_p.h
@@ -93,7 +93,7 @@ class Q_AUTOTEST_EXPORT QQuickDragHandler : public QQuickSinglePointHandler
Q_PROPERTY(QVector2D translation READ translation NOTIFY translationChanged)
public:
- explicit QQuickDragHandler(QObject *parent = 0);
+ explicit QQuickDragHandler(QObject *parent = nullptr);
~QQuickDragHandler();
void handleEventPoint(QQuickEventPoint *point) override;
@@ -118,13 +118,19 @@ protected:
private:
void ungrab();
void enforceAxisConstraints(QPointF *localPos);
- void initializeTargetStartPos(QQuickEventPoint *point);
+ bool targetContains(QQuickEventPoint *point);
+ QPointF localTargetPosition(QQuickEventPoint *point);
private:
- QPointF m_targetStartPos;
+ QPointF m_pressScenePos;
+ QPointF m_pressTargetPos; // We must also store the local targetPos, because we cannot deduce
+ // the press target pos from the scene pos in case there was e.g a
+ // flick in one of the ancestors during the drag.
QVector2D m_translation;
+
QQuickDragAxis m_xAxis;
QQuickDragAxis m_yAxis;
+ bool m_pressedInsideTarget = false;
friend class QQuickDragAxis;
};
diff --git a/src/quick/handlers/qquickhandlersmodule.cpp b/src/quick/handlers/qquickhandlersmodule.cpp
index 8472c6a062..c9e08fe4f2 100644
--- a/src/quick/handlers/qquickhandlersmodule.cpp
+++ b/src/quick/handlers/qquickhandlersmodule.cpp
@@ -41,6 +41,7 @@
#include "qquickpointerhandler_p.h"
#include "qquickdraghandler_p.h"
#include "qquickpinchhandler_p.h"
+#include "qquickpointhandler_p.h"
#include "qquicktaphandler_p.h"
static void initResources()
@@ -82,6 +83,7 @@ static void qt_quickhandlers_defineModule(const char *uri, int major, int minor)
qmlRegisterUncreatableType<QQuickPointerHandler>(uri,major,minor,"PointerHandler",
QQuickPointerHandler::tr("PointerHandler is an abstract base class"));
+ qmlRegisterType<QQuickPointHandler>(uri,major,minor,"PointHandler");
qmlRegisterType<QQuickDragHandler>(uri,major,minor,"DragHandler");
qmlRegisterUncreatableType<QQuickDragAxis>(uri, major, minor, "DragAxis",
QQuickDragHandler::tr("DragAxis is only available as a grouped property of DragHandler"));
diff --git a/src/quick/handlers/qquickmultipointhandler.cpp b/src/quick/handlers/qquickmultipointhandler.cpp
index ff4914394c..b126b93211 100644
--- a/src/quick/handlers/qquickmultipointhandler.cpp
+++ b/src/quick/handlers/qquickmultipointhandler.cpp
@@ -298,17 +298,18 @@ void QQuickMultiPointHandler::acceptPoints(const QVector<QQuickEventPoint *> &po
bool QQuickMultiPointHandler::grabPoints(QVector<QQuickEventPoint *> points)
{
- bool canGrab = true;
+ bool allowed = true;
for (QQuickEventPoint* point : points) {
- auto grabber = point->grabberItem();
- if (grabber && (grabber->keepMouseGrab() || grabber->keepTouchGrab()))
- canGrab = false;
+ if (!canGrab(point)) {
+ allowed = false;
+ break;
+ }
}
- if (canGrab) {
+ if (allowed) {
for (QQuickEventPoint* point : points)
setExclusiveGrab(point);
}
- return canGrab;
+ return allowed;
}
QT_END_NAMESPACE
diff --git a/src/quick/handlers/qquickmultipointhandler_p.h b/src/quick/handlers/qquickmultipointhandler_p.h
index 05c3876246..67e550d387 100644
--- a/src/quick/handlers/qquickmultipointhandler_p.h
+++ b/src/quick/handlers/qquickmultipointhandler_p.h
@@ -65,7 +65,7 @@ class Q_AUTOTEST_EXPORT QQuickMultiPointHandler : public QQuickPointerDeviceHand
Q_PROPERTY(qreal pointDistanceThreshold READ pointDistanceThreshold WRITE setPointDistanceThreshold NOTIFY pointDistanceThresholdChanged)
public:
- explicit QQuickMultiPointHandler(QObject *parent = 0, int minimumPointCount = 2);
+ explicit QQuickMultiPointHandler(QObject *parent = nullptr, int minimumPointCount = 2);
~QQuickMultiPointHandler();
int minimumPointCount() const { return m_minimumPointCount; }
diff --git a/src/quick/handlers/qquickpinchhandler.cpp b/src/quick/handlers/qquickpinchhandler.cpp
index 84c4e912d1..155822197f 100644
--- a/src/quick/handlers/qquickpinchhandler.cpp
+++ b/src/quick/handlers/qquickpinchhandler.cpp
@@ -248,8 +248,8 @@ bool QQuickPinchHandler::wantsPointerEvent(QQuickPointerEvent *event)
if (!QQuickMultiPointHandler::wantsPointerEvent(event))
return false;
- if (minimumPointCount() == 2) {
- if (const auto gesture = event->asPointerNativeGestureEvent()) {
+ if (const auto gesture = event->asPointerNativeGestureEvent()) {
+ if (minimumPointCount() == 2) {
switch (gesture->type()) {
case Qt::BeginNativeGesture:
case Qt::EndNativeGesture:
@@ -259,6 +259,8 @@ bool QQuickPinchHandler::wantsPointerEvent(QQuickPointerEvent *event)
default:
return false;
}
+ } else {
+ return false;
}
}
@@ -349,13 +351,18 @@ void QQuickPinchHandler::handlePointerEventImpl(QQuickPointerEvent *event)
}
} else {
bool containsReleasedPoints = event->isReleaseEvent();
- if (!active() && !containsReleasedPoints) {
+ if (!active()) {
// Verify that at least one of the points has moved beyond threshold needed to activate the handler
for (QQuickEventPoint *point : qAsConst(m_currentPoints)) {
- if (QQuickWindowPrivate::dragOverThreshold(point)) {
- if (grabPoints(m_currentPoints))
- setActive(true);
+ if (!containsReleasedPoints && QQuickWindowPrivate::dragOverThreshold(point) && grabPoints(m_currentPoints)) {
+ setActive(true);
break;
+ } else {
+ setPassiveGrab(point);
+ }
+ if (point->state() == QQuickEventPoint::Pressed) {
+ point->setAccepted(false); // don't stop propagation
+ setPassiveGrab(point);
}
}
if (!active())
diff --git a/src/quick/handlers/qquickpinchhandler_p.h b/src/quick/handlers/qquickpinchhandler_p.h
index 7d6b7d9509..9a17971416 100644
--- a/src/quick/handlers/qquickpinchhandler_p.h
+++ b/src/quick/handlers/qquickpinchhandler_p.h
@@ -82,7 +82,7 @@ public:
};
Q_ENUM(PinchOrigin)
- explicit QQuickPinchHandler(QObject *parent = 0);
+ explicit QQuickPinchHandler(QObject *parent = nullptr);
~QQuickPinchHandler();
qreal minimumScale() const { return m_minimumScale; }
diff --git a/src/quick/handlers/qquickpointerdevicehandler.cpp b/src/quick/handlers/qquickpointerdevicehandler.cpp
index 1521b58d57..06831613b6 100644
--- a/src/quick/handlers/qquickpointerdevicehandler.cpp
+++ b/src/quick/handlers/qquickpointerdevicehandler.cpp
@@ -75,7 +75,8 @@ QQuickPointerDeviceHandler::~QQuickPointerDeviceHandler()
The types of pointing devices that can activate this Pointer Handler.
- By default, this property is set to \l PointerDevice.AllDevices.
+ By default, this property is set to
+ \l{QtQuick::PointerDevice::type} {PointerDevice.AllDevices}.
If you set it to an OR combination of device types, it will ignore events
from non-matching devices.
@@ -110,7 +111,8 @@ void QQuickPointerDeviceHandler::setAcceptedDevices(QQuickPointerDevice::DeviceT
The types of pointing instruments (finger, stylus, eraser, etc.)
that can activate this Pointer Handler.
- By default, this property is set to \l PointerDevice.AllPointerTypes.
+ By default, this property is set to
+ \l {QtQuick::PointerDevice::pointerType} {PointerDevice.AllPointerTypes}.
If you set it to an OR combination of device types, it will ignore events
from non-matching events.
diff --git a/src/quick/handlers/qquickpointerdevicehandler_p.h b/src/quick/handlers/qquickpointerdevicehandler_p.h
index 9e30fa0be4..1638604ea7 100644
--- a/src/quick/handlers/qquickpointerdevicehandler_p.h
+++ b/src/quick/handlers/qquickpointerdevicehandler_p.h
@@ -63,7 +63,7 @@ class Q_AUTOTEST_EXPORT QQuickPointerDeviceHandler : public QQuickPointerHandler
Q_PROPERTY(Qt::KeyboardModifiers acceptedModifiers READ acceptedModifiers WRITE setAcceptedModifiers NOTIFY acceptedModifiersChanged)
public:
- explicit QQuickPointerDeviceHandler(QObject *parent = 0);
+ explicit QQuickPointerDeviceHandler(QObject *parent = nullptr);
~QQuickPointerDeviceHandler();
QQuickPointerDevice::DeviceTypes acceptedDevices() const { return m_acceptedDevices; }
diff --git a/src/quick/handlers/qquickpointerhandler.cpp b/src/quick/handlers/qquickpointerhandler.cpp
index faebdf3621..959030b8fe 100644
--- a/src/quick/handlers/qquickpointerhandler.cpp
+++ b/src/quick/handlers/qquickpointerhandler.cpp
@@ -42,6 +42,7 @@
QT_BEGIN_NAMESPACE
Q_LOGGING_CATEGORY(lcPointerHandlerDispatch, "qt.quick.handler.dispatch")
+Q_LOGGING_CATEGORY(lcPointerHandlerGrab, "qt.quick.handler.grab")
Q_LOGGING_CATEGORY(lcPointerHandlerActive, "qt.quick.handler.active")
/*!
@@ -67,6 +68,7 @@ QQuickPointerHandler::QQuickPointerHandler(QObject *parent)
, m_targetExplicitlySet(false)
, m_hadKeepMouseGrab(false)
, m_hadKeepTouchGrab(false)
+ , m_grabPermissions(CanTakeOverFromItems | CanTakeOverFromHandlersOfDifferentType | ApprovesTakeOverByAnything)
{
}
@@ -94,7 +96,7 @@ QQuickPointerHandler::~QQuickPointerHandler()
*/
void QQuickPointerHandler::onGrabChanged(QQuickPointerHandler *grabber, QQuickEventPoint::GrabState stateChange, QQuickEventPoint *point)
{
- qCDebug(lcPointerHandlerDispatch) << point << stateChange << grabber;
+ qCDebug(lcPointerHandlerGrab) << point << stateChange << grabber;
Q_ASSERT(point);
if (grabber == this) {
bool wasCanceled = false;
@@ -145,7 +147,7 @@ void QQuickPointerHandler::onGrabChanged(QQuickPointerHandler *grabber, QQuickEv
*/
void QQuickPointerHandler::setPassiveGrab(QQuickEventPoint *point, bool grab)
{
- qCDebug(lcPointerHandlerDispatch) << point << grab;
+ qCDebug(lcPointerHandlerGrab) << point << grab;
if (grab) {
point->setGrabberPointerHandler(this, false);
} else {
@@ -153,14 +155,124 @@ void QQuickPointerHandler::setPassiveGrab(QQuickEventPoint *point, bool grab)
}
}
-void QQuickPointerHandler::setExclusiveGrab(QQuickEventPoint *point, bool grab)
+/*!
+ Check whether it's OK to take an exclusive grab of the \a point.
+
+ The default implementation will call approveGrabTransition() to check this
+ handler's \l grabPermissions. If grabbing can be done only by taking over
+ the exclusive grab from an Item, approveGrabTransition() checks the Item's
+ \l keepMouseGrab or \l keepTouchGrab flags appropriately. If grabbing can
+ be done only by taking over another handler's exclusive grab, canGrab()
+ also calls approveGrabTransition() on the handler which is about to lose
+ its grab. Either one can deny the takeover.
+*/
+bool QQuickPointerHandler::canGrab(QQuickEventPoint *point)
{
- // TODO m_hadKeepMouseGrab m_hadKeepTouchGrab
- qCDebug(lcPointerHandlerDispatch) << point << grab;
- // Don't allow one handler to cancel another's grab, unless it is stealing it for itself
- if (!grab && point->grabberPointerHandler() != this)
+ QQuickPointerHandler *existingPhGrabber = point->grabberPointerHandler();
+ return approveGrabTransition(point, this) &&
+ (existingPhGrabber ? existingPhGrabber->approveGrabTransition(point, this) : true);
+}
+
+/*!
+ Check this handler's rules to see if \l proposedGrabber will be allowed to take
+ the exclusive grab. This function may be called twice: once on the instance which
+ will take the grab, and once on the instance which would thereby lose its grab,
+ in case of a takeover scenario.
+*/
+bool QQuickPointerHandler::approveGrabTransition(QQuickEventPoint *point, QObject *proposedGrabber)
+{
+ bool allowed = false;
+ if (proposedGrabber == this) {
+ QObject* existingGrabber = point->exclusiveGrabber();
+ allowed = (existingGrabber == nullptr) || ((m_grabPermissions & CanTakeOverFromAnything) == CanTakeOverFromAnything);
+ if (existingGrabber) {
+ if (QQuickPointerHandler *existingPhGrabber = point->grabberPointerHandler()) {
+ if (!allowed && (m_grabPermissions & CanTakeOverFromHandlersOfDifferentType) &&
+ existingPhGrabber->metaObject()->className() != metaObject()->className())
+ allowed = true;
+ if (!allowed && (m_grabPermissions & CanTakeOverFromHandlersOfSameType) &&
+ existingPhGrabber->metaObject()->className() == metaObject()->className())
+ allowed = true;
+ } else if ((m_grabPermissions & CanTakeOverFromItems)) {
+ QQuickItem * existingItemGrabber = point->grabberItem();
+ if (existingItemGrabber && !((existingItemGrabber->keepMouseGrab() && point->pointerEvent()->asPointerMouseEvent()) ||
+ (existingItemGrabber->keepTouchGrab() && point->pointerEvent()->asPointerTouchEvent())))
+ allowed = true;
+ }
+ }
+ } else {
+ // proposedGrabber is different: that means this instance will lose its grab
+ if (proposedGrabber) {
+ if ((m_grabPermissions & ApprovesTakeOverByAnything) == ApprovesTakeOverByAnything)
+ allowed = true;
+ if (!allowed && (m_grabPermissions & ApprovesTakeOverByHandlersOfDifferentType) &&
+ proposedGrabber->metaObject()->className() != metaObject()->className())
+ allowed = true;
+ if (!allowed && (m_grabPermissions & ApprovesTakeOverByHandlersOfSameType) &&
+ proposedGrabber->metaObject()->className() == metaObject()->className())
+ allowed = true;
+ if (!allowed && (m_grabPermissions & ApprovesTakeOverByItems) && proposedGrabber->inherits("QQuickItem"))
+ allowed = true;
+ } else {
+ if (!allowed && (m_grabPermissions & ApprovesCancellation))
+ allowed = true;
+ }
+ }
+ qCDebug(lcPointerHandlerGrab) << "point" << hex << point->pointId() << "permission" <<
+ QMetaEnum::fromType<GrabPermissions>().valueToKeys(grabPermissions()) <<
+ ':' << this << (allowed ? "approved to" : "denied to") << proposedGrabber;
+ return allowed;
+}
+
+/*!
+ \qmlproperty bool QtQuick::PointerHandler::grabPermission
+
+ This property specifies the permissions when this handler's logic decides
+ to take over the exclusive grab, or when it is asked to approve grab
+ takeover or cancellation by another handler.
+
+ The default is
+ \c {CanTakeOverFromItems | CanTakeOverFromHandlersOfDifferentType | ApprovesTakeOverByAnything}
+ which allows most takeover scenarios but avoids e.g. two PinchHandlers fighting
+ over the same touchpoints.
+*/
+void QQuickPointerHandler::setGrabPermissions(GrabPermissions grabPermission)
+{
+ if (m_grabPermissions == grabPermission)
return;
- point->setGrabberPointerHandler(grab ? this : nullptr, true);
+
+ m_grabPermissions = grabPermission;
+ emit grabPermissionChanged();
+}
+
+/*!
+ \internal
+ Acquire or give up the exclusive grab of the given \a point, according to
+ the \a grab state, and subject to the rules: canGrab(), and the rule not to
+ relinquish another handler's grab. Returns true if permission is granted,
+ or if the exclusive grab has already been acquired or relinquished as
+ specified. Returns false if permission is denied either by this handler or
+ by the handler or item from which this handler would take over
+*/
+bool QQuickPointerHandler::setExclusiveGrab(QQuickEventPoint *point, bool grab)
+{
+ if ((grab && point->exclusiveGrabber() == this) || (!grab && point->exclusiveGrabber() != this))
+ return true;
+ // TODO m_hadKeepMouseGrab m_hadKeepTouchGrab
+ bool allowed = true;
+ if (grab) {
+ allowed = canGrab(point);
+ } else {
+ QQuickPointerHandler *existingPhGrabber = point->grabberPointerHandler();
+ // Ask before allowing one handler to cancel another's grab
+ if (existingPhGrabber && existingPhGrabber != this && !existingPhGrabber->approveGrabTransition(point, nullptr))
+ allowed = false;
+ }
+ qCDebug(lcPointerHandlerGrab) << point << (grab ? "grab" : "ungrab") << (allowed ? "allowed" : "forbidden") <<
+ point->exclusiveGrabber() << "->" << (grab ? this : nullptr);
+ if (allowed)
+ point->setGrabberPointerHandler(grab ? this : nullptr, true);
+ return allowed;
}
/*!
@@ -169,7 +281,7 @@ void QQuickPointerHandler::setExclusiveGrab(QQuickEventPoint *point, bool grab)
*/
void QQuickPointerHandler::cancelAllGrabs(QQuickEventPoint *point)
{
- qCDebug(lcPointerHandlerDispatch) << point;
+ qCDebug(lcPointerHandlerGrab) << point;
point->cancelAllGrabs(this);
}
@@ -207,7 +319,7 @@ void QQuickPointerHandler::setEnabled(bool enabled)
The Item which this handler will manipulate.
- By default, it is the same as the \l parent: the Item within which
+ By default, it is the same as the \l [QML] {parent}, the Item within which
the handler is declared. However, it can sometimes be useful to set the
target to a different Item, in order to handle events within one item
but manipulate another; or to \c null, to disable the default behavior
@@ -219,7 +331,9 @@ void QQuickPointerHandler::setTarget(QQuickItem *target)
if (m_target == target)
return;
+ QQuickItem *oldTarget = m_target;
m_target = target;
+ onTargetChanged(oldTarget);
emit targetChanged();
}
@@ -288,10 +402,10 @@ void QQuickPointerHandler::handlePointerEventImpl(QQuickPointerEvent *event)
The \l Item which is the scope of the handler; the Item in which it was declared.
The handler will handle events on behalf of this Item, which means a
pointer event is relevant if at least one of its event points occurs within
- the Item's interior. Initially \l target() is the same, but target()
+ the Item's interior. Initially \l [QML] {target} {target()} is the same, but it
can be reassigned.
- \sa QQuick::PointerHandler::target(), QObject::parent()
+ \sa {target}, QObject::parent()
*/
/*!
diff --git a/src/quick/handlers/qquickpointerhandler_p.h b/src/quick/handlers/qquickpointerhandler_p.h
index 24a058275d..9ea6a8b5e2 100644
--- a/src/quick/handlers/qquickpointerhandler_p.h
+++ b/src/quick/handlers/qquickpointerhandler_p.h
@@ -60,18 +60,36 @@ QT_BEGIN_NAMESPACE
Q_DECLARE_LOGGING_CATEGORY(lcPointerHandlerDispatch)
-class Q_QUICK_PRIVATE_EXPORT QQuickPointerHandler : public QObject
+class Q_QUICK_PRIVATE_EXPORT QQuickPointerHandler : public QObject, public QQmlParserStatus
{
Q_OBJECT
+ Q_INTERFACES(QQmlParserStatus)
+
Q_PROPERTY(bool enabled READ enabled WRITE setEnabled NOTIFY enabledChanged)
Q_PROPERTY(bool active READ active NOTIFY activeChanged)
Q_PROPERTY(QQuickItem * target READ target WRITE setTarget NOTIFY targetChanged)
Q_PROPERTY(QQuickItem * parent READ parentItem CONSTANT)
+ Q_PROPERTY(GrabPermissions grabPermissions READ grabPermissions WRITE setGrabPermissions NOTIFY grabPermissionChanged)
public:
- explicit QQuickPointerHandler(QObject *parent = 0);
+ explicit QQuickPointerHandler(QObject *parent = nullptr);
virtual ~QQuickPointerHandler();
+ enum GrabPermission {
+ TakeOverForbidden = 0x0,
+ CanTakeOverFromHandlersOfSameType = 0x01,
+ CanTakeOverFromHandlersOfDifferentType= 0x02,
+ CanTakeOverFromItems = 0x04,
+ CanTakeOverFromAnything = 0x0F,
+ ApprovesTakeOverByHandlersOfSameType = 0x10,
+ ApprovesTakeOverByHandlersOfDifferentType= 0x20,
+ ApprovesTakeOverByItems = 0x40,
+ ApprovesCancellation = 0x80,
+ ApprovesTakeOverByAnything = 0xF0
+ };
+ Q_DECLARE_FLAGS(GrabPermissions, GrabPermission)
+ Q_FLAG(GrabPermissions)
+
public:
bool enabled() const { return m_enabled; }
void setEnabled(bool enabled);
@@ -85,11 +103,18 @@ public:
void handlePointerEvent(QQuickPointerEvent *event);
+ GrabPermissions grabPermissions() const { return static_cast<GrabPermissions>(m_grabPermissions); }
+ void setGrabPermissions(GrabPermissions grabPermissions);
+
+ void classBegin() override { }
+ void componentComplete() override { }
+
Q_SIGNALS:
void enabledChanged();
void activeChanged();
void targetChanged();
void grabChanged(QQuickEventPoint *point);
+ void grabPermissionChanged();
void canceled(QQuickEventPoint *point);
protected:
@@ -97,10 +122,13 @@ protected:
virtual bool wantsPointerEvent(QQuickPointerEvent *event);
virtual void handlePointerEventImpl(QQuickPointerEvent *event);
void setActive(bool active);
+ virtual void onTargetChanged(QQuickItem *oldTarget) { Q_UNUSED(oldTarget); }
virtual void onActiveChanged() { }
virtual void onGrabChanged(QQuickPointerHandler *grabber, QQuickEventPoint::GrabState stateChange, QQuickEventPoint *point);
+ virtual bool canGrab(QQuickEventPoint *point);
+ virtual bool approveGrabTransition(QQuickEventPoint *point, QObject *proposedGrabber);
void setPassiveGrab(QQuickEventPoint *point, bool grab = true);
- void setExclusiveGrab(QQuickEventPoint *point, bool grab = true);
+ bool setExclusiveGrab(QQuickEventPoint *point, bool grab = true);
void cancelAllGrabs(QQuickEventPoint *point);
QPointF eventPos(const QQuickEventPoint *point) const;
bool parentContains(const QQuickEventPoint *point) const;
@@ -113,11 +141,15 @@ private:
bool m_targetExplicitlySet : 1;
bool m_hadKeepMouseGrab : 1; // some handlers override target()->setKeepMouseGrab(); this remembers previous state
bool m_hadKeepTouchGrab : 1; // some handlers override target()->setKeepTouchGrab(); this remembers previous state
+ uint m_reserved : 19;
+ uint8_t m_grabPermissions : 8;
friend class QQuickEventPoint;
friend class QQuickWindowPrivate;
};
+Q_DECLARE_OPERATORS_FOR_FLAGS(QQuickPointerHandler::GrabPermissions)
+
QT_END_NAMESPACE
QML_DECLARE_TYPE(QQuickPointerHandler)
diff --git a/src/quick/handlers/qquickpointhandler.cpp b/src/quick/handlers/qquickpointhandler.cpp
new file mode 100644
index 0000000000..7e2d40452c
--- /dev/null
+++ b/src/quick/handlers/qquickpointhandler.cpp
@@ -0,0 +1,164 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qquickpointhandler_p.h"
+#include <private/qquickwindow_p.h>
+#include <QDebug>
+
+QT_BEGIN_NAMESPACE
+
+/*!
+ \qmltype PointHandler
+ \instantiates QQuickPointHandler
+ \inherits SinglePointHandler
+ \inqmlmodule Qt.labs.handlers
+ \ingroup qtquick-handlers
+ \brief Handler for reacting to a single touchpoint.
+
+ PointHandler can be used to show feedback about a touchpoint or the mouse
+ position, or to otherwise react to pointer events.
+
+ When a press event occurs, each instance of PointHandler chooses a
+ single point which is not yet "taken" at that moment: if the press
+ occurs within the bounds of the \l {PointerHandler::parent}, and
+ no sibling PointHandler within the same \l {PointerHandler::parent}
+ has yet acquired a passive grab on that point, and if the other
+ constraints such as \l {SinglePointHandler::acceptedButtons},
+ \l {PointerDeviceHandler::acceptedDevices} etc. are satisfied, it's
+ eligible, and the PointHandler then acquires a passive grab. In
+ this way, the \l {PointerHandler::parent} acts like an exclusive
+ group: there can be multiple instances of PointHandler, and the
+ set of pressed touchpoints will be distributed among them. Each
+ PointHandler which has chosen a point to track has its \l active
+ property \c true. It then continues to track its chosen point
+ until release: the properties of the \l point will be kept
+ up-to-date. Any Item can bind to these properties, and thereby
+ follow the point's movements.
+
+ By being only a passive grabber, it has the ability to keep independent
+ oversight of all movements. The passive grab cannot be stolen or overridden
+ even when other gestures are detected and exclusive grabs occur.
+
+ If your goal is orthogonal surveillance of eventpoints, an older
+ alternative was QObject::installEventFilter(), but that has never been a
+ built-in QtQuick feature: it requires some C++ code, such as a QQuickItem
+ subclass. PointHandler is more efficient than that, because only pointer
+ events will be delivered to it, during the course of normal event delivery
+ in QQuickWindow; whereas an event filter needs to filter all QEvents of all
+ types, and thus sets itself up as a potential event delivery bottleneck.
+
+ One possible use case is to add this handler to a transparent Item which is
+ on top of the rest of the scene (by having a high \l{Item::z} {z} value),
+ so that when a point is freshly pressed, it will be delivered to that Item
+ and its handlers first, providing the opportunity to take the passive grab
+ as early as possible. Such an item (like a pane of glass over the whole UI)
+ can be a convenient parent for other Items which visualize the kind of reactive
+ feedback which must always be on top; and likewise it can be the parent for
+ popups, popovers, dialogs and so on. If it will be used in that way, it can
+ be helpful for your main.cpp to use QQmlContext::setContextProperty() to
+ make the "glass pane" accessible by ID to the entire UI, so that other
+ Items and PointHandlers can be reparented to it.
+
+ \snippet pointerHandlers/pointHandler.qml 0
+
+ Like all pointer handlers, a PointHandler has a \l target property, which
+ may be used as a convenient place to put a point-tracking Item; but
+ PointHandler will not automatically manipulate the \c target item in any way.
+ You need to use bindings to make it react to the \l point.
+
+ \note On macOS, PointHandler does not react to the trackpad by default.
+ That is because macOS can provide either native gesture recognition, or raw
+ touchpoints, but not both. We prefer to use the native gesture event in
+ PinchHandler, so we do not want to disable it by enabling touch. However
+ MultiPointTouchArea does enable touch, thus disabling native gesture
+ recognition within the entire window; so it's an alternative if you only
+ want to react to all the touchpoints but do not require the smooth
+ native-gesture experience.
+
+ \sa MultiPointTouchArea
+*/
+
+QQuickPointHandler::QQuickPointHandler(QObject *parent)
+ : QQuickSinglePointHandler(parent)
+{
+ setIgnoreAdditionalPoints();
+}
+
+QQuickPointHandler::~QQuickPointHandler()
+{
+}
+
+bool QQuickPointHandler::wantsEventPoint(QQuickEventPoint *pt)
+{
+ // On press, we want it unless a sibling of the same type also does.
+ if (pt->state() == QQuickEventPoint::Pressed && QQuickSinglePointHandler::wantsEventPoint(pt)) {
+ for (const QQuickPointerHandler *grabber : pt->passiveGrabbers()) {
+ if (grabber && grabber->parent() == parent() &&
+ grabber->metaObject()->className() == metaObject()->className())
+ return false;
+ }
+ return true;
+ }
+ // If we've already been interested in a point, stay interested, even if it has strayed outside bounds.
+ return (pt->state() != QQuickEventPoint::Pressed && point().id() == pt->pointId());
+}
+
+void QQuickPointHandler::handleEventPoint(QQuickEventPoint *point)
+{
+ switch (point->state()) {
+ case QQuickEventPoint::Pressed:
+ setPassiveGrab(point);
+ setActive(true);
+ break;
+ case QQuickEventPoint::Released:
+ setActive(false);
+ break;
+ default:
+ break;
+ }
+ point->setAccepted(false); // Just lurking... don't interfere with propagation
+ emit translationChanged();
+}
+
+QVector2D QQuickPointHandler::translation() const
+{
+ return QVector2D(point().position() - point().pressPosition());
+}
+
+QT_END_NAMESPACE
diff --git a/src/quick/handlers/qquickpointhandler_p.h b/src/quick/handlers/qquickpointhandler_p.h
new file mode 100644
index 0000000000..5babab0c4d
--- /dev/null
+++ b/src/quick/handlers/qquickpointhandler_p.h
@@ -0,0 +1,81 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QQUICKPONTHANDLER_H
+#define QQUICKPONTHANDLER_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include "qquicksinglepointhandler_p.h"
+
+QT_BEGIN_NAMESPACE
+
+class Q_AUTOTEST_EXPORT QQuickPointHandler : public QQuickSinglePointHandler
+{
+ Q_OBJECT
+ Q_PROPERTY(QVector2D translation READ translation NOTIFY translationChanged)
+
+public:
+ explicit QQuickPointHandler(QObject *parent = 0);
+ ~QQuickPointHandler();
+
+ QVector2D translation() const;
+
+Q_SIGNALS:
+ void translationChanged();
+
+protected:
+ bool wantsEventPoint(QQuickEventPoint *pt) override;
+ void handleEventPoint(QQuickEventPoint *point) override;
+};
+
+QT_END_NAMESPACE
+
+QML_DECLARE_TYPE(QQuickPointHandler)
+
+#endif // QQUICKPONTHANDLER_H
diff --git a/src/quick/handlers/qquicksinglepointhandler.cpp b/src/quick/handlers/qquicksinglepointhandler.cpp
index dee168a8e4..1a5537b732 100644
--- a/src/quick/handlers/qquicksinglepointhandler.cpp
+++ b/src/quick/handlers/qquicksinglepointhandler.cpp
@@ -217,7 +217,7 @@ void QQuickSinglePointHandler::moveTarget(QPointF pos, QQuickEventPoint *point)
The mouse buttons which can activate this Pointer Handler.
- By default, this property is set to \l Qt.LeftButton.
+ By default, this property is set to \l {QtQuick::MouseEvent::button} {Qt.LeftButton}.
It can be set to an OR combination of mouse buttons, and will ignore events
from other buttons.
@@ -360,7 +360,8 @@ void QQuickHandlerPoint::reset()
\qmlproperty QPointF QtQuick::HandlerPoint::position
\brief The position within the \c parent Item
- This is the position of the event point relative to the bounds of the \l parent.
+ This is the position of the event point relative to the bounds of
+ the \l {PointerHandler::parent} {parent}.
*/
/*!
@@ -378,7 +379,7 @@ void QQuickHandlerPoint::reset()
\brief The pressed position within the \c parent Item
This is the position at which this point was pressed, relative to the
- bounds of the \l parent.
+ bounds of the \l {PointerHandler::parent} {parent}.
*/
/*!
@@ -469,7 +470,7 @@ void QQuickHandlerPoint::reset()
If the contact patch is unknown, or the device is not a touchscreen,
these values will be zero.
- \sa QtQuick::EventPoint::ellipseDiameters, QtQuick::TouchPoint::ellipseDiameters, QTouchEvent::TouchPoint::ellipseDiameters
+ \sa QtQuick::EventTouchPoint::ellipseDiameters, QtQuick::TouchPoint::ellipseDiameters, QTouchEvent::TouchPoint::ellipseDiameters
*/
QT_END_NAMESPACE
diff --git a/src/quick/handlers/qquicksinglepointhandler_p.h b/src/quick/handlers/qquicksinglepointhandler_p.h
index 386cea253a..7606b4f7ba 100644
--- a/src/quick/handlers/qquicksinglepointhandler_p.h
+++ b/src/quick/handlers/qquicksinglepointhandler_p.h
@@ -111,7 +111,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickSinglePointHandler : public QQuickPointerDevi
Q_PROPERTY(Qt::MouseButtons acceptedButtons READ acceptedButtons WRITE setAcceptedButtons NOTIFY acceptedButtonsChanged)
Q_PROPERTY(QQuickHandlerPoint point READ point NOTIFY pointChanged)
public:
- explicit QQuickSinglePointHandler(QObject *parent = 0);
+ explicit QQuickSinglePointHandler(QObject *parent = nullptr);
virtual ~QQuickSinglePointHandler() { }
Qt::MouseButtons acceptedButtons() const { return m_acceptedButtons; }
diff --git a/src/quick/handlers/qquicktaphandler.cpp b/src/quick/handlers/qquicktaphandler.cpp
index e5b728db0f..902ff0df10 100644
--- a/src/quick/handlers/qquicktaphandler.cpp
+++ b/src/quick/handlers/qquicktaphandler.cpp
@@ -61,14 +61,20 @@ int QQuickTapHandler::m_touchMultiTapDistanceSquared(-1);
TapHandler is a handler for taps on a touchscreen or clicks on a mouse.
- Detection of a valid tap gesture depends on \l gesturePolicy.
+ Detection of a valid tap gesture depends on \l gesturePolicy. The default
+ value is DragThreshold, which requires the press and release to be close
+ together in both space and time. In this case, DragHandler is able to
+ function using only a passive grab, and therefore does not interfere with
+ event delivery to any other Items or Pointer Handlers. So the default
+ gesturePolicy is useful when you want to modify behavior of an existing
+ control or Item by adding a TapHandler with bindings and/or JavaScript
+ callbacks.
+
Note that buttons (such as QPushButton) are often implemented not to care
whether the press and release occur close together: if you press the button
and then change your mind, you need to drag all the way off the edge of the
- button in order to cancel the click. Therefore the default
- \l gesturePolicy is \c TapHandler.ReleaseWithinBounds. If you want to require
- that the press and release are close together in both space and time,
- set it to \c TapHandler.DragThreshold.
+ button in order to cancel the click. For this use case, set the
+ \l gesturePolicy to \c TapHandler.ReleaseWithinBounds.
For multi-tap gestures (double-tap, triple-tap etc.), the distance moved
must not exceed QPlatformTheme::MouseDoubleClickDistance with mouse and
@@ -81,7 +87,7 @@ int QQuickTapHandler::m_touchMultiTapDistanceSquared(-1);
QQuickTapHandler::QQuickTapHandler(QObject *parent)
: QQuickSinglePointHandler(parent)
, m_pressed(false)
- , m_gesturePolicy(ReleaseWithinBounds)
+ , m_gesturePolicy(DragThreshold)
, m_tapCount(0)
, m_longPressThreshold(-1)
, m_lastTapTimestamp(0.0)
@@ -165,7 +171,7 @@ void QQuickTapHandler::handleEventPoint(QQuickEventPoint *point)
}
/*!
- \qmlproperty real TapHandler::longPressThreshold
+ \qmlproperty real QtQuick::TapHandler::longPressThreshold
The time in seconds that an event point must be pressed in order to
trigger a long press gesture and emit the \l longPressed() signal.
@@ -203,39 +209,53 @@ void QQuickTapHandler::timerEvent(QTimerEvent *event)
}
/*!
- \qmlproperty enumeration TapHandler::gesturePolicy
+ \qmlsignal QtQuick::TapHandler::tapped()
+
+ This signal is emitted when the pointer device taps the item.
+ */
+
+/*!
+ \qmlsignal QtQuick::TapHandler::longPressed()
+
+ This signal is emitted when a press occurs that is longer than the
+ \l {TapHandler::longPressThreshold} {long press threshold}.
+ */
+
+/*!
+ \qmlproperty enumeration QtQuick::TapHandler::gesturePolicy
The spatial constraint for a tap or long press gesture to be recognized,
in addition to the constraint that the release must occur before
\l longPressThreshold has elapsed. If these constraints are not satisfied,
the \l tapped signal is not emitted, and \l tapCount is not incremented.
- If the spatial constraint is violated, \l isPressed transitions immediately
+ If the spatial constraint is violated, \l pressed transitions immediately
from true to false, regardless of the time held.
\value TapHandler.DragThreshold
- The event point must not move significantly. If the mouse, finger
- or stylus moves past the system-wide drag threshold
- (QStyleHints::startDragDistance), the tap gesture is canceled, even
- if the button or finger is still pressed. This policy can be useful
- whenever TapHandler needs to cooperate with other pointer handlers
- (for example \l DragHandler), because in this case TapHandler will
- never grab.
+ (the default value) The event point must not move significantly.
+ If the mouse, finger or stylus moves past the system-wide drag
+ threshold (QStyleHints::startDragDistance), the tap gesture is
+ canceled, even if the button or finger is still pressed. This policy
+ can be useful whenever TapHandler needs to cooperate with other
+ pointer handlers (for example \l DragHandler) or event-handling Items
+ (for example QtQuick Controls), because in this case TapHandler
+ will not take the exclusive grab, but merely a passive grab.
\value TapHandler.WithinBounds
If the event point leaves the bounds of the \l target item, the tap
- gesture is canceled. The TapHandler will grab on press, but release
- the grab as soon as the boundary constraint is no longer satisfied.
+ gesture is canceled. The TapHandler will take the exclusive grab on
+ press, but will release the grab as soon as the boundary constraint
+ is no longer satisfied.
\value TapHandler.ReleaseWithinBounds
- (the default value) At the time of release (the mouse button is
- released or the finger is lifted), if the event point is outside
- the bounds of the \l target item, a tap gesture is not recognized.
- This is the default value, because it corresponds to typical button
- behavior: you can cancel a click by dragging outside the button,
- and you can also change your mind by dragging back inside the button
- before release. Note that it's necessary for TapHandler to grab on
- press and retain it until release (greedy grab) in order to detect
- this gesture.
+ At the time of release (the mouse button is released or the finger
+ is lifted), if the event point is outside the bounds of the
+ \l target item, a tap gesture is not recognized. This corresponds to
+ typical behavior for button widgets: you can cancel a click by
+ dragging outside the button, and you can also change your mind by
+ dragging back inside the button before release. Note that it's
+ necessary for TapHandler take the exclusive grab on press and retain
+ it until release in order to detect this gesture.
*/
void QQuickTapHandler::setGesturePolicy(QQuickTapHandler::GesturePolicy gesturePolicy)
{
@@ -247,7 +267,7 @@ void QQuickTapHandler::setGesturePolicy(QQuickTapHandler::GesturePolicy gestureP
}
/*!
- \qmlproperty bool TapHandler::pressed
+ \qmlproperty bool QtQuick::TapHandler::pressed
\readonly
Holds true whenever the mouse or touch point is pressed,
@@ -290,6 +310,10 @@ void QQuickTapHandler::setPressed(bool press, bool cancel, QQuickEventPoint *poi
qCDebug(lcTapHandler) << objectName() << "tapped" << m_tapCount << "times";
emit tapped();
emit tapCountChanged();
+ if (m_tapCount == 1)
+ emit singleTapped();
+ else if (m_tapCount == 2)
+ emit doubleTapped();
m_lastTapTimestamp = ts;
m_lastTapPos = point->scenePosition();
} else {
@@ -301,6 +325,8 @@ void QQuickTapHandler::setPressed(bool press, bool cancel, QQuickEventPoint *poi
// on release, ungrab after emitting changed signals
setExclusiveGrab(point, press);
}
+ if (cancel)
+ emit canceled(point);
}
}
@@ -326,27 +352,27 @@ void QQuickTapHandler::updateTimeHeld()
}
/*!
- \qmlproperty int TapHandler::tapCount
+ \qmlproperty int QtQuick::TapHandler::tapCount
\readonly
The number of taps which have occurred within the time and space
constraints to be considered a single gesture. For example, to detect
- a double-tap, you can write:
+ a triple-tap, you can write:
\qml
Rectangle {
width: 100; height: 30
- signal doubleTap
+ signal tripleTap
TapHandler {
acceptedButtons: Qt.AllButtons
- onTapped: if (tapCount == 2) doubleTap()
+ onTapped: if (tapCount == 3) tripleTap()
}
}
\endqml
*/
/*!
- \qmlproperty real TapHandler::timeHeld
+ \qmlproperty real QtQuick::TapHandler::timeHeld
\readonly
The amount of time in seconds that a pressed point has been held, without
@@ -360,4 +386,24 @@ void QQuickTapHandler::updateTimeHeld()
handler's \l [QML] Item.
*/
+/*!
+ \qmlsignal TapHandler::singleTapped
+ \since 5.11
+
+ This signal is emitted when the \l target is tapped once. After an amount
+ of time greater than QStyleHints::mouseDoubleClickInterval, it can be
+ tapped again; but if the time until the next tap is less, \l tapCount
+ will increase.
+*/
+
+/*!
+ \qmlsignal TapHandler::doubleTapped
+ \since 5.11
+
+ This signal is emitted when the \l target is tapped twice within a short
+ span of time (QStyleHints::mouseDoubleClickInterval) and distance
+ (QPlatformTheme::MouseDoubleClickDistance or
+ QPlatformTheme::TouchDoubleTapDistance). This signal always occurs
+ after singleTapped, tapped and tapCountChanged.
+*/
QT_END_NAMESPACE
diff --git a/src/quick/handlers/qquicktaphandler_p.h b/src/quick/handlers/qquicktaphandler_p.h
index 6504ec87f0..b7c1895926 100644
--- a/src/quick/handlers/qquicktaphandler_p.h
+++ b/src/quick/handlers/qquicktaphandler_p.h
@@ -75,7 +75,7 @@ public:
};
Q_ENUM(GesturePolicy)
- explicit QQuickTapHandler(QObject *parent = 0);
+ explicit QQuickTapHandler(QObject *parent = nullptr);
~QQuickTapHandler();
bool isPressed() const { return m_pressed; }
@@ -96,6 +96,8 @@ Q_SIGNALS:
void longPressThresholdChanged();
void gesturePolicyChanged();
void tapped();
+ void singleTapped();
+ void doubleTapped();
void longPressed();
protected:
diff --git a/src/quick/items/context2d/qquickcanvascontext_p.h b/src/quick/items/context2d/qquickcanvascontext_p.h
index 0746b7dcd3..95100d2912 100644
--- a/src/quick/items/context2d/qquickcanvascontext_p.h
+++ b/src/quick/items/context2d/qquickcanvascontext_p.h
@@ -69,7 +69,7 @@ class QQuickCanvasContext : public QObject
Q_OBJECT
public:
- QQuickCanvasContext(QObject *parent = 0);
+ QQuickCanvasContext(QObject *parent = nullptr);
~QQuickCanvasContext();
virtual QStringList contextNames() const = 0;
diff --git a/src/quick/items/context2d/qquickcanvasitem.cpp b/src/quick/items/context2d/qquickcanvasitem.cpp
index 57936d8cec..59917ce531 100644
--- a/src/quick/items/context2d/qquickcanvasitem.cpp
+++ b/src/quick/items/context2d/qquickcanvasitem.cpp
@@ -71,7 +71,7 @@ public:
};
QQuickCanvasPixmap::QQuickCanvasPixmap(const QImage& image)
- : m_pixmap(0)
+ : m_pixmap(nullptr)
, m_image(image)
{
@@ -123,7 +123,7 @@ QHash<QQmlEngine *,QQuickContext2DRenderThread*> QQuickContext2DRenderThread::re
QMutex QQuickContext2DRenderThread::renderThreadsMutex;
QQuickContext2DRenderThread::QQuickContext2DRenderThread(QQmlEngine *eng)
- : QThread(eng), m_engine(eng), m_eventLoopQuitHack(0)
+ : QThread(eng), m_engine(eng), m_eventLoopQuitHack(nullptr)
{
Q_ASSERT(eng);
m_eventLoopQuitHack = new QObject;
@@ -144,7 +144,7 @@ QQuickContext2DRenderThread::~QQuickContext2DRenderThread()
QQuickContext2DRenderThread *QQuickContext2DRenderThread::instance(QQmlEngine *engine)
{
- QQuickContext2DRenderThread *thread = 0;
+ QQuickContext2DRenderThread *thread = nullptr;
renderThreadsMutex.lock();
if (renderThreads.contains(engine))
thread = renderThreads.value(engine);
@@ -183,7 +183,7 @@ public:
QQuickCanvasItemPrivate::QQuickCanvasItemPrivate()
: QQuickItemPrivate()
- , context(0)
+ , context(nullptr)
, canvasSize(1, 1)
, tileSize(1, 1)
, hasCanvasSize(false)
@@ -192,9 +192,9 @@ QQuickCanvasItemPrivate::QQuickCanvasItemPrivate()
, available(false)
, renderTarget(QQuickCanvasItem::Image)
, renderStrategy(QQuickCanvasItem::Immediate)
- , textureProvider(0)
- , node(0)
- , nodeTexture(0)
+ , textureProvider(nullptr)
+ , node(nullptr)
+ , nodeTexture(nullptr)
{
implicitAntialiasing = true;
}
@@ -634,16 +634,16 @@ void QQuickCanvasItem::releaseResources()
if (d->context) {
delete d->context;
- d->context = 0;
+ d->context = nullptr;
}
- d->node = 0; // managed by the scene graph, just reset the pointer
+ d->node = nullptr; // managed by the scene graph, just reset the pointer
if (d->textureProvider) {
QQuickWindowQObjectCleanupJob::schedule(window(), d->textureProvider);
- d->textureProvider = 0;
+ d->textureProvider = nullptr;
}
if (d->nodeTexture) {
QQuickWindowQObjectCleanupJob::schedule(window(), d->nodeTexture);
- d->nodeTexture = 0;
+ d->nodeTexture = nullptr;
}
}
@@ -663,12 +663,12 @@ void QQuickCanvasItem::invalidateSceneGraph()
Q_D(QQuickCanvasItem);
if (d->context)
d->context->deleteLater();
- d->context = 0;
- d->node = 0; // managed by the scene graph, just reset the pointer
+ d->context = nullptr;
+ d->node = nullptr; // managed by the scene graph, just reset the pointer
delete d->textureProvider;
- d->textureProvider = 0;
+ d->textureProvider = nullptr;
delete d->nodeTexture;
- d->nodeTexture = 0;
+ d->nodeTexture = nullptr;
}
void QQuickCanvasItem::schedulePolish()
@@ -698,14 +698,14 @@ void QQuickCanvasItem::itemChange(QQuickItem::ItemChange change, const QQuickIte
return;
}
- if (value.window== 0)
+ if (value.window== nullptr)
return;
d->window = value.window;
QSGRenderContext *context = QQuickWindowPrivate::get(d->window)->context;
// Rendering to FramebufferObject needs a valid OpenGL context.
- if (context != 0 && (d->renderTarget != FramebufferObject || context->isValid())) {
+ if (context != nullptr && (d->renderTarget != FramebufferObject || context->isValid())) {
// Defer the call. In some (arguably incorrect) cases we get here due
// to ItemSceneChange with the user-supplied property values not yet
// set. Work this around by a deferred invoke. (QTBUG-49692)
@@ -727,7 +727,7 @@ void QQuickCanvasItem::updatePolish()
QMap<int, QV4::PersistentValue> animationCallbacks = d->animationCallbacks;
d->animationCallbacks.clear();
- QV4::ExecutionEngine *v4 = QQmlEnginePrivate::getV4Engine(qmlEngine(this));
+ QV4::ExecutionEngine *v4 = qmlEngine(this)->handle();
QV4::Scope scope(v4);
QV4::ScopedFunctionObject function(scope);
QV4::JSCallData jsCall(scope, 1);
@@ -763,11 +763,11 @@ QSGNode *QQuickCanvasItem::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData
if (!d->context || d->canvasWindow.size().isEmpty()) {
if (d->textureProvider) {
- d->textureProvider->tex = 0;
+ d->textureProvider->tex = nullptr;
d->textureProvider->fireTextureChanged();
}
delete oldNode;
- return 0;
+ return nullptr;
}
QSGInternalImageNode *node = static_cast<QSGInternalImageNode *>(oldNode);
@@ -792,13 +792,13 @@ QSGNode *QQuickCanvasItem::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData
QSGTexture *texture = factory->textureForNextFrame(d->nodeTexture, window());
if (!texture) {
delete node;
- d->node = 0;
- d->nodeTexture = 0;
+ d->node = nullptr;
+ d->nodeTexture = nullptr;
if (d->textureProvider) {
- d->textureProvider->tex = 0;
+ d->textureProvider->tex = nullptr;
d->textureProvider->fireTextureChanged();
}
- return 0;
+ return nullptr;
}
d->nodeTexture = texture;
@@ -833,7 +833,7 @@ QSGTextureProvider *QQuickCanvasItem::textureProvider() const
if (!w || !w->isSceneGraphInitialized()
|| QThread::currentThread() != QQuickWindowPrivate::get(w)->context->thread()) {
qWarning("QQuickCanvasItem::textureProvider: can only be queried on the rendering thread of an exposed window");
- return 0;
+ return nullptr;
}
#endif
if (!d->textureProvider)
@@ -879,7 +879,7 @@ void QQuickCanvasItem::getContext(QQmlV4Function *args)
QString contextId = str->toQString();
- if (d->context != 0) {
+ if (d->context != nullptr) {
if (d->context->contextNames().contains(contextId, Qt::CaseInsensitive)) {
args->setReturnValue(d->context->v4value());
return;
@@ -1210,7 +1210,7 @@ void QQuickCanvasItem::initializeContext(QQuickCanvasContext *context, const QVa
d->context = context;
d->context->init(this, args);
- d->context->setV4Engine(QQmlEnginePrivate::get(qmlEngine(this))->v4engine());
+ d->context->setV4Engine(qmlEngine(this)->handle());
connect(d->context, SIGNAL(textureChanged()), SLOT(update()));
connect(d->context, SIGNAL(textureChanged()), SIGNAL(painted()));
emit contextChanged();
diff --git a/src/quick/items/context2d/qquickcanvasitem_p.h b/src/quick/items/context2d/qquickcanvasitem_p.h
index 59de847680..7dc981a6eb 100644
--- a/src/quick/items/context2d/qquickcanvasitem_p.h
+++ b/src/quick/items/context2d/qquickcanvasitem_p.h
@@ -114,7 +114,7 @@ public:
};
Q_ENUM(RenderStrategy)
- QQuickCanvasItem(QQuickItem *parent = 0);
+ QQuickCanvasItem(QQuickItem *parent = nullptr);
~QQuickCanvasItem();
bool isAvailable() const;
diff --git a/src/quick/items/context2d/qquickcontext2d.cpp b/src/quick/items/context2d/qquickcontext2d.cpp
index 49b2bf5838..af8048f2e4 100644
--- a/src/quick/items/context2d/qquickcontext2d.cpp
+++ b/src/quick/items/context2d/qquickcontext2d.cpp
@@ -304,7 +304,7 @@ static QStringList qExtractFontFamiliesFromString(const QStringRef &fontFamilies
return extractedFamilies;
}
-/*!
+/*
Tries to set a family on \a font using the families provided in \a fontFamilyTokens.
The list is ordered by preference, with the first family having the highest preference.
@@ -364,7 +364,7 @@ if (!(usedTokens & token)) { \
return currentFont; \
}
-/*!
+/*
Parses a font string based on the CSS shorthand font property.
See: http://www.w3.org/TR/css3-fonts/#font-prop
@@ -544,46 +544,46 @@ struct QQuickJSContext2D : public QV4::Object
{
V4_OBJECT2(QQuickJSContext2D, QV4::Object)
- static QV4::ReturnedValue method_get_globalAlpha(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_globalAlpha(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_globalCompositeOperation(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_globalCompositeOperation(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_fillStyle(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_fillStyle(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_fillRule(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_fillRule(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_strokeStyle(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_strokeStyle(const QV4::BuiltinFunction *b, QV4::CallData *callData);
-
- static QV4::ReturnedValue method_get_lineCap(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_lineCap(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_lineJoin(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_lineJoin(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_lineWidth(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_lineWidth(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_miterLimit(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_miterLimit(const QV4::BuiltinFunction *b, QV4::CallData *callData);
-
- static QV4::ReturnedValue method_get_shadowBlur(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_shadowBlur(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_shadowColor(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_shadowColor(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_shadowOffsetX(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_shadowOffsetX(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_shadowOffsetY(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_shadowOffsetY(const QV4::BuiltinFunction *b, QV4::CallData *callData);
+ static QV4::ReturnedValue method_get_globalAlpha(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_globalAlpha(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_globalCompositeOperation(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_globalCompositeOperation(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_fillStyle(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_fillStyle(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_fillRule(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_fillRule(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_strokeStyle(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_strokeStyle(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+
+ static QV4::ReturnedValue method_get_lineCap(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_lineCap(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_lineJoin(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_lineJoin(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_lineWidth(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_lineWidth(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_miterLimit(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_miterLimit(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+
+ static QV4::ReturnedValue method_get_shadowBlur(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_shadowBlur(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_shadowColor(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_shadowColor(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_shadowOffsetX(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_shadowOffsetX(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_shadowOffsetY(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_shadowOffsetY(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
// should these two be on the proto?
#if QT_CONFIG(quick_path)
- static QV4::ReturnedValue method_get_path(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_path(const QV4::BuiltinFunction *b, QV4::CallData *callData);
+ static QV4::ReturnedValue method_get_path(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_path(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
#endif
- static QV4::ReturnedValue method_get_font(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_font(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_textAlign(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_textAlign(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_textBaseline(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_set_textBaseline(const QV4::BuiltinFunction *b, QV4::CallData *callData);
+ static QV4::ReturnedValue method_get_font(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_font(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_textAlign(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_textAlign(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_textBaseline(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_set_textBaseline(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
DEFINE_OBJECT_VTABLE(QQuickJSContext2D);
@@ -641,55 +641,55 @@ public:
o->defineDefaultProperty(QStringLiteral("createLinearGradient"), method_createLinearGradient, 0);
o->defineDefaultProperty(QStringLiteral("strokeRect"), method_strokeRect, 0);
o->defineDefaultProperty(QStringLiteral("closePath"), method_closePath, 0);
- o->defineAccessorProperty(QStringLiteral("canvas"), QQuickJSContext2DPrototype::method_get_canvas, 0);
+ o->defineAccessorProperty(QStringLiteral("canvas"), QQuickJSContext2DPrototype::method_get_canvas, nullptr);
return o->d();
}
- static QV4::ReturnedValue method_get_canvas(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_restore(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_reset(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_save(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_rotate(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_scale(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_translate(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_setTransform(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_transform(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_resetTransform(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_shear(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_createLinearGradient(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_createRadialGradient(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_createConicalGradient(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_createPattern(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_clearRect(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_fillRect(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_strokeRect(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_arc(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_arcTo(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_beginPath(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_bezierCurveTo(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_clip(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_closePath(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_fill(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_lineTo(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_moveTo(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_quadraticCurveTo(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_rect(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_roundedRect(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_ellipse(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_text(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_stroke(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_isPointInPath(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_drawFocusRing(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_setCaretSelectionRect(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_caretBlinkRate(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_fillText(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_strokeText(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_measureText(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_drawImage(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_createImageData(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_getImageData(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_putImageData(const QV4::BuiltinFunction *b, QV4::CallData *callData);
+ static QV4::ReturnedValue method_get_canvas(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_restore(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_reset(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_save(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_rotate(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_scale(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_translate(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_setTransform(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_transform(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_resetTransform(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_shear(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_createLinearGradient(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_createRadialGradient(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_createConicalGradient(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_createPattern(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_clearRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_fillRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_strokeRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_arc(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_arcTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_beginPath(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_bezierCurveTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_clip(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_closePath(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_fill(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_lineTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_moveTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_quadraticCurveTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_rect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_roundedRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_ellipse(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_text(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_stroke(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_isPointInPath(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_drawFocusRing(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_setCaretSelectionRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_caretBlinkRate(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_fillText(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_strokeText(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_measureText(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_drawImage(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_createImageData(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_getImageData(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_putImageData(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
@@ -701,7 +701,7 @@ struct QQuickContext2DStyle : public QV4::Object
V4_OBJECT2(QQuickContext2DStyle, QV4::Object)
V4_NEEDS_DESTROY
- static QV4::ReturnedValue gradient_proto_addColorStop(const QV4::BuiltinFunction *b, QV4::CallData *callData);
+ static QV4::ReturnedValue gradient_proto_addColorStop(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
@@ -911,7 +911,7 @@ struct QQuickJSContext2DPixelData : public QV4::Object
static QV4::ReturnedValue getIndexed(const QV4::Managed *m, uint index, bool *hasProperty);
static bool putIndexed(QV4::Managed *m, uint index, const QV4::Value &value);
- static QV4::ReturnedValue proto_get_length(const QV4::BuiltinFunction *b, QV4::CallData *callData);
+ static QV4::ReturnedValue proto_get_length(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
void QV4::Heap::QQuickJSContext2DPixelData::init()
@@ -929,9 +929,9 @@ struct QQuickJSContext2DImageData : public QV4::Object
{
V4_OBJECT2(QQuickJSContext2DImageData, QV4::Object)
- static QV4::ReturnedValue method_get_width(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_height(const QV4::BuiltinFunction *b, QV4::CallData *callData);
- static QV4::ReturnedValue method_get_data(const QV4::BuiltinFunction *b, QV4::CallData *callData);
+ static QV4::ReturnedValue method_get_width(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_height(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
+ static QV4::ReturnedValue method_get_data(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc);
};
@@ -943,9 +943,9 @@ void QV4::Heap::QQuickJSContext2DImageData::init()
QV4::Scope scope(internalClass->engine);
QV4::ScopedObject o(scope, this);
- o->defineAccessorProperty(QStringLiteral("width"), ::QQuickJSContext2DImageData::method_get_width, 0);
- o->defineAccessorProperty(QStringLiteral("height"), ::QQuickJSContext2DImageData::method_get_height, 0);
- o->defineAccessorProperty(QStringLiteral("data"), ::QQuickJSContext2DImageData::method_get_data, 0);
+ o->defineAccessorProperty(QStringLiteral("width"), ::QQuickJSContext2DImageData::method_get_width, nullptr);
+ o->defineAccessorProperty(QStringLiteral("height"), ::QQuickJSContext2DImageData::method_get_height, nullptr);
+ o->defineAccessorProperty(QStringLiteral("data"), ::QQuickJSContext2DImageData::method_get_data, nullptr);
}
DEFINE_OBJECT_VTABLE(QQuickJSContext2DImageData);
@@ -979,10 +979,10 @@ static QV4::ReturnedValue qt_create_image_data(qreal w, qreal h, QV4::ExecutionE
This property is read only.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_get_canvas(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_get_canvas(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
RETURN_RESULT(QV4::QObjectWrapper::wrap(scope.engine, r->d()->context->canvas()));
@@ -994,29 +994,29 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_get_canvas(const QV4::Buil
\sa save()
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_restore(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_restore(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
r->d()->context->popState();
- RETURN_RESULT(callData->thisObject.asReturnedValue());
+ RETURN_RESULT(thisObject->asReturnedValue());
}
/*!
\qmlmethod object QtQuick::Context2D::reset()
Resets the context state and properties to the default values.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_reset(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_reset(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
r->d()->context->reset();
- RETURN_RESULT(callData->thisObject.asReturnedValue());
+ RETURN_RESULT(thisObject->asReturnedValue());
}
/*!
@@ -1049,15 +1049,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_reset(const QV4::BuiltinFu
The current path is NOT part of the drawing state. The path can be reset by
invoking the beginPath() method.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_save(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_save(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
r->d()->context->pushState();
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
// transformations
@@ -1078,15 +1078,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_save(const QV4::BuiltinFun
where the \a angle of rotation is in radians.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_rotate(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_rotate(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 1)
- r->d()->context->rotate(callData->args[0].toNumber());
- RETURN_RESULT(callData->thisObject);
+ if (argc >= 1)
+ r->d()->context->rotate(argv[0].toNumber());
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -1106,16 +1106,16 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_rotate(const QV4::BuiltinF
\image qml-item-canvas-scale.png
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_scale(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_scale(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 2)
- r->d()->context->scale(callData->args[0].toNumber(), callData->args[1].toNumber());
- RETURN_RESULT(callData->thisObject);
+ if (argc >= 2)
+ r->d()->context->scale(argv[0].toNumber(), argv[1].toNumber());
+ RETURN_RESULT(*thisObject);
}
@@ -1153,22 +1153,22 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_scale(const QV4::BuiltinFu
\sa transform()
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_setTransform(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_setTransform(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 6)
- r->d()->context->setTransform( callData->args[0].toNumber()
- , callData->args[1].toNumber()
- , callData->args[2].toNumber()
- , callData->args[3].toNumber()
- , callData->args[4].toNumber()
- , callData->args[5].toNumber());
+ if (argc >= 6)
+ r->d()->context->setTransform( argv[0].toNumber()
+ , argv[1].toNumber()
+ , argv[2].toNumber()
+ , argv[3].toNumber()
+ , argv[4].toNumber()
+ , argv[5].toNumber());
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -1183,21 +1183,21 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_setTransform(const QV4::Bu
\sa setTransform()
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_transform(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_transform(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 6)
- r->d()->context->transform( callData->args[0].toNumber()
- , callData->args[1].toNumber()
- , callData->args[2].toNumber()
- , callData->args[3].toNumber()
- , callData->args[4].toNumber()
- , callData->args[5].toNumber());
+ if (argc >= 6)
+ r->d()->context->transform( argv[0].toNumber()
+ , argv[1].toNumber()
+ , argv[2].toNumber()
+ , argv[3].toNumber()
+ , argv[4].toNumber()
+ , argv[5].toNumber());
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -1210,15 +1210,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_transform(const QV4::Built
Translating the origin enables you to draw patterns of different objects on the canvas
without having to measure the coordinates manually for each shape.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_translate(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_translate(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 2)
- r->d()->context->translate(callData->args[0].toNumber(), callData->args[1].toNumber());
- RETURN_RESULT(callData->thisObject);
+ if (argc >= 2)
+ r->d()->context->translate(argv[0].toNumber(), argv[1].toNumber());
+ RETURN_RESULT(*thisObject);
}
@@ -1231,15 +1231,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_translate(const QV4::Built
\sa transform(), setTransform(), reset()
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_resetTransform(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_resetTransform(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
r->d()->context->setTransform(1, 0, 0, 1, 0, 0);
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -1250,16 +1250,16 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_resetTransform(const QV4::
Shears the transformation matrix by \a sh in the horizontal direction and
\a sv in the vertical direction.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_shear(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_shear(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 2)
- r->d()->context->shear(callData->args[0].toNumber(), callData->args[1].toNumber());
+ if (argc >= 2)
+ r->d()->context->shear(argv[0].toNumber(), argv[1].toNumber());
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
// compositing
@@ -1271,22 +1271,22 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_shear(const QV4::BuiltinFu
The value must be in the range from \c 0.0 (fully transparent) to \c 1.0 (fully opaque).
The default value is \c 1.0.
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_globalAlpha(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_globalAlpha(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
RETURN_RESULT(QV4::Encode(r->d()->context->state.globalAlpha));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_globalAlpha(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_globalAlpha(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT_SETTER(r)
- double globalAlpha = callData->argc() ? callData->args[0].toNumber() : qt_qnan();
+ double globalAlpha = argc ? argv[0].toNumber() : qt_qnan();
if (!qt_is_finite(globalAlpha))
@@ -1325,25 +1325,25 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_globalAlpha(const QV4::BuiltinF
extension composition modes are provided as "vendorName-operationName" syntax, for example: QPainter::CompositionMode_Exclusion is provided as
"qt-exclusion".
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_globalCompositeOperation(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_globalCompositeOperation(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
RETURN_RESULT(scope.engine->newString(qt_composite_mode_to_string(r->d()->context->state.globalCompositeOperation)));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_globalCompositeOperation(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_globalCompositeOperation(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT_SETTER(r)
- if (!callData->argc())
+ if (!argc)
THROW_TYPE_ERROR();
- QString mode = callData->args[0].toQString();
+ QString mode = argv[0].toQString();
QPainter::CompositionMode cm = qt_composite_mode_from_string(mode);
if (cm == QPainter::CompositionMode_SourceOver && mode != QLatin1String("source-over"))
RETURN_UNDEFINED();
@@ -1379,10 +1379,10 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_globalCompositeOperation(const
\sa createPattern()
\sa strokeStyle
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_fillStyle(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_fillStyle(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
QColor color = r->d()->context->state.fillStyle.color();
@@ -1400,13 +1400,13 @@ QV4::ReturnedValue QQuickJSContext2D::method_get_fillStyle(const QV4::BuiltinFun
RETURN_RESULT(r->d()->context->m_fillStyle.value());
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_fillStyle(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_fillStyle(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT_SETTER(r)
- QV4::ScopedValue value(scope, callData->argument(0));
+ QV4::ScopedValue value(scope, argc ? argv[0] : QV4::Primitive::undefinedValue());
if (value->as<Object>()) {
QColor color = scope.engine->toVariant(value, qMetaTypeId<QColor>()).value<QColor>();
@@ -1446,22 +1446,22 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_fillStyle(const QV4::BuiltinFun
\sa fillStyle
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_fillRule(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_fillRule(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
RETURN_RESULT(scope.engine->fromVariant(r->d()->context->state.fillRule));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_fillRule(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_fillRule(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT_SETTER(r)
- QV4::ScopedValue value(scope, callData->argument(0));
+ QV4::ScopedValue value(scope, argc ? argv[0] : QV4::Primitive::undefinedValue());
if ((value->isString() && value->toQString() == QLatin1String("WindingFill"))
|| (value->isInt32() && value->integerValue() == Qt::WindingFill)) {
@@ -1488,10 +1488,10 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_fillRule(const QV4::BuiltinFunc
\sa createPattern()
\sa fillStyle
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_strokeStyle(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_strokeStyle(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
QColor color = r->d()->context->state.strokeStyle.color();
@@ -1509,13 +1509,13 @@ QV4::ReturnedValue QQuickJSContext2D::method_get_strokeStyle(const QV4::BuiltinF
RETURN_RESULT(r->d()->context->m_strokeStyle.value());
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_strokeStyle(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_strokeStyle(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT_SETTER(r)
- QV4::ScopedValue value(scope, callData->argument(0));
+ QV4::ScopedValue value(scope, argc ? argv[0] : QV4::Primitive::undefinedValue());
if (value->as<Object>()) {
QColor color = scope.engine->toVariant(value, qMetaTypeId<QColor>()).value<QColor>();
@@ -1562,17 +1562,17 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_strokeStyle(const QV4::BuiltinF
\sa strokeStyle
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_createLinearGradient(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_createLinearGradient(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 4) {
- qreal x0 = callData->args[0].toNumber();
- qreal y0 = callData->args[1].toNumber();
- qreal x1 = callData->args[2].toNumber();
- qreal y1 = callData->args[3].toNumber();
+ if (argc >= 4) {
+ qreal x0 = argv[0].toNumber();
+ qreal y0 = argv[1].toNumber();
+ qreal x1 = argv[2].toNumber();
+ qreal y1 = argv[3].toNumber();
if (!qt_is_finite(x0)
|| !qt_is_finite(y0)
@@ -1589,7 +1589,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createLinearGradient(const
RETURN_RESULT(*gradient);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -1606,19 +1606,19 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createLinearGradient(const
\sa strokeStyle
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_createRadialGradient(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_createRadialGradient(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 6) {
- qreal x0 = callData->args[0].toNumber();
- qreal y0 = callData->args[1].toNumber();
- qreal r0 = callData->args[2].toNumber();
- qreal x1 = callData->args[3].toNumber();
- qreal y1 = callData->args[4].toNumber();
- qreal r1 = callData->args[5].toNumber();
+ if (argc >= 6) {
+ qreal x0 = argv[0].toNumber();
+ qreal y0 = argv[1].toNumber();
+ qreal r0 = argv[2].toNumber();
+ qreal x1 = argv[3].toNumber();
+ qreal y1 = argv[4].toNumber();
+ qreal r1 = argv[5].toNumber();
if (!qt_is_finite(x0)
|| !qt_is_finite(y0)
@@ -1641,7 +1641,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createRadialGradient(const
RETURN_RESULT(*gradient);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -1658,16 +1658,16 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createRadialGradient(const
\sa strokeStyle
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_createConicalGradient(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_createConicalGradient(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 3) {
- qreal x = callData->args[0].toNumber();
- qreal y = callData->args[1].toNumber();
- qreal angle = qRadiansToDegrees(callData->args[2].toNumber());
+ if (argc >= 3) {
+ qreal x = argv[0].toNumber();
+ qreal y = argv[1].toNumber();
+ qreal angle = qRadiansToDegrees(argv[2].toNumber());
if (!qt_is_finite(x) || !qt_is_finite(y)) {
THROW_DOM(DOMEXCEPTION_NOT_SUPPORTED_ERR, "createConicalGradient(): Incorrect arguments");
}
@@ -1685,7 +1685,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createConicalGradient(cons
RETURN_RESULT(*gradient);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -1731,18 +1731,18 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createConicalGradient(cons
\sa strokeStyle
\sa fillStyle
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_createPattern(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_createPattern(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 2) {
+ if (argc >= 2) {
QV4::Scoped<QQuickContext2DStyle> pattern(scope, scope.engine->memoryManager->allocObject<QQuickContext2DStyle>());
- QColor color = scope.engine->toVariant(callData->args[0], qMetaTypeId<QColor>()).value<QColor>();
+ QColor color = scope.engine->toVariant(argv[0], qMetaTypeId<QColor>()).value<QColor>();
if (color.isValid()) {
- int patternMode = callData->args[1].toInt32();
+ int patternMode = argv[1].toInt32();
Qt::BrushStyle style = Qt::SolidPattern;
if (patternMode >= 0 && patternMode < Qt::LinearGradientPattern) {
style = static_cast<Qt::BrushStyle>(patternMode);
@@ -1751,20 +1751,20 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createPattern(const QV4::B
} else {
QImage patternTexture;
- if (const QV4::Object *o = callData->args[0].as<Object>()) {
+ if (const QV4::Object *o = argv[0].as<Object>()) {
QV4::ScopedString s(scope, scope.engine->newString(QStringLiteral("data")));
QV4::Scoped<QQuickJSContext2DPixelData> pixelData(scope, o->get(s));
if (!!pixelData) {
patternTexture = *pixelData->d()->image;
}
} else {
- patternTexture = r->d()->context->createPixmap(QUrl(callData->args[0].toQStringNoThrow()))->image();
+ patternTexture = r->d()->context->createPixmap(QUrl(argv[0].toQStringNoThrow()))->image();
}
if (!patternTexture.isNull()) {
pattern->d()->brush->setTextureImage(patternTexture);
- QString repetition = callData->args[1].toQStringNoThrow();
+ QString repetition = argv[1].toQStringNoThrow();
if (repetition == QLatin1String("repeat") || repetition.isEmpty()) {
pattern->d()->patternRepeatX = true;
pattern->d()->patternRepeatY = true;
@@ -1802,10 +1802,10 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createPattern(const QV4::B
\endlist
Other values are ignored.
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_lineCap(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_lineCap(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
switch (r->d()->context->state.lineCap) {
@@ -1820,14 +1820,16 @@ QV4::ReturnedValue QQuickJSContext2D::method_get_lineCap(const QV4::BuiltinFunct
RETURN_RESULT(scope.engine->newString(QStringLiteral("butt")));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_lineCap(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_lineCap(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
+ if (!argc)
+ return QV4::Encode::undefined();
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- QString lineCap = callData->args[0].toQString();
+ QString lineCap = argv[0].toQString();
Qt::PenCapStyle cap;
if (lineCap == QLatin1String("round"))
cap = Qt::RoundCap;
@@ -1859,10 +1861,10 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_lineCap(const QV4::BuiltinFunct
\endlist
Other values are ignored.
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_lineJoin(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_lineJoin(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
switch (r->d()->context->state.lineJoin) {
@@ -1877,16 +1879,16 @@ QV4::ReturnedValue QQuickJSContext2D::method_get_lineJoin(const QV4::BuiltinFunc
RETURN_RESULT(scope.engine->newString(QStringLiteral("miter")));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_lineJoin(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_lineJoin(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- if (!callData->argc())
+ if (!argc)
THROW_TYPE_ERROR();
- QString lineJoin = callData->args[0].toQString();
+ QString lineJoin = argv[0].toQString();
Qt::PenJoinStyle join;
if (lineJoin == QLatin1String("round"))
join = Qt::RoundJoin;
@@ -1908,22 +1910,22 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_lineJoin(const QV4::BuiltinFunc
\qmlproperty real QtQuick::Context2D::lineWidth
Holds the current line width. Values that are not finite values greater than zero are ignored.
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_lineWidth(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_lineWidth(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
RETURN_RESULT(QV4::Encode(r->d()->context->state.lineWidth));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_lineWidth(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_lineWidth(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- qreal w = callData->argc() ? callData->args[0].toNumber() : -1;
+ qreal w = argc ? argv[0].toNumber() : -1;
if (w > 0 && qt_is_finite(w) && w != r->d()->context->state.lineWidth) {
r->d()->context->state.lineWidth = w;
@@ -1937,22 +1939,22 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_lineWidth(const QV4::BuiltinFun
Holds the current miter limit ratio.
The default miter limit value is 10.0.
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_miterLimit(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_miterLimit(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
RETURN_RESULT(QV4::Encode(r->d()->context->state.miterLimit));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_miterLimit(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_miterLimit(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- qreal ml = callData->argc() ? callData->args[0].toNumber() : -1;
+ qreal ml = argc ? argv[0].toNumber() : -1;
if (ml > 0 && qt_is_finite(ml) && ml != r->d()->context->state.miterLimit) {
r->d()->context->state.miterLimit = ml;
@@ -1966,22 +1968,22 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_miterLimit(const QV4::BuiltinFu
\qmlproperty real QtQuick::Context2D::shadowBlur
Holds the current level of blur applied to shadows
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_shadowBlur(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_shadowBlur(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
RETURN_RESULT(QV4::Encode(r->d()->context->state.shadowBlur));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_shadowBlur(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_shadowBlur(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- qreal blur = callData->argc() ? callData->args[0].toNumber() : -1;
+ qreal blur = argc ? argv[0].toNumber() : -1;
if (blur > 0 && qt_is_finite(blur) && blur != r->d()->context->state.shadowBlur) {
r->d()->context->state.shadowBlur = blur;
@@ -1994,24 +1996,24 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_shadowBlur(const QV4::BuiltinFu
\qmlproperty string QtQuick::Context2D::shadowColor
Holds the current shadow color.
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_shadowColor(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_shadowColor(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
RETURN_RESULT(scope.engine->newString(r->d()->context->state.shadowColor.name()));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_shadowColor(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_shadowColor(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
QColor color;
- if (callData->argc())
- color = qt_color_from_string(callData->args[0]);
+ if (argc)
+ color = qt_color_from_string(argv[0]);
if (color.isValid() && color != r->d()->context->state.shadowColor) {
r->d()->context->state.shadowColor = color;
@@ -2027,22 +2029,22 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_shadowColor(const QV4::BuiltinF
\sa shadowOffsetY
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_shadowOffsetX(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_shadowOffsetX(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
RETURN_RESULT(QV4::Encode(r->d()->context->state.shadowOffsetX));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_shadowOffsetX(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_shadowOffsetX(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- qreal offsetX = callData->argc() ? callData->args[0].toNumber() : qt_qnan();
+ qreal offsetX = argc ? argv[0].toNumber() : qt_qnan();
if (qt_is_finite(offsetX) && offsetX != r->d()->context->state.shadowOffsetX) {
r->d()->context->state.shadowOffsetX = offsetX;
r->d()->context->buffer()->setShadowOffsetX(offsetX);
@@ -2055,22 +2057,22 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_shadowOffsetX(const QV4::Builti
\sa shadowOffsetX
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_shadowOffsetY(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_shadowOffsetY(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
RETURN_RESULT(QV4::Encode(r->d()->context->state.shadowOffsetY));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_shadowOffsetY(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_shadowOffsetY(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- qreal offsetY = callData->argc() ? callData->args[0].toNumber() : qt_qnan();
+ qreal offsetY = argc ? argv[0].toNumber() : qt_qnan();
if (qt_is_finite(offsetY) && offsetY != r->d()->context->state.shadowOffsetY) {
r->d()->context->state.shadowOffsetY = offsetY;
r->d()->context->buffer()->setShadowOffsetY(offsetY);
@@ -2079,22 +2081,22 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_shadowOffsetY(const QV4::Builti
}
#if QT_CONFIG(quick_path)
-QV4::ReturnedValue QQuickJSContext2D::method_get_path(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_path(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
RETURN_RESULT(r->d()->context->m_v4path.value());
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_path(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_path(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- QV4::ScopedValue value(scope, callData->argument(0));
+ QV4::ScopedValue value(scope, argc ? argv[0] : QV4::Primitive::undefinedValue());
r->d()->context->beginPath();
QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, value);
if (!!qobjectWrapper) {
@@ -2114,20 +2116,20 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_path(const QV4::BuiltinFunction
\qmlmethod object QtQuick::Context2D::clearRect(real x, real y, real w, real h)
Clears all pixels on the canvas in the given rectangle to transparent black.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_clearRect(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_clearRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 4)
- r->d()->context->clearRect(callData->args[0].toNumber(),
- callData->args[1].toNumber(),
- callData->args[2].toNumber(),
- callData->args[3].toNumber());
+ if (argc >= 4)
+ r->d()->context->clearRect(argv[0].toNumber(),
+ argv[1].toNumber(),
+ argv[2].toNumber(),
+ argv[3].toNumber());
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2136,15 +2138,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_clearRect(const QV4::Built
\sa fillStyle
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_fillRect(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_fillRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 4)
- r->d()->context->fillRect(callData->args[0].toNumber(), callData->args[1].toNumber(), callData->args[2].toNumber(), callData->args[3].toNumber());
- RETURN_RESULT(callData->thisObject);
+ if (argc >= 4)
+ r->d()->context->fillRect(argv[0].toNumber(), argv[1].toNumber(), argv[2].toNumber(), argv[3].toNumber());
+ RETURN_RESULT(*thisObject);
}
@@ -2158,16 +2160,16 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_fillRect(const QV4::Builti
\sa lineJoin
\sa miterLimit
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_strokeRect(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_strokeRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 4)
- r->d()->context->strokeRect(callData->args[0].toNumber(), callData->args[1].toNumber(), callData->args[2].toNumber(), callData->args[3].toNumber());
+ if (argc >= 4)
+ r->d()->context->strokeRect(argv[0].toNumber(), argv[1].toNumber(), argv[2].toNumber(), argv[3].toNumber());
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -2192,32 +2194,32 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_strokeRect(const QV4::Buil
\sa arcTo, {http://www.w3.org/TR/2dcontext/#dom-context-2d-arc}{W3C's 2D
Context Standard for arc()}
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_arc(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_arc(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 5) {
+ if (argc >= 5) {
bool antiClockwise = false;
- if (callData->argc() == 6)
- antiClockwise = callData->args[5].toBoolean();
+ if (argc == 6)
+ antiClockwise = argv[5].toBoolean();
- qreal radius = callData->args[2].toNumber();
+ qreal radius = argv[2].toNumber();
if (qt_is_finite(radius) && radius < 0)
THROW_DOM(DOMEXCEPTION_INDEX_SIZE_ERR, "Incorrect argument radius");
- r->d()->context->arc(callData->args[0].toNumber(),
- callData->args[1].toNumber(),
+ r->d()->context->arc(argv[0].toNumber(),
+ argv[1].toNumber(),
radius,
- callData->args[3].toNumber(),
- callData->args[4].toNumber(),
+ argv[3].toNumber(),
+ argv[4].toNumber(),
antiClockwise);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -2244,26 +2246,26 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_arc(const QV4::BuiltinFunc
\sa arc, {http://www.w3.org/TR/2dcontext/#dom-context-2d-arcto}{W3C's 2D
Context Standard for arcTo()}
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_arcTo(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_arcTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 5) {
- qreal radius = callData->args[4].toNumber();
+ if (argc >= 5) {
+ qreal radius = argv[4].toNumber();
if (qt_is_finite(radius) && radius < 0)
THROW_DOM(DOMEXCEPTION_INDEX_SIZE_ERR, "Incorrect argument radius");
- r->d()->context->arcTo(callData->args[0].toNumber(),
- callData->args[1].toNumber(),
- callData->args[2].toNumber(),
- callData->args[3].toNumber(),
+ r->d()->context->arcTo(argv[0].toNumber(),
+ argv[1].toNumber(),
+ argv[2].toNumber(),
+ argv[3].toNumber(),
radius);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -2272,15 +2274,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_arcTo(const QV4::BuiltinFu
Resets the current path to a new path.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_beginPath(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_beginPath(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
r->d()->context->beginPath();
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -2303,26 +2305,26 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_beginPath(const QV4::Built
\sa {http://www.w3.org/TR/2dcontext/#dom-context-2d-beziercurveto}{W3C 2d context standard for bezierCurveTo}
\sa {http://www.openrise.com/lab/FlowerPower/}{The beautiful flower demo by using bezierCurveTo}
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_bezierCurveTo(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_bezierCurveTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 6) {
- qreal cp1x = callData->args[0].toNumber();
- qreal cp1y = callData->args[1].toNumber();
- qreal cp2x = callData->args[2].toNumber();
- qreal cp2y = callData->args[3].toNumber();
- qreal x = callData->args[4].toNumber();
- qreal y = callData->args[5].toNumber();
+ if (argc >= 6) {
+ qreal cp1x = argv[0].toNumber();
+ qreal cp1y = argv[1].toNumber();
+ qreal cp2x = argv[2].toNumber();
+ qreal cp2y = argv[3].toNumber();
+ qreal x = argv[4].toNumber();
+ qreal y = argv[5].toNumber();
if (!qt_is_finite(cp1x) || !qt_is_finite(cp1y) || !qt_is_finite(cp2x) || !qt_is_finite(cp2y) || !qt_is_finite(x) || !qt_is_finite(y))
RETURN_UNDEFINED();
r->d()->context->bezierCurveTo(cp1x, cp1y, cp2x, cp2y, x, y);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2349,14 +2351,14 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_bezierCurveTo(const QV4::B
\sa fill()
\sa {http://www.w3.org/TR/2dcontext/#dom-context-2d-clip}{W3C 2d context standard for clip}
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_clip(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_clip(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
r->d()->context->clip();
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2366,15 +2368,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_clip(const QV4::BuiltinFun
\sa {http://www.w3.org/TR/2dcontext/#dom-context-2d-closepath}{W3C 2d context standard for closePath}
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_closePath(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_closePath(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
r->d()->context->closePath();
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2386,13 +2388,13 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_closePath(const QV4::Built
\sa fillStyle
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_fill(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_fill(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r);
r->d()->context->fill();
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2400,15 +2402,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_fill(const QV4::BuiltinFun
Draws a line from the current position to the point (x, y).
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_lineTo(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_lineTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 2) {
- qreal x = callData->args[0].toNumber();
- qreal y = callData->args[1].toNumber();
+ if (argc >= 2) {
+ qreal x = argv[0].toNumber();
+ qreal y = argv[1].toNumber();
if (!qt_is_finite(x) || !qt_is_finite(y))
RETURN_UNDEFINED();
@@ -2416,7 +2418,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_lineTo(const QV4::BuiltinF
r->d()->context->lineTo(x, y);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2424,22 +2426,22 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_lineTo(const QV4::BuiltinF
Creates a new subpath with the given point.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_moveTo(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_moveTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 2) {
- qreal x = callData->args[0].toNumber();
- qreal y = callData->args[1].toNumber();
+ if (argc >= 2) {
+ qreal x = argv[0].toNumber();
+ qreal y = argv[1].toNumber();
if (!qt_is_finite(x) || !qt_is_finite(y))
RETURN_UNDEFINED();
r->d()->context->moveTo(x, y);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2449,17 +2451,17 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_moveTo(const QV4::BuiltinF
See \l{http://www.w3.org/TR/2dcontext/#dom-context-2d-quadraticcurveto}{W3C 2d context standard for quadraticCurveTo}
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_quadraticCurveTo(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_quadraticCurveTo(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 4) {
- qreal cpx = callData->args[0].toNumber();
- qreal cpy = callData->args[1].toNumber();
- qreal x = callData->args[2].toNumber();
- qreal y = callData->args[3].toNumber();
+ if (argc >= 4) {
+ qreal cpx = argv[0].toNumber();
+ qreal cpy = argv[1].toNumber();
+ qreal x = argv[2].toNumber();
+ qreal y = argv[3].toNumber();
if (!qt_is_finite(cpx) || !qt_is_finite(cpy) || !qt_is_finite(x) || !qt_is_finite(y))
RETURN_UNDEFINED();
@@ -2467,7 +2469,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_quadraticCurveTo(const QV4
r->d()->context->quadraticCurveTo(cpx, cpy, x, y);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2475,15 +2477,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_quadraticCurveTo(const QV4
Adds a rectangle at position (\c x, \c y), with the given width \c w and height \c h, as a closed subpath.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_rect(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_rect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 4)
- r->d()->context->rect(callData->args[0].toNumber(), callData->args[1].toNumber(), callData->args[2].toNumber(), callData->args[3].toNumber());
- RETURN_RESULT(callData->thisObject);
+ if (argc >= 4)
+ r->d()->context->rect(argv[0].toNumber(), argv[1].toNumber(), argv[2].toNumber(), argv[3].toNumber());
+ RETURN_RESULT(*thisObject);
}
@@ -2493,20 +2495,20 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_rect(const QV4::BuiltinFun
Adds the given rectangle rect with rounded corners to the path. The \c xRadius and \c yRadius arguments specify the radius of the
ellipses defining the corners of the rounded rectangle.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_roundedRect(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_roundedRect(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 6)
- r->d()->context->roundedRect(callData->args[0].toNumber()
- , callData->args[1].toNumber()
- , callData->args[2].toNumber()
- , callData->args[3].toNumber()
- , callData->args[4].toNumber()
- , callData->args[5].toNumber());
- RETURN_RESULT(callData->thisObject);
+ if (argc >= 6)
+ r->d()->context->roundedRect(argv[0].toNumber()
+ , argv[1].toNumber()
+ , argv[2].toNumber()
+ , argv[3].toNumber()
+ , argv[4].toNumber()
+ , argv[5].toNumber());
+ RETURN_RESULT(*thisObject);
}
@@ -2518,16 +2520,16 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_roundedRect(const QV4::Bui
The ellipse is composed of a clockwise curve, starting and finishing at zero degrees (the 3 o'clock position).
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_ellipse(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_ellipse(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 4)
- r->d()->context->ellipse(callData->args[0].toNumber(), callData->args[1].toNumber(), callData->args[2].toNumber(), callData->args[3].toNumber());
+ if (argc >= 4)
+ r->d()->context->ellipse(argv[0].toNumber(), argv[1].toNumber(), argv[2].toNumber(), argv[3].toNumber());
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -2537,22 +2539,22 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_ellipse(const QV4::Builtin
Adds the given \c text to the path as a set of closed subpaths created from the current context font supplied.
The subpaths are positioned so that the left end of the text's baseline lies at the point specified by (\c x, \c y).
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_text(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_text(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 3) {
- qreal x = callData->args[1].toNumber();
- qreal y = callData->args[2].toNumber();
+ if (argc >= 3) {
+ qreal x = argv[1].toNumber();
+ qreal y = argv[2].toNumber();
if (!qt_is_finite(x) || !qt_is_finite(y))
RETURN_UNDEFINED();
- r->d()->context->text(callData->args[0].toQStringNoThrow(), x, y);
+ r->d()->context->text(argv[0].toQStringNoThrow(), x, y);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2564,14 +2566,14 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_text(const QV4::BuiltinFun
\sa strokeStyle
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_stroke(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_stroke(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
r->d()->context->stroke();
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
@@ -2582,31 +2584,31 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_stroke(const QV4::BuiltinF
\sa {http://www.w3.org/TR/2dcontext/#dom-context-2d-ispointinpath}{W3C 2d context standard for isPointInPath}
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_isPointInPath(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_isPointInPath(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
bool pointInPath = false;
- if (callData->argc() >= 2)
- pointInPath = r->d()->context->isPointInPath(callData->args[0].toNumber(), callData->args[1].toNumber());
+ if (argc >= 2)
+ pointInPath = r->d()->context->isPointInPath(argv[0].toNumber(), argv[1].toNumber());
RETURN_RESULT(QV4::Primitive::fromBoolean(pointInPath).asReturnedValue());
}
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawFocusRing(const QV4::BuiltinFunction *b, QV4::CallData *)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawFocusRing(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *, int)
{
QV4::Scope scope(b);
THROW_DOM(DOMEXCEPTION_NOT_SUPPORTED_ERR, "Context2D::drawFocusRing is not supported");
}
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_setCaretSelectionRect(const QV4::BuiltinFunction *b, QV4::CallData *)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_setCaretSelectionRect(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *, int)
{
QV4::Scope scope(b);
THROW_DOM(DOMEXCEPTION_NOT_SUPPORTED_ERR, "Context2D::setCaretSelectionRect is not supported");
}
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_caretBlinkRate(const QV4::BuiltinFunction *b, QV4::CallData *)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_caretBlinkRate(const QV4::FunctionObject *b, const QV4::Value *, const QV4::Value *, int)
{
QV4::Scope scope(b);
THROW_DOM(DOMEXCEPTION_NOT_SUPPORTED_ERR, "Context2D::caretBlinkRate is not supported");
@@ -2635,22 +2637,22 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_caretBlinkRate(const QV4::
The default font value is "10px sans-serif".
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_font(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_font(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
RETURN_RESULT(scope.engine->newString(r->d()->context->state.font.toString()));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_font(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_font(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- QV4::ScopedString s(scope, callData->argument(0), QV4::ScopedString::Convert);
+ QV4::ScopedString s(scope, argc ? argv[0] : QV4::Primitive::undefinedValue(), QV4::ScopedString::Convert);
if (scope.engine->hasException)
RETURN_UNDEFINED();
QFont font = qt_font_from_string(s->toQString(), r->d()->context->state.font);
@@ -2674,10 +2676,10 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_font(const QV4::BuiltinFunction
\endlist
Other values are ignored. The default value is "start".
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_textAlign(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_textAlign(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
switch (r->d()->context->state.textAlign) {
@@ -2696,13 +2698,13 @@ QV4::ReturnedValue QQuickJSContext2D::method_get_textAlign(const QV4::BuiltinFun
RETURN_RESULT(scope.engine->newString(QStringLiteral("start")));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_textAlign(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_textAlign(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- QV4::ScopedString s(scope, callData->argument(0), QV4::ScopedString::Convert);
+ QV4::ScopedString s(scope, argc ? argv[0] : QV4::Primitive::undefinedValue(), QV4::ScopedString::Convert);
if (scope.engine->hasException)
RETURN_UNDEFINED();
QString textAlign = s->toQString();
@@ -2742,10 +2744,10 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_textAlign(const QV4::BuiltinFun
\endlist
Other values are ignored. The default value is "alphabetic".
*/
-QV4::ReturnedValue QQuickJSContext2D::method_get_textBaseline(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_get_textBaseline(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
switch (r->d()->context->state.textBaseline) {
@@ -2764,12 +2766,12 @@ QV4::ReturnedValue QQuickJSContext2D::method_get_textBaseline(const QV4::Builtin
RETURN_RESULT(scope.engine->newString(QStringLiteral("alphabetic")));
}
-QV4::ReturnedValue QQuickJSContext2D::method_set_textBaseline(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2D::method_set_textBaseline(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT_SETTER(r)
- QV4::ScopedString s(scope, callData->argument(0), QV4::ScopedString::Convert);
+ QV4::ScopedString s(scope, argc ? argv[0] : QV4::Primitive::undefinedValue(), QV4::ScopedString::Convert);
if (scope.engine->hasException)
RETURN_UNDEFINED();
QString textBaseline = s->toQString();
@@ -2802,22 +2804,22 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_textBaseline(const QV4::Builtin
\sa textBaseline
\sa strokeText
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_fillText(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_fillText(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 3) {
- qreal x = callData->args[1].toNumber();
- qreal y = callData->args[2].toNumber();
+ if (argc >= 3) {
+ qreal x = argv[1].toNumber();
+ qreal y = argv[2].toNumber();
if (!qt_is_finite(x) || !qt_is_finite(y))
RETURN_UNDEFINED();
- QPainterPath textPath = r->d()->context->createTextGlyphs(x, y, callData->args[0].toQStringNoThrow());
+ QPainterPath textPath = r->d()->context->createTextGlyphs(x, y, argv[0].toQStringNoThrow());
r->d()->context->buffer()->fill(textPath);
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
\qmlmethod object QtQuick::Context2D::strokeText(text, x, y)
@@ -2827,16 +2829,16 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_fillText(const QV4::Builti
\sa textBaseline
\sa fillText
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_strokeText(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_strokeText(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 3)
- r->d()->context->drawText(callData->args[0].toQStringNoThrow(), callData->args[1].toNumber(), callData->args[2].toNumber(), false);
+ if (argc >= 3)
+ r->d()->context->drawText(argv[0].toQStringNoThrow(), argv[1].toNumber(), argv[2].toNumber(), false);
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -2845,15 +2847,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_strokeText(const QV4::Buil
Returns an object with a \c width property, whose value is equivalent to
calling \l {QFontMetrics::width()} with the given \a text in the current font.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_measureText(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_measureText(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
- if (callData->argc() >= 1) {
+ if (argc >= 1) {
QFontMetrics fm(r->d()->context->state.font);
- uint width = fm.width(callData->args[0].toQStringNoThrow());
+ uint width = fm.width(argv[0].toQStringNoThrow());
QV4::ScopedObject tm(scope, scope.engine->newObject());
tm->put(QV4::ScopedString(scope, scope.engine->newIdentifier(QStringLiteral("width"))).getPointer(),
QV4::ScopedValue(scope, QV4::Primitive::fromDouble(width)));
@@ -2921,15 +2923,15 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_measureText(const QV4::Bui
\sa {http://www.w3.org/TR/2dcontext/#dom-context-2d-drawimage}{W3C 2d context standard for drawImage}
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawImage(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawImage(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2D> r(scope, *thisObject);
CHECK_CONTEXT(r)
qreal sx, sy, sw, sh, dx, dy, dw, dh;
- if (!callData->argc())
+ if (!argc)
RETURN_UNDEFINED();
//FIXME:This function should be moved to QQuickContext2D::drawImage(...)
@@ -2938,7 +2940,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawImage(const QV4::Built
QQmlRefPointer<QQuickCanvasPixmap> pixmap;
- QV4::ScopedValue arg(scope, callData->args[0]);
+ QV4::ScopedValue arg(scope, argv[0]);
if (arg->isString()) {
QUrl url(arg->toQString());
if (!url.isValid())
@@ -2981,27 +2983,27 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawImage(const QV4::Built
if (pixmap.isNull() || !pixmap->isValid())
RETURN_UNDEFINED();
- if (callData->argc() >= 9) {
- sx = callData->args[1].toNumber();
- sy = callData->args[2].toNumber();
- sw = callData->args[3].toNumber();
- sh = callData->args[4].toNumber();
- dx = callData->args[5].toNumber();
- dy = callData->args[6].toNumber();
- dw = callData->args[7].toNumber();
- dh = callData->args[8].toNumber();
- } else if (callData->argc() >= 5) {
+ if (argc >= 9) {
+ sx = argv[1].toNumber();
+ sy = argv[2].toNumber();
+ sw = argv[3].toNumber();
+ sh = argv[4].toNumber();
+ dx = argv[5].toNumber();
+ dy = argv[6].toNumber();
+ dw = argv[7].toNumber();
+ dh = argv[8].toNumber();
+ } else if (argc >= 5) {
sx = 0;
sy = 0;
sw = pixmap->width();
sh = pixmap->height();
- dx = callData->args[1].toNumber();
- dy = callData->args[2].toNumber();
- dw = callData->args[3].toNumber();
- dh = callData->args[4].toNumber();
- } else if (callData->argc() >= 3) {
- dx = callData->args[1].toNumber();
- dy = callData->args[2].toNumber();
+ dx = argv[1].toNumber();
+ dy = argv[2].toNumber();
+ dw = argv[3].toNumber();
+ dh = argv[4].toNumber();
+ } else if (argc >= 3) {
+ dx = argv[1].toNumber();
+ dy = argv[2].toNumber();
sx = 0;
sy = 0;
sw = pixmap->width();
@@ -3034,7 +3036,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawImage(const QV4::Built
r->d()->context->buffer()->drawPixmap(pixmap, QRectF(sx, sy, sw, sh), QRectF(dx, dy, dw, dh));
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
// pixel manipulation
@@ -3061,10 +3063,10 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawImage(const QV4::Built
\qmlproperty int QtQuick::CanvasImageData::width
Holds the actual width dimension of the data in the ImageData object, in device pixels.
*/
-QV4::ReturnedValue QQuickJSContext2DImageData::method_get_width(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DImageData::method_get_width(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2DImageData> imageData(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2DImageData> imageData(scope, *thisObject);
if (!imageData)
THROW_TYPE_ERROR();
QV4::Scoped<QQuickJSContext2DPixelData> r(scope, imageData->d()->pixelData.as<QQuickJSContext2DPixelData>());
@@ -3076,10 +3078,10 @@ QV4::ReturnedValue QQuickJSContext2DImageData::method_get_width(const QV4::Built
\qmlproperty int QtQuick::CanvasImageData::height
Holds the actual height dimension of the data in the ImageData object, in device pixels.
*/
-QV4::ReturnedValue QQuickJSContext2DImageData::method_get_height(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DImageData::method_get_height(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2DImageData> imageData(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2DImageData> imageData(scope, *thisObject);
if (!imageData)
THROW_TYPE_ERROR();
QV4::Scoped<QQuickJSContext2DPixelData> r(scope, imageData->d()->pixelData.as<QQuickJSContext2DPixelData>());
@@ -3091,10 +3093,10 @@ QV4::ReturnedValue QQuickJSContext2DImageData::method_get_height(const QV4::Buil
\qmlproperty object QtQuick::CanvasImageData::data
Holds the one-dimensional array containing the data in RGBA order, as integers in the range 0 to 255.
*/
-QV4::ReturnedValue QQuickJSContext2DImageData::method_get_data(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DImageData::method_get_data(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2DImageData> imageData(scope, callData->thisObject);
+ QV4::Scoped<QQuickJSContext2DImageData> imageData(scope, *thisObject);
if (!imageData)
THROW_TYPE_ERROR();
RETURN_RESULT(imageData->d()->pixelData);
@@ -3118,10 +3120,10 @@ QV4::ReturnedValue QQuickJSContext2DImageData::method_get_data(const QV4::Builti
The length attribute of a CanvasPixelArray object must return this h×w×4 number value.
This property is read only.
*/
-QV4::ReturnedValue QQuickJSContext2DPixelData::proto_get_length(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPixelData::proto_get_length(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *, int)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2DPixelData> r(scope, callData->thisObject.as<QQuickJSContext2DPixelData>());
+ QV4::Scoped<QQuickJSContext2DPixelData> r(scope, thisObject->as<QQuickJSContext2DPixelData>());
if (!r || r->d()->image->isNull())
RETURN_UNDEFINED();
@@ -3217,14 +3219,14 @@ bool QQuickJSContext2DPixelData::putIndexed(QV4::Managed *m, uint index, const Q
\sa Canvas::loadImage(), QtQuick::Canvas::unloadImage(),
QtQuick::Canvas::isImageLoaded
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_createImageData(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_createImageData(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() == 1) {
- QV4::ScopedValue arg0(scope, callData->args[0]);
+ if (argc == 1) {
+ QV4::ScopedValue arg0(scope, argv[0]);
QV4::Scoped<QQuickJSContext2DImageData> imgData(scope, arg0);
if (!!imgData) {
QV4::Scoped<QQuickJSContext2DPixelData> pa(scope, imgData->d()->pixelData.as<QQuickJSContext2DPixelData>());
@@ -3237,9 +3239,9 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createImageData(const QV4:
QImage image = r->d()->context->createPixmap(QUrl(arg0->toQStringNoThrow()))->image();
RETURN_RESULT(qt_create_image_data(image.width(), image.height(), scope.engine, image));
}
- } else if (callData->argc() == 2) {
- qreal w = callData->args[0].toNumber();
- qreal h = callData->args[1].toNumber();
+ } else if (argc == 2) {
+ qreal w = argv[0].toNumber();
+ qreal h = argv[1].toNumber();
if (!qt_is_finite(w) || !qt_is_finite(h))
THROW_DOM(DOMEXCEPTION_NOT_SUPPORTED_ERR, "createImageData(): invalid arguments");
@@ -3256,17 +3258,17 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createImageData(const QV4:
\qmlmethod CanvasImageData QtQuick::Context2D::getImageData(real sx, real sy, real sw, real sh)
Returns an CanvasImageData object containing the image data for the given rectangle of the canvas.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_getImageData(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_getImageData(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() >= 4) {
- qreal x = callData->args[0].toNumber();
- qreal y = callData->args[1].toNumber();
- qreal w = callData->args[2].toNumber();
- qreal h = callData->args[3].toNumber();
+ if (argc >= 4) {
+ qreal x = argv[0].toNumber();
+ qreal y = argv[1].toNumber();
+ qreal w = argv[2].toNumber();
+ qreal h = argv[3].toNumber();
if (!qt_is_finite(x) || !qt_is_finite(y) || !qt_is_finite(w) || !qt_is_finite(h))
THROW_DOM(DOMEXCEPTION_NOT_SUPPORTED_ERR, "getImageData(): Invalid arguments");
@@ -3283,20 +3285,20 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_getImageData(const QV4::Bu
\qmlmethod object QtQuick::Context2D::putImageData(CanvasImageData imageData, real dx, real dy, real dirtyX, real dirtyY, real dirtyWidth, real dirtyHeight)
Paints the data from the given ImageData object onto the canvas. If a dirty rectangle (\a dirtyX, \a dirtyY, \a dirtyWidth, \a dirtyHeight) is provided, only the pixels from that rectangle are painted.
*/
-QV4::ReturnedValue QQuickJSContext2DPrototype::method_putImageData(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickJSContext2DPrototype::method_putImageData(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickJSContext2D> r(scope, callData->thisObject.as<QQuickJSContext2D>());
+ QV4::Scoped<QQuickJSContext2D> r(scope, thisObject->as<QQuickJSContext2D>());
CHECK_CONTEXT(r)
- if (callData->argc() < 7)
+ if (argc < 7)
RETURN_UNDEFINED();
- QV4::ScopedValue arg0(scope, callData->args[0]);
+ QV4::ScopedValue arg0(scope, argv[0]);
if (!arg0->isObject())
THROW_DOM(DOMEXCEPTION_TYPE_MISMATCH_ERR, "Context2D::putImageData, the image data type mismatch");
- qreal dx = callData->args[1].toNumber();
- qreal dy = callData->args[2].toNumber();
+ qreal dx = argv[1].toNumber();
+ qreal dy = argv[2].toNumber();
qreal w, h, dirtyX, dirtyY, dirtyWidth, dirtyHeight;
if (!qt_is_finite(dx) || !qt_is_finite(dy))
@@ -3311,11 +3313,11 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_putImageData(const QV4::Bu
w = pixelArray->d()->image->width();
h = pixelArray->d()->image->height();
- if (callData->argc() == 7) {
- dirtyX = callData->args[3].toNumber();
- dirtyY = callData->args[4].toNumber();
- dirtyWidth = callData->args[5].toNumber();
- dirtyHeight = callData->args[6].toNumber();
+ if (argc == 7) {
+ dirtyX = argv[3].toNumber();
+ dirtyY = argv[4].toNumber();
+ dirtyWidth = argv[5].toNumber();
+ dirtyHeight = argv[6].toNumber();
if (!qt_is_finite(dirtyX) || !qt_is_finite(dirtyY) || !qt_is_finite(dirtyWidth) || !qt_is_finite(dirtyHeight))
THROW_DOM(DOMEXCEPTION_NOT_SUPPORTED_ERR, "putImageData() : Invalid arguments");
@@ -3362,7 +3364,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_putImageData(const QV4::Bu
r->d()->context->buffer()->drawImage(image, QRectF(dirtyX, dirtyY, dirtyWidth, dirtyHeight), QRectF(dx, dy, dirtyWidth, dirtyHeight));
}
- RETURN_RESULT(callData->thisObject);
+ RETURN_RESULT(*thisObject);
}
/*!
@@ -3385,25 +3387,25 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_putImageData(const QV4::Bu
gradient.addColorStop(0.7, 'rgba(0, 255, 255, 1');
\endcode
*/
-QV4::ReturnedValue QQuickContext2DStyle::gradient_proto_addColorStop(const QV4::BuiltinFunction *b, QV4::CallData *callData)
+QV4::ReturnedValue QQuickContext2DStyle::gradient_proto_addColorStop(const QV4::FunctionObject *b, const QV4::Value *thisObject, const QV4::Value *argv, int argc)
{
QV4::Scope scope(b);
- QV4::Scoped<QQuickContext2DStyle> style(scope, callData->thisObject.as<QQuickContext2DStyle>());
+ QV4::Scoped<QQuickContext2DStyle> style(scope, thisObject->as<QQuickContext2DStyle>());
if (!style)
THROW_GENERIC_ERROR("Not a CanvasGradient object");
- if (callData->argc() == 2) {
+ if (argc == 2) {
if (!style->d()->brush->gradient())
THROW_GENERIC_ERROR("Not a valid CanvasGradient object, can't get the gradient information");
QGradient gradient = *(style->d()->brush->gradient());
- qreal pos = callData->args[0].toNumber();
+ qreal pos = argv[0].toNumber();
QColor color;
- if (callData->args[1].as<Object>()) {
- color = scope.engine->toVariant(callData->args[1], qMetaTypeId<QColor>()).value<QColor>();
+ if (argv[1].as<Object>()) {
+ color = scope.engine->toVariant(argv[1], qMetaTypeId<QColor>()).value<QColor>();
} else {
- color = qt_color_from_string(callData->args[1]);
+ color = qt_color_from_string(argv[1]);
}
if (pos < 0.0 || pos > 1.0 || !qt_is_finite(pos)) {
THROW_DOM(DOMEXCEPTION_INDEX_SIZE_ERR, "CanvasGradient: parameter offset out of range");
@@ -3417,7 +3419,7 @@ QV4::ReturnedValue QQuickContext2DStyle::gradient_proto_addColorStop(const QV4::
*style->d()->brush = gradient;
}
- return callData->thisObject.asReturnedValue();
+ return thisObject->asReturnedValue();
}
void QQuickContext2D::scale(qreal x, qreal y)
@@ -4049,10 +4051,10 @@ QMutex QQuickContext2D::mutex;
QQuickContext2D::QQuickContext2D(QObject *parent)
: QQuickCanvasContext(parent)
, m_buffer(new QQuickContext2DCommandBuffer)
- , m_v4engine(0)
- , m_surface(0)
- , m_glContext(0)
- , m_thread(0)
+ , m_v4engine(nullptr)
+ , m_surface(nullptr)
+ , m_glContext(nullptr)
+ , m_thread(nullptr)
, m_grabbed(false)
{
}
@@ -4060,7 +4062,7 @@ QQuickContext2D::QQuickContext2D(QObject *parent)
QQuickContext2D::~QQuickContext2D()
{
mutex.lock();
- m_texture->setItem(0);
+ m_texture->setItem(nullptr);
delete m_buffer;
if (m_renderTarget == QQuickCanvasItem::FramebufferObject) {
@@ -4240,7 +4242,7 @@ QImage QQuickContext2D::toImage(const QRectF& bounds)
} else {
#if QT_CONFIG(opengl)
QQuickWindow *window = m_canvas->window();
- QOpenGLContext *ctx = window ? window->openglContext() : 0;
+ QOpenGLContext *ctx = window ? window->openglContext() : nullptr;
if (ctx && ctx->isValid()) {
if (ctx == QOpenGLContext::currentContext()) {
flush();
@@ -4308,7 +4310,7 @@ QQuickContext2DEngineData::QQuickContext2DEngineData(QV4::ExecutionEngine *v4)
gradientProto = proto;
proto = scope.engine->newObject();
- proto->defineAccessorProperty(scope.engine->id_length(), QQuickJSContext2DPixelData::proto_get_length, 0);
+ proto->defineAccessorProperty(scope.engine->id_length(), QQuickJSContext2DPixelData::proto_get_length, nullptr);
pixelArrayProto = proto;
}
@@ -4392,7 +4394,7 @@ void QQuickContext2D::setV4Engine(QV4::ExecutionEngine *engine)
if (m_v4engine != engine) {
m_v4engine = engine;
- if (m_v4engine == 0)
+ if (m_v4engine == nullptr)
return;
QQuickContext2DEngineData *ed = engineData(engine);
diff --git a/src/quick/items/context2d/qquickcontext2d_p.h b/src/quick/items/context2d/qquickcontext2d_p.h
index 334bf08329..4cc07027b1 100644
--- a/src/quick/items/context2d/qquickcontext2d_p.h
+++ b/src/quick/items/context2d/qquickcontext2d_p.h
@@ -181,7 +181,7 @@ public:
QQuickContext2D::TextBaseLineType textBaseline;
};
- QQuickContext2D(QObject *parent = 0);
+ QQuickContext2D(QObject *parent = nullptr);
~QQuickContext2D();
QStringList contextNames() const override;
@@ -199,7 +199,7 @@ public:
QQuickCanvasItem* canvas() const { return m_canvas; }
QQuickContext2DCommandBuffer* buffer() const { return m_buffer; }
- bool bufferValid() const { return m_buffer != 0; }
+ bool bufferValid() const { return m_buffer != nullptr; }
void popState();
void pushState();
void reset();
diff --git a/src/quick/items/context2d/qquickcontext2dtexture.cpp b/src/quick/items/context2d/qquickcontext2dtexture.cpp
index a8bf14ba9f..69ff3b3852 100644
--- a/src/quick/items/context2d/qquickcontext2dtexture.cpp
+++ b/src/quick/items/context2d/qquickcontext2dtexture.cpp
@@ -93,12 +93,12 @@ struct GLAcquireContext {
};
#endif
QQuickContext2DTexture::QQuickContext2DTexture()
- : m_context(0)
+ : m_context(nullptr)
#if QT_CONFIG(opengl)
- , m_gl(0)
+ , m_gl(nullptr)
#endif
- , m_surface(0)
- , m_item(0)
+ , m_surface(nullptr)
+ , m_item(nullptr)
, m_canvasDevicePixelRatio(1)
, m_canvasWindowChanged(false)
, m_dirtyTexture(false)
@@ -159,7 +159,7 @@ void QQuickContext2DTexture::setItem(QQuickCanvasItem* item)
m_context = (QQuickContext2D*) item->rawContext(); // FIXME
m_state = m_context->state;
} else {
- m_context = 0;
+ m_context = nullptr;
}
}
@@ -257,7 +257,7 @@ void QQuickContext2DTexture::paintWithoutTiles(QQuickContext2DCommandBuffer *ccb
bool QQuickContext2DTexture::canvasDestroyed()
{
- return m_item == 0;
+ return m_item == nullptr;
}
void QQuickContext2DTexture::paint(QQuickContext2DCommandBuffer *ccb)
@@ -349,7 +349,7 @@ QRect QQuickContext2DTexture::createTiles(const QRect& window)
int ht = xx + h1;
int vt = yy + v1;
- QQuickContext2DTile* tile = 0;
+ QQuickContext2DTile* tile = nullptr;
QPoint pos(ht * tw, vt * th);
QRect rect(pos, m_tileSize);
@@ -420,9 +420,9 @@ static inline QSize npotAdjustedSize(const QSize &size)
QQuickContext2DFBOTexture::QQuickContext2DFBOTexture()
: QQuickContext2DTexture()
- , m_fbo(0)
- , m_multisampledFbo(0)
- , m_paint_device(0)
+ , m_fbo(nullptr)
+ , m_multisampledFbo(nullptr)
+ , m_paint_device(nullptr)
{
m_displayTextures[0] = 0;
m_displayTextures[1] = 0;
@@ -567,15 +567,15 @@ QPaintDevice* QQuickContext2DFBOTexture::beginPainting()
delete m_fbo;
delete m_multisampledFbo;
delete m_paint_device;
- m_fbo = 0;
- m_multisampledFbo = 0;
- m_paint_device = 0;
- return 0;
+ m_fbo = nullptr;
+ m_multisampledFbo = nullptr;
+ m_paint_device = nullptr;
+ return nullptr;
} else if (!m_fbo || m_canvasWindowChanged) {
delete m_fbo;
delete m_multisampledFbo;
delete m_paint_device;
- m_paint_device = 0;
+ m_paint_device = nullptr;
m_fboSize = npotAdjustedSize(m_canvasWindow.size() * m_canvasDevicePixelRatio);
m_canvasWindowChanged = false;
@@ -722,7 +722,7 @@ QPaintDevice* QQuickContext2DImageTexture::beginPainting()
QQuickContext2DTexture::beginPainting();
if (m_canvasWindow.size().isEmpty())
- return 0;
+ return nullptr;
if (m_canvasWindowChanged) {
diff --git a/src/quick/items/context2d/qquickcontext2dtexture_p.h b/src/quick/items/context2d/qquickcontext2dtexture_p.h
index 0e1fbd5d34..9c4870f328 100644
--- a/src/quick/items/context2d/qquickcontext2dtexture_p.h
+++ b/src/quick/items/context2d/qquickcontext2dtexture_p.h
@@ -146,7 +146,7 @@ protected:
virtual QVector2D scaleFactor() const { return QVector2D(1, 1); }
void paintWithoutTiles(QQuickContext2DCommandBuffer *ccb);
- virtual QPaintDevice* beginPainting() {m_painting = true; return 0; }
+ virtual QPaintDevice* beginPainting() {m_painting = true; return nullptr; }
virtual void endPainting() {m_painting = false;}
virtual QQuickContext2DTile* createTile() const = 0;
virtual void compositeTile(QQuickContext2DTile* tile) = 0;
diff --git a/src/quick/items/context2d/qquickcontext2dtile.cpp b/src/quick/items/context2d/qquickcontext2dtile.cpp
index d31fee7f91..0ee3de6bcc 100644
--- a/src/quick/items/context2d/qquickcontext2dtile.cpp
+++ b/src/quick/items/context2d/qquickcontext2dtile.cpp
@@ -49,7 +49,7 @@ QT_BEGIN_NAMESPACE
QQuickContext2DTile::QQuickContext2DTile()
: m_dirty(true)
, m_rect(QRect(0, 0, 1, 1))
- , m_device(0)
+ , m_device(nullptr)
{
}
@@ -95,12 +95,12 @@ QPainter* QQuickContext2DTile::createPainter(bool smooth, bool antialiasing)
return &m_painter;
}
- return 0;
+ return nullptr;
}
#if QT_CONFIG(opengl)
QQuickContext2DFBOTile::QQuickContext2DFBOTile()
: QQuickContext2DTile()
- , m_fbo(0)
+ , m_fbo(nullptr)
{
}
diff --git a/src/quick/items/items.pri b/src/quick/items/items.pri
index 0f8061b5ef..1acb3b5265 100644
--- a/src/quick/items/items.pri
+++ b/src/quick/items/items.pri
@@ -41,8 +41,6 @@ HEADERS += \
$$PWD/qquickflickable_p.h \
$$PWD/qquickflickable_p_p.h \
$$PWD/qquickflickablebehavior_p.h \
- $$PWD/qquickrepeater_p.h \
- $$PWD/qquickrepeater_p_p.h \
$$PWD/qquickloader_p.h \
$$PWD/qquickloader_p_p.h \
$$PWD/qquicktranslate_p.h \
@@ -89,7 +87,6 @@ SOURCES += \
$$PWD/qquickmousearea.cpp \
$$PWD/qquickpincharea.cpp \
$$PWD/qquickflickable.cpp \
- $$PWD/qquickrepeater.cpp \
$$PWD/qquickloader.cpp \
$$PWD/qquicktranslate.cpp \
$$PWD/qquickclipnode.cpp \
@@ -168,6 +165,15 @@ qtConfig(quick-flipable) {
$$PWD/qquickflipable.cpp
}
+qtConfig(quick-repeater) {
+ HEADERS += \
+ $$PWD/qquickrepeater_p.h \
+ $$PWD/qquickrepeater_p_p.h
+
+ SOURCES += \
+ $$PWD/qquickrepeater.cpp
+}
+
qtConfig(quick-shadereffect) {
HEADERS += \
$$PWD/qquickshadereffectsource_p.h \
diff --git a/src/quick/items/qquickaccessibleattached.cpp b/src/quick/items/qquickaccessibleattached.cpp
index c559ee8887..252d6538e2 100644
--- a/src/quick/items/qquickaccessibleattached.cpp
+++ b/src/quick/items/qquickaccessibleattached.cpp
@@ -410,7 +410,7 @@ void QQuickAccessibleAttached::setIgnored(bool ignored)
bool QQuickAccessibleAttached::doAction(const QString &actionName)
{
- QMetaMethod *sig = 0;
+ QMetaMethod *sig = nullptr;
if (actionName == QAccessibleActionInterface::pressAction())
sig = &sigPress;
else if (actionName == QAccessibleActionInterface::toggleAction())
diff --git a/src/quick/items/qquickanchors.cpp b/src/quick/items/qquickanchors.cpp
index 45b405bd82..8ee4229013 100644
--- a/src/quick/items/qquickanchors.cpp
+++ b/src/quick/items/qquickanchors.cpp
@@ -252,35 +252,35 @@ void QQuickAnchorsPrivate::clearItem(QQuickItem *item)
if (!item)
return;
if (fill == item)
- fill = 0;
+ fill = nullptr;
if (centerIn == item)
- centerIn = 0;
+ centerIn = nullptr;
if (leftAnchorItem == item) {
- leftAnchorItem = 0;
+ leftAnchorItem = nullptr;
usedAnchors &= ~QQuickAnchors::LeftAnchor;
}
if (rightAnchorItem == item) {
- rightAnchorItem = 0;
+ rightAnchorItem = nullptr;
usedAnchors &= ~QQuickAnchors::RightAnchor;
}
if (topAnchorItem == item) {
- topAnchorItem = 0;
+ topAnchorItem = nullptr;
usedAnchors &= ~QQuickAnchors::TopAnchor;
}
if (bottomAnchorItem == item) {
- bottomAnchorItem = 0;
+ bottomAnchorItem = nullptr;
usedAnchors &= ~QQuickAnchors::BottomAnchor;
}
if (vCenterAnchorItem == item) {
- vCenterAnchorItem = 0;
+ vCenterAnchorItem = nullptr;
usedAnchors &= ~QQuickAnchors::VCenterAnchor;
}
if (hCenterAnchorItem == item) {
- hCenterAnchorItem = 0;
+ hCenterAnchorItem = nullptr;
usedAnchors &= ~QQuickAnchors::HCenterAnchor;
}
if (baselineAnchorItem == item) {
- baselineAnchorItem = 0;
+ baselineAnchorItem = nullptr;
usedAnchors &= ~QQuickAnchors::BaselineAnchor;
}
}
@@ -462,7 +462,7 @@ void QQuickAnchorsPrivate::updateOnComplete()
std::sort(dependencies, dependencies + 9);
- QQuickItem *lastDependency = 0;
+ QQuickItem *lastDependency = nullptr;
for (int i = 0; i < 9; ++i) {
QQuickItem *dependency = dependencies[i];
if (lastDependency != dependency) {
@@ -542,7 +542,7 @@ void QQuickAnchors::setFill(QQuickItem *f)
void QQuickAnchors::resetFill()
{
- setFill(0);
+ setFill(nullptr);
}
QQuickItem *QQuickAnchors::centerIn() const
@@ -578,7 +578,7 @@ void QQuickAnchors::setCenterIn(QQuickItem* c)
void QQuickAnchors::resetCenterIn()
{
- setCenterIn(0);
+ setCenterIn(nullptr);
}
bool QQuickAnchorsPrivate::calcStretch(QQuickItem *edge1Item,
@@ -1324,6 +1324,19 @@ QQuickAnchors::Anchors QQuickAnchors::usedAnchors() const
return static_cast<QQuickAnchors::Anchors>(d->usedAnchors);
}
+Qt::Orientations QQuickAnchors::activeDirections() const
+{
+ Q_D(const QQuickAnchors);
+ if (d->fill || d->centerIn)
+ return Qt::Horizontal | Qt::Vertical;
+ Qt::Orientations o;
+ if (d->usedAnchors & QQuickAnchors::Horizontal_Mask)
+ o |= Qt::Horizontal;
+ if (d->usedAnchors & QQuickAnchors::Vertical_Mask)
+ o |= Qt::Vertical;
+ return o;
+}
+
bool QQuickAnchorsPrivate::checkHValid() const
{
if (usedAnchors & QQuickAnchors::LeftAnchor &&
diff --git a/src/quick/items/qquickanchors_p.h b/src/quick/items/qquickanchors_p.h
index f00b8b5ba7..931b963534 100644
--- a/src/quick/items/qquickanchors_p.h
+++ b/src/quick/items/qquickanchors_p.h
@@ -86,8 +86,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickAnchors : public QObject
Q_PROPERTY(bool alignWhenCentered READ alignWhenCentered WRITE setAlignWhenCentered NOTIFY centerAlignedChanged)
public:
- QQuickAnchors(QQuickItem *item, QObject *parent=0);
- virtual ~QQuickAnchors();
+ QQuickAnchors(QQuickItem *item, QObject *parent=nullptr);
+ ~QQuickAnchors() override;
enum Anchor
#if defined(Q_CC_CLANG) || !defined(Q_CC_GNU) // meaning: clang and msvc, but NOT gcc proper (because, you know, Q_CC_CLANG implies Q_CC_GNU)
@@ -174,6 +174,7 @@ public:
void resetCenterIn();
Anchors usedAnchors() const;
+ Qt::Orientations activeDirections() const;
bool mirrored();
diff --git a/src/quick/items/qquickanchors_p_p.h b/src/quick/items/qquickanchors_p_p.h
index ae6ca02786..0a834276ae 100644
--- a/src/quick/items/qquickanchors_p_p.h
+++ b/src/quick/items/qquickanchors_p_p.h
@@ -60,15 +60,15 @@ QT_BEGIN_NAMESPACE
class QQuickAnchorLine
{
public:
- QQuickAnchorLine() : item(0), anchorLine(QQuickAnchors::InvalidAnchor) {}
+ QQuickAnchorLine() {}
QQuickAnchorLine(QQuickItem *i, QQuickAnchors::Anchor l) : item(i), anchorLine(l) {}
QQuickAnchorLine(QQuickItem *i, uint l)
: item(i)
, anchorLine(static_cast<QQuickAnchors::Anchor>(l))
{ Q_ASSERT(l < ((QQuickAnchors::BaselineAnchor << 1) - 1)); }
- QQuickItem *item;
- QQuickAnchors::Anchor anchorLine;
+ QQuickItem *item = nullptr;
+ QQuickAnchors::Anchor anchorLine = QQuickAnchors::InvalidAnchor;
};
inline bool operator==(const QQuickAnchorLine& a, const QQuickAnchorLine& b)
diff --git a/src/quick/items/qquickanimatedimage.cpp b/src/quick/items/qquickanimatedimage.cpp
index 5bc5b0faff..26dfdb07a6 100644
--- a/src/quick/items/qquickanimatedimage.cpp
+++ b/src/quick/items/qquickanimatedimage.cpp
@@ -54,26 +54,26 @@ QT_BEGIN_NAMESPACE
QQuickPixmap* QQuickAnimatedImagePrivate::infoForCurrentFrame(QQmlEngine *engine)
{
- if (!_movie)
- return 0;
+ if (!movie)
+ return nullptr;
- int current = _movie->currentFrameNumber();
+ int current = movie->currentFrameNumber();
if (!frameMap.contains(current)) {
QUrl requestedUrl;
- QQuickPixmap *pixmap = 0;
- if (engine && !_movie->fileName().isEmpty()) {
+ QQuickPixmap *pixmap = nullptr;
+ if (engine && !movie->fileName().isEmpty()) {
requestedUrl.setUrl(QString::fromUtf8("quickanimatedimage://%1#%2")
- .arg(_movie->fileName())
+ .arg(movie->fileName())
.arg(current));
}
if (!requestedUrl.isEmpty()) {
if (QQuickPixmap::isCached(requestedUrl, QSize(), QQuickImageProviderOptions()))
pixmap = new QQuickPixmap(engine, requestedUrl);
else
- pixmap = new QQuickPixmap(requestedUrl, _movie->currentImage());
+ pixmap = new QQuickPixmap(requestedUrl, movie->currentImage());
} else {
pixmap = new QQuickPixmap;
- pixmap->setImage(_movie->currentImage());
+ pixmap->setImage(movie->currentImage());
}
frameMap.insert(current, pixmap);
}
@@ -138,7 +138,7 @@ QQuickPixmap* QQuickAnimatedImagePrivate::infoForCurrentFrame(QQmlEngine *engine
QQuickAnimatedImage::QQuickAnimatedImage(QQuickItem *parent)
: QQuickImage(*(new QQuickAnimatedImagePrivate), parent)
{
- QObject::connect(this, &QQuickImageBase::cacheChanged, this, &QQuickAnimatedImage::onCacheChanged);
+ connect(this, &QQuickImageBase::cacheChanged, this, &QQuickAnimatedImage::onCacheChanged);
}
QQuickAnimatedImage::~QQuickAnimatedImage()
@@ -148,7 +148,7 @@ QQuickAnimatedImage::~QQuickAnimatedImage()
if (d->reply)
d->reply->deleteLater();
#endif
- delete d->_movie;
+ delete d->movie;
qDeleteAll(d->frameMap);
d->frameMap.clear();
}
@@ -164,9 +164,9 @@ QQuickAnimatedImage::~QQuickAnimatedImage()
bool QQuickAnimatedImage::isPaused() const
{
Q_D(const QQuickAnimatedImage);
- if (!d->_movie)
+ if (!d->movie)
return d->paused;
- return d->_movie->state()==QMovie::Paused;
+ return d->movie->state()==QMovie::Paused;
}
void QQuickAnimatedImage::setPaused(bool pause)
@@ -174,11 +174,11 @@ void QQuickAnimatedImage::setPaused(bool pause)
Q_D(QQuickAnimatedImage);
if (pause == d->paused)
return;
- if (!d->_movie) {
+ if (!d->movie) {
d->paused = pause;
emit pausedChanged();
} else {
- d->_movie->setPaused(pause);
+ d->movie->setPaused(pause);
}
}
@@ -203,9 +203,9 @@ void QQuickAnimatedImage::setPaused(bool pause)
bool QQuickAnimatedImage::isPlaying() const
{
Q_D(const QQuickAnimatedImage);
- if (!d->_movie)
+ if (!d->movie)
return d->playing;
- return d->_movie->state()!=QMovie::NotRunning;
+ return d->movie->state()!=QMovie::NotRunning;
}
void QQuickAnimatedImage::setPlaying(bool play)
@@ -213,15 +213,15 @@ void QQuickAnimatedImage::setPlaying(bool play)
Q_D(QQuickAnimatedImage);
if (play == d->playing)
return;
- if (!d->_movie) {
+ if (!d->movie) {
d->playing = play;
emit playingChanged();
return;
}
if (play)
- d->_movie->start();
+ d->movie->start();
else
- d->_movie->stop();
+ d->movie->stop();
}
/*!
@@ -237,27 +237,53 @@ void QQuickAnimatedImage::setPlaying(bool play)
int QQuickAnimatedImage::currentFrame() const
{
Q_D(const QQuickAnimatedImage);
- if (!d->_movie)
- return d->preset_currentframe;
- return d->_movie->currentFrameNumber();
+ if (!d->movie)
+ return d->presetCurrentFrame;
+ return d->movie->currentFrameNumber();
}
void QQuickAnimatedImage::setCurrentFrame(int frame)
{
Q_D(QQuickAnimatedImage);
- if (!d->_movie) {
- d->preset_currentframe = frame;
+ if (!d->movie) {
+ d->presetCurrentFrame = frame;
return;
}
- d->_movie->jumpToFrame(frame);
+ d->movie->jumpToFrame(frame);
}
int QQuickAnimatedImage::frameCount() const
{
Q_D(const QQuickAnimatedImage);
- if (!d->_movie)
+ if (!d->movie)
return 0;
- return d->_movie->frameCount();
+ return d->movie->frameCount();
+}
+
+/*!
+ \qmlproperty real QtQuick::AnimatedImage::speed
+ \since QtQuick 2.11
+
+ This property holds the speed of the animation.
+
+ The speed is measured in percentage of the original animated image speed.
+ The default speed is 1.0 (original speed).
+*/
+qreal QQuickAnimatedImage::speed() const
+{
+ Q_D(const QQuickAnimatedImage);
+ return d->speed;
+}
+
+void QQuickAnimatedImage::setSpeed(qreal speed)
+{
+ Q_D(QQuickAnimatedImage);
+ if (d->speed != speed) {
+ d->speed = speed;
+ if (d->movie)
+ d->movie->setSpeed(qRound(speed * 100.0));
+ emit speedChanged();
+ }
}
void QQuickAnimatedImage::setSource(const QUrl &url)
@@ -269,7 +295,7 @@ void QQuickAnimatedImage::setSource(const QUrl &url)
#if QT_CONFIG(qml_network)
if (d->reply) {
d->reply->deleteLater();
- d->reply = 0;
+ d->reply = nullptr;
}
#endif
@@ -278,10 +304,7 @@ void QQuickAnimatedImage::setSource(const QUrl &url)
d->frameMap.clear();
d->oldPlaying = isPlaying();
- if (d->_movie) {
- d->setMovie(nullptr);
- }
-
+ d->setMovie(nullptr);
d->url = url;
emit sourceChanged(d->url);
@@ -335,10 +358,8 @@ void QQuickAnimatedImage::load()
req.setAttribute(QNetworkRequest::HttpPipeliningAllowedAttribute, true);
d->reply = qmlEngine(this)->networkAccessManager()->get(req);
- QObject::connect(d->reply, SIGNAL(finished()),
- this, SLOT(movieRequestFinished()));
- QObject::connect(d->reply, SIGNAL(downloadProgress(qint64,qint64)),
- this, SLOT(requestProgress(qint64,qint64)));
+ connect(d->reply, &QNetworkReply::finished, this, &QQuickAnimatedImage::movieRequestFinished);
+ connect(d->reply, SIGNAL(downloadProgress(qint64,qint64)), this, SLOT(requestProgress(qint64,qint64)));
#endif
}
}
@@ -369,7 +390,7 @@ void QQuickAnimatedImage::movieRequestFinished()
}
#endif
- if (!d->_movie || !d->_movie->isValid()) {
+ if (!d->movie || !d->movie->isValid()) {
qmlWarning(this) << "Error Reading Animated Image File " << d->url.toString();
d->setMovie(nullptr);
d->setImage(QImage());
@@ -390,12 +411,11 @@ void QQuickAnimatedImage::movieRequestFinished()
return;
}
- connect(d->_movie, SIGNAL(stateChanged(QMovie::MovieState)),
- this, SLOT(playingStatusChanged()));
- connect(d->_movie, SIGNAL(frameChanged(int)),
- this, SLOT(movieUpdate()));
+ connect(d->movie, &QMovie::stateChanged, this, &QQuickAnimatedImage::playingStatusChanged);
+ connect(d->movie, &QMovie::frameChanged, this, &QQuickAnimatedImage::movieUpdate);
if (d->cache)
- d->_movie->setCacheMode(QMovie::CacheAll);
+ d->movie->setCacheMode(QMovie::CacheAll);
+ d->movie->setSpeed(qRound(d->speed * 100.0));
d->status = Ready;
emit statusChanged(d->status);
@@ -406,22 +426,21 @@ void QQuickAnimatedImage::movieRequestFinished()
}
bool pausedAtStart = d->paused;
- if (d->playing) {
- d->_movie->start();
- }
+ if (d->playing)
+ d->movie->start();
if (pausedAtStart)
- d->_movie->setPaused(true);
+ d->movie->setPaused(true);
if (d->paused || !d->playing) {
- d->_movie->jumpToFrame(d->preset_currentframe);
- d->preset_currentframe = 0;
+ d->movie->jumpToFrame(d->presetCurrentFrame);
+ d->presetCurrentFrame = 0;
}
d->setPixmap(*d->infoForCurrentFrame(qmlEngine(this)));
if (isPlaying() != d->oldPlaying)
emit playingChanged();
- if (d->_movie)
- d->currentSourceSize = d->_movie->currentPixmap().size();
+ if (d->movie)
+ d->currentSourceSize = d->movie->currentPixmap().size();
else
d->currentSourceSize = QSize(0, 0);
@@ -440,7 +459,7 @@ void QQuickAnimatedImage::movieUpdate()
d->frameMap.clear();
}
- if (d->_movie) {
+ if (d->movie) {
d->setPixmap(*d->infoForCurrentFrame(qmlEngine(this)));
emit frameChanged();
}
@@ -450,12 +469,12 @@ void QQuickAnimatedImage::playingStatusChanged()
{
Q_D(QQuickAnimatedImage);
- if ((d->_movie->state() != QMovie::NotRunning) != d->playing) {
- d->playing = (d->_movie->state() != QMovie::NotRunning);
+ if ((d->movie->state() != QMovie::NotRunning) != d->playing) {
+ d->playing = (d->movie->state() != QMovie::NotRunning);
emit playingChanged();
}
- if ((d->_movie->state() == QMovie::Paused) != d->paused) {
- d->paused = (d->_movie->state() == QMovie::Paused);
+ if ((d->movie->state() == QMovie::Paused) != d->paused) {
+ d->paused = (d->movie->state() == QMovie::Paused);
emit pausedChanged();
}
}
@@ -466,13 +485,11 @@ void QQuickAnimatedImage::onCacheChanged()
if (!cache()) {
qDeleteAll(d->frameMap);
d->frameMap.clear();
- if (d->_movie) {
- d->_movie->setCacheMode(QMovie::CacheNone);
- }
+ if (d->movie)
+ d->movie->setCacheMode(QMovie::CacheNone);
} else {
- if (d->_movie) {
- d->_movie->setCacheMode(QMovie::CacheAll);
- }
+ if (d->movie)
+ d->movie->setCacheMode(QMovie::CacheAll);
}
}
@@ -488,13 +505,15 @@ void QQuickAnimatedImage::componentComplete()
load();
}
-void QQuickAnimatedImagePrivate::setMovie(QMovie *movie)
+void QQuickAnimatedImagePrivate::setMovie(QMovie *m)
{
+ if (movie == m)
+ return;
Q_Q(QQuickAnimatedImage);
const int oldFrameCount = q->frameCount();
- delete _movie;
- _movie = movie;
+ delete movie;
+ movie = m;
if (oldFrameCount != q->frameCount())
emit q->frameCountChanged();
diff --git a/src/quick/items/qquickanimatedimage_p.h b/src/quick/items/qquickanimatedimage_p.h
index f7a6bd808b..6b5db215bd 100644
--- a/src/quick/items/qquickanimatedimage_p.h
+++ b/src/quick/items/qquickanimatedimage_p.h
@@ -70,12 +70,13 @@ class Q_AUTOTEST_EXPORT QQuickAnimatedImage : public QQuickImage
Q_PROPERTY(bool paused READ isPaused WRITE setPaused NOTIFY pausedChanged)
Q_PROPERTY(int currentFrame READ currentFrame WRITE setCurrentFrame NOTIFY frameChanged)
Q_PROPERTY(int frameCount READ frameCount NOTIFY frameCountChanged)
+ Q_PROPERTY(qreal speed READ speed WRITE setSpeed NOTIFY speedChanged REVISION 11)
// read-only for AnimatedImage
Q_PROPERTY(QSize sourceSize READ sourceSize NOTIFY sourceSizeChanged)
public:
- QQuickAnimatedImage(QQuickItem *parent=0);
+ QQuickAnimatedImage(QQuickItem *parent=nullptr);
~QQuickAnimatedImage();
bool isPlaying() const;
@@ -89,6 +90,9 @@ public:
int frameCount() const;
+ qreal speed() const;
+ void setSpeed(qreal speed);
+
// Extends QQuickImage's src property
void setSource(const QUrl&) override;
virtual QSize sourceSize();
@@ -98,6 +102,7 @@ Q_SIGNALS:
void pausedChanged();
void frameChanged();
void frameCountChanged();
+ Q_REVISION(11) void speedChanged();
private Q_SLOTS:
void movieUpdate();
diff --git a/src/quick/items/qquickanimatedimage_p_p.h b/src/quick/items/qquickanimatedimage_p_p.h
index 68c4f2d359..1a74f67424 100644
--- a/src/quick/items/qquickanimatedimage_p_p.h
+++ b/src/quick/items/qquickanimatedimage_p_p.h
@@ -70,28 +70,30 @@ class QQuickAnimatedImagePrivate : public QQuickImagePrivate
public:
QQuickAnimatedImagePrivate()
- : playing(true), paused(false), preset_currentframe(0), _movie(0), oldPlaying(false)
+ : playing(true), paused(false), oldPlaying(false), padding(0)
+ , presetCurrentFrame(0), speed(1.0), currentSourceSize(0, 0), movie(nullptr)
#if QT_CONFIG(qml_network)
- , reply(0), redirectCount(0)
+ , reply(nullptr), redirectCount(0)
#endif
- , currentSourceSize(0, 0)
{
}
QQuickPixmap *infoForCurrentFrame(QQmlEngine *engine);
+ void setMovie(QMovie *movie);
- bool playing;
- bool paused;
- int preset_currentframe;
- QMovie *_movie;
- bool oldPlaying;
+ bool playing : 1;
+ bool paused : 1;
+ bool oldPlaying : 1;
+ unsigned padding: 29;
+ int presetCurrentFrame;
+ qreal speed;
+ QSize currentSourceSize;
+ QMovie *movie;
#if QT_CONFIG(qml_network)
QNetworkReply *reply;
int redirectCount;
#endif
QMap<int, QQuickPixmap *> frameMap;
- QSize currentSourceSize;
- void setMovie(QMovie *movie);
};
QT_END_NAMESPACE
diff --git a/src/quick/items/qquickanimatedsprite.cpp b/src/quick/items/qquickanimatedsprite.cpp
index 4e71b0c65f..741e4607e5 100644
--- a/src/quick/items/qquickanimatedsprite.cpp
+++ b/src/quick/items/qquickanimatedsprite.cpp
@@ -69,9 +69,67 @@ QT_BEGIN_NAMESPACE
as multiple frames in the same image file. You can play it at a fixed speed, at the
frame rate of your display, or manually advance and control the progress.
- For details of how a sprite animation is defined see the \l{Sprite Animations} overview.
- Note that the AnimatedSprite type does not use Sprite types to define multiple animations,
- but instead encapsulates a single animation itself.
+ Consider the following sprite sheet:
+
+ \image animatedsprite-loading.png
+
+ It can be divided up into four frames:
+
+ \image animatedsprite-loading-frames.png
+
+ To play each of these frames at a speed of 500 milliseconds per frame, the
+ following code can be used:
+
+ \table
+ \header
+ \li Code
+ \li Result
+ \row
+ \li
+ \code
+ AnimatedSprite {
+ source: "loading.png"
+ frameWidth: 64
+ frameHeight: 64
+ frameCount: 4
+ frameDuration: 500
+ }
+ \endcode
+ \li
+ \image animatedsprite-loading-interpolated.gif
+ \endtable
+
+ By default, the frames are interpolated (blended together) to make the
+ animation appear smoother. To disable this, set \l interpolate to \c false:
+
+ \table
+ \header
+ \li Code
+ \li Result
+ \row
+ \li
+ \code
+ AnimatedSprite {
+ source: "loading.png"
+ frameWidth: 64
+ frameHeight: 64
+ frameCount: 4
+ frameDuration: 500
+ interpolate: false
+ }
+ \endcode
+ \li
+ \image animatedsprite-loading.gif
+ \endtable
+
+ To control how AnimatedSprite responds to being scaled, use the
+ \l {Item::}{smooth} property.
+
+ Note that unlike \l SpriteSequence, the AnimatedSprite type does not use
+ \l Sprite to define multiple animations, but instead encapsulates a
+ single animation itself.
+
+ \sa {Sprite Animations}
*/
/*!
@@ -105,7 +163,7 @@ QT_BEGIN_NAMESPACE
/*!
\qmlproperty int QtQuick::AnimatedSprite::frameDuration
- Duration of each frame of the animation. Values equal to or below 0 are invalid.
+ Duration of each frame of the animation in milliseconds. Values equal to or below 0 are invalid.
If frameRate is valid then it will be used to calculate the duration of the frames.
If not, and frameDuration is valid, then frameDuration will be used.
@@ -210,7 +268,6 @@ QT_BEGIN_NAMESPACE
Stops, then starts the sprite animation.
*/
-//TODO: Implicitly size element to size of sprite
QQuickAnimatedSprite::QQuickAnimatedSprite(QQuickItem *parent) :
QQuickItem(*(new QQuickAnimatedSpritePrivate), parent)
{
@@ -516,6 +573,7 @@ void QQuickAnimatedSprite::setFrameHeight(int arg)
if (d->m_sprite->m_frameHeight != arg) {
d->m_sprite->setFrameHeight(arg);
Q_EMIT frameHeightChanged(arg);
+ setImplicitHeight(frameHeight());
reloadImage();
}
}
@@ -527,6 +585,7 @@ void QQuickAnimatedSprite::setFrameWidth(int arg)
if (d->m_sprite->m_frameWidth != arg) {
d->m_sprite->setFrameWidth(arg);
Q_EMIT frameWidthChanged(arg);
+ setImplicitWidth(frameWidth());
reloadImage();
}
}
@@ -641,6 +700,17 @@ QSGSpriteNode* QQuickAnimatedSprite::initNode()
if (image.isNull())
return nullptr;
+ // If frameWidth or frameHeight are not explicitly set, frameWidth
+ // will be set to the width of the image divided by the number of frames,
+ // and frameHeight will be set to the height of the image.
+ // In this case, QQuickAnimatedSprite currently won't emit frameWidth/HeightChanged
+ // at all, so we have to do this here, as it's the only place where assembledImage()
+ // is called (which calculates the "implicit" frameWidth/Height.
+ // In addition, currently the "implicit" frameWidth/Height are only calculated once,
+ // even after changing to a different source.
+ setImplicitWidth(frameWidth());
+ setImplicitHeight(frameHeight());
+
QSGSpriteNode *node = d->sceneGraphContext()->createSpriteNode();
d->m_sheetSize = QSize(image.size());
diff --git a/src/quick/items/qquickanimatedsprite_p.h b/src/quick/items/qquickanimatedsprite_p.h
index 276e6fbb92..d7e60b909c 100644
--- a/src/quick/items/qquickanimatedsprite_p.h
+++ b/src/quick/items/qquickanimatedsprite_p.h
@@ -94,7 +94,7 @@ class Q_AUTOTEST_EXPORT QQuickAnimatedSprite : public QQuickItem
Q_PROPERTY(int currentFrame READ currentFrame WRITE setCurrentFrame NOTIFY currentFrameChanged)
public:
- explicit QQuickAnimatedSprite(QQuickItem *parent = 0);
+ explicit QQuickAnimatedSprite(QQuickItem *parent = nullptr);
enum LoopParameters {
Infinite = -1
};
diff --git a/src/quick/items/qquickborderimage.cpp b/src/quick/items/qquickborderimage.cpp
index 75e3a3dbed..4bf34f0417 100644
--- a/src/quick/items/qquickborderimage.cpp
+++ b/src/quick/items/qquickborderimage.cpp
@@ -278,7 +278,7 @@ void QQuickBorderImage::setSource(const QUrl &url)
#if QT_CONFIG(qml_network)
if (d->sciReply) {
d->sciReply->deleteLater();
- d->sciReply = 0;
+ d->sciReply = nullptr;
}
#endif
@@ -559,12 +559,12 @@ void QQuickBorderImage::sciRequestFinished()
if (d->sciReply->error() != QNetworkReply::NoError) {
d->status = Error;
d->sciReply->deleteLater();
- d->sciReply = 0;
+ d->sciReply = nullptr;
emit statusChanged(d->status);
} else {
QQuickGridScaledImage sci(d->sciReply);
d->sciReply->deleteLater();
- d->sciReply = 0;
+ d->sciReply = nullptr;
setGridScaledImage(sci);
}
}
@@ -629,7 +629,7 @@ QSGNode *QQuickBorderImage::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeDat
if (!texture || width() <= 0 || height() <= 0) {
delete oldNode;
- return 0;
+ return nullptr;
}
QSGInternalImageNode *node = static_cast<QSGInternalImageNode *>(oldNode);
diff --git a/src/quick/items/qquickborderimage_p.h b/src/quick/items/qquickborderimage_p.h
index f43e6c8e1e..61bd26ba83 100644
--- a/src/quick/items/qquickborderimage_p.h
+++ b/src/quick/items/qquickborderimage_p.h
@@ -69,7 +69,7 @@ class Q_AUTOTEST_EXPORT QQuickBorderImage : public QQuickImageBase
Q_PROPERTY(QSize sourceSize READ sourceSize NOTIFY sourceSizeChanged)
public:
- QQuickBorderImage(QQuickItem *parent=0);
+ QQuickBorderImage(QQuickItem *parent=nullptr);
~QQuickBorderImage();
QQuickScaleGrid *border();
diff --git a/src/quick/items/qquickdrag.cpp b/src/quick/items/qquickdrag.cpp
index 6dc005a03c..d377b1dad4 100644
--- a/src/quick/items/qquickdrag.cpp
+++ b/src/quick/items/qquickdrag.cpp
@@ -67,8 +67,8 @@ public:
return static_cast<QQuickDragAttachedPrivate *>(QObjectPrivate::get(attached)); }
QQuickDragAttachedPrivate()
- : attachedItem(0)
- , mimeData(0)
+ : attachedItem(nullptr)
+ , mimeData(nullptr)
, proposedAction(Qt::MoveAction)
, supportedActions(Qt::MoveAction | Qt::CopyAction | Qt::LinkAction)
, active(false)
@@ -231,7 +231,7 @@ void QQuickDragAttachedPrivate::deliverLeaveEvent()
if (window) {
QDragLeaveEvent event;
deliverEvent(window, &event);
- window = 0;
+ window = nullptr;
}
}
@@ -686,7 +686,7 @@ int QQuickDragAttached::drop()
return acceptedAction;
d->active = false;
- QObject *target = 0;
+ QObject *target = nullptr;
if (d->window) {
QPoint scenePos = d->attachedItem->mapToScene(d->hotSpot).toPoint();
@@ -732,7 +732,7 @@ void QQuickDragAttached::cancel()
d->deliverLeaveEvent();
if (d->target) {
- d->target = 0;
+ d->target = nullptr;
emit targetChanged();
}
@@ -783,7 +783,7 @@ Qt::DropAction QQuickDragAttachedPrivate::startDrag(Qt::DropActions supportedAct
deliverLeaveEvent();
if (target) {
- target = 0;
+ target = nullptr;
emit q->targetChanged();
}
@@ -836,7 +836,7 @@ void QQuickDragAttached::startDrag(QQmlV4Function *args)
}
QQuickDrag::QQuickDrag(QObject *parent)
-: QObject(parent), _target(0), _axis(XAndYAxis), _xmin(-FLT_MAX),
+: QObject(parent), _target(nullptr), _axis(XAndYAxis), _xmin(-FLT_MAX),
_xmax(FLT_MAX), _ymin(-FLT_MAX), _ymax(FLT_MAX), _active(false), _filterChildren(false),
_smoothed(true), _threshold(QGuiApplication::styleHints()->startDragDistance())
{
@@ -861,9 +861,9 @@ void QQuickDrag::setTarget(QQuickItem *t)
void QQuickDrag::resetTarget()
{
- if (_target == 0)
+ if (_target == nullptr)
return;
- _target = 0;
+ _target = nullptr;
emit targetChanged();
}
diff --git a/src/quick/items/qquickdrag_p.h b/src/quick/items/qquickdrag_p.h
index 17e9d8c690..6bfbae74c9 100644
--- a/src/quick/items/qquickdrag_p.h
+++ b/src/quick/items/qquickdrag_p.h
@@ -83,7 +83,7 @@ class QQuickDragGrabber
typedef QIntrusiveList<Item, &Item::node> ItemList;
public:
- QQuickDragGrabber() : m_target(0) {}
+ QQuickDragGrabber() : m_target(nullptr) {}
~QQuickDragGrabber() { while (!m_items.isEmpty()) delete m_items.first(); }
@@ -94,10 +94,10 @@ public:
else if (!m_items.isEmpty())
return *m_items.first();
else
- return 0;
+ return nullptr;
}
void setTarget(QObject *target) { m_target = target; }
- void resetTarget() { m_target = 0; }
+ void resetTarget() { m_target = nullptr; }
bool isEmpty() const { return m_items.isEmpty(); }
@@ -136,7 +136,7 @@ class QQuickDragMimeData : public QMimeData
Q_OBJECT
public:
QQuickDragMimeData()
- : m_source(0)
+ : m_source(nullptr)
{
}
@@ -173,7 +173,7 @@ class Q_AUTOTEST_EXPORT QQuickDrag : public QObject
//### consider drag and drop
public:
- QQuickDrag(QObject *parent=0);
+ QQuickDrag(QObject *parent=nullptr);
~QQuickDrag();
enum DragType { None, Automatic, Internal };
diff --git a/src/quick/items/qquickdroparea.cpp b/src/quick/items/qquickdroparea.cpp
index c7606f90e1..b77fb40cb1 100644
--- a/src/quick/items/qquickdroparea.cpp
+++ b/src/quick/items/qquickdroparea.cpp
@@ -78,7 +78,7 @@ public:
};
QQuickDropAreaPrivate::QQuickDropAreaPrivate()
- : drag(0)
+ : drag(nullptr)
, containsDrag(false)
{
}
@@ -303,7 +303,7 @@ void QQuickDropArea::dragLeaveEvent(QDragLeaveEvent *)
emit exited();
d->containsDrag = false;
- d->source = 0;
+ d->source = nullptr;
emit containsDragChanged();
if (d->drag)
emit d->drag->sourceChanged();
@@ -328,7 +328,7 @@ void QQuickDropArea::dropEvent(QDropEvent *event)
emit dropped(&dragTargetEvent);
d->containsDrag = false;
- d->source = 0;
+ d->source = nullptr;
emit containsDragChanged();
if (d->drag)
emit d->drag->sourceChanged();
diff --git a/src/quick/items/qquickevents.cpp b/src/quick/items/qquickevents.cpp
index 8653d758de..1be4bafe28 100644
--- a/src/quick/items/qquickevents.cpp
+++ b/src/quick/items/qquickevents.cpp
@@ -134,13 +134,13 @@ Item {
It contains a bitwise combination of:
\list
- \li Qt.NoModifier - No modifier key is pressed.
- \li Qt.ShiftModifier - A Shift key on the keyboard is pressed.
- \li Qt.ControlModifier - A Ctrl key on the keyboard is pressed.
- \li Qt.AltModifier - An Alt key on the keyboard is pressed.
- \li Qt.MetaModifier - A Meta key on the keyboard is pressed.
- \li Qt.KeypadModifier - A keypad button is pressed.
- \li Qt.GroupSwitchModifier - X11 only. A Mode_switch key on the keyboard is pressed.
+ \li \l {Qt::NoModifier} {Qt.NoModifier} - No modifier key is pressed.
+ \li \l {Qt::ShiftModifier} {Qt.ShiftModifier} - A Shift key on the keyboard is pressed.
+ \li \l {Qt::ControlModifier} {Qt.ControlModifier} - A Ctrl key on the keyboard is pressed.
+ \li \l {Qt::AltModifier} {Qt.AltModifier} - An Alt key on the keyboard is pressed.
+ \li \l {Qt::MetaModifier} {Qt.MetaModifier} - A Meta key on the keyboard is pressed.
+ \li \l {Qt::KeypadModifier} {Qt.KeypadModifier} - A keypad button is pressed.
+ \li \l {Qt::GroupSwitchModifier} {Qt.GroupSwitchModifier} - X11 only. A Mode_switch key on the keyboard is pressed.
\endlist
For example, to react to a Shift key + Enter key combination:
@@ -184,7 +184,7 @@ Item {
\brief Provides information about a mouse event
- The position of the mouse can be found via the \l x and \l y properties.
+ The position of the mouse can be found via the \l {Item::x} {x} and \l {Item::y} {y} properties.
The button that caused the event is available via the \l button property.
\sa MouseArea
@@ -218,17 +218,17 @@ Item {
This property holds the button that caused the event. It can be one of:
\list
- \li Qt.LeftButton
- \li Qt.RightButton
- \li Qt.MiddleButton
+ \li \l {Qt::LeftButton} {Qt.LeftButton}
+ \li \l {Qt::RightButton} {Qt.RightButton}
+ \li \l {Qt::MiddleButton} {Qt.MiddleButton}
\endlist
*/
/*!
\qmlproperty bool QtQuick::MouseEvent::wasHeld
- This property is true if the mouse button has been held pressed longer the
- threshold (800ms).
+ This property is true if the mouse button has been held pressed longer
+ than the threshold (800ms).
*/
/*!
@@ -241,9 +241,9 @@ Item {
It contains a bitwise combination of:
\list
- \li Qt.LeftButton
- \li Qt.RightButton
- \li Qt.MiddleButton
+ \li \l {Qt::LeftButton} {Qt.LeftButton}
+ \li \l {Qt::RightButton} {Qt.RightButton}
+ \li \l {Qt::MiddleButton} {Qt.MiddleButton}
\endlist
*/
@@ -255,12 +255,12 @@ Item {
It contains a bitwise combination of:
\list
- \li Qt.NoModifier - No modifier key is pressed.
- \li Qt.ShiftModifier - A Shift key on the keyboard is pressed.
- \li Qt.ControlModifier - A Ctrl key on the keyboard is pressed.
- \li Qt.AltModifier - An Alt key on the keyboard is pressed.
- \li Qt.MetaModifier - A Meta key on the keyboard is pressed.
- \li Qt.KeypadModifier - A keypad button is pressed.
+ \li \l {Qt::NoModifier} {Qt.NoModifier} - No modifier key is pressed.
+ \li \l {Qt::ShiftModifier} {Qt.ShiftModifier} - A Shift key on the keyboard is pressed.
+ \li \l {Qt::ControlModifier} {Qt.ControlModifier} - A Ctrl key on the keyboard is pressed.
+ \li \l {Qt::AltModifier} {Qt.AltModifier} - An Alt key on the keyboard is pressed.
+ \li \l {Qt::MetaModifier} {Qt.MetaModifier} - A Meta key on the keyboard is pressed.
+ \li \l {Qt::KeypadModifier} {Qt.KeypadModifier} - A keypad button is pressed.
\endlist
For example, to react to a Shift key + Left mouse button click:
@@ -288,20 +288,24 @@ Item {
The value can be one of:
- \value Qt.MouseEventNotSynthesized The most common value. On platforms where
- such information is available, this value indicates that the event
- represents a genuine mouse event from the system.
+ \list
+ \li \l{Qt::MouseEventNotSynthesized} {Qt.MouseEventNotSynthesized}
+ - The most common value. On platforms where such information is
+ available, this value indicates that the event represents a genuine
+ mouse event from the system.
- \value Qt.MouseEventSynthesizedBySystem Indicates that the mouse event was
+ \li \l{Qt::MouseEventSynthesizedBySystem} {Qt.MouseEventSynthesizedBySystem} - Indicates that the mouse event was
synthesized from a touch or tablet event by the platform.
- \value Qt.MouseEventSynthesizedByQt Indicates that the mouse event was
- synthesized from an unhandled touch or tablet event by Qt.
+ \li \l{Qt::MouseEventSynthesizedByQt} {Qt.MouseEventSynthesizedByQt}
+ - Indicates that the mouse event was synthesized from an unhandled
+ touch or tablet event by Qt.
- \value Qt.MouseEventSynthesizedByApplication Indicates that the mouse event
- was synthesized by the application. This allows distinguishing
- application-generated mouse events from the ones that are coming from the
- system or are synthesized by Qt.
+ \li \l{Qt::MouseEventSynthesizedByApplication} {Qt.MouseEventSynthesizedByApplication}
+ - Indicates that the mouse event was synthesized by the application.
+ This allows distinguishing application-generated mouse events from
+ the ones that are coming from the system or are synthesized by Qt.
+ \endlist
For example, to react only to events which come from an actual mouse:
\qml
@@ -326,13 +330,29 @@ Item {
*/
/*!
+ \qmlproperty int QtQuick::MouseEvent::flags
+ \since 5.11
+
+ This property holds the flags that provide additional information about the
+ mouse event.
+
+ \list
+ \li \l {Qt::MouseEventCreatedDoubleClick} {Qt.MouseEventCreatedDoubleClick}
+ - Indicates that Qt has created a double click event from this event.
+ This flag is set in the event originating from a button press, and not
+ in the resulting double click event.
+ \endlist
+*/
+
+/*!
\qmltype WheelEvent
\instantiates QQuickWheelEvent
\inqmlmodule QtQuick
\ingroup qtquick-input-events
\brief Provides information about a mouse wheel event
- The position of the mouse can be found via the \l x and \l y properties.
+ The position of the mouse can be found via the
+ \l {Item::x} {x} and \l {Item::y} {y} properties.
\sa MouseArea
*/
@@ -366,9 +386,9 @@ Item {
It contains a bitwise combination of:
\list
- \li Qt.LeftButton
- \li Qt.RightButton
- \li Qt.MiddleButton
+ \li \l {Qt::LeftButton} {Qt.LeftButton}
+ \li \l {Qt::RightButton} {Qt.RightButton}
+ \li \l {Qt::MiddleButton} {Qt.MiddleButton}
\endlist
*/
@@ -406,12 +426,12 @@ Item {
It contains a bitwise combination of:
\list
- \li Qt.NoModifier - No modifier key is pressed.
- \li Qt.ShiftModifier - A Shift key on the keyboard is pressed.
- \li Qt.ControlModifier - A Ctrl key on the keyboard is pressed.
- \li Qt.AltModifier - An Alt key on the keyboard is pressed.
- \li Qt.MetaModifier - A Meta key on the keyboard is pressed.
- \li Qt.KeypadModifier - A keypad button is pressed.
+ \li \l {Qt::NoModifier} {Qt.NoModifier} - No modifier key is pressed.
+ \li \l {Qt::ShiftModifier} {Qt.ShiftModifier} - A Shift key on the keyboard is pressed.
+ \li \l {Qt::ControlModifier} {Qt.ControlModifier} - A Ctrl key on the keyboard is pressed.
+ \li \l {Qt::AltModifier} {Qt.AltModifier} - An Alt key on the keyboard is pressed.
+ \li \l {Qt::MetaModifier} {Qt.MetaModifier} - A Meta key on the keyboard is pressed.
+ \li \l {Qt::KeypadModifier} {Qt.KeypadModifier} - A keypad button is pressed.
\endlist
For example, to react to a Control key pressed during the wheel event:
@@ -485,13 +505,46 @@ Item {
\l {QTabletEvent::tangentialPressure}{tangentialPressure}
\value DeviceType.Puck
a device that is similar to a flat mouse with a
- transparent circle with cross-hairs (same as \l QTabletEvent::Puck)
+ transparent circle with cross-hairs
+ (same as \l {QTabletEvent::Puck} {Puck})
+ \value DeviceType.AllDevices
+ any of the above; used as a default value for construction
\sa QTouchDevice::DeviceType
*/
/*!
\readonly
+ \qmlproperty enumeration QtQuick::PointerDevice::pointerType
+
+ This property holds a value indicating what is interacting with
+ the device. Think of the device as having a planar 2D surface, and
+ the value of this property as identifying what interacts with the
+ device.
+
+ There is some redundancy between this property and \l {PointerDevice::type}.
+ If a tocuchscreen is used, then the device is TouchScreen and
+ pointerType is Finger (always).
+
+ Valid values are:
+
+ \value PointerDevice.GenericPointer
+ a mouse or something acting like a mouse (the core pointer on X11)
+ \value PointerDevice.Finger
+ the user's finger
+ \value PointerDevice.Pen
+ the drawing end of a stylus
+ \value PointerDevice.Eraser
+ the other end of the stylus (if it has a virtual eraser on the other end)
+ \value PointerDevice.Cursor
+ a cursor in the pre-computer sense of the word
+ \value PointerDevice.AllPointerTypes
+ any of the above (used as a default value in constructors)
+*/
+
+
+/*!
+ \readonly
\qmlproperty enumeration QtQuick::PointerDevice::capabilities
This property holds a bitwise combination of the capabilities of the
@@ -508,11 +561,11 @@ Item {
\value CapabilityFlag.Pressure
the \l {QtQuick::EventTouchPoint::pressure}{pressure} property
\value CapabilityFlag.Velocity
- the \l {QtQuick::PointerEvent::velocity}{velocity} property
+ the \l {QtQuick::EventPoint::velocity}{velocity} property
\value CapabilityFlag.Scroll
- a \l {QtQuick::PointerDevice::DeviceType::Mouse}{Mouse} has a wheel, or the
+ a \l {QtQuick::PointerDevice::type}{Mouse} has a wheel, or the
operating system recognizes scroll gestures on a
- \l {QtQuick::PointerDevice::DeviceType::TouchPad}{TouchPad}
+ \l {QtQuick::PointerDevice::type}{TouchPad}
\value CapabilityFlag.Hover
events are sent even when no button is pressed, or the finger or stylus
is not in contact with the surface
@@ -572,8 +625,7 @@ QQuickPointerDevice *QQuickPointerDevice::touchDevice(const QTouchDevice *d)
int maximumTouchPoints = 10;
QQuickPointerDevice::Capabilities caps = QQuickPointerDevice::Capabilities(QTouchDevice::Position);
if (d) {
- QQuickPointerDevice::Capabilities caps =
- static_cast<QQuickPointerDevice::Capabilities>(static_cast<int>(d->capabilities()) & 0x0F);
+ caps = static_cast<QQuickPointerDevice::Capabilities>(static_cast<int>(d->capabilities()) & 0xFF);
if (d->type() == QTouchDevice::TouchPad) {
type = QQuickPointerDevice::TouchPad;
caps |= QQuickPointerDevice::Scroll;
@@ -639,8 +691,8 @@ QQuickPointerDevice *QQuickPointerDevice::tabletDevice(qint64 id)
\qmlproperty point QtQuick::EventPoint::scenePosition
This property holds the coordinates of the position supplied by the event,
- relative to the scene. If a contact patch is available from the \l device,
- this point represents its centroid.
+ relative to the scene. If a contact patch is available from the
+ \l {QtQuick::PointerEvent::device} {device}, this point represents its centroid.
*/
/*!
@@ -698,7 +750,7 @@ QQuickPointerDevice *QQuickPointerDevice::tabletDevice(qint64 id)
presses a finger against the touchscreen, it will be a larger number.
In other cases, it will be -1.
- \sa PointerDevice.uniqueId
+ \sa {QtQuick::EventTouchPoint::uniqueId}{uniqueId}
*/
/*!
@@ -790,17 +842,19 @@ QQuickItem *QQuickEventPoint::grabberItem() const
void QQuickEventPoint::setGrabberItem(QQuickItem *grabber)
{
if (grabber != m_exclusiveGrabber.data()) {
+ QQuickPointerHandler *oldGrabberHandler = grabberPointerHandler();
+ if (oldGrabberHandler && !oldGrabberHandler->approveGrabTransition(this, grabber))
+ return;
if (Q_UNLIKELY(lcPointerGrab().isDebugEnabled())) {
qCDebug(lcPointerGrab) << pointDeviceName(this) << "point" << hex << m_pointId << pointStateString(this)
<< ": grab" << m_exclusiveGrabber << "->" << grabber;
}
- QQuickPointerHandler *oldGrabberHandler = grabberPointerHandler();
- QQuickItem *oldGrabberItem = grabberItem();
m_exclusiveGrabber = QPointer<QObject>(grabber);
m_grabberIsHandler = false;
m_sceneGrabPos = m_scenePos;
+ QQuickItem *oldGrabberItem = grabberItem();
if (oldGrabberHandler)
- oldGrabberHandler->onGrabChanged(oldGrabberHandler, CancelGrabExclusive, this);
+ oldGrabberHandler->onGrabChanged(oldGrabberHandler, (grabber ? CancelGrabExclusive : UngrabExclusive), this);
else if (oldGrabberItem && oldGrabberItem != grabber && grabber && pointerEvent()->asPointerTouchEvent())
oldGrabberItem->touchUngrabEvent();
for (QPointer<QQuickPointerHandler> passiveGrabber : m_passiveGrabbers)
@@ -837,26 +891,24 @@ void QQuickEventPoint::setGrabberPointerHandler(QQuickPointerHandler *grabber, b
}
if (exclusive) {
if (grabber != m_exclusiveGrabber.data()) {
+ QQuickPointerHandler *oldGrabberHandler = grabberPointerHandler();
+ QQuickItem *oldGrabberItem = grabberItem();
+ m_exclusiveGrabber = QPointer<QObject>(grabber);
+ m_grabberIsHandler = true;
+ m_sceneGrabPos = m_scenePos;
if (grabber) {
- // set variables before notifying the new grabber
- m_exclusiveGrabber = QPointer<QObject>(grabber);
- m_grabberIsHandler = true;
- m_sceneGrabPos = m_scenePos;
grabber->onGrabChanged(grabber, GrabExclusive, this);
for (QPointer<QQuickPointerHandler> passiveGrabber : m_passiveGrabbers) {
if (passiveGrabber != grabber)
passiveGrabber->onGrabChanged(grabber, OverrideGrabPassive, this);
}
- } else if (QQuickPointerHandler *oldGrabberPointerHandler = qmlobject_cast<QQuickPointerHandler *>(m_exclusiveGrabber.data())) {
- oldGrabberPointerHandler->onGrabChanged(oldGrabberPointerHandler, UngrabExclusive, this);
- } else if (!m_exclusiveGrabber.isNull()) {
- // If there is a previous grabber and it's not a PointerHandler, it must be an Item.
- QQuickItem *oldGrabberItem = static_cast<QQuickItem *>(m_exclusiveGrabber.data());
- // If this point came from a touchscreen, notify that previous grabber Item that it's losing its touch grab.
- if (pointerEvent()->asPointerTouchEvent())
- oldGrabberItem->touchUngrabEvent();
}
- // set variables after notifying the old grabber
+ if (oldGrabberHandler)
+ oldGrabberHandler->onGrabChanged(oldGrabberHandler, (grabber ? CancelGrabExclusive : UngrabExclusive), this);
+ else if (oldGrabberItem && pointerEvent()->asPointerTouchEvent())
+ oldGrabberItem->touchUngrabEvent();
+ // touchUngrabEvent() can result in the grabber being set to null (MPTA does that, for example).
+ // So set it again to ensure that final state is what we want.
m_exclusiveGrabber = QPointer<QObject>(grabber);
m_grabberIsHandler = true;
m_sceneGrabPos = m_scenePos;
@@ -1032,22 +1084,27 @@ void QQuickEventPoint::setAccepted(bool accepted)
\qmlproperty size QtQuick::EventTouchPoint::ellipseDiameters
This property holds the diameters of the contact patch, if the event
- comes from a touchpoint and the \l device provides this information.
-
- A touchpoint is modeled as an elliptical area where the finger is pressed
- against the touchscreen. (In fact, it could also be modeled as a bitmap; but
- in that case we expect an elliptical bounding estimate to be fitted to the
- contact patch before the event is sent.) The harder the user presses, the
- larger the contact patch; so, these diameters provide an alternate way of
- detecting pressure, in case the device does not include a separate pressure
- sensor. The ellipse is centered on \l scenePos (\l pos in the PointerHandler's
+ comes from a touchpoint and the \l {QtQuick::PointerEvent::device} {device}
+ provides this information.
+
+ A touchpoint is modeled as an elliptical area where the finger is
+ pressed against the touchscreen. (In fact, it could also be
+ modeled as a bitmap; but in that case we expect an elliptical
+ bounding estimate to be fitted to the contact patch before the
+ event is sent.) The harder the user presses, the larger the
+ contact patch; so, these diameters provide an alternate way of
+ detecting pressure, in case the device does not include a separate
+ pressure sensor. The ellipse is centered on
+ \l {QtQuick::EventPoint::scenePosition} {scenePosition}
+ (\l {QtQuick::EventPoint::position} {position} in the PointerHandler's
Item's local coordinates). The \l rotation property provides the
- rotation of the ellipse, if known. It is expected that if the \l rotation
- is zero, the verticalDiameter of the ellipse is the larger one (the major axis),
- because of the usual hand position, reaching upward or outward across the surface.
+ rotation of the ellipse, if known. It is expected that if the
+ \l rotation is zero, the verticalDiameter of the ellipse is the
+ larger one (the major axis), because of the usual hand position,
+ reaching upward or outward across the surface.
- If the contact patch is unknown, or the \l device is not a touchscreen,
- these values will be zero.
+ If the contact patch is unknown, or the \l {QtQuick::PointerEvent::device} {device}
+ is not a touchscreen, these values will be zero.
*/
QQuickEventTouchPoint::QQuickEventTouchPoint(QQuickPointerTouchEvent *parent)
@@ -1131,8 +1188,8 @@ QVector2D QQuickEventPoint::estimatedVelocity() const
A PointerEvent is an event describing contact or movement across a surface,
provided by a mouse, a touchpoint (single finger on a touchscreen), or a
- stylus on a graphics tablet. The \l device property provides more
- information about where the event came from.
+ stylus on a graphics tablet. The \l {QtQuick::PointerEvent::device} {device}
+ property provides more information about where the event came from.
\sa PointerHandler
@@ -1158,8 +1215,8 @@ QVector2D QQuickEventPoint::estimatedVelocity() const
\qmlproperty enumeration QtQuick::PointerEvent::button
This property holds the \l {Qt::MouseButton}{button} that caused the event,
- if any. If the \l device does not have buttons, or the event is a hover
- event, it will be \c Qt.NoButton.
+ if any. If the \l {QtQuick::PointerEvent::device} {device} does not have
+ buttons, or the event is a hover event, it will be \c Qt.NoButton.
*/
/*!
diff --git a/src/quick/items/qquickevents_p_p.h b/src/quick/items/qquickevents_p_p.h
index 09a63febdc..c4f0b60d92 100644
--- a/src/quick/items/qquickevents_p_p.h
+++ b/src/quick/items/qquickevents_p_p.h
@@ -84,7 +84,7 @@ class QQuickKeyEvent : public QObject
public:
QQuickKeyEvent()
- : event(QEvent::None, 0, 0)
+ : event(QEvent::None, 0, nullptr)
{}
void reset(QEvent::Type type, int key, Qt::KeyboardModifiers modifiers,
@@ -131,15 +131,18 @@ class Q_QUICK_PRIVATE_EXPORT QQuickMouseEvent : public QObject
Q_PROPERTY(bool wasHeld READ wasHeld)
Q_PROPERTY(bool isClick READ isClick)
Q_PROPERTY(bool accepted READ isAccepted WRITE setAccepted)
+ Q_REVISION(11) Q_PROPERTY(int flags READ flags)
public:
QQuickMouseEvent()
- : _x(0), _y(0), _button(Qt::NoButton), _buttons(Qt::NoButton), _modifiers(Qt::NoModifier)
- , _source(Qt::MouseEventNotSynthesized), _wasHeld(false), _isClick(false), _accepted(false)
+ : _buttons(Qt::NoButton), _modifiers(Qt::NoModifier)
+ , _wasHeld(false), _isClick(false), _accepted(false)
+ , _flags(Qt::MouseEventFlags(nullptr))
{}
void reset(qreal x, qreal y, Qt::MouseButton button, Qt::MouseButtons buttons,
- Qt::KeyboardModifiers modifiers, bool isClick = false, bool wasHeld = false)
+ Qt::KeyboardModifiers modifiers, bool isClick = false, bool wasHeld = false,
+ Qt::MouseEventFlags flags = nullptr)
{
_x = x;
_y = y;
@@ -150,6 +153,7 @@ public:
_wasHeld = wasHeld;
_isClick = isClick;
_accepted = true;
+ _flags = flags;
}
qreal x() const { return _x; }
@@ -169,17 +173,18 @@ public:
bool isAccepted() { return _accepted; }
void setAccepted(bool accepted) { _accepted = accepted; }
-
+ int flags() const { return _flags; }
private:
- qreal _x;
- qreal _y;
- Qt::MouseButton _button;
+ qreal _x = 0;
+ qreal _y = 0;
+ Qt::MouseButton _button = Qt::NoButton;
Qt::MouseButtons _buttons;
Qt::KeyboardModifiers _modifiers;
- Qt::MouseEventSource _source;
+ Qt::MouseEventSource _source = Qt::MouseEventNotSynthesized;
bool _wasHeld : 1;
bool _isClick : 1;
bool _accepted : 1;
+ Qt::MouseEventFlags _flags;
};
class QQuickWheelEvent : public QObject
@@ -196,8 +201,7 @@ class QQuickWheelEvent : public QObject
public:
QQuickWheelEvent()
- : _x(0), _y(0), _buttons(Qt::NoButton), _modifiers(Qt::NoModifier)
- , _inverted(false), _accepted(false)
+ : _buttons(Qt::NoButton), _modifiers(Qt::NoModifier)
{}
void reset(qreal x, qreal y, const QPoint &angleDelta, const QPoint &pixelDelta,
@@ -224,14 +228,14 @@ public:
void setAccepted(bool accepted) { _accepted = accepted; }
private:
- qreal _x;
- qreal _y;
+ qreal _x = 0;
+ qreal _y = 0;
QPoint _angleDelta;
QPoint _pixelDelta;
Qt::MouseButtons _buttons;
Qt::KeyboardModifiers _modifiers;
- bool _inverted;
- bool _accepted;
+ bool _inverted = false;
+ bool _accepted = false;
};
class Q_QUICK_PRIVATE_EXPORT QQuickCloseEvent : public QObject
@@ -240,14 +244,13 @@ class Q_QUICK_PRIVATE_EXPORT QQuickCloseEvent : public QObject
Q_PROPERTY(bool accepted READ isAccepted WRITE setAccepted)
public:
- QQuickCloseEvent()
- : _accepted(true) {}
+ QQuickCloseEvent() {}
bool isAccepted() { return _accepted; }
void setAccepted(bool accepted) { _accepted = accepted; }
private:
- bool _accepted;
+ bool _accepted = true;
};
class Q_QUICK_PRIVATE_EXPORT QQuickEventPoint : public QObject
@@ -306,7 +309,6 @@ public:
void setExclusiveGrabber(QObject *exclusiveGrabber);
QQuickItem *grabberItem() const;
- Q_DECL_DEPRECATED QQuickItem *grabber() const { return grabberItem(); }
void setGrabberItem(QQuickItem *exclusiveGrabber);
QQuickPointerHandler *grabberPointerHandler() const;
@@ -390,12 +392,10 @@ public:
QQuickPointerEvent(QObject *parent = nullptr, QQuickPointerDevice *device = nullptr)
: QObject(parent)
, m_device(device)
- , m_event(nullptr)
- , m_button(Qt::NoButton)
, m_pressedButtons(Qt::NoButton)
- { }
+ {}
- virtual ~QQuickPointerEvent();
+ ~QQuickPointerEvent() override;
public: // property accessors
QQuickPointerDevice *device() const { return m_device; }
@@ -437,8 +437,8 @@ public: // helpers for C++ only (during event delivery)
protected:
QQuickPointerDevice *m_device;
- QInputEvent *m_event; // original event as received by QQuickWindow
- Qt::MouseButton m_button;
+ QInputEvent *m_event = nullptr; // original event as received by QQuickWindow
+ Qt::MouseButton m_button = Qt::NoButton;
Qt::MouseButtons m_pressedButtons;
Q_DISABLE_COPY(QQuickPointerEvent)
@@ -483,9 +483,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPointerTouchEvent : public QQuickPointerEvent
public:
QQuickPointerTouchEvent(QObject *parent = nullptr, QQuickPointerDevice *device = nullptr)
: QQuickPointerEvent(parent, device)
- , m_pointCount(0)
, m_synthMouseEvent(QEvent::MouseMove, QPointF(), Qt::NoButton, Qt::NoButton, Qt::NoModifier)
- { }
+ {}
QQuickPointerEvent *reset(QEvent *) override;
void localize(QQuickItem *target) override;
@@ -511,7 +510,7 @@ public:
QTouchEvent *asTouchEvent() const;
private:
- int m_pointCount;
+ int m_pointCount = 0;
QVector<QQuickEventTouchPoint *> m_touchPoints;
mutable QMouseEvent m_synthMouseEvent;
@@ -567,7 +566,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPointerDevice : public QObject
Q_PROPERTY(QPointingDeviceUniqueId uniqueId READ uniqueId CONSTANT)
public:
- enum DeviceType {
+ enum DeviceType : qint16 {
UnknownDevice = 0x0000,
Mouse = 0x0001,
TouchScreen = 0x0002,
@@ -575,25 +574,25 @@ public:
Puck = 0x0008,
Stylus = 0x0010,
Airbrush = 0x0020,
- AllDevices = 0x003F
+ AllDevices = 0x7FFF
};
Q_DECLARE_FLAGS(DeviceTypes, DeviceType)
Q_ENUM(DeviceType)
Q_FLAG(DeviceTypes)
- enum PointerType {
+ enum PointerType : qint16 {
GenericPointer = 0x0001,
Finger = 0x0002,
Pen = 0x0004,
Eraser = 0x0008,
Cursor = 0x0010,
- AllPointerTypes = 0x001F
+ AllPointerTypes = 0x7FFF
};
Q_DECLARE_FLAGS(PointerTypes, PointerType)
Q_ENUM(PointerType)
Q_FLAG(PointerTypes)
- enum CapabilityFlag {
+ enum CapabilityFlag : qint16 {
Position = QTouchDevice::Position,
Area = QTouchDevice::Area,
Pressure = QTouchDevice::Pressure,
@@ -611,7 +610,7 @@ public:
DeviceType type() const { return m_deviceType; }
PointerType pointerType() const { return m_pointerType; }
- Capabilities capabilities() const { return m_capabilities; }
+ Capabilities capabilities() const { return static_cast<Capabilities>(m_capabilities); }
bool hasCapability(CapabilityFlag cap) { return m_capabilities & cap; }
int maximumTouchPoints() const { return m_maximumTouchPoints; }
int buttonCount() const { return m_buttonCount; }
@@ -627,19 +626,21 @@ public:
private:
QQuickPointerDevice(DeviceType devType, PointerType pType, Capabilities caps, int maxPoints, int buttonCount, const QString &name, qint64 uniqueId = 0)
- : m_deviceType(devType), m_pointerType(pType), m_capabilities(caps)
- , m_maximumTouchPoints(maxPoints), m_buttonCount(buttonCount), m_name(name)
+ : m_deviceType(devType), m_pointerType(pType), m_capabilities(static_cast<qint16>(caps))
+ , m_maximumTouchPoints(static_cast<qint8>(maxPoints)), m_buttonCount(static_cast<qint8>(buttonCount)), m_name(name)
, m_uniqueId(QPointingDeviceUniqueId::fromNumericId(uniqueId))
{
}
- ~QQuickPointerDevice() { }
+ ~QQuickPointerDevice() override { }
private:
+ // begin 64-bit field
DeviceType m_deviceType;
PointerType m_pointerType;
- Capabilities m_capabilities;
- int m_maximumTouchPoints;
- int m_buttonCount;
+ qint16 m_capabilities;
+ qint8 m_maximumTouchPoints;
+ qint8 m_buttonCount;
+ // end 64-bit field
QString m_name;
QPointingDeviceUniqueId m_uniqueId;
QVector<QQuickPointerHandler *> m_eventDeliveryTargets; // during delivery, handlers which have already seen the event
diff --git a/src/quick/items/qquickflickable.cpp b/src/quick/items/qquickflickable.cpp
index cd918cef5f..8cb64377cc 100644
--- a/src/quick/items/qquickflickable.cpp
+++ b/src/quick/items/qquickflickable.cpp
@@ -172,13 +172,13 @@ class QQuickFlickableReboundTransition : public QQuickTransitionManager
{
public:
QQuickFlickableReboundTransition(QQuickFlickable *f, const QString &name)
- : flickable(f), axisData(0), propName(name), active(false)
+ : flickable(f), axisData(nullptr), propName(name), active(false)
{
}
~QQuickFlickableReboundTransition()
{
- flickable = 0;
+ flickable = nullptr;
}
bool startTransition(QQuickFlickablePrivate::AxisData *data, qreal toPos) {
@@ -252,12 +252,12 @@ QQuickFlickablePrivate::QQuickFlickablePrivate()
, lastPressTime(0)
, deceleration(QML_FLICK_DEFAULTDECELERATION)
, maxVelocity(QML_FLICK_DEFAULTMAXVELOCITY), reportedVelocitySmoothing(100)
- , delayedPressEvent(0), pressDelay(0), fixupDuration(400)
- , flickBoost(1.0), fixupMode(Normal), vTime(0), visibleArea(0)
+ , delayedPressEvent(nullptr), pressDelay(0), fixupDuration(400)
+ , flickBoost(1.0), fixupMode(Normal), vTime(0), visibleArea(nullptr)
, flickableDirection(QQuickFlickable::AutoFlickDirection)
, boundsBehavior(QQuickFlickable::DragAndOvershootBounds)
, boundsMovement(QQuickFlickable::FollowBoundsBehavior)
- , rebound(0)
+ , rebound(nullptr)
{
}
@@ -317,7 +317,7 @@ void QQuickFlickablePrivate::itemGeometryChanged(QQuickItem *item, QQuickGeometr
{
Q_Q(QQuickFlickable);
if (item == contentItem) {
- Qt::Orientations orient = 0;
+ Qt::Orientations orient = nullptr;
if (change.xChange())
orient |= Qt::Horizontal;
if (change.yChange())
@@ -725,7 +725,19 @@ QQuickFlickable::~QQuickFlickable()
These properties hold the surface coordinate currently at the top-left
corner of the Flickable. For example, if you flick an image up 100 pixels,
- \c contentY will be 100.
+ \c contentY will increase by 100.
+
+ \note If you flick back to the origin (the top-left corner), after the
+ rebound animation, \c contentX will settle to the same value as \c originX,
+ and \c contentY to \c originY. These are usually (0,0), however ListView
+ and GridView may have an arbitrary origin due to delegate size variation,
+ or item insertion/removal outside the visible region. So if you want to
+ implement something like a vertical scrollbar, one way is to use
+ \c {y: (contentY - originY) * (height / contentHeight)}
+ for the position; another way is to use the normalized values in
+ \l {QtQuick::Flickable::visibleArea}{visibleArea}.
+
+ \sa originX, originY
*/
qreal QQuickFlickable::contentX() const
{
@@ -739,7 +751,8 @@ void QQuickFlickable::setContentX(qreal pos)
d->hData.explicitValue = true;
d->resetTimeline(d->hData);
d->hData.vTime = d->timeline.time();
- movementEnding(true, false);
+ if (isMoving() || isFlicking())
+ movementEnding(true, false);
if (-pos != d->hData.move.value())
d->hData.move.setValue(-pos);
}
@@ -756,7 +769,8 @@ void QQuickFlickable::setContentY(qreal pos)
d->vData.explicitValue = true;
d->resetTimeline(d->vData);
d->vData.vTime = d->timeline.time();
- movementEnding(false, true);
+ if (isMoving() || isFlicking())
+ movementEnding(false, true);
if (-pos != d->vData.move.value())
d->vData.move.setValue(-pos);
}
@@ -1421,17 +1435,23 @@ void QQuickFlickable::wheelEvent(QWheelEvent *event)
case Qt::ScrollUpdate:
if (d->scrollingPhase)
d->pressed = true;
-#ifdef Q_OS_OSX
+#ifdef Q_OS_MACOS
+ // TODO eliminate this timer when ScrollMomentum has been added
d->movementEndingTimer.start(MovementEndingTimerInterval, this);
#endif
break;
case Qt::ScrollEnd:
+ // TODO most of this should be done at transition to ScrollMomentum phase,
+ // then do what the movementEndingTimer triggers at transition to ScrollEnd phase
d->pressed = false;
d->scrollingPhase = false;
d->draggingEnding();
event->accept();
returnToBounds();
d->lastPosTime = -1;
+#ifdef Q_OS_MACOS
+ d->movementEndingTimer.start(MovementEndingTimerInterval, this);
+#endif
return;
}
@@ -1535,7 +1555,7 @@ void QQuickFlickablePrivate::clearDelayedPress()
if (delayedPressEvent) {
delayedPressTimer.stop();
delete delayedPressEvent;
- delayedPressEvent = 0;
+ delayedPressEvent = nullptr;
}
}
@@ -1545,7 +1565,7 @@ void QQuickFlickablePrivate::replayDelayedPress()
if (delayedPressEvent) {
// Losing the grab will clear the delayed press event; take control of it here
QScopedPointer<QMouseEvent> mouseEvent(delayedPressEvent);
- delayedPressEvent = 0;
+ delayedPressEvent = nullptr;
delayedPressTimer.stop();
// If we have the grab, release before delivering the event
@@ -1838,7 +1858,7 @@ int QQuickFlickablePrivate::data_count(QQmlListProperty<QObject> *)
QObject *QQuickFlickablePrivate::data_at(QQmlListProperty<QObject> *, int)
{
// XXX todo
- return 0;
+ return nullptr;
}
void QQuickFlickablePrivate::data_clear(QQmlListProperty<QObject> *)
@@ -2150,6 +2170,8 @@ void QQuickFlickable::setRightMargin(qreal m)
This is usually (0,0), however ListView and GridView may have an arbitrary
origin due to delegate size variation, or item insertion/removal outside
the visible region.
+
+ \sa contentX, contentY
*/
qreal QQuickFlickable::originY() const
@@ -2180,25 +2202,25 @@ qreal QQuickFlickable::originX() const
void QQuickFlickable::resizeContent(qreal w, qreal h, QPointF center)
{
Q_D(QQuickFlickable);
- if (w != d->hData.viewSize) {
- qreal oldSize = d->hData.viewSize;
- d->hData.viewSize = w;
- d->contentItem->setWidth(w);
+ const qreal oldHSize = d->hData.viewSize;
+ const qreal oldVSize = d->vData.viewSize;
+ const bool needToUpdateWidth = w != oldHSize;
+ const bool needToUpdateHeight = h != oldVSize;
+ d->hData.viewSize = w;
+ d->vData.viewSize = h;
+ d->contentItem->setSize(QSizeF(w, h));
+ if (needToUpdateWidth)
emit contentWidthChanged();
- if (center.x() != 0) {
- qreal pos = center.x() * w / oldSize;
- setContentX(contentX() + pos - center.x());
- }
- }
- if (h != d->vData.viewSize) {
- qreal oldSize = d->vData.viewSize;
- d->vData.viewSize = h;
- d->contentItem->setHeight(h);
+ if (needToUpdateHeight)
emit contentHeightChanged();
- if (center.y() != 0) {
- qreal pos = center.y() * h / oldSize;
- setContentY(contentY() + pos - center.y());
- }
+
+ if (center.x() != 0) {
+ qreal pos = center.x() * w / oldHSize;
+ setContentX(contentX() + pos - center.x());
+ }
+ if (center.y() != 0) {
+ qreal pos = center.y() * h / oldVSize;
+ setContentY(contentY() + pos - center.y());
}
d->updateBeginningEnd();
}
@@ -2654,13 +2676,15 @@ void QQuickFlickable::movementEnding(bool hMovementEnding, bool vMovementEnding)
if (hMovementEnding && d->hData.moving
&& (!d->pressed && !d->stealMouse)) {
d->hData.moving = false;
- d->hMoved = false;
+ if (!d->scrollingPhase)
+ d->hMoved = false;
emit movingHorizontallyChanged();
}
if (vMovementEnding && d->vData.moving
&& (!d->pressed && !d->stealMouse)) {
d->vData.moving = false;
- d->vMoved = false;
+ if (!d->scrollingPhase)
+ d->vMoved = false;
emit movingVerticallyChanged();
}
if (wasMoving && !isMoving()) {
diff --git a/src/quick/items/qquickflickable_p.h b/src/quick/items/qquickflickable_p.h
index 4ad01323a4..939e3af698 100644
--- a/src/quick/items/qquickflickable_p.h
+++ b/src/quick/items/qquickflickable_p.h
@@ -115,7 +115,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickFlickable : public QQuickItem
Q_CLASSINFO("DefaultProperty", "flickableData")
public:
- QQuickFlickable(QQuickItem *parent=0);
+ QQuickFlickable(QQuickItem *parent=nullptr);
~QQuickFlickable();
QQmlListProperty<QObject> flickableData();
diff --git a/src/quick/items/qquickflickable_p_p.h b/src/quick/items/qquickflickable_p_p.h
index 54cc67875a..08f069e830 100644
--- a/src/quick/items/qquickflickable_p_p.h
+++ b/src/quick/items/qquickflickable_p_p.h
@@ -99,16 +99,17 @@ public:
struct AxisData {
AxisData(QQuickFlickablePrivate *fp, void (QQuickFlickablePrivate::*func)(qreal))
: move(fp, func)
- , transitionToBounds(0)
+ , transitionToBounds(nullptr)
, viewSize(-1), lastPos(0), previousDragDelta(0), velocity(0), startMargin(0), endMargin(0)
, origin(0), overshoot(0)
, transitionTo(0)
, continuousFlickVelocity(0), velocityTime(), vTime(0)
, smoothVelocity(fp), atEnd(false), atBeginning(true)
, transitionToSet(false)
- , fixingUp(false), inOvershoot(false), moving(false), flicking(false)
+ , fixingUp(false), inOvershoot(false), inRebound(false), moving(false), flicking(false)
, dragging(false), extentsChanged(false)
, explicitValue(false), minExtentDirty(true), maxExtentDirty(true)
+ , unused(0)
{}
~AxisData();
@@ -168,6 +169,7 @@ public:
bool explicitValue : 1;
mutable bool minExtentDirty : 1;
mutable bool maxExtentDirty : 1;
+ uint unused : 19;
};
bool flickX(qreal velocity);
@@ -282,7 +284,7 @@ class QQuickFlickableVisibleArea : public QObject
Q_PROPERTY(qreal heightRatio READ heightRatio NOTIFY heightRatioChanged)
public:
- QQuickFlickableVisibleArea(QQuickFlickable *parent=0);
+ QQuickFlickableVisibleArea(QQuickFlickable *parent=nullptr);
qreal xPosition() const;
qreal widthRatio() const;
diff --git a/src/quick/items/qquickflipable.cpp b/src/quick/items/qquickflipable.cpp
index 4273ed4881..fbba8eed89 100644
--- a/src/quick/items/qquickflipable.cpp
+++ b/src/quick/items/qquickflipable.cpp
@@ -68,7 +68,7 @@ class QQuickFlipablePrivate : public QQuickItemPrivate
{
Q_DECLARE_PUBLIC(QQuickFlipable)
public:
- QQuickFlipablePrivate() : current(QQuickFlipable::Front), front(0), back(0), sideDirty(false) {}
+ QQuickFlipablePrivate() : current(QQuickFlipable::Front), front(nullptr), back(nullptr), sideDirty(false) {}
void transformChanged() override;
void updateSide();
@@ -178,7 +178,7 @@ void QQuickFlipable::setBack(QQuickItem *back)
qmlWarning(this) << tr("back is a write-once property");
return;
}
- if (back == 0)
+ if (back == nullptr)
return;
d->back = back;
d->back->setParentItem(this);
diff --git a/src/quick/items/qquickflipable_p.h b/src/quick/items/qquickflipable_p.h
index ec922725ef..d70cd02d35 100644
--- a/src/quick/items/qquickflipable_p.h
+++ b/src/quick/items/qquickflipable_p.h
@@ -74,7 +74,7 @@ class Q_AUTOTEST_EXPORT QQuickFlipable : public QQuickItem
//### flipAxis
//### flipRotation
public:
- QQuickFlipable(QQuickItem *parent=0);
+ QQuickFlipable(QQuickItem *parent=nullptr);
~QQuickFlipable();
QQuickItem *front() const;
diff --git a/src/quick/items/qquickfocusscope_p.h b/src/quick/items/qquickfocusscope_p.h
index b65e543343..af750fc127 100644
--- a/src/quick/items/qquickfocusscope_p.h
+++ b/src/quick/items/qquickfocusscope_p.h
@@ -59,7 +59,7 @@ class Q_AUTOTEST_EXPORT QQuickFocusScope : public QQuickItem
{
Q_OBJECT
public:
- QQuickFocusScope(QQuickItem *parent=0);
+ QQuickFocusScope(QQuickItem *parent=nullptr);
virtual ~QQuickFocusScope();
};
diff --git a/src/quick/items/qquickframebufferobject.cpp b/src/quick/items/qquickframebufferobject.cpp
index 5a40d6b705..48f8b8db5c 100644
--- a/src/quick/items/qquickframebufferobject.cpp
+++ b/src/quick/items/qquickframebufferobject.cpp
@@ -57,7 +57,7 @@ public:
QQuickFramebufferObjectPrivate()
: followsItemSize(true)
, mirrorVertically(false)
- , node(0)
+ , node(nullptr)
{
}
@@ -194,10 +194,10 @@ class QSGFramebufferObjectNode : public QSGTextureProvider, public QSGSimpleText
public:
QSGFramebufferObjectNode()
- : window(0)
- , fbo(0)
- , msDisplayFbo(0)
- , renderer(0)
+ : window(nullptr)
+ , fbo(nullptr)
+ , msDisplayFbo(nullptr)
+ , renderer(nullptr)
, renderPending(true)
, invalidatePending(false)
, devicePixelRatio(1)
@@ -282,13 +282,13 @@ QSGNode *QQuickFramebufferObject::updatePaintNode(QSGNode *node, UpdatePaintNode
// that easily so with this logic, the renderer only goes away when
// the scenegraph is invalidated or it is removed from the scene.
if (!n && (width() <= 0 || height() <= 0))
- return 0;
+ return nullptr;
Q_D(QQuickFramebufferObject);
if (!n) {
if (!isOpenGL(d->sceneGraphRenderContext()))
- return 0;
+ return nullptr;
if (!d->node)
d->node = new QSGFramebufferObjectNode;
n = d->node;
@@ -313,10 +313,11 @@ QSGNode *QQuickFramebufferObject::updatePaintNode(QSGNode *node, UpdatePaintNode
desiredFboSize *= n->devicePixelRatio;
if (n->fbo && ((d->followsItemSize && n->fbo->size() != desiredFboSize) || n->invalidatePending)) {
+ delete n->texture();
delete n->fbo;
- n->fbo = 0;
+ n->fbo = nullptr;
delete n->msDisplayFbo;
- n->msDisplayFbo = 0;
+ n->msDisplayFbo = nullptr;
n->invalidatePending = false;
}
@@ -367,10 +368,10 @@ QSGTextureProvider *QQuickFramebufferObject::textureProvider() const
QQuickWindow *w = window();
if (!w || !w->openglContext() || QThread::currentThread() != w->openglContext()->thread()) {
qWarning("QQuickFramebufferObject::textureProvider: can only be queried on the rendering thread of an exposed window");
- return 0;
+ return nullptr;
}
if (!isOpenGL(d->sceneGraphRenderContext()))
- return 0;
+ return nullptr;
if (!d->node)
d->node = new QSGFramebufferObjectNode;
return d->node;
@@ -385,13 +386,13 @@ void QQuickFramebufferObject::releaseResources()
// forget about the node. Since it is the node we returned from updatePaintNode
// it will be managed by the scene graph.
Q_D(QQuickFramebufferObject);
- d->node = 0;
+ d->node = nullptr;
}
void QQuickFramebufferObject::invalidateSceneGraph()
{
Q_D(QQuickFramebufferObject);
- d->node = 0;
+ d->node = nullptr;
}
/*!
@@ -410,7 +411,7 @@ void QQuickFramebufferObject::invalidateSceneGraph()
* GUI thread is blocked.
*/
QQuickFramebufferObject::Renderer::Renderer()
- : data(0)
+ : data(nullptr)
{
}
@@ -438,7 +439,7 @@ QQuickFramebufferObject::Renderer::~Renderer()
*/
QOpenGLFramebufferObject *QQuickFramebufferObject::Renderer::framebufferObject() const
{
- return data ? ((QSGFramebufferObjectNode *) data)->fbo : 0;
+ return data ? ((QSGFramebufferObjectNode *) data)->fbo : nullptr;
}
/*!
diff --git a/src/quick/items/qquickgenericshadereffect.cpp b/src/quick/items/qquickgenericshadereffect.cpp
index 305ef7e778..248c2b6ec3 100644
--- a/src/quick/items/qquickgenericshadereffect.cpp
+++ b/src/quick/items/qquickgenericshadereffect.cpp
@@ -61,7 +61,7 @@ QQuickGenericShaderEffect::QQuickGenericShaderEffect(QQuickShaderEffect *item, Q
, m_mgr(nullptr)
, m_fragNeedsUpdate(true)
, m_vertNeedsUpdate(true)
- , m_dirty(0)
+ , m_dirty(nullptr)
{
qRegisterMetaType<QSGGuiThreadShaderEffectManager::ShaderInfo::Type>("ShaderInfo::Type");
for (int i = 0; i < NShader; ++i)
@@ -134,7 +134,7 @@ void QQuickGenericShaderEffect::setMesh(const QVariant &mesh)
return;
if (m_mesh)
- disconnect(m_mesh, SIGNAL(geometryChanged()), this, 0);
+ disconnect(m_mesh, SIGNAL(geometryChanged()), this, nullptr);
m_mesh = newMesh;
@@ -290,7 +290,7 @@ QSGNode *QQuickGenericShaderEffect::handleUpdatePaintNode(QSGNode *oldNode, QQui
m_dirty &= ~QSGShaderEffectNode::DirtyShaderGeometry;
}
- m_dirty = 0;
+ m_dirty = nullptr;
for (int i = 0; i < NShader; ++i) {
m_dirtyConstants[i].clear();
m_dirtyTextures[i].clear();
diff --git a/src/quick/items/qquickgenericshadereffect_p.h b/src/quick/items/qquickgenericshadereffect_p.h
index ab19816493..3f6f92921b 100644
--- a/src/quick/items/qquickgenericshadereffect_p.h
+++ b/src/quick/items/qquickgenericshadereffect_p.h
@@ -66,7 +66,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickGenericShaderEffect : public QObject
Q_OBJECT
public:
- QQuickGenericShaderEffect(QQuickShaderEffect *item, QObject *parent = 0);
+ QQuickGenericShaderEffect(QQuickShaderEffect *item, QObject *parent = nullptr);
~QQuickGenericShaderEffect();
QByteArray fragmentShader() const { return m_fragShader; }
diff --git a/src/quick/items/qquickgraphicsinfo.cpp b/src/quick/items/qquickgraphicsinfo.cpp
index a36133874b..e809bdd827 100644
--- a/src/quick/items/qquickgraphicsinfo.cpp
+++ b/src/quick/items/qquickgraphicsinfo.cpp
@@ -63,7 +63,7 @@ QT_BEGIN_NAMESPACE
QQuickGraphicsInfo::QQuickGraphicsInfo(QQuickItem *item)
: QObject(item)
- , m_window(0)
+ , m_window(nullptr)
, m_api(Unknown)
, m_shaderType(UnknownShadingLanguage)
, m_shaderCompilationType(ShaderCompilationType(0))
diff --git a/src/quick/items/qquickgridview.cpp b/src/quick/items/qquickgridview.cpp
index 10262e8cc0..1f5cda9d18 100644
--- a/src/quick/items/qquickgridview.cpp
+++ b/src/quick/items/qquickgridview.cpp
@@ -230,7 +230,7 @@ public:
: flow(QQuickGridView::FlowLeftToRight)
, cellWidth(100), cellHeight(100), columns(1)
, snapMode(QQuickGridView::NoSnap)
- , highlightXAnimator(0), highlightYAnimator(0)
+ , highlightXAnimator(nullptr), highlightYAnimator(nullptr)
{}
~QQuickGridViewPrivate()
{
@@ -390,7 +390,7 @@ FxViewItem *QQuickGridViewPrivate::snapItemAt(qreal pos) const
if (itemTop+rowSize()/2 >= pos && itemTop - rowSize()/2 <= pos)
return item;
}
- return 0;
+ return nullptr;
}
int QQuickGridViewPrivate::snapIndex() const
@@ -508,12 +508,14 @@ bool QQuickGridViewPrivate::addVisibleItems(qreal fillFrom, qreal fillTo, qreal
}
int colNum = qFloor((colPos+colSize()/2) / colSize());
- FxGridItemSG *item = 0;
+ FxGridItemSG *item = nullptr;
bool changed = false;
+ QQmlIncubator::IncubationMode incubationMode = doBuffer ? QQmlIncubator::Asynchronous : QQmlIncubator::AsynchronousIfNested;
+
while (modelIndex < model->count() && rowPos <= fillTo + rowSize()*(columns - colNum)/(columns+1)) {
qCDebug(lcItemViewDelegateLifecycle) << "refill: append item" << modelIndex << colPos << rowPos;
- if (!(item = static_cast<FxGridItemSG*>(createItem(modelIndex, doBuffer))))
+ if (!(item = static_cast<FxGridItemSG*>(createItem(modelIndex, incubationMode))))
break;
if (!transitioner || !transitioner->canTransition(QQuickItemViewTransitioner::PopulateTransition, true)) // pos will be set by layoutVisibleItems()
item->setPosition(colPos, rowPos, true);
@@ -535,20 +537,19 @@ bool QQuickGridViewPrivate::addVisibleItems(qreal fillFrom, qreal fillTo, qreal
if (visibleItems.count()) {
FxGridItemSG *firstItem = static_cast<FxGridItemSG*>(visibleItems.constFirst());
rowPos = firstItem->rowPos();
- colNum = qFloor((firstItem->colPos()+colSize()/2) / colSize());
- if (--colNum < 0) {
- colNum = columns - 1;
- rowPos -= rowSize();
- }
- } else {
- colNum = qFloor((colPos+colSize()/2) / colSize());
+ colPos = firstItem->colPos();
+ }
+ colNum = qFloor((colPos+colSize()/2) / colSize());
+ if (--colNum < 0) {
+ colNum = columns - 1;
+ rowPos -= rowSize();
}
// Prepend
colPos = colNum * colSize();
while (visibleIndex > 0 && rowPos + rowSize() - 1 >= fillFrom - rowSize()*(colNum+1)/(columns+1)){
qCDebug(lcItemViewDelegateLifecycle) << "refill: prepend item" << visibleIndex-1 << "top pos" << rowPos << colPos;
- if (!(item = static_cast<FxGridItemSG*>(createItem(visibleIndex-1, doBuffer))))
+ if (!(item = static_cast<FxGridItemSG*>(createItem(visibleIndex-1, incubationMode))))
break;
--visibleIndex;
if (!transitioner || !transitioner->canTransition(QQuickItemViewTransitioner::PopulateTransition, true)) // pos will be set by layoutVisibleItems()
@@ -579,7 +580,7 @@ void QQuickGridViewPrivate::removeItem(FxViewItem *item)
bool QQuickGridViewPrivate::removeNonVisibleItems(qreal bufferFrom, qreal bufferTo)
{
- FxGridItemSG *item = 0;
+ FxGridItemSG *item = nullptr;
bool changed = false;
while (visibleItems.count() > 1
@@ -699,14 +700,14 @@ void QQuickGridViewPrivate::createHighlight()
bool changed = false;
if (highlight) {
if (trackedItem == highlight)
- trackedItem = 0;
+ trackedItem = nullptr;
delete highlight;
- highlight = 0;
+ highlight = nullptr;
delete highlightXAnimator;
delete highlightYAnimator;
- highlightXAnimator = 0;
- highlightYAnimator = 0;
+ highlightXAnimator = nullptr;
+ highlightYAnimator = nullptr;
changed = true;
}
@@ -892,7 +893,6 @@ void QQuickGridViewPrivate::initializeCurrentItem()
void QQuickGridViewPrivate::fixupPosition()
{
- moveReason = Other;
if (flow == QQuickGridView::FlowLeftToRight)
fixupY();
else
@@ -2410,11 +2410,11 @@ bool QQuickGridViewPrivate::applyInsertionChange(const QQmlChangeSet::Change &ch
} else {
while (i >= 0) {
// item is before first visible e.g. in cache buffer
- FxViewItem *item = 0;
+ FxViewItem *item = nullptr;
if (change.isMove() && (item = currentChanges.removedItems.take(change.moveKey(modelIndex + i))))
item->index = modelIndex + i;
if (!item)
- item = createItem(modelIndex + i);
+ item = createItem(modelIndex + i, QQmlIncubator::Synchronous);
if (!item)
return false;
@@ -2462,12 +2462,12 @@ bool QQuickGridViewPrivate::applyInsertionChange(const QQmlChangeSet::Change &ch
int i = 0;
int to = buffer+displayMarginEnd+tempPos+size()-1;
while (i < count && rowPos <= to + rowSize()*(columns - colNum)/qreal(columns+1)) {
- FxViewItem *item = 0;
+ FxViewItem *item = nullptr;
if (change.isMove() && (item = currentChanges.removedItems.take(change.moveKey(modelIndex + i))))
item->index = modelIndex + i;
bool newItem = !item;
if (!item)
- item = createItem(modelIndex + i);
+ item = createItem(modelIndex + i, QQmlIncubator::Synchronous);
if (!item)
return false;
diff --git a/src/quick/items/qquickgridview_p.h b/src/quick/items/qquickgridview_p.h
index 5c6da2b433..7daeaf41a1 100644
--- a/src/quick/items/qquickgridview_p.h
+++ b/src/quick/items/qquickgridview_p.h
@@ -81,7 +81,7 @@ public:
};
Q_ENUM(Flow)
- QQuickGridView(QQuickItem *parent=0);
+ QQuickGridView(QQuickItem *parent=nullptr);
~QQuickGridView();
void setHighlightFollowsCurrentItem(bool) override;
diff --git a/src/quick/items/qquickimage.cpp b/src/quick/items/qquickimage.cpp
index 7e13e5e0e1..dc2cd17b4e 100644
--- a/src/quick/items/qquickimage.cpp
+++ b/src/quick/items/qquickimage.cpp
@@ -57,7 +57,7 @@ class QQuickImageTextureProvider : public QSGTextureProvider
Q_OBJECT
public:
QQuickImageTextureProvider()
- : m_texture(0)
+ : m_texture(nullptr)
, m_smooth(false)
{
}
@@ -97,7 +97,7 @@ QQuickImagePrivate::QQuickImagePrivate()
, mipmap(false)
, hAlign(QQuickImage::AlignHCenter)
, vAlign(QQuickImage::AlignVCenter)
- , provider(0)
+ , provider(nullptr)
{
}
@@ -583,7 +583,7 @@ QSGTextureProvider *QQuickImage::textureProvider() const
if (!d->window || !d->sceneGraphRenderContext() || QThread::currentThread() != d->sceneGraphRenderContext()->thread()) {
qWarning("QQuickImage::textureProvider: can only be queried on the rendering thread of an exposed window");
- return 0;
+ return nullptr;
}
if (!d->provider) {
@@ -601,7 +601,7 @@ void QQuickImage::invalidateSceneGraph()
{
Q_D(QQuickImage);
delete d->provider;
- d->provider = 0;
+ d->provider = nullptr;
}
void QQuickImage::releaseResources()
@@ -609,7 +609,7 @@ void QQuickImage::releaseResources()
Q_D(QQuickImage);
if (d->provider) {
QQuickWindowQObjectCleanupJob::schedule(window(), d->provider);
- d->provider = 0;
+ d->provider = nullptr;
}
}
@@ -628,7 +628,7 @@ QSGNode *QQuickImage::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *)
if (!texture || width() <= 0 || height() <= 0) {
delete oldNode;
- return 0;
+ return nullptr;
}
QSGInternalImageNode *node = static_cast<QSGInternalImageNode *>(oldNode);
@@ -736,7 +736,7 @@ QSGNode *QQuickImage::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *)
|| nsrect.isEmpty()
|| !qt_is_finite(nsrect.width()) || !qt_is_finite(nsrect.height())) {
delete node;
- return 0;
+ return nullptr;
}
if (d->pixmapChanged) {
diff --git a/src/quick/items/qquickimage_p.h b/src/quick/items/qquickimage_p.h
index 09b2c1eeb7..7fb4413900 100644
--- a/src/quick/items/qquickimage_p.h
+++ b/src/quick/items/qquickimage_p.h
@@ -70,7 +70,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickImage : public QQuickImageBase
Q_PROPERTY(bool autoTransform READ autoTransform WRITE setAutoTransform NOTIFY autoTransformChanged REVISION 2)
public:
- QQuickImage(QQuickItem *parent=0);
+ QQuickImage(QQuickItem *parent=nullptr);
~QQuickImage();
enum HAlignment { AlignLeft = Qt::AlignLeft,
diff --git a/src/quick/items/qquickimagebase_p.h b/src/quick/items/qquickimagebase_p.h
index 4d4a6fceaf..eb04a1d162 100644
--- a/src/quick/items/qquickimagebase_p.h
+++ b/src/quick/items/qquickimagebase_p.h
@@ -70,7 +70,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickImageBase : public QQuickImplicitSizeItem
Q_PROPERTY(bool mirror READ mirror WRITE setMirror NOTIFY mirrorChanged)
public:
- QQuickImageBase(QQuickItem *parent=0);
+ QQuickImageBase(QQuickItem *parent=nullptr);
~QQuickImageBase();
enum Status { Null, Ready, Loading, Error };
Q_ENUM(Status)
diff --git a/src/quick/items/qquickitem.cpp b/src/quick/items/qquickitem.cpp
index f8374bdbc2..3a0aea517c 100644
--- a/src/quick/items/qquickitem.cpp
+++ b/src/quick/items/qquickitem.cpp
@@ -87,8 +87,9 @@ QT_BEGIN_NAMESPACE
Q_DECLARE_LOGGING_CATEGORY(DBG_MOUSE_TARGET)
Q_DECLARE_LOGGING_CATEGORY(DBG_HOVER_TRACE)
+Q_DECLARE_LOGGING_CATEGORY(lcTransient)
-void debugFocusTree(QQuickItem *item, QQuickItem *scope = 0, int depth = 1)
+void debugFocusTree(QQuickItem *item, QQuickItem *scope = nullptr, int depth = 1)
{
if (DBG_FOCUS().isEnabled(QtDebugMsg)) {
qCDebug(DBG_FOCUS)
@@ -302,9 +303,9 @@ void QQuickContents::itemChildAdded(QQuickItem *, QQuickItem *item)
}
QQuickItemKeyFilter::QQuickItemKeyFilter(QQuickItem *item)
-: m_processPost(false), m_next(0)
+: m_processPost(false), m_next(nullptr)
{
- QQuickItemPrivate *p = item?QQuickItemPrivate::get(item):0;
+ QQuickItemPrivate *p = item?QQuickItemPrivate::get(item):nullptr;
if (p) {
m_next = p->extra.value().keyHandler;
p->extra->keyHandler = this;
@@ -785,7 +786,7 @@ const SigMap sigMap[] = {
{ Qt::Key_Menu, "menuPressed" },
{ Qt::Key_VolumeUp, "volumeUpPressed" },
{ Qt::Key_VolumeDown, "volumeDownPressed" },
- { 0, 0 }
+ { 0, nullptr }
};
QByteArray QQuickKeysAttached::keyToSignal(int key)
@@ -970,7 +971,7 @@ bool QQuickKeysAttached::isConnected(const char *signalName) const
Keys.onEscapePressed: {
console.log("escapeItem is handling escape");
- event.accepted = true;
+ // event.accepted is set to true by default for the specific key handlers
}
}
@@ -1543,6 +1544,13 @@ QQuickKeysAttached *QQuickKeysAttached::qmlAttachedProperties(QObject *obj)
mirroring is not the desired behavior, or if the child item already implements mirroring in
some custom way.
+ To set the layout direction based on the \l {Default Layout Direction}{default layout direction}
+ of the application, use the following code:
+
+ \code
+ LayoutMirroring.enabled: Qt.application.layoutDirection === Qt.RightToLeft
+ \endcode
+
See \l {Right-to-left User Interfaces} for further details on using \c LayoutMirroring and
other related features to implement right-to-left support for an application.
*/
@@ -1569,7 +1577,7 @@ QQuickKeysAttached *QQuickKeysAttached::qmlAttachedProperties(QObject *obj)
*/
-QQuickLayoutMirroringAttached::QQuickLayoutMirroringAttached(QObject *parent) : QObject(parent), itemPrivate(0)
+QQuickLayoutMirroringAttached::QQuickLayoutMirroringAttached(QObject *parent) : QObject(parent), itemPrivate(nullptr)
{
if (QQuickItem *item = qobject_cast<QQuickItem *>(parent))
itemPrivate = QQuickItemPrivate::get(item);
@@ -1723,7 +1731,7 @@ void QQuickItemPrivate::setLayoutMirror(bool mirror)
*/
QQuickEnterKeyAttached::QQuickEnterKeyAttached(QObject *parent)
- : QObject(parent), itemPrivate(0), keyType(Qt::EnterKeyDefault)
+ : QObject(parent), itemPrivate(nullptr), keyType(Qt::EnterKeyDefault)
{
if (QQuickItem *item = qobject_cast<QQuickItem*>(parent)) {
itemPrivate = QQuickItemPrivate::get(item);
@@ -1776,7 +1784,7 @@ void QQuickItemPrivate::updateSubFocusItem(QQuickItem *scope, bool focus)
if (oldSubFocusItem) {
QQuickItem *sfi = scopePrivate->subFocusItem->parentItem();
while (sfi && sfi != scope) {
- QQuickItemPrivate::get(sfi)->subFocusItem = 0;
+ QQuickItemPrivate::get(sfi)->subFocusItem = nullptr;
sfi = sfi->parentItem();
}
}
@@ -1789,7 +1797,7 @@ void QQuickItemPrivate::updateSubFocusItem(QQuickItem *scope, bool focus)
sfi = sfi->parentItem();
}
} else {
- scopePrivate->subFocusItem = 0;
+ scopePrivate->subFocusItem = nullptr;
}
}
@@ -2067,7 +2075,7 @@ void QQuickItemPrivate::updateSubFocusItem(QQuickItem *scope, bool focus)
In the QPainter / QWidget world, it is some times favorable to
cache complex content in a pixmap, image or texture. In Qt Quick,
because of the techniques already applied by the \l {Qt Quick
- Scene Graph Renderer} {scene graph renderer}, this will in most
+ Scene Graph OpenGL Renderer} {scene graph renderer}, this will in most
cases not be the case. Excessive draw calls are already reduced
because of batching and a cache will in most cases end up blending
more pixels than the original content. The overhead of rendering
@@ -2374,13 +2382,13 @@ QQuickItem::~QQuickItem()
if (d->windowRefCount > 1)
d->windowRefCount = 1; // Make sure window is set to null in next call to derefWindow().
if (d->parentItem)
- setParentItem(0);
+ setParentItem(nullptr);
else if (d->window)
d->derefWindow();
// XXX todo - optimize
while (!d->childItems.isEmpty())
- d->childItems.constFirst()->setParentItem(0);
+ d->childItems.constFirst()->setParentItem(nullptr);
if (!d->changeListeners.isEmpty()) {
const auto listeners = d->changeListeners; // NOTE: intentional copy (QTBUG-54732)
@@ -2420,14 +2428,14 @@ QQuickItem::~QQuickItem()
}
if (d->extra.isAllocated()) {
- delete d->extra->contents; d->extra->contents = 0;
+ delete d->extra->contents; d->extra->contents = nullptr;
#if QT_CONFIG(quick_shadereffect)
- delete d->extra->layer; d->extra->layer = 0;
+ delete d->extra->layer; d->extra->layer = nullptr;
#endif
}
- delete d->_anchors; d->_anchors = 0;
- delete d->_stateGroup; d->_stateGroup = 0;
+ delete d->_anchors; d->_anchors = nullptr;
+ delete d->_stateGroup; d->_stateGroup = nullptr;
}
/*!
@@ -2542,7 +2550,7 @@ QQuickItem* QQuickItemPrivate::nextPrevItemInTabFocusChain(QQuickItem *item, boo
bool all = QGuiApplication::styleHints()->tabFocusBehavior() == Qt::TabFocusAllControls;
- QQuickItem *from = 0;
+ QQuickItem *from = nullptr;
bool isTabFence = item->d_func()->isTabFence;
if (forward) {
if (!isTabFence)
@@ -2677,7 +2685,7 @@ void QQuickItem::setParentItem(QQuickItem *parentItem)
if (parentItem) {
QQuickItem *itemAncestor = parentItem;
- while (itemAncestor != 0) {
+ while (itemAncestor != nullptr) {
if (Q_UNLIKELY(itemAncestor == this)) {
qWarning() << "QQuickItem::setParentItem: Parent" << parentItem << "is already part of the subtree of" << this;
return;
@@ -2689,12 +2697,12 @@ void QQuickItem::setParentItem(QQuickItem *parentItem)
d->removeFromDirtyList();
QQuickItem *oldParentItem = d->parentItem;
- QQuickItem *scopeFocusedItem = 0;
+ QQuickItem *scopeFocusedItem = nullptr;
if (oldParentItem) {
QQuickItemPrivate *op = QQuickItemPrivate::get(oldParentItem);
- QQuickItem *scopeItem = 0;
+ QQuickItem *scopeItem = nullptr;
if (hasFocus() || op->subFocusItem == this)
scopeFocusedItem = this;
@@ -2724,7 +2732,7 @@ void QQuickItem::setParentItem(QQuickItem *parentItem)
QQuickWindowPrivate::get(d->window)->parentlessItems.remove(this);
}
- QQuickWindow *parentWindow = parentItem ? QQuickItemPrivate::get(parentItem)->window : 0;
+ QQuickWindow *parentWindow = parentItem ? QQuickItemPrivate::get(parentItem)->window : nullptr;
if (d->window == parentWindow) {
// Avoid freeing and reallocating resources if the window stays the same.
d->parentItem = parentItem;
@@ -2744,7 +2752,7 @@ void QQuickItem::setParentItem(QQuickItem *parentItem)
QQuickWindowPrivate::get(d->window)->parentlessItems.insert(this);
d->setEffectiveVisibleRecur(d->calcEffectiveVisible());
- d->setEffectiveEnableRecur(0, d->calcEffectiveEnable());
+ d->setEffectiveEnableRecur(nullptr, d->calcEffectiveEnable());
if (d->parentItem) {
if (!scopeFocusedItem) {
@@ -2808,7 +2816,8 @@ void QQuickItem::stackBefore(const QQuickItem *sibling)
{
Q_D(QQuickItem);
if (!sibling || sibling == this || !d->parentItem || d->parentItem != QQuickItemPrivate::get(sibling)->parentItem) {
- qWarning("QQuickItem::stackBefore: Cannot stack before %p, which must be a sibling", sibling);
+ qWarning().nospace() << "QQuickItem::stackBefore: Cannot stack "
+ << this << " before " << sibling << ", which must be a sibling";
return;
}
@@ -2852,7 +2861,8 @@ void QQuickItem::stackAfter(const QQuickItem *sibling)
{
Q_D(QQuickItem);
if (!sibling || sibling == this || !d->parentItem || d->parentItem != QQuickItemPrivate::get(sibling)->parentItem) {
- qWarning("QQuickItem::stackAfter: Cannot stack after %p, which must be a sibling", sibling);
+ qWarning().nospace() << "QQuickItem::stackAfter: Cannot stack "
+ << this << " after " << sibling << ", which must be a sibling";
return;
}
@@ -2942,6 +2952,7 @@ void QQuickItemPrivate::addChild(QQuickItem *child)
if (childPrivate->subtreeHoverEnabled && !subtreeHoverEnabled)
setHasHoverInChild(true);
+ childPrivate->recursiveRefFromEffectItem(extra.value().recursiveEffectRefCount);
markSortedChildrenDirty(child);
dirty(QQuickItemPrivate::ChildrenChanged);
@@ -2970,6 +2981,7 @@ void QQuickItemPrivate::removeChild(QQuickItem *child)
if (childPrivate->subtreeHoverEnabled && subtreeHoverEnabled)
setHasHoverInChild(false);
+ childPrivate->recursiveRefFromEffectItem(-extra.value().recursiveEffectRefCount);
markSortedChildrenDirty(child);
dirty(QQuickItemPrivate::ChildrenChanged);
@@ -2990,7 +3002,7 @@ void QQuickItemPrivate::refWindow(QQuickWindow *c)
// derefWindow() decrements the reference count.
Q_Q(QQuickItem);
- Q_ASSERT((window != 0) == (windowRefCount > 0));
+ Q_ASSERT((window != nullptr) == (windowRefCount > 0));
Q_ASSERT(c);
if (++windowRefCount > 1) {
if (c != window)
@@ -2998,7 +3010,7 @@ void QQuickItemPrivate::refWindow(QQuickWindow *c)
return; // Window already set.
}
- Q_ASSERT(window == 0);
+ Q_ASSERT(window == nullptr);
window = c;
if (polishScheduled)
@@ -3022,7 +3034,7 @@ void QQuickItemPrivate::refWindow(QQuickWindow *c)
void QQuickItemPrivate::derefWindow()
{
Q_Q(QQuickItem);
- Q_ASSERT((window != 0) == (windowRefCount > 0));
+ Q_ASSERT((window != nullptr) == (windowRefCount > 0));
if (!window)
return; // This can happen when destroying recursive shader effect sources.
@@ -3038,7 +3050,7 @@ void QQuickItemPrivate::derefWindow()
c->removeGrabber(q);
#if QT_CONFIG(cursor)
if (c->cursorItem == q) {
- c->cursorItem = 0;
+ c->cursorItem = nullptr;
window->unsetCursor();
}
#endif
@@ -3048,17 +3060,17 @@ void QQuickItemPrivate::derefWindow()
if (!parentItem)
c->parentlessItems.remove(q);
- window = 0;
+ window = nullptr;
- itemNodeInstance = 0;
+ itemNodeInstance = nullptr;
if (extra.isAllocated()) {
- extra->opacityNode = 0;
- extra->clipNode = 0;
- extra->rootNode = 0;
+ extra->opacityNode = nullptr;
+ extra->clipNode = nullptr;
+ extra->rootNode = nullptr;
}
- paintNode = 0;
+ paintNode = nullptr;
for (int ii = 0; ii < childItems.count(); ++ii) {
QQuickItem *child = childItems.at(ii);
@@ -3068,8 +3080,8 @@ void QQuickItemPrivate::derefWindow()
dirty(Window);
if (extra.isAllocated() && extra->screenAttached)
- extra->screenAttached->windowChanged(0);
- itemChange(QQuickItem::ItemSceneChange, (QQuickWindow *)0);
+ extra->screenAttached->windowChanged(nullptr);
+ itemChange(QQuickItem::ItemSceneChange, (QQuickWindow *)nullptr);
}
@@ -3155,8 +3167,8 @@ bool QQuickItem::isComponentComplete() const
}
QQuickItemPrivate::QQuickItemPrivate()
- : _anchors(0)
- , _stateGroup(0)
+ : _anchors(nullptr)
+ , _stateGroup(nullptr)
, flags(0)
, widthValid(false)
, heightValid(false)
@@ -3197,13 +3209,13 @@ QQuickItemPrivate::QQuickItemPrivate()
, touchEnabled(false)
#endif
, dirtyAttributes(0)
- , nextDirtyItem(0)
- , prevDirtyItem(0)
- , window(0)
+ , nextDirtyItem(nullptr)
+ , prevDirtyItem(nullptr)
+ , window(nullptr)
, windowRefCount(0)
- , parentItem(0)
+ , parentItem(nullptr)
, sortedChildItems(&childItems)
- , subFocusItem(0)
+ , subFocusItem(nullptr)
, x(0)
, y(0)
, width(0)
@@ -3211,8 +3223,8 @@ QQuickItemPrivate::QQuickItemPrivate()
, implicitWidth(0)
, implicitHeight(0)
, baselineOffset(0)
- , itemNodeInstance(0)
- , paintNode(0)
+ , itemNodeInstance(nullptr)
+ , paintNode(nullptr)
{
}
@@ -3253,7 +3265,7 @@ void QQuickItemPrivate::data_append(QQmlListProperty<QObject> *prop, QObject *o)
// because there can be multiple handlers...
that->setAcceptedMouseButtons(Qt::AllButtons);
QQuickItemPrivate *p = QQuickItemPrivate::get(that);
- p->extra.value().pointerHandlers.append(pointerHandler);
+ p->extra.value().pointerHandlers.prepend(pointerHandler);
} else {
QQuickWindow *thisWindow = qmlobject_cast<QQuickWindow *>(o);
QQuickItem *item = that;
@@ -3264,11 +3276,13 @@ void QQuickItemPrivate::data_append(QQmlListProperty<QObject> *prop, QObject *o)
}
if (thisWindow) {
- if (itemWindow)
+ if (itemWindow) {
+ qCDebug(lcTransient) << thisWindow << "is transient for" << itemWindow;
thisWindow->setTransientParent(itemWindow);
- else
+ } else {
QObject::connect(item, SIGNAL(windowChanged(QQuickWindow*)),
thisWindow, SLOT(setTransientParent_helper(QQuickWindow*)));
+ }
}
o->setParent(that);
}
@@ -3335,7 +3349,7 @@ QObject *QQuickItemPrivate::data_at(QQmlListProperty<QObject> *property, int i)
const int j = i - resourcesCount;
if (j < children_count(&childrenProperty))
return children_at(&childrenProperty, j);
- return 0;
+ return nullptr;
}
void QQuickItemPrivate::data_clear(QQmlListProperty<QObject> *property)
@@ -3389,7 +3403,7 @@ QQuickItem *QQuickItemPrivate::children_at(QQmlListProperty<QQuickItem> *prop, i
{
QQuickItemPrivate *p = QQuickItemPrivate::get(static_cast<QQuickItem *>(prop->object));
if (index >= p->childItems.count() || index < 0)
- return 0;
+ return nullptr;
else
return p->childItems.at(index);
}
@@ -3401,7 +3415,7 @@ void QQuickItemPrivate::children_append(QQmlListProperty<QQuickItem> *prop, QQui
QQuickItem *that = static_cast<QQuickItem *>(prop->object);
if (o->parentItem() == that)
- o->setParentItem(0);
+ o->setParentItem(nullptr);
o->setParentItem(that);
}
@@ -3417,7 +3431,7 @@ void QQuickItemPrivate::children_clear(QQmlListProperty<QQuickItem> *prop)
QQuickItem *that = static_cast<QQuickItem *>(prop->object);
QQuickItemPrivate *p = QQuickItemPrivate::get(that);
while (!p->childItems.isEmpty())
- p->childItems.at(0)->setParentItem(0);
+ p->childItems.at(0)->setParentItem(nullptr);
}
int QQuickItemPrivate::visibleChildren_count(QQmlListProperty<QQuickItem> *prop)
@@ -3437,14 +3451,14 @@ QQuickItem *QQuickItemPrivate::visibleChildren_at(QQmlListProperty<QQuickItem> *
QQuickItemPrivate *p = QQuickItemPrivate::get(static_cast<QQuickItem *>(prop->object));
const int childCount = p->childItems.count();
if (index >= childCount || index < 0)
- return 0;
+ return nullptr;
int visibleCount = -1;
for (int i = 0; i < childCount; i++) {
if (p->childItems.at(i)->isVisible()) visibleCount++;
if (visibleCount == index) return p->childItems.at(i);
}
- return 0;
+ return nullptr;
}
int QQuickItemPrivate::transform_count(QQmlListProperty<QQuickTransform> *prop)
@@ -3508,7 +3522,7 @@ QQuickTransform *QQuickItemPrivate::transform_at(QQmlListProperty<QQuickTransfor
QQuickItemPrivate *p = QQuickItemPrivate::get(that);
if (idx < 0 || idx >= p->transforms.count())
- return 0;
+ return nullptr;
else
return p->transforms.at(idx);
}
@@ -3655,7 +3669,7 @@ void QQuickItemPrivate::siblingOrderChanged()
QQmlListProperty<QObject> QQuickItemPrivate::data()
{
- return QQmlListProperty<QObject>(q_func(), 0, QQuickItemPrivate::data_append,
+ return QQmlListProperty<QObject>(q_func(), nullptr, QQuickItemPrivate::data_append,
QQuickItemPrivate::data_count,
QQuickItemPrivate::data_at,
QQuickItemPrivate::data_clear);
@@ -3667,8 +3681,9 @@ QQmlListProperty<QObject> QQuickItemPrivate::data()
\qmlproperty real QtQuick::Item::childrenRect.y
\qmlproperty real QtQuick::Item::childrenRect.width
\qmlproperty real QtQuick::Item::childrenRect.height
+ \readonly
- This property holds the collective position and size of the item's
+ This read-only property holds the collective position and size of the item's
children.
This property is useful if you need to access the collective geometry
@@ -3833,11 +3848,11 @@ QSGNode *QQuickItem::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *upda
{
Q_UNUSED(updatePaintNodeData)
delete oldNode;
- return 0;
+ return nullptr;
}
QQuickItem::UpdatePaintNodeData::UpdatePaintNodeData()
-: transformNode(0)
+: transformNode(nullptr)
{
}
@@ -3948,8 +3963,8 @@ void QQuickItem::inputMethodEvent(QInputMethodEvent *event)
/*!
This event handler can be reimplemented in a subclass to receive focus-in
- events for an item. The event information is provided by the
- \a event parameter.
+ events for an item. The event information is provided by the \c event
+ parameter.
*/
void QQuickItem::focusInEvent(QFocusEvent * /*event*/)
{
@@ -3965,8 +3980,8 @@ void QQuickItem::focusInEvent(QFocusEvent * /*event*/)
/*!
This event handler can be reimplemented in a subclass to receive focus-out
- events for an item. The event information is provided by the
- \a event parameter.
+ events for an item. The event information is provided by the \c event
+ parameter.
*/
void QQuickItem::focusOutEvent(QFocusEvent * /*event*/)
{
@@ -4402,7 +4417,7 @@ void QQuickItem::mapFromItem(QQmlV4Function *args) const
QV4::Scope scope(v4);
QV4::ScopedValue item(scope, (*args)[0]);
- QQuickItem *itemObj = 0;
+ QQuickItem *itemObj = nullptr;
if (!item->isNull()) {
QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, item->as<QV4::QObjectWrapper>());
if (qobjectWrapper)
@@ -4490,7 +4505,7 @@ void QQuickItem::mapToItem(QQmlV4Function *args) const
QV4::Scope scope(v4);
QV4::ScopedValue item(scope, (*args)[0]);
- QQuickItem *itemObj = 0;
+ QQuickItem *itemObj = nullptr;
if (!item->isNull()) {
QV4::Scoped<QV4::QObjectWrapper> qobjectWrapper(scope, item->as<QV4::QObjectWrapper>());
if (qobjectWrapper)
@@ -4723,12 +4738,12 @@ QQuickItem *QQuickItem::childAt(qreal x, qreal y) const
&& child->height() > point.y())
return child;
}
- return 0;
+ return nullptr;
}
QQmlListProperty<QObject> QQuickItemPrivate::resources()
{
- return QQmlListProperty<QObject>(q_func(), 0, QQuickItemPrivate::resources_append,
+ return QQmlListProperty<QObject>(q_func(), nullptr, QQuickItemPrivate::resources_append,
QQuickItemPrivate::resources_count,
QQuickItemPrivate::resources_at,
QQuickItemPrivate::resources_clear);
@@ -4753,7 +4768,7 @@ QQmlListProperty<QObject> QQuickItemPrivate::resources()
*/
QQmlListProperty<QQuickItem> QQuickItemPrivate::children()
{
- return QQmlListProperty<QQuickItem>(q_func(), 0, QQuickItemPrivate::children_append,
+ return QQmlListProperty<QQuickItem>(q_func(), nullptr, QQuickItemPrivate::children_append,
QQuickItemPrivate::children_count,
QQuickItemPrivate::children_at,
QQuickItemPrivate::children_clear);
@@ -4773,7 +4788,7 @@ QQmlListProperty<QQuickItem> QQuickItemPrivate::children()
QQmlListProperty<QQuickItem> QQuickItemPrivate::visibleChildren()
{
return QQmlListProperty<QQuickItem>(q_func(),
- 0,
+ nullptr,
QQuickItemPrivate::visibleChildren_count,
QQuickItemPrivate::visibleChildren_at);
@@ -4923,7 +4938,7 @@ void QQuickItem::setState(const QString &state)
*/
QQmlListProperty<QQuickTransform> QQuickItem::transform()
{
- return QQmlListProperty<QQuickTransform>(this, 0, QQuickItemPrivate::transform_append,
+ return QQmlListProperty<QQuickTransform>(this, nullptr, QQuickItemPrivate::transform_append,
QQuickItemPrivate::transform_count,
QQuickItemPrivate::transform_at,
QQuickItemPrivate::transform_clear);
@@ -5171,8 +5186,8 @@ void QQuickItem::updateInputMethod(Qt::InputMethodQueries queries)
}
#endif // im
-/*! \internal */
// XXX todo - do we want/need this anymore?
+/*! \internal */
QRectF QQuickItem::boundingRect() const
{
Q_D(const QQuickItem);
@@ -5806,19 +5821,24 @@ bool QQuickItem::isVisible() const
return d->effectiveVisible;
}
-void QQuickItem::setVisible(bool v)
+void QQuickItemPrivate::setVisible(bool visible)
{
- Q_D(QQuickItem);
- if (v == d->explicitVisible)
+ if (visible == explicitVisible)
return;
- d->explicitVisible = v;
- if (!v)
- d->dirty(QQuickItemPrivate::Visible);
+ explicitVisible = visible;
+ if (!visible)
+ dirty(QQuickItemPrivate::Visible);
- const bool childVisibilityChanged = d->setEffectiveVisibleRecur(d->calcEffectiveVisible());
- if (childVisibilityChanged && d->parentItem)
- emit d->parentItem->visibleChildrenChanged(); // signal the parent, not this!
+ const bool childVisibilityChanged = setEffectiveVisibleRecur(calcEffectiveVisible());
+ if (childVisibilityChanged && parentItem)
+ emit parentItem->visibleChildrenChanged(); // signal the parent, not this!
+}
+
+void QQuickItem::setVisible(bool v)
+{
+ Q_D(QQuickItem);
+ d->setVisible(v);
}
/*!
@@ -6052,8 +6072,8 @@ void QQuickItemPrivate::removeFromDirtyList()
if (prevDirtyItem) {
if (nextDirtyItem) QQuickItemPrivate::get(nextDirtyItem)->prevDirtyItem = prevDirtyItem;
*prevDirtyItem = nextDirtyItem;
- prevDirtyItem = 0;
- nextDirtyItem = 0;
+ prevDirtyItem = nullptr;
+ nextDirtyItem = nullptr;
}
Q_ASSERT(!prevDirtyItem);
Q_ASSERT(!nextDirtyItem);
@@ -6062,28 +6082,48 @@ void QQuickItemPrivate::removeFromDirtyList()
void QQuickItemPrivate::refFromEffectItem(bool hide)
{
++extra.value().effectRefCount;
- if (1 == extra->effectRefCount) {
+ if (extra->effectRefCount == 1) {
dirty(EffectReference);
- if (parentItem) QQuickItemPrivate::get(parentItem)->dirty(ChildrenStackingChanged);
+ if (parentItem)
+ QQuickItemPrivate::get(parentItem)->dirty(ChildrenStackingChanged);
}
if (hide) {
if (++extra->hideRefCount == 1)
dirty(HideReference);
}
+ recursiveRefFromEffectItem(1);
+}
+
+void QQuickItemPrivate::recursiveRefFromEffectItem(int refs)
+{
+ Q_Q(QQuickItem);
+ if (!refs)
+ return;
+ extra.value().recursiveEffectRefCount += refs;
+ for (int ii = 0; ii < childItems.count(); ++ii) {
+ QQuickItem *child = childItems.at(ii);
+ QQuickItemPrivate::get(child)->recursiveRefFromEffectItem(refs);
+ }
+ // Polish may rely on the effect ref count so trigger one, if item is not visible
+ // (if visible, it will be triggered automatically).
+ if (!effectiveVisible && refs > 0 && extra.value().recursiveEffectRefCount == 1) // it wasn't referenced, now it's referenced
+ q->polish();
}
void QQuickItemPrivate::derefFromEffectItem(bool unhide)
{
Q_ASSERT(extra->effectRefCount);
--extra->effectRefCount;
- if (0 == extra->effectRefCount) {
+ if (extra->effectRefCount == 0) {
dirty(EffectReference);
- if (parentItem) QQuickItemPrivate::get(parentItem)->dirty(ChildrenStackingChanged);
+ if (parentItem)
+ QQuickItemPrivate::get(parentItem)->dirty(ChildrenStackingChanged);
}
if (unhide) {
if (--extra->hideRefCount == 0)
dirty(HideReference);
}
+ recursiveRefFromEffectItem(-1);
}
void QQuickItemPrivate::setCulled(bool cull)
@@ -7102,7 +7142,7 @@ QQuickItem *QQuickItem::scopedFocusItem() const
{
Q_D(const QQuickItem);
if (!isFocusScope())
- return 0;
+ return nullptr;
else
return d->subFocusItem;
}
@@ -7409,10 +7449,18 @@ void QQuickItem::unsetCursor()
void QQuickItem::grabMouse()
{
Q_D(QQuickItem);
- if (!d->window)
+ if (!d->window || d->window->mouseGrabberItem() == this)
return;
QQuickWindowPrivate *windowPriv = QQuickWindowPrivate::get(d->window);
- windowPriv->setMouseGrabber(this);
+ bool fromTouch = windowPriv->isDeliveringTouchAsMouse();
+ auto point = fromTouch ?
+ windowPriv->pointerEventInstance(windowPriv->touchMouseDevice)->pointById(windowPriv->touchMouseId) :
+ windowPriv->pointerEventInstance(QQuickPointerDevice::genericMouseDevice())->point(0);
+ if (point) {
+ QQuickItem *oldGrabber = point->grabberItem();
+ point->setGrabberItem(this);
+ windowPriv->sendUngrabEvent(oldGrabber, fromTouch);
+ }
}
/*!
@@ -7430,7 +7478,7 @@ void QQuickItem::ungrabMouse()
if (!d->window)
return;
QQuickWindowPrivate *windowPriv = QQuickWindowPrivate::get(d->window);
- windowPriv->removeGrabber(this, true, false);
+ windowPriv->removeGrabber(this, true, windowPriv->isDeliveringTouchAsMouse());
}
@@ -7560,9 +7608,75 @@ void QQuickItem::setKeepTouchGrab(bool keep)
bool QQuickItem::contains(const QPointF &point) const
{
Q_D(const QQuickItem);
- qreal x = point.x();
- qreal y = point.y();
- return x >= 0 && y >= 0 && x <= d->width && y <= d->height;
+ if (d->mask) {
+ bool res = false;
+ d->extra->maskContains.invoke(d->mask,
+ Qt::DirectConnection,
+ Q_RETURN_ARG(bool, res),
+ Q_ARG(QPointF, point));
+ return res;
+ } else {
+ qreal x = point.x();
+ qreal y = point.y();
+ return x >= 0 && y >= 0 && x <= d->width && y <= d->height;
+ }
+}
+
+/*!
+ \qmlproperty QObject* QtQuick::Item::containmentMask
+ \since 5.11
+ This property holds an optional mask for the Item to be used in the
+ QtQuick::Item::contains method.
+ QtQuick::Item::contains main use is currently to determine whether
+ an input event has landed into the item or not.
+
+ By default the \l contains method will return true for any point
+ within the Item's bounding box. \c containmentMask allows for a
+ more fine-grained control. For example, the developer could
+ define and use an AnotherItem element as containmentMask,
+ which has a specialized contains method, like:
+
+ \code
+ Item { id: item; containmentMask: AnotherItem { id: anotherItem } }
+ \endcode
+
+ \e{item}'s contains method would then return true only if
+ \e{anotherItem}'s contains implementation returns true.
+*/
+QObject *QQuickItem::containmentMask() const
+{
+ Q_D(const QQuickItem);
+ return d->mask.data();
+}
+
+void QQuickItem::setContainmentMask(QObject *mask)
+{
+ Q_D(QQuickItem);
+ // an Item can't mask itself (to prevent infinite loop in contains())
+ if (d->mask.data() == mask || mask == static_cast<QObject *>(this))
+ return;
+
+ QQuickItem *quickMask = qobject_cast<QQuickItem *>(d->mask);
+ if (quickMask) {
+ QQuickItemPrivate *maskPrivate = QQuickItemPrivate::get(quickMask);
+ maskPrivate->registerAsContainmentMask(this, false); // removed from use as my mask
+ }
+
+ if (mask) {
+ int methodIndex = mask->metaObject()->indexOfMethod(QByteArrayLiteral("contains(QPointF)"));
+ if (methodIndex < 0) {
+ qmlWarning(this) << QStringLiteral("QQuickItem: Object set as mask does not have an invokable contains method, ignoring it.");
+ return;
+ }
+ d->extra.value().maskContains = mask->metaObject()->method(methodIndex);
+ }
+ d->mask = mask;
+ quickMask = qobject_cast<QQuickItem *>(mask);
+ if (quickMask) {
+ QQuickItemPrivate *maskPrivate = QQuickItemPrivate::get(quickMask);
+ maskPrivate->registerAsContainmentMask(this, true); // telling maskPrivate that "this" is using it as mask
+ }
+ emit containmentMaskChanged();
}
/*!
@@ -7949,7 +8063,7 @@ QSGTextureProvider *QQuickItem::textureProvider() const
#if QT_CONFIG(quick_shadereffect)
Q_D(const QQuickItem);
return d->extra.isAllocated() && d->extra->layer && d->extra->layer->effectSource() ?
- d->extra->layer->effectSource()->textureProvider() : 0;
+ d->extra->layer->effectSource()->textureProvider() : nullptr;
#else
return 0;
#endif
@@ -7988,9 +8102,9 @@ QQuickItemLayer::QQuickItemLayer(QQuickItem *item)
, m_wrapMode(QQuickShaderEffectSource::ClampToEdge)
, m_format(QQuickShaderEffectSource::RGBA)
, m_name("source")
- , m_effectComponent(0)
- , m_effect(0)
- , m_effectSource(0)
+ , m_effectComponent(nullptr)
+ , m_effect(nullptr)
+ , m_effectSource(nullptr)
, m_textureMirroring(QQuickShaderEffectSource::MirrorVertically)
, m_samples(0)
{
@@ -8091,7 +8205,7 @@ void QQuickItemLayer::deactivate()
deactivateEffect();
delete m_effectSource;
- m_effectSource = 0;
+ m_effectSource = nullptr;
QQuickItemPrivate *id = QQuickItemPrivate::get(m_item);
id->removeItemChangeListener(this, QQuickItemPrivate::Geometry | QQuickItemPrivate::Opacity | QQuickItemPrivate::Parent | QQuickItemPrivate::Visibility | QQuickItemPrivate::SiblingOrder);
@@ -8128,7 +8242,7 @@ void QQuickItemLayer::deactivateEffect()
Q_ASSERT(m_effectComponent);
delete m_effect;
- m_effect = 0;
+ m_effect = nullptr;
}
@@ -8436,7 +8550,7 @@ void QQuickItemLayer::itemParentChanged(QQuickItem *item, QQuickItem *parent)
Q_UNUSED(item)
Q_ASSERT(item == m_item);
Q_ASSERT(parent != m_effectSource);
- Q_ASSERT(parent == 0 || parent != m_effect);
+ Q_ASSERT(parent == nullptr || parent != m_effect);
m_effectSource->setParentItem(parent);
if (parent)
@@ -8508,15 +8622,16 @@ void QQuickItemLayer::updateMatrix()
QQuickItemPrivate::ExtraData::ExtraData()
: z(0), scale(1), rotation(0), opacity(1),
- contents(0), screenAttached(0), layoutDirectionAttached(0),
- enterKeyAttached(0),
- keyHandler(0),
+ contents(nullptr), screenAttached(nullptr), layoutDirectionAttached(nullptr),
+ enterKeyAttached(nullptr),
+ keyHandler(nullptr),
#if QT_CONFIG(quick_shadereffect)
- layer(0),
+ layer(nullptr),
#endif
effectRefCount(0), hideRefCount(0),
- opacityNode(0), clipNode(0), rootNode(0),
- acceptedMouseButtons(0), origin(QQuickItem::Center),
+ recursiveEffectRefCount(0),
+ opacityNode(nullptr), clipNode(nullptr), rootNode(nullptr),
+ acceptedMouseButtons(nullptr), origin(QQuickItem::Center),
transparentForPositioner(false)
{
}
diff --git a/src/quick/items/qquickitem.h b/src/quick/items/qquickitem.h
index f6ee54e94d..cfdb2ad5b7 100644
--- a/src/quick/items/qquickitem.h
+++ b/src/quick/items/qquickitem.h
@@ -60,7 +60,7 @@ class Q_QUICK_EXPORT QQuickTransform : public QObject
Q_OBJECT
public:
explicit QQuickTransform(QObject *parent = nullptr);
- ~QQuickTransform();
+ ~QQuickTransform() override;
void appendToItem(QQuickItem *);
void prependToItem(QQuickItem *);
@@ -144,6 +144,7 @@ class Q_QUICK_EXPORT QQuickItem : public QObject, public QQmlParserStatus
Q_PROPERTY(bool antialiasing READ antialiasing WRITE setAntialiasing NOTIFY antialiasingChanged RESET resetAntialiasing)
Q_PROPERTY(qreal implicitWidth READ implicitWidth WRITE setImplicitWidth NOTIFY implicitWidthChanged)
Q_PROPERTY(qreal implicitHeight READ implicitHeight WRITE setImplicitHeight NOTIFY implicitHeightChanged)
+ Q_PROPERTY(QObject *containmentMask READ containmentMask WRITE setContainmentMask NOTIFY containmentMaskChanged REVISION 11)
Q_PRIVATE_PROPERTY(QQuickItem::d_func(), QQuickItemLayer *layer READ layer DESIGNABLE false CONSTANT FINAL)
@@ -197,7 +198,7 @@ public:
Q_ENUM(TransformOrigin)
explicit QQuickItem(QQuickItem *parent = nullptr);
- virtual ~QQuickItem();
+ ~QQuickItem() override;
QQuickWindow *window() const;
QQuickItem *parentItem() const;
@@ -320,6 +321,8 @@ public:
QSharedPointer<QQuickItemGrabResult> grabToImage(const QSize &targetSize = QSize());
Q_INVOKABLE virtual bool contains(const QPointF &point) const;
+ QObject *containmentMask() const;
+ void setContainmentMask(QObject *mask);
QTransform itemTransform(QQuickItem *, bool *) const;
QPointF mapToItem(const QQuickItem *item, const QPointF &point) const;
@@ -390,6 +393,7 @@ Q_SIGNALS:
void zChanged();
void implicitWidthChanged();
void implicitHeightChanged();
+ Q_REVISION(11) void containmentMaskChanged();
protected:
bool event(QEvent *) override;
diff --git a/src/quick/items/qquickitem_p.h b/src/quick/items/qquickitem_p.h
index 9ed5286f22..93287cf0aa 100644
--- a/src/quick/items/qquickitem_p.h
+++ b/src/quick/items/qquickitem_p.h
@@ -93,11 +93,11 @@ class QQuickContents : public QQuickItemChangeListener
{
public:
QQuickContents(QQuickItem *item);
- ~QQuickContents();
+ ~QQuickContents() override;
QRectF rectF() const { return m_contents; }
- inline void calcGeometry(QQuickItem *changed = 0);
+ inline void calcGeometry(QQuickItem *changed = nullptr);
void complete();
protected:
@@ -108,8 +108,8 @@ protected:
//void itemVisibilityChanged(QQuickItem *item)
private:
- bool calcHeight(QQuickItem *changed = 0);
- bool calcWidth(QQuickItem *changed = 0);
+ bool calcHeight(QQuickItem *changed = nullptr);
+ bool calcWidth(QQuickItem *changed = nullptr);
void updateRect();
QQuickItem *m_item;
@@ -154,7 +154,7 @@ class QQuickItemLayer : public QObject, public QQuickItemChangeListener
public:
QQuickItemLayer(QQuickItem *item);
- ~QQuickItemLayer();
+ ~QQuickItemLayer() override;
void classBegin();
void componentComplete();
@@ -255,7 +255,7 @@ public:
static const QQuickItemPrivate* get(const QQuickItem *item) { return item->d_func(); }
QQuickItemPrivate();
- ~QQuickItemPrivate();
+ ~QQuickItemPrivate() override;
void init(QQuickItem *parent);
QQmlListProperty<QObject> data();
@@ -311,7 +311,6 @@ public:
static void transform_clear(QQmlListProperty<QQuickTransform> *list);
void _q_resourceObjectDeleted(QObject *);
- void _q_windowChanged(QQuickWindow *w);
quint64 _q_createJSWrapper(QV4::ExecutionEngine *engine);
enum ChangeType {
@@ -331,7 +330,7 @@ public:
Q_DECLARE_FLAGS(ChangeTypes, ChangeType)
struct ChangeListener {
- ChangeListener(QQuickItemChangeListener *l = nullptr, QQuickItemPrivate::ChangeTypes t = 0) : listener(l), types(t), gTypes(QQuickGeometryChange::All) {}
+ ChangeListener(QQuickItemChangeListener *l = nullptr, QQuickItemPrivate::ChangeTypes t = nullptr) : listener(l), types(t), gTypes(QQuickGeometryChange::All) {}
ChangeListener(QQuickItemChangeListener *l, QQuickGeometryChange gt) : listener(l), types(Geometry), gTypes(gt) {}
QQuickItemChangeListener *listener;
QQuickItemPrivate::ChangeTypes types;
@@ -361,13 +360,19 @@ public:
#endif
QPointF userTransformOriginPoint;
+ // these do not include child items
int effectRefCount;
int hideRefCount;
+ // updated recursively for child items as well
+ int recursiveEffectRefCount;
QSGOpacityNode *opacityNode;
QQuickDefaultClipNode *clipNode;
QSGRootNode *rootNode;
+ // Mask contains() method
+ QMetaMethod maskContains;
+
QObjectList resourcesList;
// Although acceptedMouseButtons is inside ExtraData, we actually store
@@ -382,6 +387,10 @@ public:
// 26 bits padding
};
QLazilyAllocated<ExtraData> extra;
+ // Contains mask
+ QPointer<QObject> mask;
+ // If the mask is an Item, inform it that it's being used as a mask (true) or is no longer being used (false)
+ virtual void registerAsContainmentMask(QQuickItem * /* maskedItem */, bool /* set */) { }
QQuickAnchors *anchors() const;
mutable QQuickAnchors *_anchors;
@@ -574,6 +583,8 @@ public:
virtual bool handlePointerEvent(QQuickPointerEvent *, bool avoidExclusiveGrabber = false);
+ virtual void setVisible(bool visible);
+
bool isTransparentForPositioner() const;
void setTransparentForPositioner(bool trans);
@@ -594,9 +605,9 @@ public:
- (rootNode) (shader effect source's root node)
*/
- QSGOpacityNode *opacityNode() const { return extra.isAllocated()?extra->opacityNode:0; }
- QQuickDefaultClipNode *clipNode() const { return extra.isAllocated()?extra->clipNode:0; }
- QSGRootNode *rootNode() const { return extra.isAllocated()?extra->rootNode:0; }
+ QSGOpacityNode *opacityNode() const { return extra.isAllocated()?extra->opacityNode:nullptr; }
+ QQuickDefaultClipNode *clipNode() const { return extra.isAllocated()?extra->clipNode:nullptr; }
+ QSGRootNode *rootNode() const { return extra.isAllocated()?extra->rootNode:nullptr; }
QSGTransformNode *itemNodeInstance;
QSGNode *paintNode;
@@ -606,6 +617,7 @@ public:
// A reference from an effect item means that this item is used by the effect, so
// it should insert a root node.
void refFromEffectItem(bool hide);
+ void recursiveRefFromEffectItem(int refs);
void derefFromEffectItem(bool unhide);
void itemChange(QQuickItem::ItemChange, const QQuickItem::ItemChangeData &);
@@ -627,7 +639,7 @@ public:
class QQuickItemKeyFilter
{
public:
- QQuickItemKeyFilter(QQuickItem * = 0);
+ QQuickItemKeyFilter(QQuickItem * = nullptr);
virtual ~QQuickItemKeyFilter();
virtual void keyPressed(QKeyEvent *event, bool post);
@@ -649,17 +661,15 @@ class QQuickKeyNavigationAttachedPrivate : public QObjectPrivate
{
public:
QQuickKeyNavigationAttachedPrivate()
- : QObjectPrivate(),
- left(0), right(0), up(0), down(0), tab(0), backtab(0),
- leftSet(false), rightSet(false), upSet(false), downSet(false),
+ : leftSet(false), rightSet(false), upSet(false), downSet(false),
tabSet(false), backtabSet(false) {}
- QQuickItem *left;
- QQuickItem *right;
- QQuickItem *up;
- QQuickItem *down;
- QQuickItem *tab;
- QQuickItem *backtab;
+ QQuickItem *left = nullptr;
+ QQuickItem *right = nullptr;
+ QQuickItem *up = nullptr;
+ QQuickItem *down = nullptr;
+ QQuickItem *tab = nullptr;
+ QQuickItem *backtab = nullptr;
bool leftSet : 1;
bool rightSet : 1;
bool upSet : 1;
@@ -682,7 +692,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickKeyNavigationAttached : public QObject, publi
Q_PROPERTY(Priority priority READ priority WRITE setPriority NOTIFY priorityChanged)
public:
- QQuickKeyNavigationAttached(QObject * = 0);
+ QQuickKeyNavigationAttached(QObject * = nullptr);
QQuickItem *left() const;
void setLeft(QQuickItem *);
@@ -727,7 +737,7 @@ class QQuickLayoutMirroringAttached : public QObject
Q_PROPERTY(bool childrenInherit READ childrenInherit WRITE setChildrenInherit NOTIFY childrenInheritChanged)
public:
- explicit QQuickLayoutMirroringAttached(QObject *parent = 0);
+ explicit QQuickLayoutMirroringAttached(QObject *parent = nullptr);
bool enabled() const;
void setEnabled(bool);
@@ -770,8 +780,7 @@ class QQuickKeysAttachedPrivate : public QObjectPrivate
{
public:
QQuickKeysAttachedPrivate()
- : QObjectPrivate(), inPress(false), inRelease(false)
- , inIM(false), enabled(true), imeItem(0), item(0)
+ : inPress(false), inRelease(false), inIM(false), enabled(true)
{}
//loop detection
@@ -781,9 +790,9 @@ public:
bool enabled : 1;
- QQuickItem *imeItem;
+ QQuickItem *imeItem = nullptr;
QList<QQuickItem *> targets;
- QQuickItem *item;
+ QQuickItem *item = nullptr;
QQuickKeyEvent theKeyEvent;
};
@@ -797,8 +806,8 @@ class QQuickKeysAttached : public QObject, public QQuickItemKeyFilter
Q_PROPERTY(Priority priority READ priority WRITE setPriority NOTIFY priorityChanged)
public:
- QQuickKeysAttached(QObject *parent=0);
- ~QQuickKeysAttached();
+ QQuickKeysAttached(QObject *parent=nullptr);
+ ~QQuickKeysAttached() override;
bool enabled() const { Q_D(const QQuickKeysAttached); return d->enabled; }
void setEnabled(bool enabled) {
@@ -886,7 +895,7 @@ private:
Qt::MouseButtons QQuickItemPrivate::acceptedMouseButtons() const
{
return ((extra.flag() ? Qt::LeftButton : Qt::MouseButton(0)) |
- (extra.isAllocated() ? extra->acceptedMouseButtons : Qt::MouseButtons(0)));
+ (extra.isAllocated() ? extra->acceptedMouseButtons : Qt::MouseButtons(nullptr)));
}
QSGContext *QQuickItemPrivate::sceneGraphContext() const
@@ -908,7 +917,7 @@ void QQuickItemPrivate::markSortedChildrenDirty(QQuickItem *child)
if (child->z() != 0. || sortedChildItems != &childItems) {
if (sortedChildItems != &childItems)
delete sortedChildItems;
- sortedChildItems = 0;
+ sortedChildItems = nullptr;
}
}
diff --git a/src/quick/items/qquickitemanimation.cpp b/src/quick/items/qquickitemanimation.cpp
index 4b5c81b4d4..e913e5ba05 100644
--- a/src/quick/items/qquickitemanimation.cpp
+++ b/src/quick/items/qquickitemanimation.cpp
@@ -371,7 +371,7 @@ QAbstractAnimationJob* QQuickParentAnimation::transition(QQuickStateActions &act
if (data->actions.count()) {
QSequentialAnimationGroupJob *topLevelGroup = new QSequentialAnimationGroupJob;
- QActionAnimation *viaAction = d->via ? new QActionAnimation : 0;
+ QActionAnimation *viaAction = d->via ? new QActionAnimation : nullptr;
QActionAnimation *targetAction = new QActionAnimation;
//we'll assume the common case by far is to have children, and always create ag
QParallelAnimationGroupJob *ag = new QParallelAnimationGroupJob;
@@ -409,7 +409,7 @@ QAbstractAnimationJob* QQuickParentAnimation::transition(QQuickStateActions &act
delete data;
delete viaData;
}
- return 0;
+ return nullptr;
}
/*!
@@ -922,12 +922,12 @@ QAbstractAnimationJob* QQuickPathAnimation::transition(QQuickStateActions &actio
pa->setEasingCurve(d->easingCurve);
return initInstance(pa);
} else {
- pa->setFromSourcedValue(0);
- pa->setAnimValue(0);
+ pa->setFromSourcedValue(nullptr);
+ pa->setAnimValue(nullptr);
delete pa;
delete data;
}
- return 0;
+ return nullptr;
}
void QQuickPathAnimationUpdater::setValue(qreal v)
@@ -955,7 +955,7 @@ void QQuickPathAnimationUpdater::setValue(qreal v)
qreal angle;
bool fixed = orientation == QQuickPathAnimation::Fixed;
- QPointF currentPos = !painterPath.isEmpty() ? path->sequentialPointAt(painterPath, pathLength, attributePoints, prevBez, v, fixed ? 0 : &angle) : path->sequentialPointAt(v, fixed ? 0 : &angle);
+ QPointF currentPos = !painterPath.isEmpty() ? path->sequentialPointAt(painterPath, pathLength, attributePoints, prevBez, v, fixed ? nullptr : &angle) : path->sequentialPointAt(v, fixed ? nullptr : &angle);
//adjust position according to anchor point
if (!anchorPoint.isNull()) {
diff --git a/src/quick/items/qquickitemanimation_p.h b/src/quick/items/qquickitemanimation_p.h
index 3b3fad9cc4..b803455f12 100644
--- a/src/quick/items/qquickitemanimation_p.h
+++ b/src/quick/items/qquickitemanimation_p.h
@@ -68,7 +68,7 @@ class Q_AUTOTEST_EXPORT QQuickParentAnimation : public QQuickAnimationGroup
Q_PROPERTY(QQuickItem *via READ via WRITE setVia NOTIFY viaChanged)
public:
- QQuickParentAnimation(QObject *parent=0);
+ QQuickParentAnimation(QObject *parent=nullptr);
virtual ~QQuickParentAnimation();
QQuickItem *target() const;
@@ -89,7 +89,7 @@ protected:
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
};
class QQuickAnchorAnimationPrivate;
@@ -102,7 +102,7 @@ class Q_AUTOTEST_EXPORT QQuickAnchorAnimation : public QQuickAbstractAnimation
Q_PROPERTY(QEasingCurve easing READ easing WRITE setEasing NOTIFY easingChanged)
public:
- QQuickAnchorAnimation(QObject *parent=0);
+ QQuickAnchorAnimation(QObject *parent=nullptr);
virtual ~QQuickAnchorAnimation();
QQmlListProperty<QQuickItem> targets();
@@ -121,7 +121,7 @@ protected:
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
};
#if QT_CONFIG(quick_path)
@@ -145,7 +145,7 @@ class Q_AUTOTEST_EXPORT QQuickPathAnimation : public QQuickAbstractAnimation
Q_PROPERTY(qreal endRotation READ endRotation WRITE setEndRotation NOTIFY endRotationChanged)
public:
- QQuickPathAnimation(QObject *parent=0);
+ QQuickPathAnimation(QObject *parent=nullptr);
virtual ~QQuickPathAnimation();
enum Orientation {
@@ -188,7 +188,7 @@ protected:
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
Q_SIGNALS:
void durationChanged(int);
void easingChanged(const QEasingCurve &);
diff --git a/src/quick/items/qquickitemanimation_p_p.h b/src/quick/items/qquickitemanimation_p_p.h
index 2d075dfab3..83b9899197 100644
--- a/src/quick/items/qquickitemanimation_p_p.h
+++ b/src/quick/items/qquickitemanimation_p_p.h
@@ -65,7 +65,7 @@ class QQuickParentAnimationPrivate : public QQuickAnimationGroupPrivate
Q_DECLARE_PUBLIC(QQuickParentAnimation)
public:
QQuickParentAnimationPrivate()
- : QQuickAnimationGroupPrivate(), target(0), newParent(0), via(0) {}
+ : QQuickAnimationGroupPrivate(), target(nullptr), newParent(nullptr), via(nullptr) {}
QQuickItem *target;
QQuickItem *newParent;
@@ -91,7 +91,7 @@ public:
class QQuickPathAnimationUpdater : public QQuickBulkValueUpdater
{
public:
- QQuickPathAnimationUpdater() : path(0), pathLength(0), target(0), reverse(false),
+ QQuickPathAnimationUpdater() : path(nullptr), pathLength(0), target(nullptr), reverse(false),
fromSourced(false), fromDefined(false), toDefined(false),
toX(0), toY(0), currentV(0), orientation(QQuickPathAnimation::Fixed),
entryInterval(0), exitInterval(0) {}
@@ -128,10 +128,10 @@ class QQuickPathAnimationPrivate;
class QQuickPathAnimationAnimator : public QQuickBulkValueAnimator
{
public:
- QQuickPathAnimationAnimator(QQuickPathAnimationPrivate * = 0);
+ QQuickPathAnimationAnimator(QQuickPathAnimationPrivate * = nullptr);
~QQuickPathAnimationAnimator();
- void clearTemplate() { animationTemplate = 0; }
+ void clearTemplate() { animationTemplate = nullptr; }
QQuickPathAnimationUpdater *pathUpdater() const { return static_cast<QQuickPathAnimationUpdater*>(getAnimValue()); }
private:
@@ -142,7 +142,7 @@ class QQuickPathAnimationPrivate : public QQuickAbstractAnimationPrivate
{
Q_DECLARE_PUBLIC(QQuickPathAnimation)
public:
- QQuickPathAnimationPrivate() : path(0), target(0),
+ QQuickPathAnimationPrivate() : path(nullptr), target(nullptr),
orientation(QQuickPathAnimation::Fixed), entryDuration(0), exitDuration(0), duration(250) {}
QQuickPath *path;
diff --git a/src/quick/items/qquickitemchangelistener_p.h b/src/quick/items/qquickitemchangelistener_p.h
index cb0af75c4c..31d06c9983 100644
--- a/src/quick/items/qquickitemchangelistener_p.h
+++ b/src/quick/items/qquickitemchangelistener_p.h
@@ -135,7 +135,7 @@ public:
virtual void itemImplicitWidthChanged(QQuickItem *) {}
virtual void itemImplicitHeightChanged(QQuickItem *) {}
- virtual QQuickAnchorsPrivate *anchorPrivate() { return 0; }
+ virtual QQuickAnchorsPrivate *anchorPrivate() { return nullptr; }
};
QT_END_NAMESPACE
diff --git a/src/quick/items/qquickitemgrabresult.cpp b/src/quick/items/qquickitemgrabresult.cpp
index c3f8d4f024..003fde8c9e 100644
--- a/src/quick/items/qquickitemgrabresult.cpp
+++ b/src/quick/items/qquickitemgrabresult.cpp
@@ -62,9 +62,9 @@ class QQuickItemGrabResultPrivate : public QObjectPrivate
{
public:
QQuickItemGrabResultPrivate()
- : cacheEntry(0)
- , qmlEngine(0)
- , texture(0)
+ : cacheEntry(nullptr)
+ , qmlEngine(nullptr)
+ , texture(nullptr)
{
}
@@ -266,7 +266,7 @@ void QQuickItemGrabResult::render()
d->image = d->texture->toImage();
delete d->texture;
- d->texture = 0;
+ d->texture = nullptr;
disconnect(d->window.data(), &QQuickWindow::beforeSynchronizing, this, &QQuickItemGrabResult::setup);
disconnect(d->window.data(), &QQuickWindow::afterRendering, this, &QQuickItemGrabResult::render);
@@ -281,17 +281,17 @@ QQuickItemGrabResult *QQuickItemGrabResultPrivate::create(QQuickItem *item, cons
if (size.width() < 1 || size.height() < 1) {
qmlWarning(item) << "grabToImage: item has invalid dimensions";
- return 0;
+ return nullptr;
}
if (!item->window()) {
qmlWarning(item) << "grabToImage: item is not attached to a window";
- return 0;
+ return nullptr;
}
if (!item->window()->isVisible()) {
qmlWarning(item) << "grabToImage: item's window is not visible";
- return 0;
+ return nullptr;
}
QQuickItemGrabResult *result = new QQuickItemGrabResult();
diff --git a/src/quick/items/qquickitemsmodule.cpp b/src/quick/items/qquickitemsmodule.cpp
index 62312845b2..51a91e1f7a 100644
--- a/src/quick/items/qquickitemsmodule.cpp
+++ b/src/quick/items/qquickitemsmodule.cpp
@@ -74,7 +74,9 @@
#if QT_CONFIG(quick_positioners)
#include "qquickpositioners_p.h"
#endif
+#if QT_CONFIG(quick_repeater)
#include "qquickrepeater_p.h"
+#endif
#include "qquickloader_p.h"
#if QT_CONFIG(quick_animatedimage)
#include "qquickanimatedimage_p.h"
@@ -111,6 +113,10 @@
#include <private/qqmlmetatype_p.h>
#include <QtQuick/private/qquickaccessibleattached_p.h>
+QT_BEGIN_NAMESPACE
+Q_DECLARE_LOGGING_CATEGORY(lcTransient)
+QT_END_NAMESPACE
+
static QQmlPrivate::AutoParentResult qquickitem_autoParent(QObject *obj, QObject *parent)
{
// When setting a parent (especially during dynamic object creation) in QML,
@@ -125,6 +131,7 @@ static QQmlPrivate::AutoParentResult qquickitem_autoParent(QObject *obj, QObject
QQuickWindow *win = qmlobject_cast<QQuickWindow *>(obj);
if (win) {
// A Window inside an Item should be transient for that item's window
+ qCDebug(lcTransient) << win << "is transient for" << parentItem->window();
win->setTransientParent(parentItem->window());
return QQmlPrivate::Parented;
}
@@ -134,6 +141,7 @@ static QQmlPrivate::AutoParentResult qquickitem_autoParent(QObject *obj, QObject
QQuickWindow *win = qmlobject_cast<QQuickWindow *>(obj);
if (win) {
// A Window inside a Window should be transient for it
+ qCDebug(lcTransient) << win << "is transient for" << parentWindow;
win->setTransientParent(parentWindow);
return QQmlPrivate::Parented;
} else {
@@ -207,7 +215,9 @@ static void qt_quickitems_defineModule(const char *uri, int major, int minor)
qmlRegisterType<QQuickPathView>(uri,major,minor,"PathView");
#endif
qmlRegisterType<QQuickRectangle>(uri,major,minor,"Rectangle");
+#if QT_CONFIG(quick_repeater)
qmlRegisterType<QQuickRepeater>(uri,major,minor,"Repeater");
+#endif
qmlRegisterType<QQuickTranslate>(uri,major,minor,"Translate");
qmlRegisterType<QQuickRotation>(uri,major,minor,"Rotation");
qmlRegisterType<QQuickScale>(uri,major,minor,"Scale");
@@ -290,7 +300,8 @@ static void qt_quickitems_defineModule(const char *uri, int major, int minor)
qmlRegisterType<QQuickMultiPointTouchArea>("QtQuick", 2, 0, "MultiPointTouchArea");
qmlRegisterType<QQuickTouchPoint>("QtQuick", 2, 0, "TouchPoint");
- qmlRegisterType<QQuickGrabGestureEvent>();
+ qmlRegisterUncreatableType<QQuickGrabGestureEvent>(uri,major,minor, "GestureEvent",
+ QQuickMouseEvent::tr("GestureEvent is only available in the context of handling the gestureStarted signal from MultiPointTouchArea"));
#if QT_CONFIG(accessibility)
qmlRegisterUncreatableType<QQuickAccessibleAttached>("QtQuick", 2, 0, "Accessible",QQuickAccessibleAttached::tr("Accessible is only available via attached properties"));
@@ -406,6 +417,11 @@ static void qt_quickitems_defineModule(const char *uri, int major, int minor)
#if QT_CONFIG(quick_path)
qmlRegisterType<QQuickPathAngleArc>(uri, 2, 11, "PathAngleArc");
#endif
+
+#if QT_CONFIG(quick_animatedimage)
+ qmlRegisterType<QQuickAnimatedImage, 11>(uri, 2, 11,"AnimatedImage");
+#endif
+ qmlRegisterType<QQuickItem, 11>(uri, 2, 11,"Item");
}
static void initResources()
diff --git a/src/quick/items/qquickitemview.cpp b/src/quick/items/qquickitemview.cpp
index 1d0d042839..f2e055e874 100644
--- a/src/quick/items/qquickitemview.cpp
+++ b/src/quick/items/qquickitemview.cpp
@@ -54,7 +54,7 @@ Q_LOGGING_CATEGORY(lcItemViewDelegateLifecycle, "qt.quick.itemview.lifecycle")
FxViewItem::FxViewItem(QQuickItem *i, QQuickItemView *v, bool own, QQuickItemViewAttached *attached)
: item(i)
, view(v)
- , transitionableItem(0)
+ , transitionableItem(nullptr)
, attached(attached)
, ownItem(own)
, releaseAfterTransition(false)
@@ -69,9 +69,9 @@ FxViewItem::~FxViewItem()
delete transitionableItem;
if (ownItem && item) {
trackGeometry(false);
- item->setParentItem(0);
+ item->setParentItem(nullptr);
item->deleteLater();
- item = 0;
+ item = nullptr;
}
}
@@ -275,7 +275,7 @@ QQuickItemView::~QQuickItemView()
QQuickItem *QQuickItemView::currentItem() const
{
Q_D(const QQuickItemView);
- return d->currentItem ? d->currentItem->item : 0;
+ return d->currentItem ? d->currentItem->item : nullptr;
}
QVariant QQuickItemView::model() const
@@ -304,12 +304,12 @@ void QQuickItemView::setModel(const QVariant &m)
QQmlInstanceModel *oldModel = d->model;
d->clear();
- d->model = 0;
+ d->model = nullptr;
d->setPosition(d->contentStartOffset());
d->modelVariant = model;
QObject *object = qvariant_cast<QObject*>(model);
- QQmlInstanceModel *vim = 0;
+ QQmlInstanceModel *vim = nullptr;
if (object && (vim = qobject_cast<QQmlInstanceModel *>(object))) {
if (d->ownModel) {
delete oldModel;
@@ -362,7 +362,7 @@ QQmlComponent *QQuickItemView::delegate() const
return dataModel->delegate();
}
- return 0;
+ return nullptr;
}
void QQuickItemView::setDelegate(QQmlComponent *delegate)
@@ -382,7 +382,7 @@ void QQuickItemView::setDelegate(QQmlComponent *delegate)
if (isComponentComplete()) {
d->releaseVisibleItems();
d->releaseItem(d->currentItem);
- d->currentItem = 0;
+ d->currentItem = nullptr;
d->updateSectionCriteria();
d->refill();
d->moveReason = QQuickItemViewPrivate::SetIndex;
@@ -586,7 +586,7 @@ QQmlComponent *QQuickItemView::header() const
QQuickItem *QQuickItemView::headerItem() const
{
Q_D(const QQuickItemView);
- return d->header ? d->header->item : 0;
+ return d->header ? d->header->item : nullptr;
}
void QQuickItemView::setHeader(QQmlComponent *headerComponent)
@@ -595,7 +595,7 @@ void QQuickItemView::setHeader(QQmlComponent *headerComponent)
if (d->headerComponent != headerComponent) {
d->applyPendingChanges();
delete d->header;
- d->header = 0;
+ d->header = nullptr;
d->headerComponent = headerComponent;
d->markExtentsDirty();
@@ -621,7 +621,7 @@ QQmlComponent *QQuickItemView::footer() const
QQuickItem *QQuickItemView::footerItem() const
{
Q_D(const QQuickItemView);
- return d->footer ? d->footer->item : 0;
+ return d->footer ? d->footer->item : nullptr;
}
void QQuickItemView::setFooter(QQmlComponent *footerComponent)
@@ -630,7 +630,7 @@ void QQuickItemView::setFooter(QQmlComponent *footerComponent)
if (d->footerComponent != footerComponent) {
d->applyPendingChanges();
delete d->footer;
- d->footer = 0;
+ d->footer = nullptr;
d->footerComponent = footerComponent;
if (isComponentComplete()) {
@@ -666,7 +666,7 @@ void QQuickItemView::setHighlight(QQmlComponent *highlightComponent)
QQuickItem *QQuickItemView::highlightItem() const
{
Q_D(const QQuickItemView);
- return d->highlight ? d->highlight->item : 0;
+ return d->highlight ? d->highlight->item : nullptr;
}
bool QQuickItemView::highlightFollowsCurrentItem() const
@@ -799,7 +799,7 @@ void QQuickItemView::setHighlightMoveDuration(int duration)
QQuickTransition *QQuickItemView::populateTransition() const
{
Q_D(const QQuickItemView);
- return d->transitioner ? d->transitioner->populateTransition : 0;
+ return d->transitioner ? d->transitioner->populateTransition : nullptr;
}
void QQuickItemView::setPopulateTransition(QQuickTransition *transition)
@@ -815,7 +815,7 @@ void QQuickItemView::setPopulateTransition(QQuickTransition *transition)
QQuickTransition *QQuickItemView::addTransition() const
{
Q_D(const QQuickItemView);
- return d->transitioner ? d->transitioner->addTransition : 0;
+ return d->transitioner ? d->transitioner->addTransition : nullptr;
}
void QQuickItemView::setAddTransition(QQuickTransition *transition)
@@ -831,7 +831,7 @@ void QQuickItemView::setAddTransition(QQuickTransition *transition)
QQuickTransition *QQuickItemView::addDisplacedTransition() const
{
Q_D(const QQuickItemView);
- return d->transitioner ? d->transitioner->addDisplacedTransition : 0;
+ return d->transitioner ? d->transitioner->addDisplacedTransition : nullptr;
}
void QQuickItemView::setAddDisplacedTransition(QQuickTransition *transition)
@@ -847,7 +847,7 @@ void QQuickItemView::setAddDisplacedTransition(QQuickTransition *transition)
QQuickTransition *QQuickItemView::moveTransition() const
{
Q_D(const QQuickItemView);
- return d->transitioner ? d->transitioner->moveTransition : 0;
+ return d->transitioner ? d->transitioner->moveTransition : nullptr;
}
void QQuickItemView::setMoveTransition(QQuickTransition *transition)
@@ -863,7 +863,7 @@ void QQuickItemView::setMoveTransition(QQuickTransition *transition)
QQuickTransition *QQuickItemView::moveDisplacedTransition() const
{
Q_D(const QQuickItemView);
- return d->transitioner ? d->transitioner->moveDisplacedTransition : 0;
+ return d->transitioner ? d->transitioner->moveDisplacedTransition : nullptr;
}
void QQuickItemView::setMoveDisplacedTransition(QQuickTransition *transition)
@@ -879,7 +879,7 @@ void QQuickItemView::setMoveDisplacedTransition(QQuickTransition *transition)
QQuickTransition *QQuickItemView::removeTransition() const
{
Q_D(const QQuickItemView);
- return d->transitioner ? d->transitioner->removeTransition : 0;
+ return d->transitioner ? d->transitioner->removeTransition : nullptr;
}
void QQuickItemView::setRemoveTransition(QQuickTransition *transition)
@@ -895,7 +895,7 @@ void QQuickItemView::setRemoveTransition(QQuickTransition *transition)
QQuickTransition *QQuickItemView::removeDisplacedTransition() const
{
Q_D(const QQuickItemView);
- return d->transitioner ? d->transitioner->removeDisplacedTransition : 0;
+ return d->transitioner ? d->transitioner->removeDisplacedTransition : nullptr;
}
void QQuickItemView::setRemoveDisplacedTransition(QQuickTransition *transition)
@@ -911,7 +911,7 @@ void QQuickItemView::setRemoveDisplacedTransition(QQuickTransition *transition)
QQuickTransition *QQuickItemView::displacedTransition() const
{
Q_D(const QQuickItemView);
- return d->transitioner ? d->transitioner->displacedTransition : 0;
+ return d->transitioner ? d->transitioner->displacedTransition : nullptr;
}
void QQuickItemView::setDisplacedTransition(QQuickTransition *transition)
@@ -926,7 +926,6 @@ void QQuickItemView::setDisplacedTransition(QQuickTransition *transition)
void QQuickItemViewPrivate::positionViewAtIndex(int index, int mode)
{
- Q_Q(QQuickItemView);
if (!isValid())
return;
if (mode < QQuickItemView::Beginning || mode > QQuickItemView::SnapPosition)
@@ -953,11 +952,16 @@ void QQuickItemViewPrivate::positionViewAtIndex(int index, int mode)
item = visibleItem(idx);
}
if (item) {
+ const bool stickyHeader = hasStickyHeader();
+ const bool stickyFooter = hasStickyFooter();
+ const qreal stickyHeaderSize = stickyHeader ? headerSize() : 0;
+ const qreal stickyFooterSize = stickyFooter ? footerSize() : 0;
+
const qreal itemPos = item->position();
switch (mode) {
case QQuickItemView::Beginning:
pos = itemPos;
- if (header && (index < 0 || hasStickyHeader()))
+ if (header && (index < 0 || stickyHeader))
pos -= headerSize();
break;
case QQuickItemView::Center:
@@ -965,30 +969,29 @@ void QQuickItemViewPrivate::positionViewAtIndex(int index, int mode)
break;
case QQuickItemView::End:
pos = itemPos - viewSize + item->size();
- if (footer && (index >= modelCount || hasStickyFooter()))
+ if (footer && (index >= modelCount || stickyFooter))
pos += footerSize();
break;
case QQuickItemView::Visible:
- if (itemPos > pos + viewSize)
- pos = itemPos - viewSize + item->size();
- else if (item->endPosition() <= pos)
- pos = itemPos;
+ if (itemPos > pos + viewSize - stickyFooterSize)
+ pos = item->endPosition() - viewSize + stickyFooterSize;
+ else if (item->endPosition() <= pos - stickyHeaderSize)
+ pos = itemPos - stickyHeaderSize;
break;
case QQuickItemView::Contain:
- if (item->endPosition() >= pos + viewSize)
- pos = itemPos - viewSize + item->size();
- if (itemPos < pos)
- pos = itemPos;
+ if (item->endPosition() >= pos + viewSize + stickyFooterSize)
+ pos = itemPos - viewSize + item->size() + stickyFooterSize;
+ if (itemPos - stickyHeaderSize < pos)
+ pos = itemPos - stickyHeaderSize;
break;
case QQuickItemView::SnapPosition:
- pos = itemPos - highlightRangeStart;
+ pos = itemPos - highlightRangeStart - stickyHeaderSize;
break;
}
pos = qMin(pos, maxExtent);
qreal minExtent = calculatedMinExtent();
pos = qMax(pos, minExtent);
moveReason = QQuickItemViewPrivate::Other;
- q->cancelFlick();
setPosition(pos);
if (highlight) {
@@ -1231,7 +1234,7 @@ void QQuickItemViewPrivate::itemGeometryChanged(QQuickItem *item, QQuickGeometry
// start new transitions
bool prevInLayout = inLayout;
if (!inLayout) {
- FxViewItem *actualItem = transitioner ? visibleItem(currentIndex) : 0;
+ FxViewItem *actualItem = transitioner ? visibleItem(currentIndex) : nullptr;
if (actualItem && actualItem->transitionRunning())
inLayout = true;
}
@@ -1246,16 +1249,26 @@ void QQuickItemViewPrivate::itemGeometryChanged(QQuickItem *item, QQuickGeometry
void QQuickItemView::destroyRemoved()
{
Q_D(QQuickItemView);
+
+ bool hasRemoveTransition = false;
+ bool hasRemoveTransitionAsTarget = false;
+ if (d->transitioner) {
+ hasRemoveTransition = d->transitioner->canTransition(QQuickItemViewTransitioner::RemoveTransition, false);
+ hasRemoveTransitionAsTarget = d->transitioner->canTransition(QQuickItemViewTransitioner::RemoveTransition, true);
+ }
+
for (QList<FxViewItem*>::Iterator it = d->visibleItems.begin();
it != d->visibleItems.end();) {
FxViewItem *item = *it;
if (item->index == -1 && (!item->attached || item->attached->delayRemove() == false)) {
- if (d->transitioner && d->transitioner->canTransition(QQuickItemViewTransitioner::RemoveTransition, true)) {
+ if (hasRemoveTransitionAsTarget) {
// don't remove from visibleItems until next layout()
d->runDelayedRemoveTransition = true;
QObject::disconnect(item->attached, SIGNAL(delayRemoveChanged()), this, SLOT(destroyRemoved()));
++it;
} else {
+ if (hasRemoveTransition)
+ d->runDelayedRemoveTransition = true;
d->releaseItem(item);
it = d->visibleItems.erase(it);
}
@@ -1384,7 +1397,6 @@ void QQuickItemView::trackedPositionChanged()
pos = qMax(trackedPos, toItemPos);
}
if (viewPos != pos) {
- cancelFlick();
d->calcVelocity = true;
d->setPosition(pos);
d->calcVelocity = false;
@@ -1546,14 +1558,14 @@ QQuickItemViewPrivate::QQuickItemViewPrivate()
, layoutDirection(Qt::LeftToRight), verticalLayoutDirection(QQuickItemView::TopToBottom)
, moveReason(Other)
, visibleIndex(0)
- , currentIndex(-1), currentItem(0)
- , trackedItem(0), requestedIndex(-1)
- , highlightComponent(0), highlight(0)
+ , currentIndex(-1), currentItem(nullptr)
+ , trackedItem(nullptr), requestedIndex(-1)
+ , highlightComponent(nullptr), highlight(nullptr)
, highlightRange(QQuickItemView::NoHighlightRange)
, highlightRangeStart(0), highlightRangeEnd(0)
, highlightMoveDuration(150)
- , headerComponent(0), header(0), footerComponent(0), footer(0)
- , transitioner(0)
+ , headerComponent(nullptr), header(nullptr), footerComponent(nullptr), footer(nullptr)
+ , transitioner(nullptr)
, minExtent(0), maxExtent(0)
, ownModel(false), wrap(false)
, keyNavigationEnabled(true)
@@ -1571,7 +1583,7 @@ QQuickItemViewPrivate::QQuickItemViewPrivate()
QQuickItemViewPrivate::~QQuickItemViewPrivate()
{
if (transitioner)
- transitioner->setChangeListener(0);
+ transitioner->setChangeListener(nullptr);
delete transitioner;
}
@@ -1637,7 +1649,7 @@ FxViewItem *QQuickItemViewPrivate::visibleItem(int modelIndex) const {
return item;
}
}
- return 0;
+ return nullptr;
}
// should rename to firstItemInView() to avoid confusion with other "*visible*" methods
@@ -1697,7 +1709,7 @@ void QQuickItemViewPrivate::updateCurrent(int modelIndex)
if (currentItem->attached)
currentItem->attached->setIsCurrentItem(false);
releaseItem(currentItem);
- currentItem = 0;
+ currentItem = nullptr;
currentIndex = modelIndex;
emit q->currentIndexChanged();
emit q->currentItemChanged();
@@ -1717,7 +1729,7 @@ void QQuickItemViewPrivate::updateCurrent(int modelIndex)
FxViewItem *oldCurrentItem = currentItem;
int oldCurrentIndex = currentIndex;
currentIndex = modelIndex;
- currentItem = createItem(modelIndex, false);
+ currentItem = createItem(modelIndex, QQmlIncubator::AsynchronousIfNested);
if (oldCurrentItem && oldCurrentItem->attached && (!currentItem || oldCurrentItem->item != currentItem->item))
oldCurrentItem->attached->setIsCurrentItem(false);
if (currentItem) {
@@ -1738,7 +1750,9 @@ void QQuickItemViewPrivate::updateCurrent(int modelIndex)
void QQuickItemViewPrivate::clear()
{
+ Q_Q(QQuickItemView);
currentChanges.reset();
+ bufferedChanges.reset();
timeline.clear();
releaseVisibleItems();
@@ -1750,10 +1764,13 @@ void QQuickItemViewPrivate::clear()
}
releasePendingTransition.clear();
+ auto oldCurrentItem = currentItem;
releaseItem(currentItem);
- currentItem = 0;
+ currentItem = nullptr;
+ if (oldCurrentItem)
+ emit q->currentItemChanged();
createHighlight();
- trackedItem = 0;
+ trackedItem = nullptr;
if (requestedIndex >= 0) {
if (model)
@@ -1796,56 +1813,61 @@ void QQuickItemViewPrivate::refill(qreal from, qreal to)
if (!isValid() || !q->isComponentComplete())
return;
- bufferPause.stop();
- currentChanges.reset();
+ do {
+ bufferPause.stop();
+ if (currentChanges.hasPendingChanges() || bufferedChanges.hasPendingChanges()) {
+ currentChanges.reset();
+ bufferedChanges.reset();
+ releaseVisibleItems();
+ }
- int prevCount = itemCount;
- itemCount = model->count();
- qreal bufferFrom = from - buffer;
- qreal bufferTo = to + buffer;
- qreal fillFrom = from;
- qreal fillTo = to;
-
- bool added = addVisibleItems(fillFrom, fillTo, bufferFrom, bufferTo, false);
- bool removed = removeNonVisibleItems(bufferFrom, bufferTo);
-
- if (requestedIndex == -1 && buffer && bufferMode != NoBuffer) {
- if (added) {
- // We've already created a new delegate this frame.
- // Just schedule a buffer refill.
- bufferPause.start();
- } else {
- if (bufferMode & BufferAfter)
- fillTo = bufferTo;
- if (bufferMode & BufferBefore)
- fillFrom = bufferFrom;
- added |= addVisibleItems(fillFrom, fillTo, bufferFrom, bufferTo, true);
+ int prevCount = itemCount;
+ itemCount = model->count();
+ qreal bufferFrom = from - buffer;
+ qreal bufferTo = to + buffer;
+ qreal fillFrom = from;
+ qreal fillTo = to;
+
+ bool added = addVisibleItems(fillFrom, fillTo, bufferFrom, bufferTo, false);
+ bool removed = removeNonVisibleItems(bufferFrom, bufferTo);
+
+ if (requestedIndex == -1 && buffer && bufferMode != NoBuffer) {
+ if (added) {
+ // We've already created a new delegate this frame.
+ // Just schedule a buffer refill.
+ bufferPause.start();
+ } else {
+ if (bufferMode & BufferAfter)
+ fillTo = bufferTo;
+ if (bufferMode & BufferBefore)
+ fillFrom = bufferFrom;
+ added |= addVisibleItems(fillFrom, fillTo, bufferFrom, bufferTo, true);
+ }
}
- }
- if (added || removed) {
- markExtentsDirty();
- updateBeginningEnd();
- visibleItemsChanged();
- updateHeader();
- updateFooter();
- updateViewport();
- }
+ if (added || removed) {
+ markExtentsDirty();
+ updateBeginningEnd();
+ visibleItemsChanged();
+ updateHeader();
+ updateFooter();
+ updateViewport();
+ }
- if (prevCount != itemCount)
- emit q->countChanged();
+ if (prevCount != itemCount)
+ emit q->countChanged();
+ } while (currentChanges.hasPendingChanges() || bufferedChanges.hasPendingChanges());
}
void QQuickItemViewPrivate::regenerate(bool orientationChanged)
{
Q_Q(QQuickItemView);
if (q->isComponentComplete()) {
- currentChanges.reset();
if (orientationChanged) {
delete header;
- header = 0;
+ header = nullptr;
delete footer;
- footer = 0;
+ footer = nullptr;
}
clear();
updateHeader();
@@ -1876,6 +1898,9 @@ void QQuickItemViewPrivate::layout()
inLayout = true;
+ // viewBounds contains bounds before any add/remove/move operation to the view
+ QRectF viewBounds(q->contentX(), q->contentY(), q->width(), q->height());
+
if (!isValid() && !visibleItems.count()) {
clear();
setPosition(contentStartOffset());
@@ -1934,14 +1959,14 @@ void QQuickItemViewPrivate::layout()
if (transitioner) {
// items added in the last refill() may need to be transitioned in - e.g. a remove
// causes items to slide up into view
- if (transitioner->canTransition(QQuickItemViewTransitioner::MoveTransition, false)
- || transitioner->canTransition(QQuickItemViewTransitioner::RemoveTransition, false)) {
+ if (lastIndexInView != -1 &&
+ (transitioner->canTransition(QQuickItemViewTransitioner::MoveTransition, false)
+ || transitioner->canTransition(QQuickItemViewTransitioner::RemoveTransition, false))) {
translateAndTransitionItemsAfter(lastIndexInView, insertionPosChanges, removalPosChanges);
}
prepareVisibleItemTransitions();
- QRectF viewBounds(q->contentX(), q->contentY(), q->width(), q->height());
for (QList<FxViewItem*>::Iterator it = releasePendingTransition.begin();
it != releasePendingTransition.end(); ) {
FxViewItem *item = *it;
@@ -1978,7 +2003,6 @@ bool QQuickItemViewPrivate::applyModelChanges(ChangeResult *totalInsertionResult
}
updateUnrequestedIndexes();
- moveReason = QQuickItemViewPrivate::Other;
FxViewItem *prevVisibleItemsFirst = visibleItems.count() ? *visibleItems.constBegin() : 0;
int prevItemCount = itemCount;
@@ -2100,8 +2124,11 @@ bool QQuickItemViewPrivate::applyModelChanges(ChangeResult *totalInsertionResult
if (currentChanges.currentRemoved && currentItem) {
if (currentItem->item && currentItem->attached)
currentItem->attached->setIsCurrentItem(false);
+ auto oldCurrentItem = currentItem;
releaseItem(currentItem);
- currentItem = 0;
+ currentItem = nullptr;
+ if (oldCurrentItem)
+ emit q->currentItemChanged();
}
if (!currentIndexCleared)
updateCurrent(currentChanges.newCurrentIndex);
@@ -2313,12 +2340,12 @@ void QQuickItemViewPrivate::viewItemTransitionFinished(QQuickItemViewTransitiona
When the item becomes available, refill() will be called and the item
will be returned on the next call to createItem().
*/
-FxViewItem *QQuickItemViewPrivate::createItem(int modelIndex, bool asynchronous)
+FxViewItem *QQuickItemViewPrivate::createItem(int modelIndex, QQmlIncubator::IncubationMode incubationMode)
{
Q_Q(QQuickItemView);
- if (requestedIndex == modelIndex && asynchronous)
- return 0;
+ if (requestedIndex == modelIndex && incubationMode == QQmlIncubator::Asynchronous)
+ return nullptr;
for (int i=0; i<releasePendingTransition.count(); i++) {
if (releasePendingTransition.at(i)->index == modelIndex
@@ -2328,14 +2355,20 @@ FxViewItem *QQuickItemViewPrivate::createItem(int modelIndex, bool asynchronous)
}
}
- if (asynchronous)
- requestedIndex = modelIndex;
inRequest = true;
- QObject* object = model->object(modelIndex, asynchronous);
+ QObject* object = model->object(modelIndex, incubationMode);
QQuickItem *item = qmlobject_cast<QQuickItem*>(object);
+
if (!item) {
- if (object) {
+ if (!object) {
+ if (requestedIndex == -1 && model->incubationStatus(modelIndex) == QQmlIncubator::Loading) {
+ // The reason we didn't receive an item is because it's incubating async. We keep track
+ // of this by assigning the index we're waiting for to 'requestedIndex'. This will e.g. let
+ // the view avoid unnecessary layout calls until the item has been loaded.
+ requestedIndex = modelIndex;
+ }
+ } else {
model->release(object);
if (!delegateValidated) {
delegateValidated = true;
@@ -2344,7 +2377,7 @@ FxViewItem *QQuickItemViewPrivate::createItem(int modelIndex, bool asynchronous)
}
}
inRequest = false;
- return 0;
+ return nullptr;
} else {
item->setParentItem(q->contentItem());
if (requestedIndex == modelIndex)
@@ -2397,7 +2430,7 @@ void QQuickItemView::destroyingItem(QObject *object)
Q_D(QQuickItemView);
QQuickItem* item = qmlobject_cast<QQuickItem*>(object);
if (item) {
- item->setParentItem(0);
+ item->setParentItem(nullptr);
d->unrequestedItems.remove(item);
}
}
@@ -2408,7 +2441,7 @@ bool QQuickItemViewPrivate::releaseItem(FxViewItem *item)
if (!item || !model)
return true;
if (trackedItem == item)
- trackedItem = 0;
+ trackedItem = nullptr;
item->trackGeometry(false);
QQmlInstanceModel::ReleaseFlags flags = model->release(item->item);
@@ -2418,7 +2451,7 @@ bool QQuickItemViewPrivate::releaseItem(FxViewItem *item)
QQuickItemPrivate::get(item->item)->setCulled(true);
unrequestedItems.insert(item->item, model->indexOf(item->item, q));
} else if (flags & QQmlInstanceModel::Destroyed) {
- item->item->setParentItem(0);
+ item->item->setParentItem(nullptr);
}
}
delete item;
@@ -2434,7 +2467,7 @@ QQuickItem *QQuickItemViewPrivate::createComponentItem(QQmlComponent *component,
{
Q_Q(const QQuickItemView);
- QQuickItem *item = 0;
+ QQuickItem *item = nullptr;
if (component) {
QQmlContext *creationContext = component->creationContext();
QQmlContext *context = new QQmlContext(
diff --git a/src/quick/items/qquickitemview_p.h b/src/quick/items/qquickitemview_p.h
index b38bc6174f..483fc1a09f 100644
--- a/src/quick/items/qquickitemview_p.h
+++ b/src/quick/items/qquickitemview_p.h
@@ -128,7 +128,7 @@ public:
};
Q_ENUM(VerticalLayoutDirection)
- QQuickItemView(QQuickFlickablePrivate &dd, QQuickItem *parent = 0);
+ QQuickItemView(QQuickFlickablePrivate &dd, QQuickItem *parent = nullptr);
~QQuickItemView();
QVariant model() const;
diff --git a/src/quick/items/qquickitemview_p_p.h b/src/quick/items/qquickitemview_p_p.h
index 374b8388ba..e250cf0ccb 100644
--- a/src/quick/items/qquickitemview_p_p.h
+++ b/src/quick/items/qquickitemview_p_p.h
@@ -206,7 +206,7 @@ public:
void refill(qreal from, qreal to);
void mirrorChange() override;
- FxViewItem *createItem(int modelIndex, bool asynchronous = false);
+ FxViewItem *createItem(int modelIndex,QQmlIncubator::IncubationMode incubationMode = QQmlIncubator::AsynchronousIfNested);
virtual bool releaseItem(FxViewItem *item);
QQuickItem *createHighlightItem() const;
diff --git a/src/quick/items/qquickitemviewtransition.cpp b/src/quick/items/qquickitemviewtransition.cpp
index 745e5b275f..5cd28d0acb 100644
--- a/src/quick/items/qquickitemviewtransition.cpp
+++ b/src/quick/items/qquickitemviewtransition.cpp
@@ -69,11 +69,11 @@ protected:
QQuickItemViewTransitionJob::QQuickItemViewTransitionJob()
- : m_transitioner(0)
- , m_item(0)
+ : m_transitioner(nullptr)
+ , m_item(nullptr)
, m_type(QQuickItemViewTransitioner::NoTransition)
, m_isTarget(false)
- , m_wasDeleted(0)
+ , m_wasDeleted(nullptr)
{
}
@@ -143,12 +143,12 @@ void QQuickItemViewTransitionJob::finished()
m_transitioner->finishedTransition(this, m_item);
if (deleted)
return;
- m_wasDeleted = 0;
+ m_wasDeleted = nullptr;
- m_transitioner = 0;
+ m_transitioner = nullptr;
}
- m_item = 0;
+ m_item = nullptr;
m_toPos.setX(0);
m_toPos.setY(0);
m_type = QQuickItemViewTransitioner::NoTransition;
@@ -157,12 +157,12 @@ void QQuickItemViewTransitionJob::finished()
QQuickItemViewTransitioner::QQuickItemViewTransitioner()
- : populateTransition(0)
- , addTransition(0), addDisplacedTransition(0)
- , moveTransition(0), moveDisplacedTransition(0)
- , removeTransition(0), removeDisplacedTransition(0)
- , displacedTransition(0)
- , changeListener(0)
+ : populateTransition(nullptr)
+ , addTransition(nullptr), addDisplacedTransition(nullptr)
+ , moveTransition(nullptr), moveDisplacedTransition(nullptr)
+ , removeTransition(nullptr), removeDisplacedTransition(nullptr)
+ , displacedTransition(nullptr)
+ , changeListener(nullptr)
, usePopulateTransition(false)
{
}
@@ -172,7 +172,7 @@ QQuickItemViewTransitioner::~QQuickItemViewTransitioner()
typedef QSet<QQuickItemViewTransitionJob *>::iterator JobIt;
for (JobIt it = runningJobs.begin(), end = runningJobs.end(); it != end; ++it)
- (*it)->m_transitioner = 0;
+ (*it)->m_transitioner = nullptr;
}
bool QQuickItemViewTransitioner::canTransition(QQuickItemViewTransitioner::TransitionType type, bool asTarget) const
@@ -249,12 +249,12 @@ void QQuickItemViewTransitioner::resetTargetLists()
QQuickTransition *QQuickItemViewTransitioner::transitionObject(QQuickItemViewTransitioner::TransitionType type, bool asTarget) const
{
if (type == QQuickItemViewTransitioner::NoTransition)
- return 0;
+ return nullptr;
if (type == PopulateTransition)
asTarget = true; // no separate displaced transition
- QQuickTransition *trans = 0;
+ QQuickTransition *trans = nullptr;
switch (type) {
case NoTransition:
break;
@@ -276,7 +276,7 @@ QQuickTransition *QQuickItemViewTransitioner::transitionObject(QQuickItemViewTra
trans = displacedTransition;
if (trans && trans->enabled())
return trans;
- return 0;
+ return nullptr;
}
const QList<int> &QQuickItemViewTransitioner::targetIndexes(QQuickItemViewTransitioner::TransitionType type) const
@@ -328,7 +328,7 @@ void QQuickItemViewTransitioner::finishedTransition(QQuickItemViewTransitionJob
QQuickItemViewTransitionableItem::QQuickItemViewTransitionableItem(QQuickItem *i)
: item(i)
- , transition(0)
+ , transition(nullptr)
, nextTransitionType(QQuickItemViewTransitioner::NoTransition)
, isTransitionTarget(false)
, nextTransitionToSet(false)
@@ -563,7 +563,7 @@ void QQuickItemViewTransitionableItem::stopTransition()
QQuickViewTransitionAttached::QQuickViewTransitionAttached(QObject *parent)
- : QObject(parent), m_item(0), m_index(-1)
+ : QObject(parent), m_item(nullptr), m_index(-1)
{
}
/*!
diff --git a/src/quick/items/qquickitemviewtransition_p.h b/src/quick/items/qquickitemviewtransition_p.h
index 3d2f5361b1..29a62f7f10 100644
--- a/src/quick/items/qquickitemviewtransition_p.h
+++ b/src/quick/items/qquickitemviewtransition_p.h
@@ -58,6 +58,8 @@ QT_REQUIRE_CONFIG(quick_viewtransitions);
#include <QtCore/qobject.h>
#include <QtCore/qpoint.h>
#include <QtQml/qqml.h>
+#include <private/qqmlguard_p.h>
+#include <private/qquicktransition_p.h>
QT_BEGIN_NAMESPACE
@@ -115,14 +117,14 @@ public:
QList<QObject *> moveTransitionTargets;
QList<QObject *> removeTransitionTargets;
- QQuickTransition *populateTransition;
- QQuickTransition *addTransition;
- QQuickTransition *addDisplacedTransition;
- QQuickTransition *moveTransition;
- QQuickTransition *moveDisplacedTransition;
- QQuickTransition *removeTransition;
- QQuickTransition *removeDisplacedTransition;
- QQuickTransition *displacedTransition;
+ QQmlGuard<QQuickTransition> populateTransition;
+ QQmlGuard<QQuickTransition> addTransition;
+ QQmlGuard<QQuickTransition> addDisplacedTransition;
+ QQmlGuard<QQuickTransition> moveTransition;
+ QQmlGuard<QQuickTransition> moveDisplacedTransition;
+ QQmlGuard<QQuickTransition> removeTransition;
+ QQmlGuard<QQuickTransition> removeDisplacedTransition;
+ QQmlGuard<QQuickTransition> displacedTransition;
private:
friend class QQuickItemViewTransitionJob;
diff --git a/src/quick/items/qquicklistview.cpp b/src/quick/items/qquicklistview.cpp
index a6236d9801..33becd71ec 100644
--- a/src/quick/items/qquicklistview.cpp
+++ b/src/quick/items/qquicklistview.cpp
@@ -176,9 +176,9 @@ public:
, snapMode(QQuickListView::NoSnap)
, headerPositioning(QQuickListView::InlineHeader)
, footerPositioning(QQuickListView::InlineFooter)
- , highlightPosAnimator(0), highlightWidthAnimator(0), highlightHeightAnimator(0)
+ , highlightPosAnimator(nullptr), highlightWidthAnimator(nullptr), highlightHeightAnimator(nullptr)
, highlightMoveVelocity(400), highlightResizeVelocity(400), highlightResizeDuration(-1)
- , sectionCriteria(0), currentSectionItem(0), nextSectionItem(0)
+ , sectionCriteria(nullptr), currentSectionItem(nullptr), nextSectionItem(nullptr)
, overshootDist(0.0), correctFlick(false), inFlickCorrection(false)
{
highlightMoveDuration = -1; //override default value set in base class
@@ -195,8 +195,8 @@ public:
//----------------------------------------------------------------------------
QQuickViewSection::QQuickViewSection(QQuickListView *parent)
- : QObject(parent), m_criteria(FullString), m_delegate(0), m_labelPositioning(InlineLabels)
- , m_view(parent ? QQuickListViewPrivate::get(parent) : 0)
+ : QObject(parent), m_criteria(FullString), m_delegate(nullptr), m_labelPositioning(InlineLabels)
+ , m_view(parent ? QQuickListViewPrivate::get(parent) : nullptr)
{
}
@@ -258,7 +258,7 @@ public:
}
inline QQuickItem *section() const {
- return item && attached ? static_cast<QQuickListViewAttached*>(attached)->m_sectionItem : 0;
+ return item && attached ? static_cast<QQuickListViewAttached*>(attached)->m_sectionItem : nullptr;
}
void setSection(QQuickItem *s) {
static_cast<QQuickListViewAttached*>(attached)->m_sectionItem = s;
@@ -389,7 +389,7 @@ bool QQuickListViewPrivate::isBottomToTop() const
FxViewItem *QQuickListViewPrivate::itemBefore(int modelIndex) const
{
if (modelIndex < visibleIndex)
- return 0;
+ return nullptr;
int idx = 1;
int lastIndex = -1;
while (idx < visibleItems.count()) {
@@ -402,7 +402,7 @@ FxViewItem *QQuickListViewPrivate::itemBefore(int modelIndex) const
}
if (lastIndex == modelIndex-1)
return visibleItems.constLast();
- return 0;
+ return nullptr;
}
void QQuickListViewPrivate::setPosition(qreal pos)
@@ -530,7 +530,7 @@ qreal QQuickListViewPrivate::snapPosAt(qreal pos)
FxViewItem *QQuickListViewPrivate::snapItemAt(qreal pos)
{
- FxViewItem *snapItem = 0;
+ FxViewItem *snapItem = nullptr;
qreal prevItemSize = 0;
for (FxViewItem *item : qAsConst(visibleItems)) {
if (item->index == -1)
@@ -561,13 +561,13 @@ void QQuickListViewPrivate::clear()
{
for (int i = 0; i < sectionCacheSize; ++i) {
delete sectionCache[i];
- sectionCache[i] = 0;
+ sectionCache[i] = nullptr;
}
visiblePos = 0;
releaseSectionItem(currentSectionItem);
- currentSectionItem = 0;
+ currentSectionItem = nullptr;
releaseSectionItem(nextSectionItem);
- nextSectionItem = 0;
+ nextSectionItem = nullptr;
lastVisibleSection = QString();
QQuickItemViewPrivate::clear();
}
@@ -629,13 +629,13 @@ bool QQuickListViewPrivate::releaseItem(FxViewItem *item)
if (!sectionCache[i]) {
sectionCache[i] = att->m_sectionItem;
sectionCache[i]->setVisible(false);
- att->m_sectionItem = 0;
+ att->m_sectionItem = nullptr;
break;
}
++i;
} while (i < sectionCacheSize);
delete att->m_sectionItem;
- att->m_sectionItem = 0;
+ att->m_sectionItem = nullptr;
}
return released;
@@ -669,11 +669,13 @@ bool QQuickListViewPrivate::addVisibleItems(qreal fillFrom, qreal fillTo, qreal
}
}
+ QQmlIncubator::IncubationMode incubationMode = doBuffer ? QQmlIncubator::Asynchronous : QQmlIncubator::AsynchronousIfNested;
+
bool changed = false;
- FxListItemSG *item = 0;
+ FxListItemSG *item = nullptr;
qreal pos = itemEnd;
while (modelIndex < model->count() && pos <= fillTo) {
- if (!(item = static_cast<FxListItemSG*>(createItem(modelIndex, doBuffer))))
+ if (!(item = static_cast<FxListItemSG*>(createItem(modelIndex, incubationMode))))
break;
qCDebug(lcItemViewDelegateLifecycle) << "refill: append item" << modelIndex << "pos" << pos << "buffer" << doBuffer << "item" << (QObject *)(item->item);
if (!transitioner || !transitioner->canTransition(QQuickItemViewTransitioner::PopulateTransition, true)) // pos will be set by layoutVisibleItems()
@@ -690,7 +692,7 @@ bool QQuickListViewPrivate::addVisibleItems(qreal fillFrom, qreal fillTo, qreal
return changed;
while (visibleIndex > 0 && visibleIndex <= model->count() && visiblePos > fillFrom) {
- if (!(item = static_cast<FxListItemSG*>(createItem(visibleIndex-1, doBuffer))))
+ if (!(item = static_cast<FxListItemSG*>(createItem(visibleIndex-1, incubationMode))))
break;
qCDebug(lcItemViewDelegateLifecycle) << "refill: prepend item" << visibleIndex-1 << "current top pos" << visiblePos << "buffer" << doBuffer << "item" << (QObject *)(item->item);
--visibleIndex;
@@ -720,7 +722,7 @@ void QQuickListViewPrivate::removeItem(FxViewItem *item)
bool QQuickListViewPrivate::removeNonVisibleItems(qreal bufferFrom, qreal bufferTo)
{
- FxViewItem *item = 0;
+ FxViewItem *item = nullptr;
bool changed = false;
// Remove items from the start of the view.
@@ -862,16 +864,16 @@ void QQuickListViewPrivate::createHighlight()
bool changed = false;
if (highlight) {
if (trackedItem == highlight)
- trackedItem = 0;
+ trackedItem = nullptr;
delete highlight;
- highlight = 0;
+ highlight = nullptr;
delete highlightPosAnimator;
delete highlightWidthAnimator;
delete highlightHeightAnimator;
- highlightPosAnimator = 0;
- highlightWidthAnimator = 0;
- highlightHeightAnimator = 0;
+ highlightPosAnimator = nullptr;
+ highlightWidthAnimator = nullptr;
+ highlightHeightAnimator = nullptr;
changed = true;
}
@@ -960,13 +962,13 @@ bool QQuickListViewPrivate::movingFromHighlight()
QQuickItem * QQuickListViewPrivate::getSectionItem(const QString &section)
{
Q_Q(QQuickListView);
- QQuickItem *sectionItem = 0;
+ QQuickItem *sectionItem = nullptr;
int i = sectionCacheSize-1;
while (i >= 0 && !sectionCache[i])
--i;
if (i >= 0) {
sectionItem = sectionCache[i];
- sectionCache[i] = 0;
+ sectionCache[i] = nullptr;
sectionItem->setVisible(true);
QQmlContext *context = QQmlEngine::contextForObject(sectionItem)->parentContext();
context->setContextProperty(QLatin1String("section"), section);
@@ -1023,13 +1025,13 @@ void QQuickListViewPrivate::releaseSectionItems()
if (listItem->section()) {
qreal pos = listItem->position();
releaseSectionItem(listItem->section());
- listItem->setSection(0);
+ listItem->setSection(nullptr);
listItem->setPosition(pos);
}
}
for (int i = 0; i < sectionCacheSize; ++i) {
delete sectionCache[i];
- sectionCache[i] = 0;
+ sectionCache[i] = nullptr;
}
}
@@ -1051,7 +1053,7 @@ void QQuickListViewPrivate::updateInlineSection(FxListItemSG *listItem)
} else if (listItem->section()) {
qreal pos = listItem->position();
releaseSectionItem(listItem->section());
- listItem->setSection(0);
+ listItem->setSection(nullptr);
listItem->setPosition(pos);
}
}
@@ -1067,8 +1069,8 @@ void QQuickListViewPrivate::updateStickySections()
qreal startPos = hasStickyHeader() ? header->endPosition() : viewPos;
qreal endPos = hasStickyFooter() ? footer->position() : viewPos + size();
- QQuickItem *sectionItem = 0;
- QQuickItem *lastSectionItem = 0;
+ QQuickItem *sectionItem = nullptr;
+ QQuickItem *lastSectionItem = nullptr;
int index = 0;
while (index < visibleItems.count()) {
if (QQuickItem *section = static_cast<FxListItemSG *>(visibleItems.at(index))->section()) {
@@ -1127,7 +1129,7 @@ void QQuickListViewPrivate::updateStickySections()
currentSectionItem->setX(pos);
} else if (currentSectionItem) {
releaseSectionItem(currentSectionItem);
- currentSectionItem = 0;
+ currentSectionItem = nullptr;
}
// Next section footer
@@ -1159,7 +1161,7 @@ void QQuickListViewPrivate::updateStickySections()
nextSectionItem->setX(pos);
} else if (nextSectionItem) {
releaseSectionItem(nextSectionItem);
- nextSectionItem = 0;
+ nextSectionItem = nullptr;
}
}
@@ -1175,7 +1177,7 @@ void QQuickListViewPrivate::updateSections()
QString prevSection;
if (visibleIndex > 0)
prevSection = sectionAt(visibleIndex-1);
- QQuickListViewAttached *prevAtt = 0;
+ QQuickListViewAttached *prevAtt = nullptr;
int prevIdx = -1;
int idx = -1;
for (FxViewItem *item : qAsConst(visibleItems)) {
@@ -1466,9 +1468,6 @@ void QQuickListViewPrivate::itemGeometryChanged(QQuickItem *item, QQuickGeometry
void QQuickListViewPrivate::fixupPosition()
{
- if ((haveHighlightRange && highlightRange == QQuickListView::StrictlyEnforceRange)
- || snapMode != QQuickListView::NoSnap)
- moveReason = Other;
if (orient == QQuickListView::Vertical)
fixupY();
else
@@ -3267,11 +3266,11 @@ bool QQuickListViewPrivate::applyInsertionChange(const QQmlChangeSet::Change &ch
} else {
for (i = count-1; i >= 0 && pos >= from; --i) {
// item is before first visible e.g. in cache buffer
- FxViewItem *item = 0;
+ FxViewItem *item = nullptr;
if (change.isMove() && (item = currentChanges.removedItems.take(change.moveKey(modelIndex + i))))
item->index = modelIndex + i;
if (!item)
- item = createItem(modelIndex + i);
+ item = createItem(modelIndex + i, QQmlIncubator::Synchronous);
if (!item)
return false;
@@ -3308,12 +3307,12 @@ bool QQuickListViewPrivate::applyInsertionChange(const QQmlChangeSet::Change &ch
} else {
for (int i = 0; i < count && pos <= lastVisiblePos; ++i) {
visibleAffected = true;
- FxViewItem *item = 0;
+ FxViewItem *item = nullptr;
if (change.isMove() && (item = currentChanges.removedItems.take(change.moveKey(modelIndex + i))))
item->index = modelIndex + i;
bool newItem = !item;
if (!item)
- item = createItem(modelIndex + i);
+ item = createItem(modelIndex + i, QQmlIncubator::Synchronous);
if (!item)
return false;
diff --git a/src/quick/items/qquicklistview_p.h b/src/quick/items/qquicklistview_p.h
index f8db0f0f8f..9a9b325b1e 100644
--- a/src/quick/items/qquicklistview_p.h
+++ b/src/quick/items/qquicklistview_p.h
@@ -71,7 +71,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickViewSection : public QObject
Q_PROPERTY(QQmlComponent *delegate READ delegate WRITE setDelegate NOTIFY delegateChanged)
Q_PROPERTY(int labelPositioning READ labelPositioning WRITE setLabelPositioning NOTIFY labelPositioningChanged)
public:
- QQuickViewSection(QQuickListView *parent=0);
+ QQuickViewSection(QQuickListView *parent=nullptr);
QString property() const { return m_property; }
void setProperty(const QString &);
@@ -132,7 +132,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickListView : public QQuickItemView
Q_CLASSINFO("DefaultProperty", "data")
public:
- QQuickListView(QQuickItem *parent=0);
+ QQuickListView(QQuickItem *parent=nullptr);
~QQuickListView();
qreal spacing() const;
@@ -206,7 +206,7 @@ class QQuickListViewAttached : public QQuickItemViewAttached
public:
QQuickListViewAttached(QObject *parent)
- : QQuickItemViewAttached(parent), m_sectionItem(0) {}
+ : QQuickItemViewAttached(parent), m_sectionItem(nullptr) {}
~QQuickListViewAttached() {}
public:
diff --git a/src/quick/items/qquickloader.cpp b/src/quick/items/qquickloader.cpp
index 27afe5a5db..34f30e81a3 100644
--- a/src/quick/items/qquickloader.cpp
+++ b/src/quick/items/qquickloader.cpp
@@ -48,11 +48,13 @@
QT_BEGIN_NAMESPACE
+Q_DECLARE_LOGGING_CATEGORY(lcTransient)
+
static const QQuickItemPrivate::ChangeTypes watchedChanges
= QQuickItemPrivate::Geometry | QQuickItemPrivate::ImplicitWidth | QQuickItemPrivate::ImplicitHeight;
QQuickLoaderPrivate::QQuickLoaderPrivate()
- : item(0), object(0), component(0), itemContext(0), incubator(0), updatingSize(false),
+ : item(nullptr), object(nullptr), component(nullptr), itemContext(nullptr), incubator(nullptr), updatingSize(false),
active(true), loadingFromSource(false), asynchronous(false)
{
}
@@ -60,7 +62,7 @@ QQuickLoaderPrivate::QQuickLoaderPrivate()
QQuickLoaderPrivate::~QQuickLoaderPrivate()
{
delete itemContext;
- itemContext = 0;
+ itemContext = nullptr;
delete incubator;
disposeInitialPropertyValues();
}
@@ -94,7 +96,13 @@ void QQuickLoaderPrivate::clear()
incubator->clear();
delete itemContext;
- itemContext = 0;
+ itemContext = nullptr;
+
+ // Prevent any bindings from running while waiting for deletion. Without
+ // this we may get transient errors from use of 'parent', for example.
+ QQmlContext *context = qmlContext(object);
+ if (context)
+ QQmlContextData::get(context)->invalidate();
if (loadingFromSource && component) {
// disconnect since we deleteLater
@@ -103,7 +111,7 @@ void QQuickLoaderPrivate::clear()
QObject::disconnect(component, SIGNAL(progressChanged(qreal)),
q, SIGNAL(progressChanged()));
component->deleteLater();
- component = 0;
+ component = nullptr;
}
componentStrongReference.clear();
source = QUrl();
@@ -114,13 +122,13 @@ void QQuickLoaderPrivate::clear()
// We can't delete immediately because our item may have triggered
// the Loader to load a different item.
- item->setParentItem(0);
+ item->setParentItem(nullptr);
item->setVisible(false);
- item = 0;
+ item = nullptr;
}
if (object) {
object->deleteLater();
- object = 0;
+ object = nullptr;
}
}
@@ -348,22 +356,28 @@ void QQuickLoader::setActive(bool newVal)
if (d->incubator) {
d->incubator->clear();
delete d->itemContext;
- d->itemContext = 0;
+ d->itemContext = nullptr;
}
+ // Prevent any bindings from running while waiting for deletion. Without
+ // this we may get transient errors from use of 'parent', for example.
+ QQmlContext *context = qmlContext(d->object);
+ if (context)
+ QQmlContextData::get(context)->invalidate();
+
if (d->item) {
QQuickItemPrivate *p = QQuickItemPrivate::get(d->item);
p->removeItemChangeListener(d, watchedChanges);
// We can't delete immediately because our item may have triggered
// the Loader to load a different item.
- d->item->setParentItem(0);
+ d->item->setParentItem(nullptr);
d->item->setVisible(false);
- d->item = 0;
+ d->item = nullptr;
}
if (d->object) {
d->object->deleteLater();
- d->object = 0;
+ d->object = nullptr;
emit itemChanged();
}
emit statusChanged();
@@ -485,7 +499,7 @@ void QQuickLoader::setSourceComponent(QQmlComponent *comp)
void QQuickLoader::resetSourceComponent()
{
- setSourceComponent(0);
+ setSourceComponent(nullptr);
}
void QQuickLoader::loadFromSourceComponent()
@@ -642,7 +656,7 @@ void QQuickLoaderPrivate::setInitialState(QObject *obj)
if (obj) {
QQml_setParent_noEvent(itemContext, obj);
QQml_setParent_noEvent(obj, q);
- itemContext = 0;
+ itemContext = nullptr;
}
if (initialPropertyValues.isUndefined())
@@ -650,7 +664,7 @@ void QQuickLoaderPrivate::setInitialState(QObject *obj)
QQmlComponentPrivate *d = QQmlComponentPrivate::get(component);
Q_ASSERT(d && d->engine);
- QV4::ExecutionEngine *v4 = QV8Engine::getV4(d->engine);
+ QV4::ExecutionEngine *v4 = d->engine->handle();
Q_ASSERT(v4);
QV4::Scope scope(v4);
QV4::ScopedValue ipv(scope, initialPropertyValues.value());
@@ -672,6 +686,13 @@ void QQuickLoaderPrivate::incubatorStateChanged(QQmlIncubator::Status status)
if (status == QQmlIncubator::Ready) {
object = incubator->object();
item = qmlobject_cast<QQuickItem*>(object);
+ if (!item) {
+ QQuickWindow *window = qmlobject_cast<QQuickWindow*>(object);
+ if (window) {
+ qCDebug(lcTransient) << window << "is transient for" << q->window();
+ window->setTransientParent(q->window());
+ }
+ }
emit q->itemChanged();
initResize();
incubator->clear();
@@ -679,7 +700,7 @@ void QQuickLoaderPrivate::incubatorStateChanged(QQmlIncubator::Status status)
if (!incubator->errors().isEmpty())
QQmlEnginePrivate::warning(qmlEngine(q), incubator->errors());
delete itemContext;
- itemContext = 0;
+ itemContext = nullptr;
delete incubator->object();
source = QUrl();
emit q->itemChanged();
@@ -816,6 +837,18 @@ void QQuickLoader::componentComplete()
}
}
+void QQuickLoader::itemChange(QQuickItem::ItemChange change, const QQuickItem::ItemChangeData &value)
+{
+ if (change == ItemSceneChange) {
+ QQuickWindow *loadedWindow = qmlobject_cast<QQuickWindow *>(item());
+ if (loadedWindow) {
+ qCDebug(lcTransient) << loadedWindow << "is transient for" << value.window;
+ loadedWindow->setTransientParent(value.window);
+ }
+ }
+ QQuickItem::itemChange(change, value);
+}
+
/*!
\qmlsignal QtQuick::Loader::loaded()
diff --git a/src/quick/items/qquickloader_p.h b/src/quick/items/qquickloader_p.h
index 27e5d1ec8b..de1dfa9da5 100644
--- a/src/quick/items/qquickloader_p.h
+++ b/src/quick/items/qquickloader_p.h
@@ -69,7 +69,7 @@ class Q_AUTOTEST_EXPORT QQuickLoader : public QQuickImplicitSizeItem
Q_PROPERTY(bool asynchronous READ asynchronous WRITE setAsynchronous NOTIFY asynchronousChanged)
public:
- QQuickLoader(QQuickItem *parent = 0);
+ QQuickLoader(QQuickItem *parent = nullptr);
virtual ~QQuickLoader();
bool active() const;
@@ -107,6 +107,7 @@ Q_SIGNALS:
protected:
void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry) override;
void componentComplete() override;
+ void itemChange(ItemChange change, const ItemChangeData &value) override;
private:
void setSource(const QUrl &sourceUrl, bool needsClear);
diff --git a/src/quick/items/qquickmousearea.cpp b/src/quick/items/qquickmousearea.cpp
index 96f34ef276..052da9fe82 100644
--- a/src/quick/items/qquickmousearea.cpp
+++ b/src/quick/items/qquickmousearea.cpp
@@ -60,13 +60,13 @@ Q_DECLARE_LOGGING_CATEGORY(DBG_HOVER_TRACE)
QQuickMouseAreaPrivate::QQuickMouseAreaPrivate()
: enabled(true), scrollGestureEnabled(true), hovered(false), longPress(false),
moved(false), stealMouse(false), doubleClick(false), preventStealing(false),
- propagateComposedEvents(false), overThreshold(false), pressed(0),
+ propagateComposedEvents(false), overThreshold(false), pressed(nullptr),
pressAndHoldInterval(-1)
#if QT_CONFIG(draganddrop)
- , drag(0)
+ , drag(nullptr)
#endif
#if QT_CONFIG(cursor)
- , cursor(0)
+ , cursor(nullptr)
#endif
{
}
@@ -99,6 +99,7 @@ void QQuickMouseAreaPrivate::saveEvent(QMouseEvent *event)
lastButton = event->button();
lastButtons = event->buttons();
lastModifiers = event->modifiers();
+ lastFlags = event->flags();
}
bool QQuickMouseAreaPrivate::isPressAndHoldConnected()
@@ -784,7 +785,7 @@ void QQuickMouseArea::mouseMoveEvent(QMouseEvent *event)
#endif
QQuickMouseEvent &me = d->quickMouseEvent;
- me.reset(d->lastPos.x(), d->lastPos.y(), d->lastButton, d->lastButtons, d->lastModifiers, false, d->longPress);
+ me.reset(d->lastPos.x(), d->lastPos.y(), d->lastButton, d->lastButtons, d->lastModifiers, false, d->longPress, event->flags());
me.setSource(event->source());
emit mouseXChanged(&me);
me.setPosition(d->lastPos);
@@ -827,7 +828,8 @@ void QQuickMouseArea::mouseDoubleClickEvent(QMouseEvent *event)
if (d->enabled) {
d->saveEvent(event);
QQuickMouseEvent &me = d->quickMouseEvent;
- me.reset(d->lastPos.x(), d->lastPos.y(), d->lastButton, d->lastButtons, d->lastModifiers, true, false);
+ me.reset(d->lastPos.x(), d->lastPos.y(), d->lastButton, d->lastButtons, d->lastModifiers, true,
+ false, event->flags());
me.setSource(event->source());
me.setAccepted(d->isDoubleClickConnected());
emit this->doubleClicked(&me);
@@ -908,7 +910,7 @@ void QQuickMouseArea::ungrabMouse()
if (d->pressed) {
// if our mouse grab has been removed (probably by Flickable), fix our
// state
- d->pressed = 0;
+ d->pressed = nullptr;
d->stealMouse = false;
d->doubleClick = false;
d->overThreshold = false;
@@ -942,7 +944,7 @@ bool QQuickMouseArea::sendMouseEvent(QMouseEvent *event)
QPointF localPos = mapFromScene(event->windowPos());
QQuickWindow *c = window();
- QQuickItem *grabber = c ? c->mouseGrabberItem() : 0;
+ QQuickItem *grabber = c ? c->mouseGrabberItem() : nullptr;
bool stealThisEvent = d->stealMouse;
if ((stealThisEvent || contains(localPos)) && (!grabber || !grabber->keepMouseGrab())) {
QMouseEvent mouseEvent(event->type(), localPos, event->windowPos(), event->screenPos(),
@@ -963,7 +965,7 @@ bool QQuickMouseArea::sendMouseEvent(QMouseEvent *event)
default:
break;
}
- grabber = c ? c->mouseGrabberItem() : 0;
+ grabber = c ? c->mouseGrabberItem() : nullptr;
if (grabber && stealThisEvent && !grabber->keepMouseGrab() && grabber != this)
grabMouse();
@@ -1028,7 +1030,7 @@ void QQuickMouseArea::timerEvent(QTimerEvent *event)
if (d->pressed && dragged == false && d->hovered == true) {
d->longPress = true;
QQuickMouseEvent &me = d->quickMouseEvent;
- me.reset(d->lastPos.x(), d->lastPos.y(), d->lastButton, d->lastButtons, d->lastModifiers, false, d->longPress);
+ me.reset(d->lastPos.x(), d->lastPos.y(), d->lastButton, d->lastButtons, d->lastModifiers, false, d->longPress, d->lastFlags);
me.setSource(Qt::MouseEventSynthesizedByQt);
me.setAccepted(d->isPressAndHoldConnected());
emit pressAndHold(&me);
@@ -1207,7 +1209,7 @@ bool QQuickMouseArea::setPressed(Qt::MouseButton button, bool p, Qt::MouseEventS
if (wasPressed != p) {
QQuickMouseEvent &me = d->quickMouseEvent;
- me.reset(d->lastPos.x(), d->lastPos.y(), d->lastButton, d->lastButtons, d->lastModifiers, isclick, d->longPress);
+ me.reset(d->lastPos.x(), d->lastPos.y(), d->lastButton, d->lastButtons, d->lastModifiers, isclick, d->longPress, d->lastFlags);
me.setSource(source);
if (p) {
d->pressed |= button;
@@ -1418,7 +1420,7 @@ QSGNode *QQuickMouseArea::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData
Q_D(QQuickMouseArea);
if (!qmlVisualTouchDebugging())
- return 0;
+ return nullptr;
QSGInternalRectangleNode *rectangle = static_cast<QSGInternalRectangleNode *>(oldNode);
if (!rectangle) rectangle = d->sceneGraphContext()->createInternalRectangleNode();
diff --git a/src/quick/items/qquickmousearea_p.h b/src/quick/items/qquickmousearea_p.h
index ae6c56726e..0a8449957f 100644
--- a/src/quick/items/qquickmousearea_p.h
+++ b/src/quick/items/qquickmousearea_p.h
@@ -87,7 +87,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickMouseArea : public QQuickItem
Q_PROPERTY(int pressAndHoldInterval READ pressAndHoldInterval WRITE setPressAndHoldInterval NOTIFY pressAndHoldIntervalChanged RESET resetPressAndHoldInterval REVISION 9)
public:
- QQuickMouseArea(QQuickItem *parent=0);
+ QQuickMouseArea(QQuickItem *parent=nullptr);
~QQuickMouseArea();
qreal mouseX() const;
diff --git a/src/quick/items/qquickmousearea_p_p.h b/src/quick/items/qquickmousearea_p_p.h
index 2fa5f7cd44..0dd2690d43 100644
--- a/src/quick/items/qquickmousearea_p_p.h
+++ b/src/quick/items/qquickmousearea_p_p.h
@@ -61,6 +61,7 @@ QT_BEGIN_NAMESPACE
class QQuickMouseEvent;
class QQuickMouseArea;
+class QQuickPointerMask;
class QQuickMouseAreaPrivate : public QQuickItemPrivate
{
Q_DECLARE_PUBLIC(QQuickMouseArea)
@@ -99,6 +100,7 @@ public:
#if QT_CONFIG(draganddrop)
QQuickDrag *drag;
#endif
+ QPointer<QQuickPointerMask> mask;
QPointF startScene;
QPointF targetStartPos;
QPointF lastPos;
@@ -112,6 +114,7 @@ public:
#endif
QQuickMouseEvent quickMouseEvent;
QQuickWheelEvent quickWheelEvent;
+ Qt::MouseEventFlags lastFlags;
};
QT_END_NAMESPACE
diff --git a/src/quick/items/qquickmultipointtoucharea.cpp b/src/quick/items/qquickmultipointtoucharea.cpp
index bdf30469ce..dc168073e4 100644
--- a/src/quick/items/qquickmultipointtoucharea.cpp
+++ b/src/quick/items/qquickmultipointtoucharea.cpp
@@ -285,6 +285,43 @@ void QQuickTouchPoint::setUniqueId(const QPointingDeviceUniqueId &id)
emit uniqueIdChanged();
}
+
+/*!
+ \qmltype GestureEvent
+ \instantiates QQuickGrabGestureEvent
+ \inqmlmodule QtQuick
+ \ingroup qtquick-input-events
+ \brief The parameter given with the gestureStarted signal
+
+ The GestureEvent object has the current touch points, which you may choose
+ to interpret as a gesture, and an invokable method to grab the involved
+ points exclusively.
+*/
+
+/*!
+ \qmlproperty real QtQuick::GestureEvent::dragThreshold
+
+ This property holds the system setting for the distance a finger must move
+ before it is interpreted as a drag. It comes from
+ QStyleHints::startDragDistance().
+*/
+
+/*!
+ \qmlproperty list<TouchPoint> QtQuick::GestureEvent::touchPoints
+
+ This property holds the set of current touch points.
+*/
+
+/*!
+ \qmlmethod QtQuick::GestureEvent::grab()
+
+ Acquires an exclusive grab of the mouse and all the \l touchPoints, and
+ calls \l {QQuickItem::setKeepTouchGrab()}{setKeepTouchGrab()} and
+ \l {QQuickItem::setKeepMouseGrab()}{setKeepMouseGrab()} so that any
+ parent Item that \l {QQuickItem::filtersChildMouseEvents()}{filters} its
+ children's events will not be allowed to take over the grabs.
+*/
+
/*!
\qmltype MultiPointTouchArea
\instantiates QQuickMultiPointTouchArea
@@ -504,7 +541,7 @@ void QQuickMultiPointTouchArea::touchEvent(QTouchEvent *event)
case QEvent::TouchEnd: {
//if e.g. a parent Flickable has the mouse grab, don't process the touch events
QQuickWindow *c = window();
- QQuickItem *grabber = c ? c->mouseGrabberItem() : 0;
+ QQuickItem *grabber = c ? c->mouseGrabberItem() : nullptr;
if (grabber && grabber != this && grabber->keepMouseGrab() && grabber->isEnabled()) {
QQuickItem *item = this;
while ((item = item->parentItem())) {
@@ -682,7 +719,7 @@ void QQuickMultiPointTouchArea::clearTouchLists()
void QQuickMultiPointTouchArea::addTouchPoint(const QTouchEvent::TouchPoint *p)
{
- QQuickTouchPoint *dtp = 0;
+ QQuickTouchPoint *dtp = nullptr;
for (QQuickTouchPoint* tp : qAsConst(_touchPrototypes)) {
if (!tp->inUse()) {
tp->setInUse(true);
@@ -691,7 +728,7 @@ void QQuickMultiPointTouchArea::addTouchPoint(const QTouchEvent::TouchPoint *p)
}
}
- if (dtp == 0)
+ if (dtp == nullptr)
dtp = new QQuickTouchPoint(false);
dtp->setPointId(p->id());
updateTouchPoint(dtp,p);
@@ -702,7 +739,7 @@ void QQuickMultiPointTouchArea::addTouchPoint(const QTouchEvent::TouchPoint *p)
void QQuickMultiPointTouchArea::addTouchPoint(const QMouseEvent *e)
{
- QQuickTouchPoint *dtp = 0;
+ QQuickTouchPoint *dtp = nullptr;
for (QQuickTouchPoint *tp : qAsConst(_touchPrototypes))
if (!tp->inUse()) {
tp->setInUse(true);
@@ -710,7 +747,7 @@ void QQuickMultiPointTouchArea::addTouchPoint(const QMouseEvent *e)
break;
}
- if (dtp == 0)
+ if (dtp == nullptr)
dtp = new QQuickTouchPoint(false);
updateTouchPoint(dtp, e);
dtp->setPressed(true);
@@ -883,7 +920,7 @@ bool QQuickMultiPointTouchArea::sendMouseEvent(QMouseEvent *event)
QPointF localPos = mapFromScene(event->windowPos());
QQuickWindow *c = window();
- QQuickItem *grabber = c ? c->mouseGrabberItem() : 0;
+ QQuickItem *grabber = c ? c->mouseGrabberItem() : nullptr;
bool stealThisEvent = _stealMouse;
if ((stealThisEvent || contains(localPos)) && (!grabber || !grabber->keepMouseGrab())) {
QMouseEvent mouseEvent(event->type(), localPos, event->windowPos(), event->screenPos(),
@@ -907,7 +944,7 @@ bool QQuickMultiPointTouchArea::sendMouseEvent(QMouseEvent *event)
default:
break;
}
- grabber = c ? c->mouseGrabberItem() : 0;
+ grabber = c ? c->mouseGrabberItem() : nullptr;
if (grabber && stealThisEvent && !grabber->keepMouseGrab() && grabber != this)
grabMouse();
@@ -954,7 +991,7 @@ bool QQuickMultiPointTouchArea::childMouseEventFilter(QQuickItem *receiver, QEve
bool QQuickMultiPointTouchArea::shouldFilter(QEvent *event)
{
QQuickWindow *c = window();
- QQuickItem *grabber = c ? c->mouseGrabberItem() : 0;
+ QQuickItem *grabber = c ? c->mouseGrabberItem() : nullptr;
bool disabledItem = grabber && !grabber->isEnabled();
bool stealThisEvent = _stealMouse;
bool containsPoint = false;
@@ -995,7 +1032,7 @@ QSGNode *QQuickMultiPointTouchArea::updatePaintNode(QSGNode *oldNode, UpdatePain
Q_UNUSED(data);
if (!qmlVisualTouchDebugging())
- return 0;
+ return nullptr;
QSGInternalRectangleNode *rectangle = static_cast<QSGInternalRectangleNode *>(oldNode);
if (!rectangle) rectangle = QQuickItemPrivate::get(this)->sceneGraphContext()->createInternalRectangleNode();
diff --git a/src/quick/items/qquickmultipointtoucharea_p.h b/src/quick/items/qquickmultipointtoucharea_p.h
index 64fe81563d..f1550b4ac6 100644
--- a/src/quick/items/qquickmultipointtoucharea_p.h
+++ b/src/quick/items/qquickmultipointtoucharea_p.h
@@ -86,16 +86,7 @@ class Q_AUTOTEST_EXPORT QQuickTouchPoint : public QObject
public:
QQuickTouchPoint(bool qmlDefined = true)
- : _id(0),
- _x(0.0), _y(0.0),
- _pressure(0.0),
- _rotation(0),
- _qmlDefined(qmlDefined),
- _inUse(false),
- _pressed(false),
- _startX(0.0), _startY(0.0),
- _previousX(0.0), _previousY(0.0),
- _sceneX(0.0), _sceneY(0.0)
+ : _qmlDefined(qmlDefined)
{}
int pointId() const { return _id; }
@@ -171,23 +162,23 @@ Q_SIGNALS:
private:
friend class QQuickMultiPointTouchArea;
- int _id;
- qreal _x;
- qreal _y;
- qreal _pressure;
- qreal _rotation;
+ int _id = 0;
+ qreal _x = 0.0;
+ qreal _y = 0.0;
+ qreal _pressure = 0.0;
+ qreal _rotation = 0;
QSizeF _ellipseDiameters;
QVector2D _velocity;
QRectF _area;
bool _qmlDefined;
- bool _inUse; //whether the point is currently in use (only valid when _qmlDefined == true)
- bool _pressed;
- qreal _startX;
- qreal _startY;
- qreal _previousX;
- qreal _previousY;
- qreal _sceneX;
- qreal _sceneY;
+ bool _inUse = false; //whether the point is currently in use (only valid when _qmlDefined == true)
+ bool _pressed = false;
+ qreal _startX = 0.0;
+ qreal _startY = 0.0;
+ qreal _previousX = 0.0;
+ qreal _previousY = 0.0;
+ qreal _sceneX = 0.0;
+ qreal _sceneY = 0.0;
QPointingDeviceUniqueId _uniqueId;
};
@@ -197,7 +188,7 @@ class QQuickGrabGestureEvent : public QObject
Q_PROPERTY(QQmlListProperty<QObject> touchPoints READ touchPoints)
Q_PROPERTY(qreal dragThreshold READ dragThreshold)
public:
- QQuickGrabGestureEvent() : _grab(false), _dragThreshold(QGuiApplication::styleHints()->startDragDistance()) {}
+ QQuickGrabGestureEvent() : _dragThreshold(QGuiApplication::styleHints()->startDragDistance()) {}
Q_INVOKABLE void grab() { _grab = true; }
bool wantsGrab() const { return _grab; }
@@ -209,7 +200,7 @@ public:
private:
friend class QQuickMultiPointTouchArea;
- bool _grab;
+ bool _grab = false;
qreal _dragThreshold;
QList<QObject*> _touchPoints;
};
@@ -224,7 +215,7 @@ class Q_AUTOTEST_EXPORT QQuickMultiPointTouchArea : public QQuickItem
Q_PROPERTY(bool mouseEnabled READ mouseEnabled WRITE setMouseEnabled NOTIFY mouseEnabledChanged)
public:
- QQuickMultiPointTouchArea(QQuickItem *parent=0);
+ QQuickMultiPointTouchArea(QQuickItem *parent=nullptr);
~QQuickMultiPointTouchArea();
int minimumTouchPoints() const;
@@ -235,7 +226,7 @@ public:
void setMouseEnabled(bool arg);
QQmlListProperty<QQuickTouchPoint> touchPoints() {
- return QQmlListProperty<QQuickTouchPoint>(this, 0, QQuickMultiPointTouchArea::touchPoint_append, QQuickMultiPointTouchArea::touchPoint_count, QQuickMultiPointTouchArea::touchPoint_at, 0);
+ return QQmlListProperty<QQuickTouchPoint>(this, nullptr, QQuickMultiPointTouchArea::touchPoint_append, QQuickMultiPointTouchArea::touchPoint_count, QQuickMultiPointTouchArea::touchPoint_at, nullptr);
}
static void touchPoint_append(QQmlListProperty<QQuickTouchPoint> *list, QQuickTouchPoint* touch) {
diff --git a/src/quick/items/qquickopenglinfo.cpp b/src/quick/items/qquickopenglinfo.cpp
index 7f5364031a..73f9c85e94 100644
--- a/src/quick/items/qquickopenglinfo.cpp
+++ b/src/quick/items/qquickopenglinfo.cpp
@@ -69,7 +69,7 @@ QT_BEGIN_NAMESPACE
*/
QQuickOpenGLInfo::QQuickOpenGLInfo(QQuickItem *item)
: QObject(item)
- , m_window(0)
+ , m_window(nullptr)
, m_majorVersion(2)
, m_minorVersion(0)
, m_profile(NoProfile)
@@ -150,12 +150,12 @@ QQuickOpenGLInfo *QQuickOpenGLInfo::qmlAttachedProperties(QObject *object)
{
if (QQuickItem *item = qobject_cast<QQuickItem *>(object))
return new QQuickOpenGLInfo(item);
- return 0;
+ return nullptr;
}
void QQuickOpenGLInfo::updateFormat()
{
- QOpenGLContext *context = 0;
+ QOpenGLContext *context = nullptr;
if (m_window)
context = m_window->openglContext();
QSurfaceFormat format = context ? context->format() : QSurfaceFormat::defaultFormat();
diff --git a/src/quick/items/qquickopenglshadereffect.cpp b/src/quick/items/qquickopenglshadereffect.cpp
index c3e0ba05bd..cad598d2c0 100644
--- a/src/quick/items/qquickopenglshadereffect.cpp
+++ b/src/quick/items/qquickopenglshadereffect.cpp
@@ -139,7 +139,7 @@ namespace {
expected = TypeIdentifier;
break;
}
- // Fall through.
+ Q_FALLTHROUGH();
case TypeIdentifier:
typeIndex = idIndex;
typeLength = idLength;
@@ -422,8 +422,9 @@ void QQuickOpenGLShaderEffectCommon::updateShader(QQuickItem *item,
d.specialType = UniformData::Opacity;
uniformData[Key::FragmentShader].append(d);
signalMappers[Key::FragmentShader].append(0);
- const int mappedId = 1 | (Key::FragmentShader << 16);
- auto mapper = new QtPrivate::MappedSlotObject([this, mappedId](){mappedPropertyChanged(mappedId);});
+ auto mapper = new QtPrivate::MappedSlotObject([this](){
+ mappedPropertyChanged(1 | (Key::FragmentShader << 16));
+ });
const char *sourceName = "source";
d.name = sourceName;
d.setValueFromProperty(item, itemMetaObject);
@@ -483,7 +484,7 @@ void QQuickOpenGLShaderEffectCommon::updateMaterial(QQuickOpenGLShaderEffectNode
if (d.specialType != UniformData::Sampler && d.specialType != UniformData::SamplerExternal)
continue;
QSGTextureProvider *oldProvider = material->textureProviders.at(index);
- QSGTextureProvider *newProvider = 0;
+ QSGTextureProvider *newProvider = nullptr;
QQuickItem *source = qobject_cast<QQuickItem *>(qvariant_cast<QObject *>(d.value));
if (source && source->isTextureProvider())
newProvider = source->textureProvider();
@@ -623,7 +624,7 @@ QQuickOpenGLShaderEffect::QQuickOpenGLShaderEffect(QQuickShaderEffect *item, QOb
, m_item(item)
, m_itemMetaObject(nullptr)
, m_meshResolution(1, 1)
- , m_mesh(0)
+ , m_mesh(nullptr)
, m_cullMode(QQuickShaderEffect::NoCulling)
, m_status(QQuickShaderEffect::Uncompiled)
, m_common(this, [this](int mappedId){this->propertyChanged(mappedId);})
@@ -712,7 +713,7 @@ void QQuickOpenGLShaderEffect::setMesh(const QVariant &mesh)
if (newMesh && newMesh == m_mesh)
return;
if (m_mesh)
- disconnect(m_mesh, SIGNAL(geometryChanged()), this, 0);
+ disconnect(m_mesh, SIGNAL(geometryChanged()), this, nullptr);
m_mesh = newMesh;
if (m_mesh) {
connect(m_mesh, SIGNAL(geometryChanged()), this, SLOT(updateGeometry()));
@@ -765,7 +766,7 @@ QString QQuickOpenGLShaderEffect::parseLog()
maybeUpdateShaders(true);
if (m_dirtyParseLog) {
- m_common.updateParseLog(m_mesh != 0);
+ m_common.updateParseLog(m_mesh != nullptr);
m_dirtyParseLog = false;
}
return m_common.parseLog;
@@ -837,7 +838,7 @@ QSGNode *QQuickOpenGLShaderEffect::handleUpdatePaintNode(QSGNode *oldNode, QQuic
if (m_common.attributes.isEmpty() || m_item->width() <= 0 || m_item->height() <= 0) {
if (node)
delete node;
- return 0;
+ return nullptr;
}
if (!node) {
@@ -896,7 +897,7 @@ QSGNode *QQuickOpenGLShaderEffect::handleUpdatePaintNode(QSGNode *oldNode, QQuic
bool geometryUsesTextureSubRect = false;
if (m_supportsAtlasTextures && material->textureProviders.size() == 1) {
QSGTextureProvider *provider = material->textureProviders.at(0);
- if (provider->texture()) {
+ if (provider && provider->texture()) {
srcRect = provider->texture()->normalizedTextureSubRect();
geometryUsesTextureSubRect = true;
}
@@ -913,7 +914,7 @@ QSGNode *QQuickOpenGLShaderEffect::handleUpdatePaintNode(QSGNode *oldNode, QQuic
}
if (m_dirtyMesh) {
- node->setGeometry(0);
+ node->setGeometry(nullptr);
m_dirtyMesh = false;
m_dirtyGeometry = true;
}
@@ -934,7 +935,7 @@ QSGNode *QQuickOpenGLShaderEffect::handleUpdatePaintNode(QSGNode *oldNode, QQuic
emit m_item->statusChanged();
}
delete node;
- return 0;
+ return nullptr;
}
geometry = mesh->updateGeometry(geometry, m_common.attributes.count(), posIndex, srcRect, rect);
diff --git a/src/quick/items/qquickopenglshadereffect_p.h b/src/quick/items/qquickopenglshadereffect_p.h
index f602bd8b8e..a15d85bff3 100644
--- a/src/quick/items/qquickopenglshadereffect_p.h
+++ b/src/quick/items/qquickopenglshadereffect_p.h
@@ -120,8 +120,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickOpenGLShaderEffect : public QObject
Q_OBJECT
public:
- QQuickOpenGLShaderEffect(QQuickShaderEffect *item, QObject *parent = 0);
- ~QQuickOpenGLShaderEffect();
+ QQuickOpenGLShaderEffect(QQuickShaderEffect *item, QObject *parent = nullptr);
+ ~QQuickOpenGLShaderEffect() override;
QByteArray fragmentShader() const { return m_common.source.sourceCode[Key::FragmentShader]; }
void setFragmentShader(const QByteArray &code);
diff --git a/src/quick/items/qquickopenglshadereffectnode.cpp b/src/quick/items/qquickopenglshadereffectnode.cpp
index a6431135eb..d51419a275 100644
--- a/src/quick/items/qquickopenglshadereffectnode.cpp
+++ b/src/quick/items/qquickopenglshadereffectnode.cpp
@@ -111,7 +111,7 @@ void QQuickCustomMaterialShader::updateState(const RenderState &state, QSGMateri
{
typedef QQuickOpenGLShaderEffectMaterial::UniformData UniformData;
- Q_ASSERT(newEffect != 0);
+ Q_ASSERT(newEffect != nullptr);
QQuickOpenGLShaderEffectMaterial *material = static_cast<QQuickOpenGLShaderEffectMaterial *>(newEffect);
if (!material->m_emittedLogChanged && material->m_node) {
@@ -239,7 +239,7 @@ void QQuickCustomMaterialShader::updateState(const RenderState &state, QSGMateri
functions->glActiveTexture(GL_TEXTURE0);
const QQuickOpenGLShaderEffectMaterial *oldMaterial = static_cast<const QQuickOpenGLShaderEffectMaterial *>(oldEffect);
- if (oldEffect == 0 || material->cullMode != oldMaterial->cullMode) {
+ if (oldEffect == nullptr || material->cullMode != oldMaterial->cullMode) {
switch (material->cullMode) {
case QQuickShaderEffect::FrontFaceCulling:
functions->glEnable(GL_CULL_FACE);
diff --git a/src/quick/items/qquickopenglshadereffectnode_p.h b/src/quick/items/qquickopenglshadereffectnode_p.h
index 68eece7660..7c75bb3126 100644
--- a/src/quick/items/qquickopenglshadereffectnode_p.h
+++ b/src/quick/items/qquickopenglshadereffectnode_p.h
@@ -109,7 +109,7 @@ public:
}
};
- explicit QQuickOpenGLShaderEffectMaterial(QQuickOpenGLShaderEffectNode *node = 0);
+ explicit QQuickOpenGLShaderEffectMaterial(QQuickOpenGLShaderEffectNode *node = nullptr);
QSGMaterialType *type() const override;
QSGMaterialShader *createShader() const override;
int compare(const QSGMaterial *other) const override;
@@ -149,7 +149,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickOpenGLShaderEffectNode : public QObject, publ
Q_OBJECT
public:
QQuickOpenGLShaderEffectNode();
- virtual ~QQuickOpenGLShaderEffectNode();
+ ~QQuickOpenGLShaderEffectNode() override;
void preprocess() override;
diff --git a/src/quick/items/qquickpainteditem.cpp b/src/quick/items/qquickpainteditem.cpp
index 34d71f00e8..57848919f3 100644
--- a/src/quick/items/qquickpainteditem.cpp
+++ b/src/quick/items/qquickpainteditem.cpp
@@ -53,7 +53,7 @@ class QQuickPaintedItemTextureProvider : public QSGTextureProvider
{
public:
QSGPainterNode *node;
- QSGTexture *texture() const override { return node ? node->texture() : 0; }
+ QSGTexture *texture() const override { return node ? node->texture() : nullptr; }
void fireTextureChanged() { emit textureChanged(); }
};
@@ -133,12 +133,12 @@ QQuickPaintedItemPrivate::QQuickPaintedItemPrivate()
, contentsScale(1.0)
, fillColor(Qt::transparent)
, renderTarget(QQuickPaintedItem::Image)
- , performanceHints(0)
+ , performanceHints(nullptr)
, opaquePainting(false)
, antialiasing(false)
, mipmap(false)
- , textureProvider(0)
- , node(0)
+ , textureProvider(nullptr)
+ , node(nullptr)
{
}
@@ -566,10 +566,10 @@ QSGNode *QQuickPaintedItem::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeDat
if (width() <= 0 || height() <= 0) {
delete oldNode;
if (d->textureProvider) {
- d->textureProvider->node = 0;
+ d->textureProvider->node = nullptr;
d->textureProvider->fireTextureChanged();
}
- return 0;
+ return nullptr;
}
QSGPainterNode *node = static_cast<QSGPainterNode *>(oldNode);
@@ -628,17 +628,17 @@ void QQuickPaintedItem::releaseResources()
Q_D(QQuickPaintedItem);
if (d->textureProvider) {
QQuickWindowQObjectCleanupJob::schedule(window(), d->textureProvider);
- d->textureProvider = 0;
+ d->textureProvider = nullptr;
}
- d->node = 0; // Managed by the scene graph, just clear the pointer.
+ d->node = nullptr; // Managed by the scene graph, just clear the pointer.
}
void QQuickPaintedItem::invalidateSceneGraph()
{
Q_D(QQuickPaintedItem);
delete d->textureProvider;
- d->textureProvider = 0;
- d->node = 0; // Managed by the scene graph, just clear the pointer
+ d->textureProvider = nullptr;
+ d->node = nullptr; // Managed by the scene graph, just clear the pointer
}
/*!
@@ -666,7 +666,7 @@ QSGTextureProvider *QQuickPaintedItem::textureProvider() const
QQuickWindow *w = window();
if (!w || !w->openglContext() || QThread::currentThread() != w->openglContext()->thread()) {
qWarning("QQuickPaintedItem::textureProvider: can only be queried on the rendering thread of an exposed window");
- return 0;
+ return nullptr;
}
#endif
if (!d->textureProvider)
@@ -675,6 +675,10 @@ QSGTextureProvider *QQuickPaintedItem::textureProvider() const
return d->textureProvider;
}
+
+/*!
+ \reimp
+*/
void QQuickPaintedItem::itemChange(ItemChange change, const ItemChangeData &value)
{
if (change == ItemDevicePixelRatioHasChanged)
diff --git a/src/quick/items/qquickpainteditem.h b/src/quick/items/qquickpainteditem.h
index 66a0ea83c9..b057f4295d 100644
--- a/src/quick/items/qquickpainteditem.h
+++ b/src/quick/items/qquickpainteditem.h
@@ -58,7 +58,7 @@ class Q_QUICK_EXPORT QQuickPaintedItem : public QQuickItem
public:
explicit QQuickPaintedItem(QQuickItem *parent = nullptr);
- virtual ~QQuickPaintedItem();
+ ~QQuickPaintedItem() override;
enum RenderTarget {
Image,
diff --git a/src/quick/items/qquickpathview.cpp b/src/quick/items/qquickpathview.cpp
index aac2b0296a..be94cdef42 100644
--- a/src/quick/items/qquickpathview.cpp
+++ b/src/quick/items/qquickpathview.cpp
@@ -66,7 +66,7 @@ const qreal MinimumFlickVelocity = 75.0;
static QQmlOpenMetaObjectType *qPathViewAttachedType = nullptr;
QQuickPathViewAttached::QQuickPathViewAttached(QObject *parent)
-: QObject(parent), m_percent(-1), m_view(0), m_onPath(false), m_isCurrent(false)
+: QObject(parent), m_percent(-1), m_view(nullptr), m_onPath(false), m_isCurrent(false)
{
if (qPathViewAttachedType) {
m_metaobject = new QQmlOpenMetaObject(this, qPathViewAttachedType);
@@ -129,7 +129,7 @@ QQuickItem *QQuickPathViewPrivate::getItem(int modelIndex, qreal z, bool async)
requestedIndex = modelIndex;
requestedZ = z;
inRequest = true;
- QObject *object = model->object(modelIndex, async);
+ QObject *object = model->object(modelIndex, async ? QQmlIncubator::Asynchronous : QQmlIncubator::AsynchronousIfNested);
QQuickItem *item = qmlobject_cast<QQuickItem*>(object);
if (!item) {
if (object) {
diff --git a/src/quick/items/qquickpincharea.cpp b/src/quick/items/qquickpincharea.cpp
index 476acd3a3e..7ae0f9b7e3 100644
--- a/src/quick/items/qquickpincharea.cpp
+++ b/src/quick/items/qquickpincharea.cpp
@@ -151,7 +151,7 @@ QT_BEGIN_NAMESPACE
*/
QQuickPinch::QQuickPinch()
- : m_target(0), m_minScale(1.0), m_maxScale(1.0)
+ : m_target(nullptr), m_minScale(1.0), m_maxScale(1.0)
, m_minRotation(0.0), m_maxRotation(0.0)
, m_axis(NoDrag), m_xmin(-FLT_MAX), m_xmax(FLT_MAX)
, m_ymin(-FLT_MAX), m_ymax(FLT_MAX), m_active(false)
@@ -644,7 +644,8 @@ bool QQuickPinchArea::childMouseEventFilter(QQuickItem *i, QEvent *e)
return QQuickItem::childMouseEventFilter(i, e);
switch (e->type()) {
case QEvent::TouchBegin:
- clearPinch(); // fall through
+ clearPinch();
+ Q_FALLTHROUGH();
case QEvent::TouchUpdate: {
QTouchEvent *touch = static_cast<QTouchEvent*>(e);
d->touchPoints.clear();
diff --git a/src/quick/items/qquickpincharea_p.h b/src/quick/items/qquickpincharea_p.h
index 2363f1e2d4..8eff53e6dc 100644
--- a/src/quick/items/qquickpincharea_p.h
+++ b/src/quick/items/qquickpincharea_p.h
@@ -84,7 +84,7 @@ public:
void resetTarget() {
if (!m_target)
return;
- m_target = 0;
+ m_target = nullptr;
Q_EMIT targetChanged();
}
@@ -270,7 +270,7 @@ class Q_AUTOTEST_EXPORT QQuickPinchArea : public QQuickItem
Q_PROPERTY(QQuickPinch *pinch READ pinch CONSTANT)
public:
- QQuickPinchArea(QQuickItem *parent=0);
+ QQuickPinchArea(QQuickItem *parent=nullptr);
~QQuickPinchArea();
bool isEnabled() const;
diff --git a/src/quick/items/qquickpositioners.cpp b/src/quick/items/qquickpositioners.cpp
index e752e2538f..493db51666 100644
--- a/src/quick/items/qquickpositioners.cpp
+++ b/src/quick/items/qquickpositioners.cpp
@@ -69,7 +69,7 @@ void QQuickBasePositionerPrivate::unwatchChanges(QQuickItem* other)
QQuickBasePositioner::PositionedItem::PositionedItem(QQuickItem *i)
: item(i)
- , transitionableItem(0)
+ , transitionableItem(nullptr)
, index(-1)
, isNew(false)
, isVisible(true)
@@ -203,7 +203,7 @@ void QQuickBasePositioner::setSpacing(qreal s)
QQuickTransition *QQuickBasePositioner::populate() const
{
Q_D(const QQuickBasePositioner);
- return d->transitioner ? d->transitioner->populateTransition : 0;
+ return d->transitioner ? d->transitioner->populateTransition : nullptr;
}
void QQuickBasePositioner::setPopulate(QQuickTransition *transition)
@@ -220,7 +220,7 @@ void QQuickBasePositioner::setPopulate(QQuickTransition *transition)
QQuickTransition *QQuickBasePositioner::move() const
{
Q_D(const QQuickBasePositioner);
- return d->transitioner ? d->transitioner->displacedTransition : 0;
+ return d->transitioner ? d->transitioner->displacedTransition : nullptr;
}
void QQuickBasePositioner::setMove(QQuickTransition *mt)
@@ -238,7 +238,7 @@ void QQuickBasePositioner::setMove(QQuickTransition *mt)
QQuickTransition *QQuickBasePositioner::add() const
{
Q_D(const QQuickBasePositioner);
- return d->transitioner ? d->transitioner->addTransition : 0;
+ return d->transitioner ? d->transitioner->addTransition : nullptr;
}
void QQuickBasePositioner::setAdd(QQuickTransition *add)
@@ -460,15 +460,15 @@ void QQuickBasePositioner::updateAttachedProperties(QQuickPositionerAttached *sp
// be changed to run only when there are attached properties present. This
// could be a flag in the positioner that is set by the attached property
// constructor.
- QQuickPositionerAttached *prevLastProperty = 0;
- QQuickPositionerAttached *lastProperty = 0;
+ QQuickPositionerAttached *prevLastProperty = nullptr;
+ QQuickPositionerAttached *lastProperty = nullptr;
for (int ii = 0; ii < positionedItems.count(); ++ii) {
const PositionedItem &child = positionedItems.at(ii);
if (!child.item)
continue;
- QQuickPositionerAttached *property = 0;
+ QQuickPositionerAttached *property = nullptr;
if (specificProperty) {
if (specificPropertyOwner == child.item) {
@@ -503,7 +503,7 @@ void QQuickBasePositioner::updateAttachedProperties(QQuickPositionerAttached *sp
if (!child.item)
continue;
- QQuickPositionerAttached *property = 0;
+ QQuickPositionerAttached *property = nullptr;
if (specificProperty) {
if (specificPropertyOwner == child.item) {
diff --git a/src/quick/items/qquickpositioners_p.h b/src/quick/items/qquickpositioners_p.h
index ce583aefe8..94a737e1f1 100644
--- a/src/quick/items/qquickpositioners_p.h
+++ b/src/quick/items/qquickpositioners_p.h
@@ -132,7 +132,7 @@ public:
static QQuickPositionerAttached *qmlAttachedProperties(QObject *obj);
- void updateAttachedProperties(QQuickPositionerAttached *specificProperty = 0, QQuickItem *specificPropertyOwner = 0) const;
+ void updateAttachedProperties(QQuickPositionerAttached *specificProperty = nullptr, QQuickItem *specificPropertyOwner = nullptr) const;
qreal padding() const;
void setPadding(qreal padding);
@@ -231,7 +231,7 @@ class Q_AUTOTEST_EXPORT QQuickColumn : public QQuickBasePositioner
{
Q_OBJECT
public:
- QQuickColumn(QQuickItem *parent=0);
+ QQuickColumn(QQuickItem *parent=nullptr);
protected:
void doPositioning(QSizeF *contentSize) override;
@@ -247,7 +247,7 @@ class Q_AUTOTEST_EXPORT QQuickRow: public QQuickBasePositioner
Q_PROPERTY(Qt::LayoutDirection layoutDirection READ layoutDirection WRITE setLayoutDirection NOTIFY layoutDirectionChanged)
Q_PROPERTY(Qt::LayoutDirection effectiveLayoutDirection READ effectiveLayoutDirection NOTIFY effectiveLayoutDirectionChanged)
public:
- QQuickRow(QQuickItem *parent=0);
+ QQuickRow(QQuickItem *parent=nullptr);
Qt::LayoutDirection layoutDirection() const;
void setLayoutDirection (Qt::LayoutDirection);
@@ -281,7 +281,7 @@ class Q_AUTOTEST_EXPORT QQuickGrid : public QQuickBasePositioner
Q_PROPERTY(VAlignment verticalItemAlignment READ vItemAlign WRITE setVItemAlign NOTIFY verticalAlignmentChanged REVISION 1)
public:
- QQuickGrid(QQuickItem *parent=0);
+ QQuickGrid(QQuickItem *parent=nullptr);
int rows() const { return m_rows; }
void setRows(const int rows);
@@ -360,7 +360,7 @@ class Q_AUTOTEST_EXPORT QQuickFlow: public QQuickBasePositioner
Q_PROPERTY(Qt::LayoutDirection layoutDirection READ layoutDirection WRITE setLayoutDirection NOTIFY layoutDirectionChanged)
Q_PROPERTY(Qt::LayoutDirection effectiveLayoutDirection READ effectiveLayoutDirection NOTIFY effectiveLayoutDirectionChanged)
public:
- QQuickFlow(QQuickItem *parent=0);
+ QQuickFlow(QQuickItem *parent=nullptr);
enum Flow { LeftToRight, TopToBottom };
Q_ENUM(Flow)
diff --git a/src/quick/items/qquickrectangle.cpp b/src/quick/items/qquickrectangle.cpp
index 9308553a79..3895f59ae1 100644
--- a/src/quick/items/qquickrectangle.cpp
+++ b/src/quick/items/qquickrectangle.cpp
@@ -414,7 +414,7 @@ void QQuickRectangle::setGradient(QQuickGradient *gradient)
void QQuickRectangle::resetGradient()
{
- setGradient(0);
+ setGradient(nullptr);
}
/*!
@@ -489,7 +489,7 @@ QSGNode *QQuickRectangle::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData
if (width() <= 0 || height() <= 0
|| (d->color.alpha() == 0 && (!d->pen || d->pen->width() == 0 || d->pen->color().alpha() == 0))) {
delete oldNode;
- return 0;
+ return nullptr;
}
QSGInternalRectangleNode *rectangle = static_cast<QSGInternalRectangleNode *>(oldNode);
diff --git a/src/quick/items/qquickrectangle_p.h b/src/quick/items/qquickrectangle_p.h
index 52f0bc975b..c07ad835fb 100644
--- a/src/quick/items/qquickrectangle_p.h
+++ b/src/quick/items/qquickrectangle_p.h
@@ -67,7 +67,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPen : public QObject
Q_PROPERTY(QColor color READ color WRITE setColor NOTIFY penChanged)
Q_PROPERTY(bool pixelAligned READ pixelAligned WRITE setPixelAligned NOTIFY penChanged)
public:
- QQuickPen(QObject *parent=0);
+ QQuickPen(QObject *parent=nullptr);
qreal width() const;
void setWidth(qreal w);
@@ -98,7 +98,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickGradientStop : public QObject
Q_PROPERTY(QColor color READ color WRITE setColor)
public:
- QQuickGradientStop(QObject *parent=0);
+ QQuickGradientStop(QObject *parent=nullptr);
qreal position() const;
void setPosition(qreal position);
@@ -122,8 +122,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickGradient : public QObject
Q_CLASSINFO("DefaultProperty", "stops")
public:
- QQuickGradient(QObject *parent=0);
- ~QQuickGradient();
+ QQuickGradient(QObject *parent=nullptr);
+ ~QQuickGradient() override;
QQmlListProperty<QQuickGradientStop> stops();
@@ -151,7 +151,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickRectangle : public QQuickItem
Q_PROPERTY(QQuickPen * border READ border CONSTANT)
Q_PROPERTY(qreal radius READ radius WRITE setRadius NOTIFY radiusChanged)
public:
- QQuickRectangle(QQuickItem *parent=0);
+ QQuickRectangle(QQuickItem *parent=nullptr);
QColor color() const;
void setColor(const QColor &);
diff --git a/src/quick/items/qquickrendercontrol.cpp b/src/quick/items/qquickrendercontrol.cpp
index 58b76fa862..49568db552 100644
--- a/src/quick/items/qquickrendercontrol.cpp
+++ b/src/quick/items/qquickrendercontrol.cpp
@@ -133,11 +133,11 @@ extern Q_GUI_EXPORT QImage qt_gl_read_framebuffer(const QSize &size, bool alpha_
\inmodule QtQuick
*/
-QSGContext *QQuickRenderControlPrivate::sg = 0;
+QSGContext *QQuickRenderControlPrivate::sg = nullptr;
QQuickRenderControlPrivate::QQuickRenderControlPrivate()
: initialized(0),
- window(0)
+ window(nullptr)
{
if (!sg) {
qAddPostRoutine(cleanup);
@@ -149,7 +149,7 @@ QQuickRenderControlPrivate::QQuickRenderControlPrivate()
void QQuickRenderControlPrivate::cleanup()
{
delete sg;
- sg = 0;
+ sg = nullptr;
}
/*!
@@ -173,7 +173,7 @@ QQuickRenderControl::~QQuickRenderControl()
invalidate();
if (d->window)
- QQuickWindowPrivate::get(d->window)->renderControl = 0;
+ QQuickWindowPrivate::get(d->window)->renderControl = nullptr;
// It is likely that the cleanup in windowDestroyed() is not called since
// the standard pattern is to destroy the rendercontrol before the QQuickWindow.
@@ -187,16 +187,16 @@ void QQuickRenderControlPrivate::windowDestroyed()
{
if (window) {
rc->invalidate();
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
+ QCoreApplication::sendPostedEvents(nullptr, QEvent::DeferredDelete);
delete QQuickWindowPrivate::get(window)->animationController;
- QQuickWindowPrivate::get(window)->animationController = 0;
+ QQuickWindowPrivate::get(window)->animationController = nullptr;
#if QT_CONFIG(quick_shadereffect) && QT_CONFIG(opengl)
QQuickOpenGLShaderEffectMaterial::cleanupMaterialCache();
#endif
- window = 0;
+ window = nullptr;
}
}
@@ -452,11 +452,11 @@ void QQuickRenderControlPrivate::maybeUpdate()
QWindow *QQuickRenderControl::renderWindowFor(QQuickWindow *win, QPoint *offset)
{
if (!win)
- return 0;
+ return nullptr;
QQuickRenderControl *rc = QQuickWindowPrivate::get(win)->renderControl;
if (rc)
return rc->renderWindow(offset);
- return 0;
+ return nullptr;
}
QT_END_NAMESPACE
diff --git a/src/quick/items/qquickrendercontrol.h b/src/quick/items/qquickrendercontrol.h
index a626216f84..8ec9b8aafc 100644
--- a/src/quick/items/qquickrendercontrol.h
+++ b/src/quick/items/qquickrendercontrol.h
@@ -56,7 +56,7 @@ class Q_QUICK_EXPORT QQuickRenderControl : public QObject
public:
explicit QQuickRenderControl(QObject *parent = nullptr);
- ~QQuickRenderControl();
+ ~QQuickRenderControl() override;
void prepareThread(QThread *targetThread);
void initialize(QOpenGLContext *gl);
diff --git a/src/quick/items/qquickrepeater.cpp b/src/quick/items/qquickrepeater.cpp
index 6fc4c0553a..b95fa3c410 100644
--- a/src/quick/items/qquickrepeater.cpp
+++ b/src/quick/items/qquickrepeater.cpp
@@ -50,7 +50,7 @@
QT_BEGIN_NAMESPACE
QQuickRepeaterPrivate::QQuickRepeaterPrivate()
- : model(0)
+ : model(nullptr)
, ownModel(false)
, dataSourceIsObject(false)
, delegateValidated(false)
@@ -216,8 +216,8 @@ void QQuickRepeater::setModel(const QVariant &m)
d->dataSource = model;
QObject *object = qvariant_cast<QObject*>(model);
d->dataSourceAsObject = object;
- d->dataSourceIsObject = object != 0;
- QQmlInstanceModel *vim = 0;
+ d->dataSourceIsObject = object != nullptr;
+ QQmlInstanceModel *vim = nullptr;
if (object && (vim = qobject_cast<QQmlInstanceModel *>(object))) {
if (d->ownModel) {
delete d->model;
@@ -288,7 +288,7 @@ QQmlComponent *QQuickRepeater::delegate() const
return dataModel->delegate();
}
- return 0;
+ return nullptr;
}
void QQuickRepeater::setDelegate(QQmlComponent *delegate)
@@ -339,7 +339,7 @@ QQuickItem *QQuickRepeater::itemAt(int index) const
Q_D(const QQuickRepeater);
if (index >= 0 && index < d->deletables.count())
return d->deletables[index];
- return 0;
+ return nullptr;
}
void QQuickRepeater::componentComplete()
@@ -374,9 +374,12 @@ void QQuickRepeater::clear()
if (complete)
emit itemRemoved(i, item);
d->model->release(item);
- item->setParentItem(0);
}
}
+ for (QQuickItem *item : qAsConst(d->deletables)) {
+ if (item)
+ item->setParentItem(nullptr);
+ }
}
d->deletables.clear();
d->itemCount = 0;
@@ -401,7 +404,7 @@ void QQuickRepeater::regenerate()
void QQuickRepeaterPrivate::requestItems()
{
for (int i = 0; i < itemCount; i++) {
- QObject *object = model->object(i, false);
+ QObject *object = model->object(i, QQmlIncubator::AsynchronousIfNested);
if (object)
model->release(object);
}
@@ -410,7 +413,7 @@ void QQuickRepeaterPrivate::requestItems()
void QQuickRepeater::createdItem(int index, QObject *)
{
Q_D(QQuickRepeater);
- QObject *object = d->model->object(index, false);
+ QObject *object = d->model->object(index, QQmlIncubator::AsynchronousIfNested);
QQuickItem *item = qmlobject_cast<QQuickItem*>(object);
emit itemAdded(index, item);
}
@@ -479,7 +482,7 @@ void QQuickRepeater::modelUpdated(const QQmlChangeSet &changeSet, bool reset)
emit itemRemoved(index, item);
if (item) {
d->model->release(item);
- item->setParentItem(0);
+ item->setParentItem(nullptr);
}
--d->itemCount;
}
@@ -495,13 +498,20 @@ void QQuickRepeater::modelUpdated(const QQmlChangeSet &changeSet, bool reset)
QQuickItem *stackBefore = index + items.count() < d->deletables.count()
? d->deletables.at(index + items.count())
: this;
- for (int i = index; i < index + items.count(); ++i)
- d->deletables.at(i)->stackBefore(stackBefore);
+ if (stackBefore) {
+ for (int i = index; i < index + items.count(); ++i) {
+ if (i < d->deletables.count()) {
+ QPointer<QQuickItem> item = d->deletables.at(i);
+ if (item)
+ item->stackBefore(stackBefore);
+ }
+ }
+ }
} else for (int i = 0; i < insert.count; ++i) {
int modelIndex = index + i;
++d->itemCount;
- d->deletables.insert(modelIndex, 0);
- QObject *object = d->model->object(modelIndex, false);
+ d->deletables.insert(modelIndex, nullptr);
+ QObject *object = d->model->object(modelIndex, QQmlIncubator::AsynchronousIfNested);
if (object)
d->model->release(object);
}
diff --git a/src/quick/items/qquickrepeater_p.h b/src/quick/items/qquickrepeater_p.h
index b630999547..dbe3cd0c55 100644
--- a/src/quick/items/qquickrepeater_p.h
+++ b/src/quick/items/qquickrepeater_p.h
@@ -53,6 +53,10 @@
#include "qquickitem.h"
+#include <private/qtquickglobal_p.h>
+
+QT_REQUIRE_CONFIG(quick_repeater);
+
QT_BEGIN_NAMESPACE
class QQmlChangeSet;
@@ -68,7 +72,7 @@ class Q_AUTOTEST_EXPORT QQuickRepeater : public QQuickItem
Q_CLASSINFO("DefaultProperty", "delegate")
public:
- QQuickRepeater(QQuickItem *parent=0);
+ QQuickRepeater(QQuickItem *parent=nullptr);
virtual ~QQuickRepeater();
QVariant model() const;
diff --git a/src/quick/items/qquickrepeater_p_p.h b/src/quick/items/qquickrepeater_p_p.h
index 64380688c9..942f428904 100644
--- a/src/quick/items/qquickrepeater_p_p.h
+++ b/src/quick/items/qquickrepeater_p_p.h
@@ -56,6 +56,8 @@
#include <QtCore/qpointer.h>
+QT_REQUIRE_CONFIG(quick_repeater);
+
QT_BEGIN_NAMESPACE
class QQmlContext;
diff --git a/src/quick/items/qquickscalegrid_p_p.h b/src/quick/items/qquickscalegrid_p_p.h
index 7f6a31a7bd..5752f61e3f 100644
--- a/src/quick/items/qquickscalegrid_p_p.h
+++ b/src/quick/items/qquickscalegrid_p_p.h
@@ -71,7 +71,7 @@ class Q_AUTOTEST_EXPORT QQuickScaleGrid : public QObject
Q_PROPERTY(int bottom READ bottom WRITE setBottom NOTIFY borderChanged)
public:
- QQuickScaleGrid(QObject *parent=0);
+ QQuickScaleGrid(QObject *parent=nullptr);
~QQuickScaleGrid();
bool isNull() const;
diff --git a/src/quick/items/qquickscreen.cpp b/src/quick/items/qquickscreen.cpp
index 6a3eab957e..aea7e44a65 100644
--- a/src/quick/items/qquickscreen.cpp
+++ b/src/quick/items/qquickscreen.cpp
@@ -423,8 +423,8 @@ QScreen *QQuickScreenInfo::wrappedScreen() const
QQuickScreenAttached::QQuickScreenAttached(QObject* attachee)
: QQuickScreenInfo(attachee)
- , m_window(NULL)
- , m_updateMask(0)
+ , m_window(nullptr)
+ , m_updateMask(nullptr)
, m_updateMaskSet(false)
{
m_attachee = qobject_cast<QQuickItem*>(attachee);
@@ -475,7 +475,7 @@ void QQuickScreenAttached::windowChanged(QQuickWindow* c)
if (m_window)
disconnect(m_window, SIGNAL(screenChanged(QScreen*)), this, SLOT(screenChanged(QScreen*)));
m_window = c;
- screenChanged(c ? c->screen() : NULL);
+ screenChanged(c ? c->screen() : nullptr);
if (c)
connect(c, SIGNAL(screenChanged(QScreen*)), this, SLOT(screenChanged(QScreen*)));
}
diff --git a/src/quick/items/qquickshadereffect_p.h b/src/quick/items/qquickshadereffect_p.h
index 30bd018098..cabad930fc 100644
--- a/src/quick/items/qquickshadereffect_p.h
+++ b/src/quick/items/qquickshadereffect_p.h
@@ -91,7 +91,7 @@ public:
};
Q_ENUM(Status)
- QQuickShaderEffect(QQuickItem *parent = 0);
+ QQuickShaderEffect(QQuickItem *parent = nullptr);
QByteArray fragmentShader() const;
void setFragmentShader(const QByteArray &code);
diff --git a/src/quick/items/qquickshadereffectmesh_p.h b/src/quick/items/qquickshadereffectmesh_p.h
index f3ac956f60..5d6641429a 100644
--- a/src/quick/items/qquickshadereffectmesh_p.h
+++ b/src/quick/items/qquickshadereffectmesh_p.h
@@ -76,7 +76,7 @@ class QQuickShaderEffectMesh : public QObject
{
Q_OBJECT
public:
- QQuickShaderEffectMesh(QObject *parent = 0);
+ QQuickShaderEffectMesh(QObject *parent = nullptr);
virtual bool validateAttributes(const QVector<QByteArray> &attributes, int *posIndex) = 0;
// If 'geometry' != 0, 'attrCount' is the same as last time the function was called.
virtual QSGGeometry *updateGeometry(QSGGeometry *geometry, int attrCount, int posIndex,
@@ -94,7 +94,7 @@ class QQuickGridMesh : public QQuickShaderEffectMesh
Q_OBJECT
Q_PROPERTY(QSize resolution READ resolution WRITE setResolution NOTIFY resolutionChanged)
public:
- QQuickGridMesh(QObject *parent = 0);
+ QQuickGridMesh(QObject *parent = nullptr);
bool validateAttributes(const QVector<QByteArray> &attributes, int *posIndex) override;
QSGGeometry *updateGeometry(QSGGeometry *geometry, int attrCount, int posIndex,
const QRectF &srcRect, const QRectF &rect) override;
@@ -121,7 +121,7 @@ class QQuickBorderImageMesh : public QQuickShaderEffectMesh
Q_PROPERTY(TileMode horizontalTileMode READ horizontalTileMode WRITE setHorizontalTileMode NOTIFY horizontalTileModeChanged)
Q_PROPERTY(TileMode verticalTileMode READ verticalTileMode WRITE setVerticalTileMode NOTIFY verticalTileModeChanged)
public:
- QQuickBorderImageMesh(QObject *parent = 0);
+ QQuickBorderImageMesh(QObject *parent = nullptr);
bool validateAttributes(const QVector<QByteArray> &attributes, int *posIndex) override;
QSGGeometry *updateGeometry(QSGGeometry *geometry, int attrCount, int posIndex,
diff --git a/src/quick/items/qquickshadereffectsource.cpp b/src/quick/items/qquickshadereffectsource.cpp
index b4a45431c5..4782672858 100644
--- a/src/quick/items/qquickshadereffectsource.cpp
+++ b/src/quick/items/qquickshadereffectsource.cpp
@@ -56,7 +56,7 @@ class QQuickShaderEffectSourceTextureProvider : public QSGTextureProvider
Q_OBJECT
public:
QQuickShaderEffectSourceTextureProvider()
- : sourceTexture(0)
+ : sourceTexture(nullptr)
, mipmapFiltering(QSGTexture::None)
, filtering(QSGTexture::Nearest)
, horizontalWrap(QSGTexture::ClampToEdge)
@@ -183,10 +183,10 @@ public:
QQuickShaderEffectSource::QQuickShaderEffectSource(QQuickItem *parent)
: QQuickItem(parent)
- , m_provider(0)
- , m_texture(0)
+ , m_provider(nullptr)
+ , m_texture(nullptr)
, m_wrapMode(ClampToEdge)
- , m_sourceItem(0)
+ , m_sourceItem(nullptr)
, m_textureSize(0, 0)
, m_format(RGBA)
, m_samples(0)
@@ -246,7 +246,7 @@ QSGTextureProvider *QQuickShaderEffectSource::textureProvider() const
const QQuickItemPrivate *d = QQuickItemPrivate::get(this);
if (!d->window || !d->sceneGraphRenderContext() || QThread::currentThread() != d->sceneGraphRenderContext()->thread()) {
qWarning("QQuickShaderEffectSource::textureProvider: can only be queried on the rendering thread of an exposed window");
- return 0;
+ return nullptr;
}
if (!m_provider) {
@@ -334,8 +334,8 @@ void QQuickShaderEffectSource::setSourceItem(QQuickItem *item)
if (m_sourceItem) {
if (window() == m_sourceItem->window()
- || (window() == 0 && m_sourceItem->window())
- || (m_sourceItem->window() == 0 && window())) {
+ || (window() == nullptr && m_sourceItem->window())
+ || (m_sourceItem->window() == nullptr && window())) {
QQuickItemPrivate *d = QQuickItemPrivate::get(item);
// 'item' needs a window to get a scene graph node. It usually gets one through its
// parent, but if the source item is "inline" rather than a reference -- i.e.
@@ -350,7 +350,7 @@ void QQuickShaderEffectSource::setSourceItem(QQuickItem *item)
connect(m_sourceItem, SIGNAL(destroyed(QObject*)), this, SLOT(sourceItemDestroyed(QObject*)));
} else {
qWarning("ShaderEffectSource: sourceItem and ShaderEffectSource must both be children of the same window.");
- m_sourceItem = 0;
+ m_sourceItem = nullptr;
}
}
update();
@@ -361,7 +361,7 @@ void QQuickShaderEffectSource::sourceItemDestroyed(QObject *item)
{
Q_ASSERT(item == m_sourceItem);
Q_UNUSED(item);
- m_sourceItem = 0;
+ m_sourceItem = nullptr;
update();
emit sourceItemChanged();
}
@@ -662,8 +662,8 @@ void QQuickShaderEffectSource::releaseResources()
if (m_texture || m_provider) {
window()->scheduleRenderJob(new QQuickShaderEffectSourceCleanup(m_texture, m_provider),
QQuickWindow::AfterSynchronizingStage);
- m_texture = 0;
- m_provider = 0;
+ m_texture = nullptr;
+ m_provider = nullptr;
}
}
@@ -684,9 +684,9 @@ QSGNode *QQuickShaderEffectSource::updatePaintNode(QSGNode *oldNode, UpdatePaint
{
if (!m_sourceItem || m_sourceItem->width() <= 0 || m_sourceItem->height() <= 0) {
if (m_texture)
- m_texture->setItem(0);
+ m_texture->setItem(nullptr);
delete oldNode;
- return 0;
+ return nullptr;
}
ensureTexture();
@@ -745,7 +745,7 @@ QSGNode *QQuickShaderEffectSource::updatePaintNode(QSGNode *oldNode, UpdatePaint
// Don't create the paint node if we're not spanning any area
if (width() <= 0 || height() <= 0) {
delete oldNode;
- return 0;
+ return nullptr;
}
QSGInternalImageNode *node = static_cast<QSGInternalImageNode *>(oldNode);
@@ -779,8 +779,8 @@ void QQuickShaderEffectSource::invalidateSceneGraph()
delete m_texture;
if (m_provider)
delete m_provider;
- m_texture = 0;
- m_provider = 0;
+ m_texture = nullptr;
+ m_provider = nullptr;
}
void QQuickShaderEffectSource::itemChange(ItemChange change, const ItemChangeData &value)
diff --git a/src/quick/items/qquickshadereffectsource_p.h b/src/quick/items/qquickshadereffectsource_p.h
index 185c5179b6..d5bb33902a 100644
--- a/src/quick/items/qquickshadereffectsource_p.h
+++ b/src/quick/items/qquickshadereffectsource_p.h
@@ -113,8 +113,8 @@ public:
};
Q_ENUM(TextureMirroring)
- QQuickShaderEffectSource(QQuickItem *parent = 0);
- ~QQuickShaderEffectSource();
+ QQuickShaderEffectSource(QQuickItem *parent = nullptr);
+ ~QQuickShaderEffectSource() override;
WrapMode wrapMode() const;
void setWrapMode(WrapMode mode);
diff --git a/src/quick/items/qquicksprite.cpp b/src/quick/items/qquicksprite.cpp
index 8013c57938..99b1b1f430 100644
--- a/src/quick/items/qquicksprite.cpp
+++ b/src/quick/items/qquicksprite.cpp
@@ -100,7 +100,7 @@ QT_BEGIN_NAMESPACE
/*!
\qmlproperty int QtQuick::Sprite::frameDuration
- Duration of each frame of the animation. Values below 0 are invalid.
+ Duration of each frame of the animation in milliseconds. Values below 0 are invalid.
If frameRate is valid then it will be used to calculate the duration of the frames.
If not, and frameDuration is valid, then frameDuration will be used. Otherwise duration is used.
@@ -237,12 +237,12 @@ int QQuickSprite::variedDuration() const //Deals with precedence when multiple d
if (m_frameRate != unsetDuration) {
qreal fpms = (m_frameRate
- + (m_frameRateVariation * QRandomGenerator::getReal() * 2)
+ + (m_frameRateVariation * QRandomGenerator::global()->generateDouble() * 2)
- m_frameRateVariation) / 1000.0;
return qMax(qreal(0.0) , m_frames / fpms);
} else if (m_frameDuration != unsetDuration) {
int mspf = m_frameDuration
- + (m_frameDurationVariation * QRandomGenerator::getReal() * 2)
+ + (m_frameDurationVariation * QRandomGenerator::global()->generateDouble() * 2)
- m_frameDurationVariation;
return qMax(0, m_frames * mspf);
} else if (duration() >= 0) {
diff --git a/src/quick/items/qquicksprite_p.h b/src/quick/items/qquicksprite_p.h
index 2f7f6da5c0..8e119a80a9 100644
--- a/src/quick/items/qquicksprite_p.h
+++ b/src/quick/items/qquicksprite_p.h
@@ -88,8 +88,8 @@ class Q_QUICK_EXPORT QQuickSprite : public QQuickStochasticState
Q_PROPERTY(int frameDurationVariation READ frameDurationVariation WRITE setFrameDurationVariation NOTIFY frameDurationVariationChanged)
public:
- explicit QQuickSprite(QObject *parent = 0);
- ~QQuickSprite();
+ explicit QQuickSprite(QObject *parent = nullptr);
+ ~QQuickSprite() override;
QUrl source() const
{
diff --git a/src/quick/items/qquickspriteengine.cpp b/src/quick/items/qquickspriteengine.cpp
index 9deb223957..1fd15e61e3 100644
--- a/src/quick/items/qquickspriteengine.cpp
+++ b/src/quick/items/qquickspriteengine.cpp
@@ -544,7 +544,7 @@ void QQuickStochasticEngine::restart(int index)
if (m_addAdvance)
m_startTimes[index] += m_advanceTime.elapsed();
if (randomStart)
- m_startTimes[index] -= QRandomGenerator::bounded(m_duration.at(index));
+ m_startTimes[index] -= QRandomGenerator::global()->bounded(m_duration.at(index));
int time = m_duration.at(index) + m_startTimes.at(index);
for (int i=0; i<m_stateUpdates.count(); i++)
m_stateUpdates[i].second.removeAll(index);
@@ -558,13 +558,13 @@ void QQuickSpriteEngine::restart(int index) //Reimplemented to recognize and han
if (m_loaded && m_sprites.at(m_things.at(index))->frameSync()) {//Manually advanced
m_startTimes[index] = 0;
if (randomStart && m_sprites.at(m_things.at(index))->m_generatedCount)
- m_startTimes[index] += QRandomGenerator::bounded(m_sprites.at(m_things.at(index))->m_generatedCount);
+ m_startTimes[index] += QRandomGenerator::global()->bounded(m_sprites.at(m_things.at(index))->m_generatedCount);
} else {
m_startTimes[index] = m_timeOffset;
if (m_addAdvance)
m_startTimes[index] += m_advanceTime.elapsed();
if (randomStart)
- m_startTimes[index] -= QRandomGenerator::bounded(m_duration.at(index));
+ m_startTimes[index] -= QRandomGenerator::global()->bounded(m_duration.at(index));
int time = spriteDuration(index) + m_startTimes.at(index);
if (randomStart) {
int curTime = m_timeOffset + (m_addAdvance ? m_advanceTime.elapsed() : 0);
@@ -630,7 +630,7 @@ int QQuickStochasticEngine::nextState(int curState, int curThing)
int nextIdx = -1;
int goalPath = goalSeek(curState, curThing);
if (goalPath == -1){//Random
- qreal r = QRandomGenerator::getReal();
+ qreal r = QRandomGenerator::global()->generateDouble();
qreal total = 0.0;
for (QVariantMap::const_iterator iter=m_states.at(curState)->m_to.constBegin();
iter!=m_states.at(curState)->m_to.constEnd(); ++iter)
@@ -720,7 +720,7 @@ int QQuickStochasticEngine::goalSeek(int curIdx, int spriteIdx, int dist)
if (options.count()==1)
return *(options.begin());
int option = -1;
- qreal r = QRandomGenerator::getReal();
+ qreal r = QRandomGenerator::global()->generateDouble();
qreal total = 0;
for (QSet<int>::const_iterator iter=options.constBegin();
iter!=options.constEnd(); ++iter)
diff --git a/src/quick/items/qquickspriteengine_p.h b/src/quick/items/qquickspriteengine_p.h
index a1c156fa94..da917683b6 100644
--- a/src/quick/items/qquickspriteengine_p.h
+++ b/src/quick/items/qquickspriteengine_p.h
@@ -81,11 +81,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickStochasticState : public QObject //Currently
Q_PROPERTY(QString name READ name WRITE setName NOTIFY nameChanged)
public:
- QQuickStochasticState(QObject* parent = 0)
+ QQuickStochasticState(QObject* parent = nullptr)
: QObject(parent)
- , m_duration(-1)
- , m_durationVariation(0)
- , m_randomStart(false)
{
}
@@ -113,7 +110,7 @@ public:
virtual int variedDuration() const
{
return qMax(qreal(0.0) , m_duration
- + (m_durationVariation * QRandomGenerator::bounded(2.0))
+ + (m_durationVariation * QRandomGenerator::global()->bounded(2.0))
- m_durationVariation);
}
@@ -179,11 +176,11 @@ public Q_SLOTS:
private:
QString m_name;
QVariantMap m_to;
- int m_duration;
- int m_durationVariation;
+ int m_duration = -1;
+ int m_durationVariation = 0;
friend class QQuickStochasticEngine;
- bool m_randomStart;
+ bool m_randomStart = false;
};
class Q_QUICK_PRIVATE_EXPORT QQuickStochasticEngine : public QObject
@@ -193,9 +190,9 @@ class Q_QUICK_PRIVATE_EXPORT QQuickStochasticEngine : public QObject
Q_PROPERTY(QString globalGoal READ globalGoal WRITE setGlobalGoal NOTIFY globalGoalChanged)
Q_PROPERTY(QQmlListProperty<QQuickStochasticState> states READ states)
public:
- explicit QQuickStochasticEngine(QObject *parent = 0);
- QQuickStochasticEngine(const QList<QQuickStochasticState*> &states, QObject *parent = 0);
- ~QQuickStochasticEngine();
+ explicit QQuickStochasticEngine(QObject *parent = nullptr);
+ QQuickStochasticEngine(const QList<QQuickStochasticState*> &states, QObject *parent = nullptr);
+ ~QQuickStochasticEngine() override;
QQmlListProperty<QQuickStochasticState> states()
{
@@ -270,9 +267,9 @@ class Q_QUICK_PRIVATE_EXPORT QQuickSpriteEngine : public QQuickStochasticEngine
Q_OBJECT
Q_PROPERTY(QQmlListProperty<QQuickSprite> sprites READ sprites)
public:
- explicit QQuickSpriteEngine(QObject *parent = 0);
- QQuickSpriteEngine(const QList<QQuickSprite*> &sprites, QObject *parent = 0);
- ~QQuickSpriteEngine();
+ explicit QQuickSpriteEngine(QObject *parent = nullptr);
+ QQuickSpriteEngine(const QList<QQuickSprite*> &sprites, QObject *parent = nullptr);
+ ~QQuickSpriteEngine() override;
QQmlListProperty<QQuickSprite> sprites()
{
return QQmlListProperty<QQuickSprite>(this, m_sprites);
@@ -303,7 +300,7 @@ public:
QImage assembledImage(int maxSize = 2048);
private:
- int pseudospriteProgress(int, int, int *rd = 0) const;
+ int pseudospriteProgress(int, int, int *rd = nullptr) const;
QList<QQuickSprite*> m_sprites;
bool m_startedImageAssembly;
bool m_loaded;
diff --git a/src/quick/items/qquickspritesequence.cpp b/src/quick/items/qquickspritesequence.cpp
index ae466aa482..0a39c09ebc 100644
--- a/src/quick/items/qquickspritesequence.cpp
+++ b/src/quick/items/qquickspritesequence.cpp
@@ -199,7 +199,7 @@ void QQuickSpriteSequence::createEngine()
if (!d->m_goalState.isEmpty())
d->m_spriteEngine->setGoal(d->m_spriteEngine->stateIndex(d->m_goalState));
} else {
- d->m_spriteEngine = 0;
+ d->m_spriteEngine = nullptr;
}
reset();
}
diff --git a/src/quick/items/qquickspritesequence_p.h b/src/quick/items/qquickspritesequence_p.h
index ffcefecaec..899ce79e0e 100644
--- a/src/quick/items/qquickspritesequence_p.h
+++ b/src/quick/items/qquickspritesequence_p.h
@@ -77,7 +77,7 @@ class Q_AUTOTEST_EXPORT QQuickSpriteSequence : public QQuickItem
Q_CLASSINFO("DefaultProperty", "sprites")
public:
- explicit QQuickSpriteSequence(QQuickItem *parent = 0);
+ explicit QQuickSpriteSequence(QQuickItem *parent = nullptr);
QQmlListProperty<QQuickSprite> sprites();
diff --git a/src/quick/items/qquickstateoperations.cpp b/src/quick/items/qquickstateoperations.cpp
index 386bb058b5..a85b9663d3 100644
--- a/src/quick/items/qquickstateoperations.cpp
+++ b/src/quick/items/qquickstateoperations.cpp
@@ -51,8 +51,8 @@ class QQuickParentChangePrivate : public QQuickStateOperationPrivate
{
Q_DECLARE_PUBLIC(QQuickParentChange)
public:
- QQuickParentChangePrivate() : target(0), parent(0), origParent(0), origStackBefore(0),
- rewindParent(0), rewindStackBefore(0) {}
+ QQuickParentChangePrivate() : target(nullptr), parent(nullptr), origParent(nullptr), origStackBefore(nullptr),
+ rewindParent(nullptr), rewindStackBefore(nullptr) {}
QQuickItem *target;
QPointer<QQuickItem> parent;
@@ -68,7 +68,7 @@ public:
QQmlNullableValue<QQmlScriptString> scaleString;
QQmlNullableValue<QQmlScriptString> rotationString;
- void doChange(QQuickItem *targetParent, QQuickItem *stackBefore = 0);
+ void doChange(QQuickItem *targetParent, QQuickItem *stackBefore = nullptr);
};
void QQuickParentChangePrivate::doChange(QQuickItem *targetParent, QQuickItem *stackBefore)
@@ -524,13 +524,13 @@ void QQuickParentChange::saveCurrentValues()
{
Q_D(QQuickParentChange);
if (!d->target) {
- d->rewindParent = 0;
- d->rewindStackBefore = 0;
+ d->rewindParent = nullptr;
+ d->rewindStackBefore = nullptr;
return;
}
d->rewindParent = d->target->parentItem();
- d->rewindStackBefore = 0;
+ d->rewindStackBefore = nullptr;
if (!d->rewindParent)
return;
@@ -588,7 +588,7 @@ class QQuickAnchorSetPrivate : public QObjectPrivate
Q_DECLARE_PUBLIC(QQuickAnchorSet)
public:
QQuickAnchorSetPrivate()
- : usedAnchors(0), resetAnchors(0)
+ : usedAnchors(nullptr), resetAnchors(nullptr)
{
}
@@ -771,7 +771,7 @@ class QQuickAnchorChangesPrivate : public QQuickStateOperationPrivate
{
public:
QQuickAnchorChangesPrivate()
- : target(0), anchorSet(new QQuickAnchorSet)
+ : target(nullptr), anchorSet(new QQuickAnchorSet)
{
}
@@ -855,7 +855,7 @@ QQuickAnchorChanges::ActionList QQuickAnchorChanges::actions()
Q_D(QQuickAnchorChanges);
//### ASSERT these are all 0?
d->leftBinding = d->rightBinding = d->hCenterBinding = d->topBinding
- = d->bottomBinding = d->vCenterBinding = d->baselineBinding = 0;
+ = d->bottomBinding = d->vCenterBinding = d->baselineBinding = nullptr;
d->leftProp = QQmlProperty(d->target, QLatin1String("anchors.left"));
d->rightProp = QQmlProperty(d->target, QLatin1String("anchors.right"));
@@ -1236,20 +1236,20 @@ void QQuickAnchorChanges::copyOriginals(QQuickStateActionEvent *other)
//clear old values from other
//### could this be generalized for all QQuickStateActionEvents, and called after copyOriginals?
- acp->leftBinding = 0;
- acp->rightBinding = 0;
- acp->hCenterBinding = 0;
- acp->topBinding = 0;
- acp->bottomBinding = 0;
- acp->vCenterBinding = 0;
- acp->baselineBinding = 0;
- acp->origLeftBinding = 0;
- acp->origRightBinding = 0;
- acp->origHCenterBinding = 0;
- acp->origTopBinding = 0;
- acp->origBottomBinding = 0;
- acp->origVCenterBinding = 0;
- acp->origBaselineBinding = 0;
+ acp->leftBinding = nullptr;
+ acp->rightBinding = nullptr;
+ acp->hCenterBinding = nullptr;
+ acp->topBinding = nullptr;
+ acp->bottomBinding = nullptr;
+ acp->vCenterBinding = nullptr;
+ acp->baselineBinding = nullptr;
+ acp->origLeftBinding = nullptr;
+ acp->origRightBinding = nullptr;
+ acp->origHCenterBinding = nullptr;
+ acp->origTopBinding = nullptr;
+ acp->origBottomBinding = nullptr;
+ acp->origVCenterBinding = nullptr;
+ acp->origBaselineBinding = nullptr;
saveCurrentValues();
}
diff --git a/src/quick/items/qquickstateoperations_p.h b/src/quick/items/qquickstateoperations_p.h
index d61ed294cb..e947b2213f 100644
--- a/src/quick/items/qquickstateoperations_p.h
+++ b/src/quick/items/qquickstateoperations_p.h
@@ -75,7 +75,7 @@ class Q_AUTOTEST_EXPORT QQuickParentChange : public QQuickStateOperation, public
Q_PROPERTY(QQmlScriptString scale READ scale WRITE setScale)
Q_PROPERTY(QQmlScriptString rotation READ rotation WRITE setRotation)
public:
- QQuickParentChange(QObject *parent=0);
+ QQuickParentChange(QObject *parent=nullptr);
~QQuickParentChange();
QQuickItem *object() const;
@@ -138,7 +138,7 @@ class Q_AUTOTEST_EXPORT QQuickAnchorSet : public QObject
Q_PROPERTY(QQmlScriptString baseline READ baseline WRITE setBaseline RESET resetBaseline)
public:
- QQuickAnchorSet(QObject *parent=0);
+ QQuickAnchorSet(QObject *parent=nullptr);
virtual ~QQuickAnchorSet();
QQmlScriptString left() const;
@@ -187,7 +187,7 @@ class Q_AUTOTEST_EXPORT QQuickAnchorChanges : public QQuickStateOperation, publi
Q_PROPERTY(QQuickAnchorSet *anchors READ anchors CONSTANT)
public:
- QQuickAnchorChanges(QObject *parent=0);
+ QQuickAnchorChanges(QObject *parent=nullptr);
~QQuickAnchorChanges();
ActionList actions() override;
diff --git a/src/quick/items/qquicktext.cpp b/src/quick/items/qquicktext.cpp
index 5f58f0cdde..383aa2b821 100644
--- a/src/quick/items/qquicktext.cpp
+++ b/src/quick/items/qquicktext.cpp
@@ -74,7 +74,7 @@ Q_DECLARE_LOGGING_CATEGORY(DBG_HOVER_TRACE)
const QChar QQuickTextPrivate::elideChar = QChar(0x2026);
QQuickTextPrivate::QQuickTextPrivate()
- : fontInfo(font), elideLayout(0), textLine(0), lineWidth(0)
+ : fontInfo(font), elideLayout(nullptr), textLine(nullptr), lineWidth(0)
, color(0xFF000000), linkColor(0xFF0000FF), styleColor(0xFF000000)
, lineCount(1), multilengthEos(-1)
, elideMode(QQuickText::ElideNone), hAlign(QQuickText::AlignLeft), vAlign(QQuickText::AlignTop)
@@ -103,7 +103,7 @@ QQuickTextPrivate::ExtraData::ExtraData()
, explicitRightPadding(false)
, explicitBottomPadding(false)
, lineHeight(1.0)
- , doc(0)
+ , doc(nullptr)
, minimumPixelSize(12)
, minimumPointSize(12)
, nbActiveDownloads(0)
@@ -124,7 +124,7 @@ void QQuickTextPrivate::init()
QQuickTextPrivate::~QQuickTextPrivate()
{
delete elideLayout;
- delete textLine; textLine = 0;
+ delete textLine; textLine = nullptr;
if (extra.isAllocated()) {
qDeleteAll(extra->imgTags);
@@ -478,7 +478,7 @@ void QQuickTextPrivate::updateSize()
}
QQuickTextLine::QQuickTextLine()
- : QObject(), m_line(0), m_height(0), m_lineOffset(0)
+ : QObject(), m_line(nullptr), m_height(0), m_lineOffset(0)
{
}
@@ -1110,7 +1110,7 @@ QRectF QQuickTextPrivate::setupTextLayout(qreal *const baseline)
layout.clearLayout();
} else {
delete elideLayout;
- elideLayout = 0;
+ elideLayout = nullptr;
}
QTextLine firstLine = visibleCount == 1 && elideLayout
@@ -1507,9 +1507,9 @@ QQuickText::~QQuickText()
\qmlproperty bool QtQuick::Text::font.kerning
\since 5.10
- Enables or disables the kerning OpenType feature when shaping the text. This may improve performance
- when creating or changing the text, at the expense of some cosmetic features. The default value
- is true.
+ Enables or disables the kerning OpenType feature when shaping the text. Disabling this may
+ improve performance when creating or changing the text, at the expense of some cosmetic
+ features. The default value is true.
\qml
Text { text: "OATS FLAVOUR WAY"; font.kerning: false }
@@ -2363,10 +2363,10 @@ QSGNode *QQuickText::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *data
if (d->text.isEmpty()) {
delete oldNode;
- return 0;
+ return nullptr;
}
- if (d->updateType != QQuickTextPrivate::UpdatePaintNode && oldNode != 0) {
+ if (d->updateType != QQuickTextPrivate::UpdatePaintNode && oldNode != nullptr) {
// Update done in preprocess() in the nodes
d->updateType = QQuickTextPrivate::UpdateNone;
return oldNode;
@@ -2376,7 +2376,7 @@ QSGNode *QQuickText::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *data
const qreal dy = QQuickTextUtil::alignedY(d->layedOutTextRect.height() + d->lineHeightOffset(), d->availableHeight(), d->vAlign) + topPadding();
- QQuickTextNode *node = 0;
+ QQuickTextNode *node = nullptr;
if (!oldNode)
node = new QQuickTextNode(this);
else
@@ -2918,14 +2918,14 @@ void QQuickText::invalidateFontCaches()
{
Q_D(QQuickText);
- if (d->richText && d->extra.isAllocated() && d->extra->doc != 0) {
+ if (d->richText && d->extra.isAllocated() && d->extra->doc != nullptr) {
QTextBlock block;
for (block = d->extra->doc->firstBlock(); block.isValid(); block = block.next()) {
- if (block.layout() != 0 && block.layout()->engine() != 0)
+ if (block.layout() != nullptr && block.layout()->engine() != nullptr)
block.layout()->engine()->resetFontEngineCache();
}
} else {
- if (d->layout.engine() != 0)
+ if (d->layout.engine() != nullptr)
d->layout.engine()->resetFontEngineCache();
}
}
diff --git a/src/quick/items/qquicktext_p.h b/src/quick/items/qquicktext_p.h
index 6c48dd86a9..15e989c13d 100644
--- a/src/quick/items/qquicktext_p.h
+++ b/src/quick/items/qquicktext_p.h
@@ -102,8 +102,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickText : public QQuickImplicitSizeItem
Q_PROPERTY(QSizeF advance READ advance NOTIFY contentSizeChanged REVISION 10)
public:
- QQuickText(QQuickItem *parent=0);
- ~QQuickText();
+ QQuickText(QQuickItem *parent=nullptr);
+ ~QQuickText() override;
enum HAlignment { AlignLeft = Qt::AlignLeft,
AlignRight = Qt::AlignRight,
@@ -289,7 +289,7 @@ Q_SIGNALS:
Q_REVISION(9) void fontInfoChanged();
protected:
- QQuickText(QQuickTextPrivate &dd, QQuickItem *parent = 0);
+ QQuickText(QQuickTextPrivate &dd, QQuickItem *parent = nullptr);
void mousePressEvent(QMouseEvent *event) override;
void mouseReleaseEvent(QMouseEvent *event) override;
diff --git a/src/quick/items/qquicktext_p_p.h b/src/quick/items/qquicktext_p_p.h
index 6fd0876a5f..b0b1492d57 100644
--- a/src/quick/items/qquicktext_p_p.h
+++ b/src/quick/items/qquicktext_p_p.h
@@ -83,7 +83,7 @@ public:
void setLineGeometry(QTextLine &line, qreal lineWidth, qreal &height);
int lineHeightOffset() const;
- QString elidedText(qreal lineWidth, const QTextLine &line, QTextLine *nextLine = 0) const;
+ QString elidedText(qreal lineWidth, const QTextLine &line, QTextLine *nextLine = nullptr) const;
void elideFormats(int start, int length, int offset, QVector<QTextLayout::FormatRange> *elidedFormats);
void clearFormats();
diff --git a/src/quick/items/qquicktextcontrol.cpp b/src/quick/items/qquicktextcontrol.cpp
index 874c02fc99..e3080dfe48 100644
--- a/src/quick/items/qquicktextcontrol.cpp
+++ b/src/quick/items/qquicktextcontrol.cpp
@@ -95,7 +95,7 @@ static QTextLine currentTextLine(const QTextCursor &cursor)
}
QQuickTextControlPrivate::QQuickTextControlPrivate()
- : doc(0),
+ : doc(nullptr),
#if QT_CONFIG(im)
preeditCursor(0),
#endif
diff --git a/src/quick/items/qquicktextcontrol_p.h b/src/quick/items/qquicktextcontrol_p.h
index 862a81af28..c99736a874 100644
--- a/src/quick/items/qquicktextcontrol_p.h
+++ b/src/quick/items/qquicktextcontrol_p.h
@@ -77,7 +77,7 @@ class Q_AUTOTEST_EXPORT QQuickTextControl : public QInputControl
Q_OBJECT
Q_DECLARE_PRIVATE(QQuickTextControl)
public:
- explicit QQuickTextControl(QTextDocument *doc, QObject *parent = 0);
+ explicit QQuickTextControl(QTextDocument *doc, QObject *parent = nullptr);
virtual ~QQuickTextControl();
QTextDocument *document() const;
diff --git a/src/quick/items/qquicktextedit.cpp b/src/quick/items/qquicktextedit.cpp
index 8f3a8998f5..352fc48970 100644
--- a/src/quick/items/qquicktextedit.cpp
+++ b/src/quick/items/qquicktextedit.cpp
@@ -139,7 +139,7 @@ namespace {
class RootNode : public QSGTransformNode
{
public:
- RootNode() : cursorNode(0), frameDecorationsNode(0)
+ RootNode() : cursorNode(nullptr), frameDecorationsNode(nullptr)
{ }
void resetFrameDecorations(QQuickTextNode* newNode)
@@ -358,9 +358,9 @@ QString QQuickTextEdit::text() const
\qmlproperty bool QtQuick::TextEdit::font.kerning
\since 5.10
- Enables or disables the kerning OpenType feature when shaping the text. This may improve performance
- when creating or changing the text, at the expense of some cosmetic features. The default value
- is true.
+ Enables or disables the kerning OpenType feature when shaping the text. Disabling this may
+ improve performance when creating or changing the text, at the expense of some cosmetic
+ features. The default value is true.
\qml
TextEdit { text: "OATS FLAVOUR WAY"; kerning: font.false }
@@ -1968,12 +1968,11 @@ void QQuickTextEdit::triggerPreprocess()
}
typedef QQuickTextEditPrivate::Node TextNode;
-typedef QList<TextNode*>::iterator TextNodeIterator;
+using TextNodeIterator = QQuickTextEditPrivate::TextNodeIterator;
-
-static bool comesBefore(TextNode* n1, TextNode* n2)
+static inline bool operator<(const TextNode &n1, const TextNode &n2)
{
- return n1->startPos() < n2->startPos();
+ return n1.startPos() < n2.startPos();
}
static inline void updateNodeTransform(QQuickTextNode* node, const QPointF &topLeft)
@@ -1992,12 +1991,12 @@ static inline void updateNodeTransform(QQuickTextNode* node, const QPointF &topL
void QQuickTextEdit::invalidateFontCaches()
{
Q_D(QQuickTextEdit);
- if (d->document == 0)
+ if (d->document == nullptr)
return;
QTextBlock block;
for (block = d->document->firstBlock(); block.isValid(); block = block.next()) {
- if (block.layout() != 0 && block.layout()->engine() != 0)
+ if (block.layout() != nullptr && block.layout()->engine() != nullptr)
block.layout()->engine()->resetFontEngineCache();
}
}
@@ -2015,7 +2014,7 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
Q_UNUSED(updatePaintNodeData);
Q_D(QQuickTextEdit);
- if (d->updateType != QQuickTextEditPrivate::UpdatePaintNode && oldNode != 0) {
+ if (d->updateType != QQuickTextEditPrivate::UpdatePaintNode && oldNode != nullptr) {
// Update done in preprocess() in the nodes
d->updateType = QQuickTextEditPrivate::UpdateNone;
return oldNode;
@@ -2026,13 +2025,12 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
if (!oldNode) {
// If we had any QQuickTextNode node references, they were deleted along with the root node
// But here we must delete the Node structures in textNodeMap
- qDeleteAll(d->textNodeMap);
d->textNodeMap.clear();
}
RootNode *rootNode = static_cast<RootNode *>(oldNode);
TextNodeIterator nodeIterator = d->textNodeMap.begin();
- while (nodeIterator != d->textNodeMap.end() && !(*nodeIterator)->dirty())
+ while (nodeIterator != d->textNodeMap.end() && !nodeIterator->dirty())
++nodeIterator;
QQuickTextNodeEngine engine;
@@ -2045,20 +2043,19 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
int firstDirtyPos = 0;
if (nodeIterator != d->textNodeMap.end()) {
- firstDirtyPos = (*nodeIterator)->startPos();
+ firstDirtyPos = nodeIterator->startPos();
do {
- rootNode->removeChildNode((*nodeIterator)->textNode());
- delete (*nodeIterator)->textNode();
- delete *nodeIterator;
+ rootNode->removeChildNode(nodeIterator->textNode());
+ delete nodeIterator->textNode();
nodeIterator = d->textNodeMap.erase(nodeIterator);
- } while (nodeIterator != d->textNodeMap.end() && (*nodeIterator)->dirty());
+ } while (nodeIterator != d->textNodeMap.end() && nodeIterator->dirty());
}
// FIXME: the text decorations could probably be handled separately (only updated for affected textFrames)
rootNode->resetFrameDecorations(d->createTextNode());
resetEngine(&frameDecorationsEngine, d->color, d->selectedTextColor, d->selectionColor);
- QQuickTextNode *node = 0;
+ QQuickTextNode *node = nullptr;
int currentNodeSize = 0;
int nodeStart = firstDirtyPos;
@@ -2068,7 +2065,8 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
rootNode->setMatrix(basePositionMatrix);
QPointF nodeOffset;
- TextNode *firstCleanNode = (nodeIterator != d->textNodeMap.end()) ? *nodeIterator : 0;
+ const TextNode firstCleanNode = (nodeIterator != d->textNodeMap.end()) ? *nodeIterator
+ : TextNode();
QList<QTextFrame *> frames;
frames.append(d->document->rootFrame());
@@ -2078,7 +2076,8 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
frames.append(textFrame->childFrames());
frameDecorationsEngine.addFrameDecorations(d->document, textFrame);
- if (textFrame->lastPosition() < firstDirtyPos || (firstCleanNode && textFrame->firstPosition() >= firstCleanNode->startPos()))
+ if (textFrame->lastPosition() < firstDirtyPos
+ || textFrame->firstPosition() >= firstCleanNode.startPos())
continue;
node = d->createTextNode();
resetEngine(&engine, d->color, d->selectedTextColor, d->selectionColor);
@@ -2118,8 +2117,8 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
engine.addTextBlock(d->document, block, -nodeOffset, d->color, QColor(), selectionStart(), selectionEnd() - 1);
currentNodeSize += block.length();
- if ((it.atEnd()) || (firstCleanNode && block.next().position() >= firstCleanNode->startPos())) // last node that needed replacing or last block of the frame
- break;
+ if ((it.atEnd()) || block.next().position() >= firstCleanNode.startPos())
+ break; // last node that needed replacing or last block of the frame
QList<int>::const_iterator lowerBound = std::lower_bound(frameBoundaries.constBegin(), frameBoundaries.constEnd(), block.next().position());
if (currentNodeSize > nodeBreakingSize || lowerBound == frameBoundaries.constEnd() || *lowerBound > nodeStart) {
@@ -2137,16 +2136,19 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
// Now prepend the frame decorations since we want them rendered first, with the text nodes and cursor in front.
rootNode->prependChildNode(rootNode->frameDecorationsNode);
- Q_ASSERT(nodeIterator == d->textNodeMap.end() || (*nodeIterator) == firstCleanNode);
+ Q_ASSERT(nodeIterator == d->textNodeMap.end()
+ || (nodeIterator->textNode() == firstCleanNode.textNode()
+ && nodeIterator->startPos() == firstCleanNode.startPos()));
// Update the position of the subsequent text blocks.
- if (firstCleanNode) {
- QPointF oldOffset = firstCleanNode->textNode()->matrix().map(QPointF(0,0));
- QPointF currentOffset = d->document->documentLayout()->blockBoundingRect(d->document->findBlock(firstCleanNode->startPos())).topLeft();
+ if (firstCleanNode.textNode() != nullptr) {
+ QPointF oldOffset = firstCleanNode.textNode()->matrix().map(QPointF(0,0));
+ QPointF currentOffset = d->document->documentLayout()->blockBoundingRect(
+ d->document->findBlock(firstCleanNode.startPos())).topLeft();
QPointF delta = currentOffset - oldOffset;
while (nodeIterator != d->textNodeMap.end()) {
- QMatrix4x4 transformMatrix = (*nodeIterator)->textNode()->matrix();
+ QMatrix4x4 transformMatrix = nodeIterator->textNode()->matrix();
transformMatrix.translate(delta.x(), delta.y());
- (*nodeIterator)->textNode()->setMatrix(transformMatrix);
+ nodeIterator->textNode()->setMatrix(transformMatrix);
++nodeIterator;
}
@@ -2154,11 +2156,11 @@ QSGNode *QQuickTextEdit::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *
// Since we iterate over blocks from different text frames that are potentially not sorted
// we need to ensure that our list of nodes is sorted again:
- std::sort(d->textNodeMap.begin(), d->textNodeMap.end(), &comesBefore);
+ std::sort(d->textNodeMap.begin(), d->textNodeMap.end());
}
- if (d->cursorComponent == 0) {
- QSGInternalRectangleNode* cursor = 0;
+ if (d->cursorComponent == nullptr) {
+ QSGInternalRectangleNode* cursor = nullptr;
if (!isReadOnly() && d->cursorVisible && d->control->cursorOn())
cursor = d->sceneGraphContext()->createInternalRectangleNode(d->control->cursorRect(), d->color);
rootNode->resetCursorNode(cursor);
@@ -2333,22 +2335,26 @@ void QQuickTextEdit::markDirtyNodesForRange(int start, int end, int charDelta)
if (start == end)
return;
- TextNode dummyNode(start, 0);
- TextNodeIterator it = std::lower_bound(d->textNodeMap.begin(), d->textNodeMap.end(), &dummyNode, &comesBefore);
+ TextNode dummyNode(start);
+
+ const TextNodeIterator textNodeMapBegin = d->textNodeMap.begin();
+ const TextNodeIterator textNodeMapEnd = d->textNodeMap.end();
+
+ TextNodeIterator it = std::lower_bound(textNodeMapBegin, textNodeMapEnd, dummyNode);
// qLowerBound gives us the first node past the start of the affected portion, rewind to the first node
// that starts at the last position before the edit position. (there might be several because of images)
- if (it != d->textNodeMap.begin()) {
+ if (it != textNodeMapBegin) {
--it;
- TextNode otherDummy((*it)->startPos(), 0);
- it = std::lower_bound(d->textNodeMap.begin(), d->textNodeMap.end(), &otherDummy, &comesBefore);
+ TextNode otherDummy(it->startPos());
+ it = std::lower_bound(textNodeMapBegin, textNodeMapEnd, otherDummy);
}
// mark the affected nodes as dirty
- while (it != d->textNodeMap.end()) {
- if ((*it)->startPos() <= end)
- (*it)->setDirty();
+ while (it != textNodeMapEnd) {
+ if (it->startPos() <= end)
+ it->setDirty();
else if (charDelta)
- (*it)->moveStartPos(charDelta);
+ it->moveStartPos(charDelta);
else
return;
++it;
@@ -2533,8 +2539,8 @@ void QQuickTextEdit::updateWholeDocument()
{
Q_D(QQuickTextEdit);
if (!d->textNodeMap.isEmpty()) {
- for (TextNode* node : qAsConst(d->textNodeMap))
- node->setDirty();
+ for (TextNode &node : d->textNodeMap)
+ node.setDirty();
}
polish();
@@ -2678,7 +2684,7 @@ void QQuickTextEditPrivate::handleFocusEvent(QFocusEvent *event)
void QQuickTextEditPrivate::addCurrentTextNodeToRoot(QQuickTextNodeEngine *engine, QSGTransformNode *root, QQuickTextNode *node, TextNodeIterator &it, int startPos)
{
engine->addToSceneGraph(node, QQuickText::Normal, QColor());
- it = textNodeMap.insert(it, new TextNode(startPos, node));
+ it = textNodeMap.insert(it, TextNode(startPos, node));
++it;
root->appendChildNode(node);
}
diff --git a/src/quick/items/qquicktextedit_p.h b/src/quick/items/qquicktextedit_p.h
index c883e39168..7a847ffeae 100644
--- a/src/quick/items/qquicktextedit_p.h
+++ b/src/quick/items/qquicktextedit_p.h
@@ -114,7 +114,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickTextEdit : public QQuickImplicitSizeItem
Q_PROPERTY(qreal tabStopDistance READ tabStopDistance WRITE setTabStopDistance NOTIFY tabStopDistanceChanged REVISION 10)
public:
- QQuickTextEdit(QQuickItem *parent=0);
+ QQuickTextEdit(QQuickItem *parent=nullptr);
enum HAlignment {
AlignLeft = Qt::AlignLeft,
@@ -384,7 +384,7 @@ private:
void invalidateFontCaches();
protected:
- QQuickTextEdit(QQuickTextEditPrivate &dd, QQuickItem *parent = 0);
+ QQuickTextEdit(QQuickTextEditPrivate &dd, QQuickItem *parent = nullptr);
void geometryChanged(const QRectF &newGeometry,
const QRectF &oldGeometry) override;
diff --git a/src/quick/items/qquicktextedit_p_p.h b/src/quick/items/qquicktextedit_p_p.h
index 09718cb49a..46d3d5ff6b 100644
--- a/src/quick/items/qquicktextedit_p_p.h
+++ b/src/quick/items/qquicktextedit_p_p.h
@@ -59,6 +59,8 @@
#include <QtCore/qlist.h>
#include <private/qlazilyallocated_p.h>
+#include <limits>
+
QT_BEGIN_NAMESPACE
class QTextLayout;
class QQuickTextDocumentWithImageResources;
@@ -74,7 +76,8 @@ public:
typedef QQuickTextEdit Public;
struct Node {
- explicit Node(int startPos, QQuickTextNode* node)
+ explicit Node(int startPos = std::numeric_limits<int>::max(),
+ QQuickTextNode *node = nullptr)
: m_startPos(startPos), m_node(node), m_dirty(false) { }
QQuickTextNode* textNode() const { return m_node; }
void moveStartPos(int delta) { Q_ASSERT(m_startPos + delta > 0); m_startPos += delta; }
@@ -87,7 +90,7 @@ public:
QQuickTextNode* m_node;
bool m_dirty;
};
- typedef QList<Node*>::iterator TextNodeIterator;
+ typedef QList<Node>::iterator TextNodeIterator;
struct ExtraData {
ExtraData();
@@ -109,8 +112,8 @@ public:
QQuickTextEditPrivate()
: color(QRgb(0xFF000000)), selectionColor(QRgb(0xFF000080)), selectedTextColor(QRgb(0xFFFFFFFF))
, textMargin(0.0), xoff(0), yoff(0)
- , font(sourceFont), cursorComponent(0), cursorItem(0), document(0), control(0)
- , quickDocument(0), lastSelectionStart(0), lastSelectionEnd(0), lineCount(0)
+ , font(sourceFont), cursorComponent(nullptr), cursorItem(nullptr), document(nullptr), control(nullptr)
+ , quickDocument(nullptr), lastSelectionStart(0), lastSelectionEnd(0), lineCount(0)
, hAlign(QQuickTextEdit::AlignLeft), vAlign(QQuickTextEdit::AlignTop)
, format(QQuickTextEdit::PlainText), wrapMode(QQuickTextEdit::NoWrap)
, renderType(QQuickTextUtil::textRenderType<QQuickTextEdit>())
@@ -128,11 +131,6 @@ public:
{
}
- ~QQuickTextEditPrivate()
- {
- qDeleteAll(textNodeMap);
- }
-
static QQuickTextEditPrivate *get(QQuickTextEdit *item) {
return static_cast<QQuickTextEditPrivate *>(QObjectPrivate::get(item)); }
@@ -186,7 +184,7 @@ public:
QQuickTextDocumentWithImageResources *document;
QQuickTextControl *control;
QQuickTextDocument *quickDocument;
- QList<Node*> textNodeMap;
+ QList<Node> textNodeMap;
int lastSelectionStart;
int lastSelectionEnd;
diff --git a/src/quick/items/qquicktextinput.cpp b/src/quick/items/qquicktextinput.cpp
index d516b6f30c..b19c13c5ee 100644
--- a/src/quick/items/qquicktextinput.cpp
+++ b/src/quick/items/qquicktextinput.cpp
@@ -384,9 +384,9 @@ QString QQuickTextInputPrivate::realText() const
\qmlproperty bool QtQuick::TextInput::font.kerning
\since 5.10
- Enables or disables the kerning OpenType feature when shaping the text. This may improve performance
- when creating or changing the text, at the expense of some cosmetic features. The default value
- is true.
+ Enables or disables the kerning OpenType feature when shaping the text. Disabling this may
+ improve performance when creating or changing the text, at the expense of some cosmetic
+ features. The default value is true.
\qml
TextInput { text: "OATS FLAVOUR WAY"; font.kerning: false }
@@ -1108,7 +1108,8 @@ void QQuickTextInputPrivate::checkIsValid()
Q_Q(QQuickTextInput);
ValidatorState state = hasAcceptableInput(m_text);
- m_validInput = state != InvalidInput;
+ if (!m_maskData)
+ m_validInput = state != InvalidInput;
if (state != AcceptableInput) {
if (m_acceptableInput) {
m_acceptableInput = false;
@@ -1862,7 +1863,7 @@ void QQuickTextInput::invalidateFontCaches()
{
Q_D(QQuickTextInput);
- if (d->m_textLayout.engine() != 0)
+ if (d->m_textLayout.engine() != nullptr)
d->m_textLayout.engine()->resetFontEngineCache();
}
@@ -1885,7 +1886,7 @@ QSGNode *QQuickTextInput::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData
Q_UNUSED(data);
Q_D(QQuickTextInput);
- if (d->updateType != QQuickTextInputPrivate::UpdatePaintNode && oldNode != 0) {
+ if (d->updateType != QQuickTextInputPrivate::UpdatePaintNode && oldNode != nullptr) {
// Update done in preprocess() in the nodes
d->updateType = QQuickTextInputPrivate::UpdateNone;
return oldNode;
@@ -1894,13 +1895,13 @@ QSGNode *QQuickTextInput::updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData
d->updateType = QQuickTextInputPrivate::UpdateNone;
QQuickTextNode *node = static_cast<QQuickTextNode *>(oldNode);
- if (node == 0)
+ if (node == nullptr)
node = new QQuickTextNode(this);
d->textNode = node;
- const bool showCursor = !isReadOnly() && d->cursorItem == 0 && d->cursorVisible && d->m_blinkStatus;
+ const bool showCursor = !isReadOnly() && d->cursorItem == nullptr && d->cursorVisible && d->m_blinkStatus;
- if (!d->textLayoutDirty && oldNode != 0) {
+ if (!d->textLayoutDirty && oldNode != nullptr) {
if (showCursor)
node->setCursor(cursorRectangle(), d->color);
else
@@ -3561,11 +3562,15 @@ bool QQuickTextInputPrivate::finishChange(int validateFromState, bool update, bo
#if QT_CONFIG(validator)
if (m_validator) {
QString textCopy = m_text;
+ if (m_maskData)
+ textCopy = maskString(0, m_text, true);
int cursorCopy = m_cursor;
QValidator::State state = m_validator->validate(textCopy, cursorCopy);
+ if (m_maskData)
+ textCopy = m_text;
m_validInput = state != QValidator::Invalid;
m_acceptableInput = state == QValidator::Acceptable;
- if (m_validInput) {
+ if (m_validInput && !m_maskData) {
if (m_text != textCopy) {
internalSetText(textCopy, cursorCopy);
return true;
@@ -3574,31 +3579,8 @@ bool QQuickTextInputPrivate::finishChange(int validateFromState, bool update, bo
}
}
#endif
-
- if (m_maskData) {
- m_validInput = true;
- if (m_text.length() != m_maxLength) {
- m_validInput = false;
- m_acceptableInput = false;
- } else {
- for (int i = 0; i < m_maxLength; ++i) {
- if (m_maskData[i].separator) {
- if (m_text.at(i) != m_maskData[i].maskChar) {
- m_validInput = false;
- m_acceptableInput = false;
- break;
- }
- } else {
- if (!isValidInput(m_text.at(i), m_maskData[i].maskChar)) {
- m_acceptableInput = false;
- if (m_text.at(i) != m_blank)
- m_validInput = false;
- break;
- }
- }
- }
- }
- }
+ if (m_maskData)
+ checkIsValid();
if (validateFromState >= 0 && wasValidInput && !m_validInput) {
if (m_transactions.count())
@@ -3846,7 +3828,7 @@ void QQuickTextInputPrivate::parseInputMask(const QString &maskFields)
if (maskFields.isEmpty() || delimiter == 0) {
if (m_maskData) {
delete [] m_maskData;
- m_maskData = 0;
+ m_maskData = nullptr;
m_maxLength = 32767;
internalSetText(QString());
}
diff --git a/src/quick/items/qquicktextinput_p.h b/src/quick/items/qquicktextinput_p.h
index b7d3fb00fa..c46a2f8128 100644
--- a/src/quick/items/qquicktextinput_p.h
+++ b/src/quick/items/qquicktextinput_p.h
@@ -115,7 +115,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickTextInput : public QQuickImplicitSizeItem
Q_PROPERTY(qreal bottomPadding READ bottomPadding WRITE setBottomPadding RESET resetBottomPadding NOTIFY bottomPaddingChanged REVISION 6)
public:
- QQuickTextInput(QQuickItem * parent=0);
+ QQuickTextInput(QQuickItem * parent=nullptr);
~QQuickTextInput();
void componentComplete() override;
@@ -363,7 +363,7 @@ private:
void ensureActiveFocus();
protected:
- QQuickTextInput(QQuickTextInputPrivate &dd, QQuickItem *parent = 0);
+ QQuickTextInput(QQuickTextInputPrivate &dd, QQuickItem *parent = nullptr);
void geometryChanged(const QRectF &newGeometry,
const QRectF &oldGeometry) override;
diff --git a/src/quick/items/qquicktextinput_p_p.h b/src/quick/items/qquicktextinput_p_p.h
index c795aebfa9..a2e2f0f66d 100644
--- a/src/quick/items/qquicktextinput_p_p.h
+++ b/src/quick/items/qquicktextinput_p_p.h
@@ -99,9 +99,9 @@ public:
QQuickTextInputPrivate()
: hscroll(0)
, vscroll(0)
- , cursorItem(0)
- , textNode(0)
- , m_maskData(0)
+ , cursorItem(nullptr)
+ , textNode(nullptr)
+ , m_maskData(nullptr)
, color(QRgb(0xFF000000))
, selectionColor(QRgb(0xFF000080))
, selectedTextColor(QRgb(0xFFFFFFFF))
diff --git a/src/quick/items/qquicktextnode.cpp b/src/quick/items/qquicktextnode.cpp
index cf4e71adf5..13a8219cbd 100644
--- a/src/quick/items/qquicktextnode.cpp
+++ b/src/quick/items/qquicktextnode.cpp
@@ -78,7 +78,7 @@ namespace {
Creates an empty QQuickTextNode
*/
QQuickTextNode::QQuickTextNode(QQuickItem *ownerElement)
- : m_cursorNode(0), m_ownerElement(ownerElement), m_useNativeRenderer(false)
+ : m_cursorNode(nullptr), m_ownerElement(ownerElement), m_useNativeRenderer(false)
{
#ifdef QSG_RUNTIME_DESCRIPTION
qsgnode_set_description(this, QLatin1String("text"));
@@ -125,7 +125,7 @@ QSGGlyphNode *QQuickTextNode::addGlyphs(const QPointF &position, const QGlyphRun
node->geometry()->setIndexDataPattern(QSGGeometry::StaticPattern);
node->geometry()->setVertexDataPattern(QSGGeometry::StaticPattern);
- if (parentNode == 0)
+ if (parentNode == nullptr)
parentNode = this;
parentNode->appendChildNode(node);
@@ -134,7 +134,7 @@ QSGGlyphNode *QQuickTextNode::addGlyphs(const QPointF &position, const QGlyphRun
void QQuickTextNode::setCursor(const QRectF &rect, const QColor &color)
{
- if (m_cursorNode != 0)
+ if (m_cursorNode != nullptr)
delete m_cursorNode;
QSGRenderContext *sg = QQuickItemPrivate::get(m_ownerElement)->sceneGraphRenderContext();
@@ -147,7 +147,7 @@ void QQuickTextNode::clearCursor()
if (m_cursorNode)
removeChildNode(m_cursorNode);
delete m_cursorNode;
- m_cursorNode = 0;
+ m_cursorNode = nullptr;
}
void QQuickTextNode::addRectangleNode(const QRectF &rect, const QColor &color)
@@ -273,9 +273,9 @@ void QQuickTextNode::addTextLayout(const QPointF &position, QTextLayout *textLay
void QQuickTextNode::deleteContent()
{
- while (firstChild() != 0)
+ while (firstChild() != nullptr)
delete firstChild();
- m_cursorNode = 0;
+ m_cursorNode = nullptr;
qDeleteAll(m_textures);
m_textures.clear();
}
diff --git a/src/quick/items/qquicktextnodeengine.cpp b/src/quick/items/qquicktextnodeengine.cpp
index c179ab7163..a53ca2a2a4 100644
--- a/src/quick/items/qquicktextnodeengine.cpp
+++ b/src/quick/items/qquicktextnodeengine.cpp
@@ -75,7 +75,7 @@ QQuickTextNodeEngine::BinaryTreeNode::BinaryTreeNode(const QGlyphRun &g,
: glyphRun(g)
, boundingRect(brect)
, selectionState(selState)
- , clipNode(0)
+ , clipNode(nullptr)
, decorations(decs)
, color(c)
, backgroundColor(bc)
@@ -256,10 +256,10 @@ void QQuickTextNodeEngine::processCurrentLine()
QVarLengthArray<TextDecoration> pendingOverlines;
QVarLengthArray<TextDecoration> pendingStrikeOuts;
if (!sortedIndexes.isEmpty()) {
- QQuickDefaultClipNode *currentClipNode = m_hasSelection ? new QQuickDefaultClipNode(QRectF()) : 0;
+ QQuickDefaultClipNode *currentClipNode = m_hasSelection ? new QQuickDefaultClipNode(QRectF()) : nullptr;
bool currentClipNodeUsed = false;
for (int i=0; i<=sortedIndexes.size(); ++i) {
- BinaryTreeNode *node = 0;
+ BinaryTreeNode *node = nullptr;
if (i < sortedIndexes.size()) {
int sortedIndex = sortedIndexes.at(i);
Q_ASSERT(sortedIndex < m_currentLineTree.size());
@@ -275,7 +275,7 @@ void QQuickTextNodeEngine::processCurrentLine()
decorationRect.setY(m_position.y() + m_currentLine.y());
decorationRect.setHeight(m_currentLine.height());
- if (node != 0)
+ if (node != nullptr)
decorationRect.setRight(node->boundingRect.left());
TextDecoration textDecoration(currentSelectionState, decorationRect, lastColor);
@@ -295,14 +295,14 @@ void QQuickTextNodeEngine::processCurrentLine()
// If we've reached an unselected node from a selected node, we add the
// selection rect to the graph, and we add decoration every time the
// selection state changes, because that means the text color changes
- if (node == 0 || node->selectionState != currentSelectionState) {
+ if (node == nullptr || node->selectionState != currentSelectionState) {
currentRect.setY(m_position.y() + m_currentLine.y());
currentRect.setHeight(m_currentLine.height());
if (currentSelectionState == Selected)
m_selectionRects.append(currentRect);
- if (currentClipNode != 0) {
+ if (currentClipNode != nullptr) {
if (!currentClipNodeUsed) {
delete currentClipNode;
} else {
@@ -312,13 +312,13 @@ void QQuickTextNodeEngine::processCurrentLine()
}
}
- if (node != 0 && m_hasSelection)
+ if (node != nullptr && m_hasSelection)
currentClipNode = new QQuickDefaultClipNode(QRectF());
else
- currentClipNode = 0;
+ currentClipNode = nullptr;
currentClipNodeUsed = false;
- if (node != 0) {
+ if (node != nullptr) {
currentSelectionState = node->selectionState;
currentRect = node->boundingRect;
@@ -333,7 +333,7 @@ void QQuickTextNodeEngine::processCurrentLine()
currentRect = currentRect.united(node->boundingRect);
}
- if (node != 0) {
+ if (node != nullptr) {
if (node->selectionState == Selected) {
node->clipNode = currentClipNode;
currentClipNodeUsed = true;
@@ -449,7 +449,7 @@ void QQuickTextNodeEngine::addTextObject(const QPointF &position, const QTextCha
QTextFrameFormat::Position layoutPosition)
{
QTextObjectInterface *handler = textDocument->documentLayout()->handlerForObject(format.objectType());
- if (handler != 0) {
+ if (handler != nullptr) {
QImage image;
QSizeF size = handler->intrinsicSize(textDocument, pos, format);
@@ -651,7 +651,7 @@ void QQuickTextNodeEngine::addFrameDecorations(QTextDocument *document, QTextFra
QTextFrameFormat frameFormat = frame->format().toFrameFormat();
QTextTable *table = qobject_cast<QTextTable *>(frame);
- QRectF boundingRect = table == 0
+ QRectF boundingRect = table == nullptr
? documentLayout->frameBoundingRect(frame)
: documentLayout->tableBoundingRect(table);
@@ -674,7 +674,7 @@ void QQuickTextNodeEngine::addFrameDecorations(QTextDocument *document, QTextFra
addBorder(boundingRect.adjusted(frameFormat.leftMargin(), frameFormat.topMargin(),
-frameFormat.rightMargin(), -frameFormat.bottomMargin()),
borderWidth, borderStyle, borderBrush);
- if (table != 0) {
+ if (table != nullptr) {
int rows = table->rows();
int columns = table->columns();
@@ -781,7 +781,7 @@ void QQuickTextNodeEngine::addToSceneGraph(QQuickTextNode *parentNode,
// Add all text with unselected color first
for (int i = 0; i < nodes.size(); ++i) {
const BinaryTreeNode *node = nodes.at(i);
- parentNode->addGlyphs(node->position, node->glyphRun, node->color, style, styleColor, 0);
+ parentNode->addGlyphs(node->position, node->glyphRun, node->color, style, styleColor, nullptr);
}
for (int i = 0; i < imageNodes.size(); ++i) {
@@ -812,7 +812,7 @@ void QQuickTextNodeEngine::addToSceneGraph(QQuickTextNode *parentNode,
for (int i = 0; i < nodes.size(); ++i) {
const BinaryTreeNode *node = nodes.at(i);
QQuickDefaultClipNode *clipNode = node->clipNode;
- if (clipNode != 0 && clipNode->parent() == 0)
+ if (clipNode != nullptr && clipNode->parent() == nullptr)
parentNode->appendChildNode(clipNode);
if (node->selectionState == Selected) {
@@ -820,26 +820,26 @@ void QQuickTextNodeEngine::addToSceneGraph(QQuickTextNode *parentNode,
int previousNodeIndex = i - 1;
int nextNodeIndex = i + 1;
const BinaryTreeNode *previousNode = previousNodeIndex < 0 ? 0 : nodes.at(previousNodeIndex);
- while (previousNode != 0 && qFuzzyCompare(previousNode->boundingRect.left(), node->boundingRect.left()))
+ while (previousNode != nullptr && qFuzzyCompare(previousNode->boundingRect.left(), node->boundingRect.left()))
previousNode = --previousNodeIndex < 0 ? 0 : nodes.at(previousNodeIndex);
const BinaryTreeNode *nextNode = nextNodeIndex == nodes.size() ? 0 : nodes.at(nextNodeIndex);
- if (previousNode != 0 && previousNode->selectionState == Unselected)
+ if (previousNode != nullptr && previousNode->selectionState == Unselected)
parentNode->addGlyphs(previousNode->position, previousNode->glyphRun, color, style, styleColor, clipNode);
- if (nextNode != 0 && nextNode->selectionState == Unselected)
+ if (nextNode != nullptr && nextNode->selectionState == Unselected)
parentNode->addGlyphs(nextNode->position, nextNode->glyphRun, color, style, styleColor, clipNode);
// If the previous or next node completely overlaps this one, then we have already drawn the glyphs of
// this node
bool drawCurrent = false;
- if (previousNode != 0 || nextNode != 0) {
+ if (previousNode != nullptr || nextNode != nullptr) {
for (int i = 0; i < node->ranges.size(); ++i) {
const QPair<int, int> &range = node->ranges.at(i);
int rangeLength = range.second - range.first + 1;
- if (previousNode != 0) {
+ if (previousNode != nullptr) {
for (int j = 0; j < previousNode->ranges.size(); ++j) {
const QPair<int, int> &otherRange = previousNode->ranges.at(j);
@@ -853,7 +853,7 @@ void QQuickTextNodeEngine::addToSceneGraph(QQuickTextNode *parentNode,
}
}
- if (nextNode != 0 && rangeLength > 0) {
+ if (nextNode != nullptr && rangeLength > 0) {
for (int j = 0; j < nextNode->ranges.size(); ++j) {
const QPair<int, int> &otherRange = nextNode->ranges.at(j);
@@ -896,8 +896,8 @@ void QQuickTextNodeEngine::addToSceneGraph(QQuickTextNode *parentNode,
void QQuickTextNodeEngine::mergeFormats(QTextLayout *textLayout, QVarLengthArray<QTextLayout::FormatRange> *mergedFormats)
{
- Q_ASSERT(mergedFormats != 0);
- if (textLayout == 0)
+ Q_ASSERT(mergedFormats != nullptr);
+ if (textLayout == nullptr)
return;
QVector<QTextLayout::FormatRange> additionalFormats = textLayout->formats();
@@ -911,7 +911,7 @@ void QQuickTextNodeEngine::mergeFormats(QTextLayout *textLayout, QVarLengthArray
QTextLayout::FormatRange *lastFormat = mergedFormats->data() + mergedFormats->size() - 1;
if (additionalFormat.start < lastFormat->start + lastFormat->length) {
- QTextLayout::FormatRange *mergedRange = 0;
+ QTextLayout::FormatRange *mergedRange = nullptr;
int length = additionalFormat.length;
if (additionalFormat.start > lastFormat->start) {
diff --git a/src/quick/items/qquicktextutil.cpp b/src/quick/items/qquicktextutil.cpp
index 6aa6c5cb4b..eb356a9c48 100644
--- a/src/quick/items/qquicktextutil.cpp
+++ b/src/quick/items/qquicktextutil.cpp
@@ -48,7 +48,7 @@ QT_BEGIN_NAMESPACE
QQuickItem *QQuickTextUtil::createCursor(
QQmlComponent *component, QQuickItem *parent, const QRectF &rectangle, const char *className)
{
- QQuickItem *item = 0;
+ QQuickItem *item = nullptr;
if (component->isReady()) {
QQmlContext *creationContext = component->creationContext();
diff --git a/src/quick/items/qquicktranslate_p.h b/src/quick/items/qquicktranslate_p.h
index b0199cef40..b6ea43342c 100644
--- a/src/quick/items/qquicktranslate_p.h
+++ b/src/quick/items/qquicktranslate_p.h
@@ -66,7 +66,7 @@ class Q_AUTOTEST_EXPORT QQuickTranslate : public QQuickTransform
Q_PROPERTY(qreal y READ y WRITE setY NOTIFY yChanged)
public:
- QQuickTranslate(QObject *parent = 0);
+ QQuickTranslate(QObject *parent = nullptr);
~QQuickTranslate();
qreal x() const;
@@ -96,7 +96,7 @@ class Q_AUTOTEST_EXPORT QQuickScale : public QQuickTransform
Q_PROPERTY(qreal yScale READ yScale WRITE setYScale NOTIFY yScaleChanged)
Q_PROPERTY(qreal zScale READ zScale WRITE setZScale NOTIFY zScaleChanged)
public:
- QQuickScale(QObject *parent = 0);
+ QQuickScale(QObject *parent = nullptr);
~QQuickScale();
QVector3D origin() const;
@@ -133,7 +133,7 @@ class Q_AUTOTEST_EXPORT QQuickRotation : public QQuickTransform
Q_PROPERTY(qreal angle READ angle WRITE setAngle NOTIFY angleChanged)
Q_PROPERTY(QVector3D axis READ axis WRITE setAxis NOTIFY axisChanged)
public:
- QQuickRotation(QObject *parent = 0);
+ QQuickRotation(QObject *parent = nullptr);
~QQuickRotation();
QVector3D origin() const;
@@ -164,7 +164,7 @@ class Q_AUTOTEST_EXPORT QQuickMatrix4x4 : public QQuickTransform
Q_PROPERTY(QMatrix4x4 matrix READ matrix WRITE setMatrix NOTIFY matrixChanged)
public:
- QQuickMatrix4x4(QObject *parent = 0);
+ QQuickMatrix4x4(QObject *parent = nullptr);
~QQuickMatrix4x4();
QMatrix4x4 matrix() const;
diff --git a/src/quick/items/qquickview.cpp b/src/quick/items/qquickview.cpp
index 954ea5553a..17f6539974 100644
--- a/src/quick/items/qquickview.cpp
+++ b/src/quick/items/qquickview.cpp
@@ -70,13 +70,13 @@ void QQuickViewPrivate::init(QQmlEngine* e)
{
// The content item has CppOwnership policy (set in QQuickWindow). Ensure the presence of a JS
// wrapper so that the garbage collector can see the policy.
- QV4::ExecutionEngine *v4 = QQmlEnginePrivate::getV4Engine(engine.data());
+ QV4::ExecutionEngine *v4 = engine.data()->handle();
QV4::QObjectWrapper::wrap(v4, contentItem);
}
}
QQuickViewPrivate::QQuickViewPrivate()
- : root(0), component(0), resizeMode(QQuickView::SizeViewToRootObject), initialSize(0,0)
+ : root(nullptr), component(nullptr), resizeMode(QQuickView::SizeViewToRootObject), initialSize(0,0)
{
}
@@ -94,11 +94,11 @@ void QQuickViewPrivate::execute()
if (root) {
delete root;
- root = 0;
+ root = nullptr;
}
if (component) {
delete component;
- component = 0;
+ component = nullptr;
}
if (!source.isEmpty()) {
QML_MEMORY_SCOPE_URL(engine.data()->baseUrl().resolved(source));
@@ -202,6 +202,16 @@ QQuickView::QQuickView(QQmlEngine* engine, QWindow *parent)
}
/*!
+ \internal
+*/
+QQuickView::QQuickView(const QUrl &source, QQuickRenderControl *control)
+ : QQuickWindow(*(new QQuickViewPrivate), control)
+{
+ d_func()->init();
+ setSource(source);
+}
+
+/*!
Destroys the QQuickView.
*/
QQuickView::~QQuickView()
@@ -210,7 +220,7 @@ QQuickView::~QQuickView()
// be a child of the QQuickViewPrivate, and will be destroyed by its dtor
Q_D(QQuickView);
delete d->root;
- d->root = 0;
+ d->root = nullptr;
}
/*!
@@ -254,7 +264,7 @@ void QQuickView::setContent(const QUrl& url, QQmlComponent *component, QObject*
if (d->component && d->component->isError()) {
const QList<QQmlError> errorList = d->component->errors();
for (const QQmlError &error : errorList) {
- QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), 0).warning()
+ QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
<< error;
}
emit statusChanged(status());
@@ -283,7 +293,7 @@ QUrl QQuickView::source() const
QQmlEngine* QQuickView::engine() const
{
Q_D(const QQuickView);
- return d->engine ? const_cast<QQmlEngine *>(d->engine.data()) : 0;
+ return d->engine ? const_cast<QQmlEngine *>(d->engine.data()) : nullptr;
}
/*!
@@ -296,7 +306,7 @@ QQmlEngine* QQuickView::engine() const
QQmlContext* QQuickView::rootContext() const
{
Q_D(const QQuickView);
- return d->engine ? d->engine.data()->rootContext() : 0;
+ return d->engine ? d->engine.data()->rootContext() : nullptr;
}
/*!
@@ -465,7 +475,7 @@ void QQuickView::continueExecute()
if (d->component->isError()) {
const QList<QQmlError> errorList = d->component->errors();
for (const QQmlError &error : errorList) {
- QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), 0).warning()
+ QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
<< error;
}
emit statusChanged(status());
@@ -477,7 +487,7 @@ void QQuickView::continueExecute()
if (d->component->isError()) {
const QList<QQmlError> errorList = d->component->errors();
for (const QQmlError &error : errorList) {
- QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), 0).warning()
+ QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
<< error;
}
emit statusChanged(status());
@@ -511,7 +521,7 @@ void QQuickViewPrivate::setRootObject(QObject *obj)
<< "Ensure your QML code is written for QtQuick 2, and uses a root that is or" << endl
<< "inherits from QtQuick's Item (not a Timer, QtObject, etc)." << endl;
delete obj;
- root = 0;
+ root = nullptr;
}
if (root) {
initialSize = rootObjectSize();
diff --git a/src/quick/items/qquickview.h b/src/quick/items/qquickview.h
index 014d02e7f5..ecae25e90b 100644
--- a/src/quick/items/qquickview.h
+++ b/src/quick/items/qquickview.h
@@ -62,7 +62,8 @@ public:
explicit QQuickView(QWindow *parent = nullptr);
QQuickView(QQmlEngine* engine, QWindow *parent);
explicit QQuickView(const QUrl &source, QWindow *parent = nullptr);
- virtual ~QQuickView();
+ QQuickView(const QUrl &source, QQuickRenderControl *renderControl);
+ ~QQuickView() override;
QUrl source() const;
diff --git a/src/quick/items/qquickview_p.h b/src/quick/items/qquickview_p.h
index f92d4b95d6..3f284c0519 100644
--- a/src/quick/items/qquickview_p.h
+++ b/src/quick/items/qquickview_p.h
@@ -93,7 +93,7 @@ public:
void updateSize();
void setRootObject(QObject *);
- void init(QQmlEngine* e = 0);
+ void init(QQmlEngine* e = nullptr);
QSize rootObjectSize() const;
diff --git a/src/quick/items/qquickwindow.cpp b/src/quick/items/qquickwindow.cpp
index 462790e1b1..26b97d452a 100644
--- a/src/quick/items/qquickwindow.cpp
+++ b/src/quick/items/qquickwindow.cpp
@@ -1,6 +1,6 @@
/****************************************************************************
**
-** Copyright (C) 2017 The Qt Company Ltd.
+** Copyright (C) 2018 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
** This file is part of the QtQuick module of the Qt Toolkit.
@@ -78,6 +78,9 @@
# include <private/qopenglvertexarrayobject_p.h>
# include <private/qsgdefaultrendercontext_p.h>
#endif
+#ifndef QT_NO_DEBUG_STREAM
+#include <private/qdebug_p.h>
+#endif
QT_BEGIN_NAMESPACE
@@ -88,6 +91,7 @@ Q_LOGGING_CATEGORY(DBG_MOUSE_TARGET, "qt.quick.mouse.target")
Q_LOGGING_CATEGORY(DBG_HOVER_TRACE, "qt.quick.hover.trace")
Q_LOGGING_CATEGORY(DBG_FOCUS, "qt.quick.focus")
Q_LOGGING_CATEGORY(DBG_DIRTY, "qt.quick.dirty")
+Q_LOGGING_CATEGORY(lcTransient, "qt.quick.window.transient")
extern Q_GUI_EXPORT QImage qt_gl_read_framebuffer(const QSize &size, bool alpha_format, bool include_alpha);
@@ -481,25 +485,25 @@ void QQuickWindowPrivate::renderSceneGraph(const QSize &size)
}
QQuickWindowPrivate::QQuickWindowPrivate()
- : contentItem(0)
- , activeFocusItem(0)
+ : contentItem(nullptr)
+ , activeFocusItem(nullptr)
#if QT_CONFIG(cursor)
- , cursorItem(0)
+ , cursorItem(nullptr)
#endif
#if QT_CONFIG(draganddrop)
- , dragGrabber(0)
+ , dragGrabber(nullptr)
#endif
, touchMouseId(-1)
, touchMouseDevice(nullptr)
, touchMousePressTimestamp(0)
- , dirtyItemList(0)
+ , dirtyItemList(nullptr)
, devicePixelRatio(0)
- , context(0)
- , renderer(0)
- , windowManager(0)
- , renderControl(0)
+ , context(nullptr)
+ , renderer(nullptr)
+ , windowManager(nullptr)
+ , renderControl(nullptr)
, pointerEventRecursionGuard(0)
- , customRenderStage(0)
+ , customRenderStage(nullptr)
, clearColor(Qt::white)
, clearBeforeRendering(true)
, persistentGLContext(true)
@@ -509,10 +513,10 @@ QQuickWindowPrivate::QQuickWindowPrivate()
, allowChildEventFiltering(true)
, allowDoubleClick(true)
, lastFocusReason(Qt::OtherFocusReason)
- , renderTarget(0)
+ , renderTarget(nullptr)
, renderTargetId(0)
- , vaoHelper(0)
- , incubationController(0)
+ , vaoHelper(nullptr)
+ , incubationController(nullptr)
{
#if QT_CONFIG(draganddrop)
dragGrabber = new QQuickDragGrabber;
@@ -578,13 +582,21 @@ void QQuickWindowPrivate::init(QQuickWindow *c, QQuickRenderControl *control)
QObject::connect(q, SIGNAL(focusObjectChanged(QObject*)), q, SIGNAL(activeFocusItemChanged()));
QObject::connect(q, SIGNAL(screenChanged(QScreen*)), q, SLOT(handleScreenChanged(QScreen*)));
-
+ QObject::connect(qApp, SIGNAL(applicationStateChanged(Qt::ApplicationState)),
+ q, SLOT(handleApplicationStateChanged(Qt::ApplicationState)));
QObject::connect(q, SIGNAL(frameSwapped()), q, SLOT(runJobsAfterSwap()), Qt::DirectConnection);
if (QQmlInspectorService *service = QQmlDebugConnector::service<QQmlInspectorService>())
service->addWindow(q);
}
+void QQuickWindow::handleApplicationStateChanged(Qt::ApplicationState state)
+{
+ Q_D(QQuickWindow);
+ if (state != Qt::ApplicationActive && d->contentItem)
+ d->contentItem->windowDeactivateEvent();
+}
+
/*!
\property QQuickWindow::data
\internal
@@ -592,7 +604,7 @@ void QQuickWindowPrivate::init(QQuickWindow *c, QQuickRenderControl *control)
QQmlListProperty<QObject> QQuickWindowPrivate::data()
{
- return QQmlListProperty<QObject>(q_func(), 0, QQuickWindowPrivate::data_append,
+ return QQmlListProperty<QObject>(q_func(), nullptr, QQuickWindowPrivate::data_append,
QQuickWindowPrivate::data_count,
QQuickWindowPrivate::data_at,
QQuickWindowPrivate::data_clear);
@@ -749,45 +761,6 @@ bool QQuickWindowPrivate::deliverTouchAsMouse(QQuickItem *item, QQuickPointerEve
return false;
}
-void QQuickWindowPrivate::setMouseGrabber(QQuickItem *grabber)
-{
- Q_Q(QQuickWindow);
- if (q->mouseGrabberItem() == grabber)
- return;
-
- QQuickItem *oldGrabber = q->mouseGrabberItem();
- qCDebug(DBG_MOUSE_TARGET) << "grabber" << oldGrabber << "->" << grabber;
-
- if (grabber && touchMouseId != -1 && touchMouseDevice) {
- // update the touch item for mouse touch id to the new grabber
- qCDebug(DBG_TOUCH_TARGET) << "TP (mouse)" << hex << touchMouseId << "->" << q->mouseGrabberItem();
- auto point = pointerEventInstance(touchMouseDevice)->pointById(touchMouseId);
- if (point) {
- auto originalEvent = pointerEventInstance(point->pointerEvent()->device());
- for (int i = 0; i < originalEvent->pointCount(); ++i)
- originalEvent->point(i)->cancelExclusiveGrab();
- point->setGrabberItem(grabber);
- for (auto handler : point->passiveGrabbers())
- point->cancelPassiveGrab(handler);
- }
- } else {
- QQuickPointerEvent *event = pointerEventInstance(QQuickPointerDevice::genericMouseDevice());
- Q_ASSERT(event->pointCount() == 1);
- auto point = event->point(0);
- point->setGrabberItem(grabber);
- for (auto handler : point->passiveGrabbers())
- point->cancelPassiveGrab(handler);
- }
-
-
- if (oldGrabber) {
- QEvent e(QEvent::UngrabMouse);
- hasFiltered.clear();
- if (!sendFilteredMouseEvent(&e, oldGrabber, oldGrabber->parentItem()))
- oldGrabber->mouseUngrabEvent();
- }
-}
-
void QQuickWindowPrivate::grabTouchPoints(QObject *grabber, const QVector<int> &ids)
{
for (int i = 0; i < ids.count(); ++i) {
@@ -835,18 +808,25 @@ void QQuickWindowPrivate::removeGrabber(QQuickItem *grabber, bool mouse, bool to
{
Q_Q(QQuickWindow);
if (Q_LIKELY(mouse) && q->mouseGrabberItem() == grabber) {
- qCDebug(DBG_MOUSE_TARGET) << "removeGrabber" << q->mouseGrabberItem() << "-> null";
- setMouseGrabber(nullptr);
+ bool fromTouch = isDeliveringTouchAsMouse();
+ auto point = fromTouch ?
+ pointerEventInstance(touchMouseDevice)->pointById(touchMouseId) :
+ pointerEventInstance(QQuickPointerDevice::genericMouseDevice())->point(0);
+ QQuickItem *oldGrabber = point->grabberItem();
+ qCDebug(DBG_MOUSE_TARGET) << "removeGrabber" << oldGrabber << "-> null";
+ point->setGrabberItem(nullptr);
+ sendUngrabEvent(oldGrabber, fromTouch);
}
if (Q_LIKELY(touch)) {
bool ungrab = false;
const auto touchDevices = QQuickPointerDevice::touchDevices();
for (auto device : touchDevices) {
- auto pointerEvent = pointerEventInstance(device);
- for (int i = 0; i < pointerEvent->pointCount(); ++i) {
- if (pointerEvent->point(i)->exclusiveGrabber() == grabber) {
- pointerEvent->point(i)->setGrabberItem(nullptr);
- ungrab = true;
+ if (auto pointerEvent = queryPointerEventInstance(device)) {
+ for (int i = 0; i < pointerEvent->pointCount(); ++i) {
+ if (pointerEvent->point(i)->exclusiveGrabber() == grabber) {
+ pointerEvent->point(i)->setGrabberItem(nullptr);
+ ungrab = true;
+ }
}
}
}
@@ -855,6 +835,19 @@ void QQuickWindowPrivate::removeGrabber(QQuickItem *grabber, bool mouse, bool to
}
}
+void QQuickWindowPrivate::sendUngrabEvent(QQuickItem *grabber, bool touch)
+{
+ if (!grabber)
+ return;
+ QEvent e(QEvent::UngrabMouse);
+ hasFiltered.clear();
+ if (!sendFilteredMouseEvent(&e, grabber, grabber->parentItem())) {
+ grabber->mouseUngrabEvent();
+ if (touch)
+ grabber->touchUngrabEvent();
+ }
+}
+
/*!
Translates the data in \a touchEvent to this window. This method leaves the item local positions in
\a touchEvent untouched (these are filled in later).
@@ -898,12 +891,12 @@ void QQuickWindowPrivate::setFocusInScope(QQuickItem *scope, QQuickItem *item, Q
qCDebug(DBG_FOCUS) << " item:" << (QObject *)item;
qCDebug(DBG_FOCUS) << " activeFocusItem:" << (QObject *)activeFocusItem;
- QQuickItemPrivate *scopePrivate = scope ? QQuickItemPrivate::get(scope) : 0;
+ QQuickItemPrivate *scopePrivate = scope ? QQuickItemPrivate::get(scope) : nullptr;
QQuickItemPrivate *itemPrivate = QQuickItemPrivate::get(item);
- QQuickItem *oldActiveFocusItem = 0;
+ QQuickItem *oldActiveFocusItem = nullptr;
QQuickItem *currentActiveFocusItem = activeFocusItem;
- QQuickItem *newActiveFocusItem = 0;
+ QQuickItem *newActiveFocusItem = nullptr;
bool sendFocusIn = false;
lastFocusReason = reason;
@@ -929,7 +922,7 @@ void QQuickWindowPrivate::setFocusInScope(QQuickItem *scope, QQuickItem *item, Q
QGuiApplication::inputMethod()->commit();
#endif
- activeFocusItem = 0;
+ activeFocusItem = nullptr;
QQuickItem *afi = oldActiveFocusItem;
while (afi && afi != scope) {
@@ -1009,7 +1002,7 @@ void QQuickWindowPrivate::clearFocusInScope(QQuickItem *scope, QQuickItem *item,
qCDebug(DBG_FOCUS) << " item:" << (QObject *)item;
qCDebug(DBG_FOCUS) << " activeFocusItem:" << (QObject *)activeFocusItem;
- QQuickItemPrivate *scopePrivate = 0;
+ QQuickItemPrivate *scopePrivate = nullptr;
if (scope) {
scopePrivate = QQuickItemPrivate::get(scope);
if ( !scopePrivate->subFocusItem )
@@ -1017,8 +1010,8 @@ void QQuickWindowPrivate::clearFocusInScope(QQuickItem *scope, QQuickItem *item,
}
QQuickItem *currentActiveFocusItem = activeFocusItem;
- QQuickItem *oldActiveFocusItem = 0;
- QQuickItem *newActiveFocusItem = 0;
+ QQuickItem *oldActiveFocusItem = nullptr;
+ QQuickItem *newActiveFocusItem = nullptr;
lastFocusReason = reason;
@@ -1035,7 +1028,7 @@ void QQuickWindowPrivate::clearFocusInScope(QQuickItem *scope, QQuickItem *item,
QGuiApplication::inputMethod()->commit();
#endif
- activeFocusItem = 0;
+ activeFocusItem = nullptr;
if (oldActiveFocusItem) {
QQuickItem *afi = oldActiveFocusItem;
@@ -1284,13 +1277,21 @@ QQuickWindow::QQuickWindow(QQuickWindowPrivate &dd, QWindow *parent)
\internal
*/
QQuickWindow::QQuickWindow(QQuickRenderControl *control)
- : QWindow(*(new QQuickWindowPrivate), 0)
+ : QWindow(*(new QQuickWindowPrivate), nullptr)
{
Q_D(QQuickWindow);
d->init(this, control);
}
-
+/*!
+ \internal
+*/
+QQuickWindow::QQuickWindow(QQuickWindowPrivate &dd, QQuickRenderControl *control)
+ : QWindow(dd, nullptr)
+{
+ Q_D(QQuickWindow);
+ d->init(this, control);
+}
/*!
Destroys the window.
@@ -1306,11 +1307,13 @@ QQuickWindow::~QQuickWindow()
d->windowManager->windowDestroyed(this);
}
- delete d->incubationController; d->incubationController = 0;
+ delete d->incubationController; d->incubationController = nullptr;
#if QT_CONFIG(draganddrop)
- delete d->dragGrabber; d->dragGrabber = 0;
+ delete d->dragGrabber; d->dragGrabber = nullptr;
#endif
- delete d->contentItem; d->contentItem = 0;
+ delete d->contentItem; d->contentItem = nullptr;
+ qDeleteAll(d->pointerEventInstances);
+ d->pointerEventInstances.clear();
d->renderJobMutex.lock();
qDeleteAll(d->beforeSynchronizingJobs);
@@ -1511,15 +1514,16 @@ QQuickItem *QQuickWindow::mouseGrabberItem() const
{
Q_D(const QQuickWindow);
- if (d->touchMouseId != -1 && d->touchMouseDevice) {
- QQuickPointerEvent *event = d->pointerEventInstance(d->touchMouseDevice);
- auto point = event->pointById(d->touchMouseId);
- return point ? point->grabberItem() : nullptr;
+ if (d->isDeliveringTouchAsMouse()) {
+ if (QQuickPointerEvent *event = d->queryPointerEventInstance(d->touchMouseDevice)) {
+ auto point = event->pointById(d->touchMouseId);
+ return point ? point->grabberItem() : nullptr;
+ }
+ } else if (QQuickPointerEvent *event = d->queryPointerEventInstance(QQuickPointerDevice::genericMouseDevice())) {
+ Q_ASSERT(event->pointCount());
+ return event->point(0)->grabberItem();
}
-
- QQuickPointerEvent *event = d->pointerEventInstance(QQuickPointerDevice::genericMouseDevice());
- Q_ASSERT(event->pointCount());
- return event->point(0)->grabberItem();
+ return nullptr;
}
@@ -1693,8 +1697,10 @@ void QQuickWindowPrivate::deliverToPassiveGrabbers(const QVector<QPointer <QQuic
alreadyFiltered = sendFilteredPointerEvent(pointerEvent, par);
sendFilteredPointerEventResult << qMakePair<QQuickItem*, bool>(par, alreadyFiltered);
}
- if (!alreadyFiltered)
+ if (!alreadyFiltered) {
+ pointerEvent->localize(handler->parentItem());
handler->handlePointerEvent(pointerEvent);
+ }
}
}
}
@@ -1709,28 +1715,31 @@ void QQuickWindowPrivate::deliverMouseEvent(QQuickPointerMouseEvent *pointerEven
if (point->exclusiveGrabber()) {
if (auto grabber = point->grabberItem()) {
+ bool handled = false;
if (sendFilteredPointerEvent(pointerEvent, grabber))
- return;
+ handled = true;
// if the grabber is an Item:
// if the update consists of changing button state, don't accept it unless
// the button is one in which the grabber is interested
Qt::MouseButtons acceptedButtons = grabber->acceptedMouseButtons();
- if (pointerEvent->button() != Qt::NoButton && acceptedButtons
+ if (!handled && pointerEvent->button() != Qt::NoButton && acceptedButtons
&& !(acceptedButtons & pointerEvent->button())) {
pointerEvent->setAccepted(false);
- return;
+ handled = true;
}
// send update
- QPointF localPos = grabber->mapFromScene(lastMousePosition);
- auto me = pointerEvent->asMouseEvent(localPos);
- me->accept();
- QCoreApplication::sendEvent(grabber, me);
- point->setAccepted(me->isAccepted());
+ if (!handled) {
+ QPointF localPos = grabber->mapFromScene(lastMousePosition);
+ auto me = pointerEvent->asMouseEvent(localPos);
+ me->accept();
+ QCoreApplication::sendEvent(grabber, me);
+ point->setAccepted(me->isAccepted());
+ }
// release event: ungrab if no buttons are pressed anymore
if (mouseIsReleased)
- setMouseGrabber(nullptr);
+ removeGrabber(grabber, true, isDeliveringTouchAsMouse());
} else {
// if the grabber is not an Item, it must be a PointerHandler
auto handler = point->grabberPointerHandler();
@@ -1740,6 +1749,7 @@ void QQuickWindowPrivate::deliverMouseEvent(QQuickPointerMouseEvent *pointerEven
if (mouseIsReleased)
point->setGrabberPointerHandler(nullptr, true);
}
+ deliverToPassiveGrabbers(point->passiveGrabbers(), pointerEvent);
} else {
bool delivered = false;
if (pointerEvent->isPressEvent()) {
@@ -1756,6 +1766,8 @@ void QQuickWindowPrivate::deliverMouseEvent(QQuickPointerMouseEvent *pointerEven
QVector<QQuickItem *> targetItems = pointerTargets(contentItem, point->scenePosition(), false, false);
for (QQuickItem *item : targetItems) {
QQuickItemPrivate *itemPrivate = QQuickItemPrivate::get(item);
+ if (!itemPrivate->extra.isAllocated() || itemPrivate->extra->pointerHandlers.isEmpty())
+ continue;
pointerEvent->localize(item);
if (!sendFilteredPointerEvent(pointerEvent, item)) {
if (itemPrivate->handlePointerEvent(pointerEvent, true)) // avoid re-delivering to grabbers
@@ -1931,7 +1943,8 @@ bool QQuickWindowPrivate::deliverNativeGestureEvent(QQuickItem *item, QNativeGes
{
QQuickItemPrivate *itemPrivate = QQuickItemPrivate::get(item);
- if ((itemPrivate->flags & QQuickItem::ItemClipsChildrenToShape) && !item->contains(event->localPos()))
+ QPointF p = item->mapFromScene(event->windowPos());
+ if ((itemPrivate->flags & QQuickItem::ItemClipsChildrenToShape) && !item->contains(p))
return false;
QList<QQuickItem *> children = itemPrivate->paintOrderChildItems();
@@ -1954,7 +1967,6 @@ bool QQuickWindowPrivate::deliverNativeGestureEvent(QQuickItem *item, QNativeGes
}
// If still not accepted, try direct delivery to the item
- QPointF p = item->mapFromScene(event->localPos());
if (item->contains(p)) {
QNativeGestureEvent copy(event->gestureType(), event->device(), p, event->windowPos(), event->screenPos(),
event->value(), 0L, 0L); // TODO can't copy things I can't access
@@ -1975,15 +1987,16 @@ bool QQuickWindowPrivate::deliverTouchCancelEvent(QTouchEvent *event)
qCDebug(DBG_TOUCH) << event;
Q_Q(QQuickWindow);
+ if (q->mouseGrabberItem())
+ q->mouseGrabberItem()->ungrabMouse();
+ touchMouseId = -1;
+ touchMouseDevice = nullptr;
+
// A TouchCancel event will typically not contain any points.
// Deliver it to all items and handlers that have active touches.
QQuickPointerEvent *pointerEvent = pointerEventInstance(QQuickPointerDevice::touchDevice(event->device()));
for (int i = 0; i < pointerEvent->pointCount(); ++i)
pointerEvent->point(i)->cancelExclusiveGrabImpl(event);
- touchMouseId = -1;
- touchMouseDevice = nullptr;
- if (q->mouseGrabberItem())
- q->mouseGrabberItem()->ungrabMouse();
// The next touch event can only be a TouchBegin, so clean up.
pointerEvent->clearGrabbers();
@@ -2202,7 +2215,7 @@ void QQuickWindowPrivate::flushFrameSynchronousEvents()
}
}
-QQuickPointerEvent *QQuickWindowPrivate::pointerEventInstance(QQuickPointerDevice *device, QEvent::Type eventType) const
+QQuickPointerEvent *QQuickWindowPrivate::queryPointerEventInstance(QQuickPointerDevice *device, QEvent::Type eventType) const
{
// Search for a matching reusable event object.
for (QQuickPointerEvent *e : pointerEventInstances) {
@@ -2215,9 +2228,14 @@ QQuickPointerEvent *QQuickWindowPrivate::pointerEventInstance(QQuickPointerDevic
if (e->device() == device)
return e;
}
+ return nullptr;
+}
- // Not found: we have to create a suitable event instance.
- QQuickPointerEvent *ev = nullptr;
+QQuickPointerEvent *QQuickWindowPrivate::pointerEventInstance(QQuickPointerDevice *device, QEvent::Type eventType) const
+{
+ QQuickPointerEvent *ev = queryPointerEventInstance(device, eventType);
+ if (ev)
+ return ev;
QQuickWindow *q = const_cast<QQuickWindow*>(q_func());
switch (device->type()) {
case QQuickPointerDevice::Mouse:
@@ -2278,6 +2296,7 @@ QQuickPointerEvent *QQuickWindowPrivate::pointerEventInstance(QEvent *event) con
void QQuickWindowPrivate::deliverPointerEvent(QQuickPointerEvent *event)
{
+ Q_Q(QQuickWindow);
// If users spin the eventloop as a result of event delivery, we disable
// event compression and send events directly. This is because we consider
// the usecase a bit evil, but we at least don't want to lose events.
@@ -2287,8 +2306,10 @@ void QQuickWindowPrivate::deliverPointerEvent(QQuickPointerEvent *event)
if (event->asPointerMouseEvent()) {
deliverMouseEvent(event->asPointerMouseEvent());
// failsafe: never allow any kind of grab to persist after release
- if (event->isReleaseEvent() && event->buttons() == Qt::NoButton)
+ if (event->isReleaseEvent() && event->buttons() == Qt::NoButton) {
event->clearGrabbers();
+ sendUngrabEvent(q->mouseGrabberItem(), false);
+ }
} else if (event->asPointerTouchEvent()) {
deliverTouchEvent(event->asPointerTouchEvent());
} else {
@@ -2399,6 +2420,7 @@ void QQuickWindowPrivate::deliverTouchEvent(QQuickPointerTouchEvent *event)
// Deliver touch points to existing grabbers
void QQuickWindowPrivate::deliverUpdatedTouchPoints(QQuickPointerTouchEvent *event)
{
+ bool done = false;
const auto grabbers = event->exclusiveGrabbers();
for (auto grabber : grabbers) {
// The grabber is guaranteed to be either an item or a handler.
@@ -2408,52 +2430,50 @@ void QQuickWindowPrivate::deliverUpdatedTouchPoints(QQuickPointerTouchEvent *eve
QQuickPointerHandler *handler = static_cast<QQuickPointerHandler *>(grabber);
receiver = static_cast<QQuickPointerHandler *>(grabber)->parentItem();
if (sendFilteredPointerEvent(event, receiver))
- return;
+ done = true;
event->localize(receiver);
handler->handlePointerEvent(event);
- if (event->allPointsAccepted())
- return;
}
+ if (done)
+ break;
// If the grabber is an item or the grabbing handler didn't handle it,
// then deliver the event to the item (which may have multiple handlers).
deliverMatchingPointsToItem(receiver, event);
}
- // If some points weren't grabbed, deliver only to non-grabber PointerHandlers
- if (!event->allPointsGrabbed()) {
- int pointCount = event->pointCount();
+ // Deliver to each eventpoint's passive grabbers (but don't visit any handler more than once)
+ int pointCount = event->pointCount();
+ for (int i = 0; i < pointCount; ++i) {
+ QQuickEventPoint *point = event->point(i);
+ deliverToPassiveGrabbers(point->passiveGrabbers(), event);
+ }
- // Deliver to each eventpoint's passive grabbers (but don't visit any handler more than once)
+ if (done)
+ return;
+
+ // If some points weren't grabbed, deliver only to non-grabber PointerHandlers in reverse paint order
+ if (!event->allPointsGrabbed()) {
+ QVector<QQuickItem *> targetItems;
for (int i = 0; i < pointCount; ++i) {
QQuickEventPoint *point = event->point(i);
- deliverToPassiveGrabbers(point->passiveGrabbers(), event);
- }
-
- // If some points weren't grabbed, deliver to non-grabber PointerHandlers in reverse paint order
- if (!event->allPointsGrabbed()) {
- QVector<QQuickItem *> targetItems;
- for (int i = 0; i < pointCount; ++i) {
- QQuickEventPoint *point = event->point(i);
- if (point->state() == QQuickEventPoint::Pressed)
- continue; // presses were delivered earlier; not the responsibility of deliverUpdatedTouchPoints
- QVector<QQuickItem *> targetItemsForPoint = pointerTargets(contentItem, point->scenePosition(), false, false);
- if (targetItems.count()) {
- targetItems = mergePointerTargets(targetItems, targetItemsForPoint);
- } else {
- targetItems = targetItemsForPoint;
- }
- }
-
- for (QQuickItem *item: targetItems) {
- if (grabbers.contains(item))
- continue;
- QQuickItemPrivate *itemPrivate = QQuickItemPrivate::get(item);
- event->localize(item);
- itemPrivate->handlePointerEvent(event, true); // avoid re-delivering to grabbers
- if (event->allPointsGrabbed())
- break;
+ if (point->state() == QQuickEventPoint::Pressed)
+ continue; // presses were delivered earlier; not the responsibility of deliverUpdatedTouchPoints
+ QVector<QQuickItem *> targetItemsForPoint = pointerTargets(contentItem, point->scenePosition(), false, false);
+ if (targetItems.count()) {
+ targetItems = mergePointerTargets(targetItems, targetItemsForPoint);
+ } else {
+ targetItems = targetItemsForPoint;
}
}
+ for (QQuickItem *item : targetItems) {
+ if (grabbers.contains(item))
+ continue;
+ QQuickItemPrivate *itemPrivate = QQuickItemPrivate::get(item);
+ event->localize(item);
+ itemPrivate->handlePointerEvent(event, true); // avoid re-delivering to grabbers
+ if (event->allPointsGrabbed())
+ break;
+ }
}
}
@@ -2492,7 +2512,7 @@ bool QQuickWindowPrivate::deliverPressOrReleaseEvent(QQuickPointerEvent *event,
continue;
deliverMatchingPointsToItem(item, event, handlersOnly);
if (event->allPointsAccepted())
- break;
+ handlersOnly = true;
}
return event->allPointsAccepted();
@@ -2507,13 +2527,12 @@ void QQuickWindowPrivate::deliverMatchingPointsToItem(QQuickItem *item, QQuickPo
// Let the Item's handlers (if any) have the event first.
// However, double click should never be delivered to handlers.
if (!pointerEvent->isDoubleClickEvent()) {
+ bool wasAccepted = pointerEvent->allPointsAccepted();
itemPrivate->handlePointerEvent(pointerEvent);
- allowDoubleClick = !(pointerEvent->asPointerMouseEvent() && pointerEvent->isPressEvent() && pointerEvent->allPointsAccepted());
+ allowDoubleClick = wasAccepted || !(pointerEvent->asPointerMouseEvent() && pointerEvent->isPressEvent() && pointerEvent->allPointsAccepted());
}
if (handlersOnly)
return;
- if (pointerEvent->allPointsAccepted() && !pointerEvent->isReleaseEvent())
- return;
// If all points are released and the item is not the grabber, it doesn't get the event.
// But if at least one point is still pressed, we might be in a potential gesture-takeover scenario.
@@ -2525,8 +2544,6 @@ void QQuickWindowPrivate::deliverMatchingPointsToItem(QQuickItem *item, QQuickPo
auto event = pointerEvent->asPointerMouseEvent();
if (event && item->acceptedMouseButtons() & event->button()) {
auto point = event->point(0);
- if (point->isAccepted())
- return;
// The only reason to already have a mouse grabber here is
// synthetic events - flickable sends one when setPressDelay is used.
auto oldMouseGrabber = q->mouseGrabberItem();
@@ -2747,7 +2764,7 @@ QQuickItem *QQuickWindowPrivate::findCursorItem(QQuickItem *item, const QPointF
if (itemPrivate->flags & QQuickItem::ItemClipsChildrenToShape) {
QPointF p = item->mapFromScene(scenePos);
if (!item->contains(p))
- return 0;
+ return nullptr;
}
if (itemPrivate->subtreeCursorEnabled) {
@@ -2766,7 +2783,7 @@ QQuickItem *QQuickWindowPrivate::findCursorItem(QQuickItem *item, const QPointF
if (item->contains(p))
return item;
}
- return 0;
+ return nullptr;
}
#endif
@@ -2820,17 +2837,10 @@ bool QQuickWindowPrivate::sendFilteredPointerEventImpl(QQuickPointerEvent *event
// get a touch event customized for delivery to filteringParent
QScopedPointer<QTouchEvent> filteringParentTouchEvent(pte->touchEventForItem(receiver, true));
if (filteringParentTouchEvent) {
- QVarLengthArray<QPair<QQuickPointerHandler *, QQuickEventPoint *>, 32> passiveGrabsToCancel;
if (filteringParent->childMouseEventFilter(receiver, filteringParentTouchEvent.data())) {
qCDebug(DBG_TOUCH) << "touch event intercepted by childMouseEventFilter of " << filteringParent;
skipDelivery.append(filteringParent);
for (auto point: qAsConst(filteringParentTouchEvent->touchPoints())) {
- auto pointerEventPoint = pte->pointById(point.id());
- for (auto handler : pointerEventPoint->passiveGrabbers()) {
- QPair<QQuickPointerHandler *, QQuickEventPoint *> grab(handler, pointerEventPoint);
- if (!passiveGrabsToCancel.contains(grab))
- passiveGrabsToCancel.append(grab);
- }
QQuickEventPoint *pt = event->pointById(point.id());
pt->setAccepted();
pt->setGrabberItem(filteringParent);
@@ -2876,12 +2886,6 @@ bool QQuickWindowPrivate::sendFilteredPointerEventImpl(QQuickPointerEvent *event
touchMouseUnset = false; // We want to leave touchMouseId and touchMouseDevice set
if (mouseEvent->isAccepted())
filteringParent->grabMouse();
- auto pointerEventPoint = pte->pointById(tp.id());
- for (auto handler : pointerEventPoint->passiveGrabbers()) {
- QPair<QQuickPointerHandler *, QQuickEventPoint *> grab(handler, pointerEventPoint);
- if (!passiveGrabsToCancel.contains(grab))
- passiveGrabsToCancel.append(grab);
- }
}
filtered = true;
}
@@ -2897,8 +2901,6 @@ bool QQuickWindowPrivate::sendFilteredPointerEventImpl(QQuickPointerEvent *event
}
}
}
- for (auto grab : passiveGrabsToCancel)
- grab.second->cancelPassiveGrab(grab.first);
}
}
}
@@ -2972,8 +2974,10 @@ void QQuickWindowPrivate::data_append(QQmlListProperty<QObject> *property, QObje
if (!o)
return;
QQuickWindow *that = static_cast<QQuickWindow *>(property->object);
- if (QQuickWindow *window = qmlobject_cast<QQuickWindow *>(o))
+ if (QQuickWindow *window = qmlobject_cast<QQuickWindow *>(o)) {
+ qCDebug(lcTransient) << window << "is transient for" << that;
window->setTransientParent(that);
+ }
QQmlListProperty<QObject> itemProperty = QQuickItemPrivate::get(that->contentItem())->data();
itemProperty.append(&itemProperty, o);
}
@@ -3039,6 +3043,7 @@ void QQuickWindowPrivate::contextCreationFailureMessage(const QSurfaceFormat &fo
#if QT_DEPRECATED_SINCE(5, 8)
+// ### Qt6: remove
/*!
Propagates an event \a e to a QQuickItem \a item on the window.
@@ -3048,7 +3053,6 @@ void QQuickWindowPrivate::contextCreationFailureMessage(const QSurfaceFormat &fo
\deprecated
*/
-// ### Qt6: remove
bool QQuickWindow::sendEvent(QQuickItem *item, QEvent *e)
{
Q_D(QQuickWindow);
@@ -3105,15 +3109,15 @@ void QQuickWindowPrivate::cleanupNodesOnShutdown(QQuickItem *item)
QQuickItemPrivate *p = QQuickItemPrivate::get(item);
if (p->itemNodeInstance) {
delete p->itemNodeInstance;
- p->itemNodeInstance = 0;
+ p->itemNodeInstance = nullptr;
if (p->extra.isAllocated()) {
- p->extra->opacityNode = 0;
- p->extra->clipNode = 0;
- p->extra->rootNode = 0;
+ p->extra->opacityNode = nullptr;
+ p->extra->clipNode = nullptr;
+ p->extra->rootNode = nullptr;
}
- p->paintNode = 0;
+ p->paintNode = nullptr;
p->dirty(QQuickItemPrivate::Window);
}
@@ -3125,7 +3129,7 @@ void QQuickWindowPrivate::cleanupNodesOnShutdown(QQuickItem *item)
if (index >= 0) {
const QMetaMethod &method = mo->method(index);
// Skip functions named invalidateSceneGraph() in QML items.
- if (strstr(method.enclosingMetaObject()->className(), "_QML_") == 0)
+ if (strstr(method.enclosingMetaObject()->className(), "_QML_") == nullptr)
method.invoke(item, Qt::DirectConnection);
}
}
@@ -3153,7 +3157,7 @@ void QQuickWindowPrivate::updateDirtyNodes()
cleanupNodes();
QQuickItem *updateList = dirtyItemList;
- dirtyItemList = 0;
+ dirtyItemList = nullptr;
if (updateList) QQuickItemPrivate::get(updateList)->prevDirtyItem = &updateList;
while (updateList) {
@@ -3169,7 +3173,7 @@ void QQuickWindowPrivate::updateDirtyNodes()
static inline QSGNode *qquickitem_before_paintNode(QQuickItemPrivate *d)
{
const QList<QQuickItem *> childItems = d->paintOrderChildItems();
- QQuickItem *before = 0;
+ QQuickItem *before = nullptr;
for (int i=0; i<childItems.size(); ++i) {
QQuickItemPrivate *dd = QQuickItemPrivate::get(childItems.at(i));
// Perform the same check as the in fetchNextNode below.
@@ -3178,7 +3182,7 @@ static inline QSGNode *qquickitem_before_paintNode(QQuickItemPrivate *d)
else
break;
}
- return Q_UNLIKELY(before) ? QQuickItemPrivate::get(before)->itemNode() : 0;
+ return Q_UNLIKELY(before) ? QQuickItemPrivate::get(before)->itemNode() : nullptr;
}
static QSGNode *fetchNextNode(QQuickItemPrivate *itemPriv, int &ii, bool &returnedPaintNode)
@@ -3210,7 +3214,7 @@ static QSGNode *fetchNextNode(QQuickItemPrivate *itemPriv, int &ii, bool &return
return childPrivate->itemNode();
}
- return 0;
+ return nullptr;
}
void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
@@ -3245,10 +3249,10 @@ void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
}
bool clipEffectivelyChanged = (dirty & (QQuickItemPrivate::Clip | QQuickItemPrivate::Window)) &&
- ((item->clip() == false) != (itemPriv->clipNode() == 0));
+ ((item->clip() == false) != (itemPriv->clipNode() == nullptr));
int effectRefCount = itemPriv->extra.isAllocated()?itemPriv->extra->effectRefCount:0;
bool effectRefEffectivelyChanged = (dirty & (QQuickItemPrivate::EffectReference | QQuickItemPrivate::Window)) &&
- ((effectRefCount == 0) != (itemPriv->rootNode() == 0));
+ ((effectRefCount == 0) != (itemPriv->rootNode() == nullptr));
if (clipEffectivelyChanged) {
QSGNode *parent = itemPriv->opacityNode() ? (QSGNode *) itemPriv->opacityNode() :
@@ -3256,7 +3260,7 @@ void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
QSGNode *child = itemPriv->rootNode();
if (item->clip()) {
- Q_ASSERT(itemPriv->clipNode() == 0);
+ Q_ASSERT(itemPriv->clipNode() == nullptr);
QQuickDefaultClipNode *clip = new QQuickDefaultClipNode(item->clipRect());
itemPriv->extra.value().clipNode = clip;
clip->update();
@@ -3282,7 +3286,7 @@ void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
}
delete itemPriv->clipNode();
- itemPriv->extra->clipNode = 0;
+ itemPriv->extra->clipNode = nullptr;
}
}
@@ -3297,18 +3301,18 @@ void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
parent = itemPriv->itemNode();
if (itemPriv->extra.isAllocated() && itemPriv->extra->effectRefCount) {
- Q_ASSERT(itemPriv->rootNode() == 0);
+ Q_ASSERT(itemPriv->rootNode() == nullptr);
QSGRootNode *root = new QSGRootNode();
itemPriv->extra->rootNode = root;
parent->reparentChildNodesTo(root);
parent->appendChildNode(root);
} else {
- Q_ASSERT(itemPriv->rootNode() != 0);
+ Q_ASSERT(itemPriv->rootNode() != nullptr);
QSGRootNode *root = itemPriv->rootNode();
parent->removeChildNode(root);
root->reparentChildNodesTo(parent);
delete itemPriv->rootNode();
- itemPriv->extra->rootNode = 0;
+ itemPriv->extra->rootNode = nullptr;
}
}
@@ -3334,7 +3338,7 @@ void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
int added = 0;
int removed = 0;
int replaced = 0;
- QSGNode *desiredNode = 0;
+ QSGNode *desiredNode = nullptr;
while (currentNode && (desiredNode = fetchNextNode(itemPriv, ii, fetchedPaintNode))) {
// uh oh... reality and our utopic paradise are diverging!
@@ -3419,11 +3423,11 @@ void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
updatePaintNodeData.transformNode = itemPriv->itemNode();
itemPriv->paintNode = item->updatePaintNode(itemPriv->paintNode, &updatePaintNodeData);
- Q_ASSERT(itemPriv->paintNode == 0 ||
- itemPriv->paintNode->parent() == 0 ||
+ Q_ASSERT(itemPriv->paintNode == nullptr ||
+ itemPriv->paintNode->parent() == nullptr ||
itemPriv->paintNode->parent() == itemPriv->childContainerNode());
- if (itemPriv->paintNode && itemPriv->paintNode->parent() == 0) {
+ if (itemPriv->paintNode && itemPriv->paintNode->parent() == nullptr) {
QSGNode *before = qquickitem_before_paintNode(itemPriv);
if (before && before->parent()) {
Q_ASSERT(before->parent() == itemPriv->childContainerNode());
@@ -3434,7 +3438,7 @@ void QQuickWindowPrivate::updateDirtyNode(QQuickItem *item)
}
} else if (itemPriv->paintNode) {
delete itemPriv->paintNode;
- itemPriv->paintNode = 0;
+ itemPriv->paintNode = nullptr;
}
}
@@ -3486,14 +3490,14 @@ void QQuickWindow::cleanupSceneGraph()
Q_D(QQuickWindow);
#if QT_CONFIG(opengl)
delete d->vaoHelper;
- d->vaoHelper = 0;
+ d->vaoHelper = nullptr;
#endif
if (!d->renderer)
return;
delete d->renderer->rootNode();
delete d->renderer;
- d->renderer = 0;
+ d->renderer = nullptr;
d->runAndClearJobs(&d->beforeSynchronizingJobs);
d->runAndClearJobs(&d->afterSynchronizingJobs);
@@ -3504,6 +3508,7 @@ void QQuickWindow::cleanupSceneGraph()
void QQuickWindow::setTransientParent_helper(QQuickWindow *window)
{
+ qCDebug(lcTransient) << this << "is transient for" << window;
setTransientParent(window);
disconnect(sender(), SIGNAL(windowChanged(QQuickWindow*)),
this, SLOT(setTransientParent_helper(QQuickWindow*)));
@@ -3542,7 +3547,7 @@ QOpenGLContext *QQuickWindow::openglContext() const
bool QQuickWindow::isSceneGraphInitialized() const
{
Q_D(const QQuickWindow);
- return d->context != 0 && d->context->isValid();
+ return d->context != nullptr && d->context->isValid();
}
/*!
@@ -3720,7 +3725,7 @@ void QQuickWindow::setRenderTarget(uint fboId, const QSize &size)
d->renderTargetSize = size;
// Unset any previously set instance...
- d->renderTarget = 0;
+ d->renderTarget = nullptr;
}
@@ -3834,7 +3839,7 @@ QQmlIncubationController *QQuickWindow::incubationController() const
Q_D(const QQuickWindow);
if (!d->windowManager)
- return 0; // TODO: make sure that this is safe
+ return nullptr; // TODO: make sure that this is safe
if (!d->incubationController)
d->incubationController = new QQuickWindowIncubationController(d->windowManager);
@@ -4078,7 +4083,7 @@ bool QQuickWindow::clearBeforeRendering() const
QSGTexture *QQuickWindow::createTextureFromImage(const QImage &image) const
{
- return createTextureFromImage(image, 0);
+ return createTextureFromImage(image, nullptr);
}
@@ -4127,7 +4132,7 @@ QSGTexture *QQuickWindow::createTextureFromImage(const QImage &image, CreateText
{
Q_D(const QQuickWindow);
if (!isSceneGraphInitialized()) // check both for d->context and d->context->isValid()
- return 0;
+ return nullptr;
uint flags = 0;
if (options & TextureCanUseAtlas) flags |= QSGRenderContext::CreateTexture_Atlas;
if (options & TextureHasMipmaps) flags |= QSGRenderContext::CreateTexture_Mipmap;
@@ -4173,7 +4178,7 @@ QSGTexture *QQuickWindow::createTextureFromId(uint id, const QSize &size, Create
Q_UNUSED(size)
Q_UNUSED(options)
#endif
- return 0;
+ return nullptr;
}
/*!
@@ -4287,7 +4292,7 @@ void QQuickWindow::resetOpenGLState()
int maxAttribs;
gl->glGetIntegerv(GL_MAX_VERTEX_ATTRIBS, &maxAttribs);
for (int i=0; i<maxAttribs; ++i) {
- gl->glVertexAttribPointer(i, 4, GL_FLOAT, GL_FALSE, 0, 0);
+ gl->glVertexAttribPointer(i, 4, GL_FLOAT, GL_FALSE, 0, nullptr);
gl->glDisableVertexAttribArray(i);
}
}
@@ -4946,6 +4951,37 @@ void QQuickWindow::setTextRenderType(QQuickWindow::TextRenderType renderType)
QQuickWindowPrivate::textRenderType = renderType;
}
+#ifndef QT_NO_DEBUG_STREAM
+QDebug operator<<(QDebug debug, const QQuickWindow *win)
+{
+ QDebugStateSaver saver(debug);
+ debug.nospace();
+ if (!win) {
+ debug << "QQuickWindow(0)";
+ return debug;
+ }
+
+ debug << win->metaObject()->className() << '(' << static_cast<const void *>(win);
+ if (win->isActive())
+ debug << " active";
+ if (win->isExposed())
+ debug << " exposed";
+ debug << ", visibility=" << win->visibility() << ", flags=" << win->flags();
+ if (!win->title().isEmpty())
+ debug << ", title=" << win->title();
+ if (!win->objectName().isEmpty())
+ debug << ", name=" << win->objectName();
+ if (win->parent())
+ debug << ", parent=" << static_cast<const void *>(win->parent());
+ if (win->transientParent())
+ debug << ", transientParent=" << static_cast<const void *>(win->transientParent());
+ debug << ", geometry=";
+ QtDebugUtils::formatQRect(debug, win->geometry());
+ debug << ')';
+ return debug;
+}
+#endif
+
#include "moc_qquickwindow.cpp"
QT_END_NAMESPACE
diff --git a/src/quick/items/qquickwindow.h b/src/quick/items/qquickwindow.h
index e5b54c8fb9..817178fdac 100644
--- a/src/quick/items/qquickwindow.h
+++ b/src/quick/items/qquickwindow.h
@@ -110,7 +110,7 @@ public:
explicit QQuickWindow(QWindow *parent = nullptr);
explicit QQuickWindow(QQuickRenderControl *renderControl);
- virtual ~QQuickWindow();
+ ~QQuickWindow() override;
QQuickItem *contentItem() const;
@@ -204,6 +204,7 @@ public Q_SLOTS:
protected:
QQuickWindow(QQuickWindowPrivate &dd, QWindow *parent = nullptr);
+ QQuickWindow(QQuickWindowPrivate &dd, QQuickRenderControl *control);
void exposeEvent(QExposeEvent *) override;
void resizeEvent(QResizeEvent *) override;
@@ -233,7 +234,7 @@ private Q_SLOTS:
void handleScreenChanged(QScreen *screen);
void setTransientParent_helper(QQuickWindow *window);
void runJobsAfterSwap();
-
+ void handleApplicationStateChanged(Qt::ApplicationState state);
private:
friend class QQuickItem;
friend class QQuickWidget;
@@ -242,6 +243,10 @@ private:
Q_DISABLE_COPY(QQuickWindow)
};
+#ifndef QT_NO_DEBUG_STREAM
+QDebug Q_QUICK_EXPORT operator<<(QDebug debug, const QQuickWindow *item);
+#endif
+
QT_END_NAMESPACE
Q_DECLARE_METATYPE(QQuickWindow *)
diff --git a/src/quick/items/qquickwindow_p.h b/src/quick/items/qquickwindow_p.h
index 8ac6cdfa36..82c01e7f54 100644
--- a/src/quick/items/qquickwindow_p.h
+++ b/src/quick/items/qquickwindow_p.h
@@ -114,9 +114,9 @@ public:
static inline QQuickWindowPrivate *get(QQuickWindow *c) { return c->d_func(); }
QQuickWindowPrivate();
- virtual ~QQuickWindowPrivate();
+ ~QQuickWindowPrivate() override;
- void init(QQuickWindow *, QQuickRenderControl *control = 0);
+ void init(QQuickWindow *, QQuickRenderControl *control = nullptr);
QQuickRootItem *contentItem;
QSet<QQuickItem *> parentlessItems;
@@ -141,11 +141,12 @@ public:
// Mouse positions are saved in widget coordinates
QPointF lastMousePosition;
bool deliverTouchAsMouse(QQuickItem *item, QQuickPointerEvent *pointerEvent);
+ bool isDeliveringTouchAsMouse() const { return touchMouseId != -1 && touchMouseDevice; }
void translateTouchEvent(QTouchEvent *touchEvent);
- void setMouseGrabber(QQuickItem *grabber);
void grabTouchPoints(QObject *grabber, const QVector<int> &ids);
void removeGrabber(QQuickItem *grabber, bool mouse = true, bool touch = true);
- static QMouseEvent *cloneMouseEvent(QMouseEvent *event, QPointF *transformedLocalPos = 0);
+ void sendUngrabEvent(QQuickItem *grabber, bool touch);
+ static QMouseEvent *cloneMouseEvent(QMouseEvent *event, QPointF *transformedLocalPos = nullptr);
void deliverToPassiveGrabbers(const QVector<QPointer <QQuickPointerHandler> > &passiveGrabbers, QQuickPointerEvent *pointerEvent);
void deliverMouseEvent(QQuickPointerMouseEvent *pointerEvent);
bool sendFilteredMouseEvent(QEvent *event, QQuickItem *receiver, QQuickItem *filteringParent);
@@ -167,6 +168,7 @@ public:
// the device-specific event instances which are reused during event delivery
mutable QVector<QQuickPointerEvent *> pointerEventInstances;
+ QQuickPointerEvent *queryPointerEventInstance(QQuickPointerDevice *device, QEvent::Type eventType = QEvent::None) const;
QQuickPointerEvent *pointerEventInstance(QQuickPointerDevice *device, QEvent::Type eventType = QEvent::None) const;
// delivery of pointer events:
@@ -203,8 +205,8 @@ public:
};
Q_DECLARE_FLAGS(FocusOptions, FocusOption)
- void setFocusInScope(QQuickItem *scope, QQuickItem *item, Qt::FocusReason reason, FocusOptions = 0);
- void clearFocusInScope(QQuickItem *scope, QQuickItem *item, Qt::FocusReason reason, FocusOptions = 0);
+ void setFocusInScope(QQuickItem *scope, QQuickItem *item, Qt::FocusReason reason, FocusOptions = nullptr);
+ void clearFocusInScope(QQuickItem *scope, QQuickItem *item, Qt::FocusReason reason, FocusOptions = nullptr);
static void notifyFocusChangesRecur(QQuickItem **item, int remaining);
void clearFocusObject() override;
diff --git a/src/quick/items/qquickwindowattached.cpp b/src/quick/items/qquickwindowattached.cpp
index d3835ed45c..37f0a812e7 100644
--- a/src/quick/items/qquickwindowattached.cpp
+++ b/src/quick/items/qquickwindowattached.cpp
@@ -47,7 +47,7 @@ QT_BEGIN_NAMESPACE
QQuickWindowAttached::QQuickWindowAttached(QObject* attachee)
: QObject(attachee)
- , m_window(NULL)
+ , m_window(nullptr)
{
m_attachee = qobject_cast<QQuickItem*>(attachee);
if (m_attachee && m_attachee->window()) // It might not be in a window yet
diff --git a/src/quick/items/qquickwindowmodule.cpp b/src/quick/items/qquickwindowmodule.cpp
index 45e3f0004d..ab3f49d5b6 100644
--- a/src/quick/items/qquickwindowmodule.cpp
+++ b/src/quick/items/qquickwindowmodule.cpp
@@ -52,6 +52,8 @@
QT_BEGIN_NAMESPACE
+Q_DECLARE_LOGGING_CATEGORY(lcTransient)
+
class QQuickWindowQmlImplPrivate : public QQuickWindowPrivate
{
public:
@@ -112,7 +114,7 @@ void QQuickWindowQmlImpl::classBegin()
{
// The content item has CppOwnership policy (set in QQuickWindow). Ensure the presence of a JS
// wrapper so that the garbage collector can see the policy.
- QV4::ExecutionEngine *v4 = QQmlEnginePrivate::getV4Engine(e);
+ QV4::ExecutionEngine *v4 = e->handle();
QV4::QObjectWrapper::wrap(v4, d->contentItem);
}
}
@@ -121,7 +123,13 @@ void QQuickWindowQmlImpl::componentComplete()
{
Q_D(QQuickWindowQmlImpl);
d->complete = true;
- if (transientParent() && !transientParent()->isVisible()) {
+ QQuickItem *itemParent = qmlobject_cast<QQuickItem *>(QObject::parent());
+ if (itemParent && !itemParent->window()) {
+ qCDebug(lcTransient) << "window" << title() << "has invisible Item parent" << itemParent << "transientParent"
+ << transientParent() << "declared visibility" << d->visibility << "; delaying show";
+ connect(itemParent, &QQuickItem::windowChanged, this,
+ &QQuickWindowQmlImpl::setWindowVisibility, Qt::QueuedConnection);
+ } else if (transientParent() && !transientParent()->isVisible()) {
connect(transientParent(), &QQuickWindow::visibleChanged, this,
&QQuickWindowQmlImpl::setWindowVisibility, Qt::QueuedConnection);
} else {
@@ -135,9 +143,10 @@ void QQuickWindowQmlImpl::setWindowVisibility()
if (transientParent() && !transientParent()->isVisible())
return;
- if (sender()) {
- disconnect(transientParent(), &QWindow::visibleChanged, this,
- &QQuickWindowQmlImpl::setWindowVisibility);
+ if (QQuickItem *senderItem = qmlobject_cast<QQuickItem *>(sender())) {
+ disconnect(senderItem, &QQuickItem::windowChanged, this, &QQuickWindowQmlImpl::setWindowVisibility);
+ } else if (sender()) {
+ disconnect(transientParent(), &QWindow::visibleChanged, this, &QQuickWindowQmlImpl::setWindowVisibility);
}
// We have deferred window creation until we have the full picture of what
diff --git a/src/quick/qtquick2.cpp b/src/quick/qtquick2.cpp
index 00fc23645b..24467a3701 100644
--- a/src/quick/qtquick2.cpp
+++ b/src/quick/qtquick2.cpp
@@ -140,7 +140,7 @@ void QQmlQtQuick2DebugStatesDelegate::updateBinding(QQmlContext *context,
if (state->isStateActive() && state->containsPropertyInRevertList(object, propertyName)) {
*inBaseState = false;
- QQmlBinding *newBinding = 0;
+ QQmlBinding *newBinding = nullptr;
if (!isLiteralValue) {
newBinding = QQmlBinding::create(&QQmlPropertyPrivate::get(property)->core,
expression.toString(), object,
diff --git a/src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer.cpp b/src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer.cpp
index 02cf8209d1..d715d900ba 100644
--- a/src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer.cpp
@@ -193,6 +193,12 @@ QRegion QSGAbstractSoftwareRenderer::optimizeRenderList()
}
}
+ if (m_obscuredRegion.contains(m_background->rect().toAlignedRect())) {
+ m_isOpaque = true;
+ } else {
+ m_isOpaque = false;
+ }
+
// Empty dirtyRegion (for second pass)
m_dirtyRegion = QRegion();
m_obscuredRegion = QRegion();
@@ -227,11 +233,11 @@ void QSGAbstractSoftwareRenderer::setBackgroundColor(const QColor &color)
renderableNode(m_background)->markMaterialDirty();
}
-void QSGAbstractSoftwareRenderer::setBackgroundSize(const QSize &size)
+void QSGAbstractSoftwareRenderer::setBackgroundRect(const QRect &rect)
{
- if (m_background->rect().size().toSize() == size)
+ if (m_background->rect().toRect() == rect)
return;
- m_background->setRect(0.0f, 0.0f, size.width(), size.height());
+ m_background->setRect(rect);
renderableNode(m_background)->markGeometryDirty();
// Invalidate the whole scene when the background is resized
markDirty();
@@ -242,21 +248,21 @@ QColor QSGAbstractSoftwareRenderer::backgroundColor()
return m_background->color();
}
-QSize QSGAbstractSoftwareRenderer::backgroundSize()
+QRect QSGAbstractSoftwareRenderer::backgroundRect()
{
- return m_background->rect().size().toSize();
+ return m_background->rect().toRect();
}
void QSGAbstractSoftwareRenderer::nodeAdded(QSGNode *node)
{
- qCDebug(lc2DRender) << "nodeAdded" << (void*)node;
+ qCDebug(lc2DRender, "nodeAdded %p", (void*)node);
m_nodeUpdater->updateNodes(node);
}
void QSGAbstractSoftwareRenderer::nodeRemoved(QSGNode *node)
{
- qCDebug(lc2DRender) << "nodeRemoved" << (void*)node;
+ qCDebug(lc2DRender, "nodeRemoved %p", (void*)node);
auto renderable = renderableNode(node);
// remove mapping
@@ -280,7 +286,7 @@ void QSGAbstractSoftwareRenderer::nodeRemoved(QSGNode *node)
void QSGAbstractSoftwareRenderer::nodeGeometryUpdated(QSGNode *node)
{
- qCDebug(lc2DRender) << "nodeGeometryUpdated";
+ qCDebug(lc2DRender, "nodeGeometryUpdated");
// Mark node as dirty
auto renderable = renderableNode(node);
@@ -293,7 +299,7 @@ void QSGAbstractSoftwareRenderer::nodeGeometryUpdated(QSGNode *node)
void QSGAbstractSoftwareRenderer::nodeMaterialUpdated(QSGNode *node)
{
- qCDebug(lc2DRender) << "nodeMaterialUpdated";
+ qCDebug(lc2DRender, "nodeMaterialUpdated");
// Mark node as dirty
auto renderable = renderableNode(node);
@@ -306,7 +312,7 @@ void QSGAbstractSoftwareRenderer::nodeMaterialUpdated(QSGNode *node)
void QSGAbstractSoftwareRenderer::nodeMatrixUpdated(QSGNode *node)
{
- qCDebug(lc2DRender) << "nodeMaterialUpdated";
+ qCDebug(lc2DRender, "nodeMaterialUpdated");
// Update children nodes
m_nodeUpdater->updateNodes(node);
@@ -314,7 +320,7 @@ void QSGAbstractSoftwareRenderer::nodeMatrixUpdated(QSGNode *node)
void QSGAbstractSoftwareRenderer::nodeOpacityUpdated(QSGNode *node)
{
- qCDebug(lc2DRender) << "nodeOpacityUpdated";
+ qCDebug(lc2DRender, "nodeOpacityUpdated");
// Update children nodes
m_nodeUpdater->updateNodes(node);
diff --git a/src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer_p.h b/src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer_p.h
index 04a17ea377..f6594d931a 100644
--- a/src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer_p.h
+++ b/src/quick/scenegraph/adaptations/software/qsgabstractsoftwarerenderer_p.h
@@ -83,9 +83,11 @@ protected:
QRegion optimizeRenderList();
void setBackgroundColor(const QColor &color);
- void setBackgroundSize(const QSize &size);
+ void setBackgroundRect(const QRect &rect);
QColor backgroundColor();
- QSize backgroundSize();
+ QRect backgroundRect();
+ // only known after calling optimizeRenderList()
+ bool isOpaque() const { return m_isOpaque; }
private:
void nodeAdded(QSGNode *node);
@@ -102,6 +104,7 @@ private:
QRegion m_dirtyRegion;
QRegion m_obscuredRegion;
+ bool m_isOpaque = false;
QSGSoftwareRenderableNodeUpdater *m_nodeUpdater;
};
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation.cpp
index 92c02b4966..a8b5944974 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation.cpp
@@ -87,6 +87,6 @@ QSGRenderLoop *QSGSoftwareAdaptation::createWindowManager()
return new QSGSoftwareRenderLoop();
}
-QSGSoftwareContext *QSGSoftwareAdaptation::instance = 0;
+QSGSoftwareContext *QSGSoftwareAdaptation::instance = nullptr;
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation_p.h b/src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation_p.h
index ffe54b5d4b..8b2a545033 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation_p.h
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwareadaptation_p.h
@@ -62,7 +62,7 @@ class QSGSoftwareContext;
class QSGSoftwareAdaptation : public QSGContextPlugin
{
public:
- QSGSoftwareAdaptation(QObject *parent = 0);
+ QSGSoftwareAdaptation(QObject *parent = nullptr);
QStringList keys() const override;
QSGContext *create(const QString &key) const override;
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarecontext.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarecontext.cpp
index aa850a80db..5b5bf005d8 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarecontext.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarecontext.cpp
@@ -205,12 +205,12 @@ QSGRendererInterface::ShaderType QSGSoftwareContext::shaderType() const
QSGRendererInterface::ShaderCompilationTypes QSGSoftwareContext::shaderCompilationType() const
{
- return 0;
+ return nullptr;
}
QSGRendererInterface::ShaderSourceTypes QSGSoftwareContext::shaderSourceType() const
{
- return 0;
+ return nullptr;
}
void *QSGSoftwareContext::getResource(QQuickWindow *window, Resource resource) const
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode.cpp
index 10291b9cb5..3b0f3c48ff 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode.cpp
@@ -318,7 +318,7 @@ void qDrawBorderPixmap(QPainter *painter, const QRect &targetRect, const QMargin
QSGSoftwareInternalImageNode::QSGSoftwareInternalImageNode()
: m_innerSourceRect(0, 0, 1, 1)
, m_subSourceRect(0, 0, 1, 1)
- , m_texture(0)
+ , m_texture(nullptr)
, m_mirror(false)
, m_smooth(true)
, m_tileHorizontal(false)
@@ -462,7 +462,7 @@ void QSGSoftwareInternalImageNode::paint(QPainter *painter)
m_targetRect.right() - m_innerTargetRect.right(), m_targetRect.bottom() - m_innerTargetRect.bottom());
QSGSoftwareHelpers::QTileRules tilerules(getTileRule(m_subSourceRect.width()), getTileRule(m_subSourceRect.height()));
QSGSoftwareHelpers::qDrawBorderPixmap(painter, m_targetRect.toRect(), margins, pm, QRect(0, 0, pm.width(), pm.height()),
- margins, tilerules, QSGSoftwareHelpers::QDrawBorderPixmap::DrawingHints(0));
+ margins, tilerules, QSGSoftwareHelpers::QDrawBorderPixmap::DrawingHints(nullptr));
return;
}
@@ -490,12 +490,13 @@ QRectF QSGSoftwareInternalImageNode::rect() const
const QPixmap &QSGSoftwareInternalImageNode::pixmap() const
{
- if (QSGSoftwarePixmapTexture *pt = qobject_cast<QSGSoftwarePixmapTexture*>(m_texture)) {
+ if (QSGSoftwarePixmapTexture *pt = qobject_cast<QSGSoftwarePixmapTexture*>(m_texture))
return pt->pixmap();
- } else {
- QSGSoftwareLayer *layer = qobject_cast<QSGSoftwareLayer*>(m_texture);
+ if (QSGSoftwareLayer *layer = qobject_cast<QSGSoftwareLayer*>(m_texture))
return layer->pixmap();
- }
+ Q_ASSERT(m_texture == nullptr);
+ static const QPixmap nullPixmap;
+ return nullPixmap;
}
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode_p.h b/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode_p.h
index f21667fdf7..5c95eb064a 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode_p.h
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalimagenode_p.h
@@ -124,8 +124,8 @@ public:
QRectF rect() const;
-private:
const QPixmap &pixmap() const;
+private:
QRectF m_targetRect;
QRectF m_innerTargetRect;
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode.cpp
index f6898b3879..bf3141bc32 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode.cpp
@@ -227,8 +227,8 @@ void QSGSoftwareInternalRectangleNode::paint(QPainter *painter)
{
//We can only check for a device pixel ratio change when we know what
//paint device is being used.
- if (painter->device()->devicePixelRatio() != m_devicePixelRatio) {
- m_devicePixelRatio = painter->device()->devicePixelRatio();
+ if (!qFuzzyCompare(painter->device()->devicePixelRatioF(), m_devicePixelRatio)) {
+ m_devicePixelRatio = painter->device()->devicePixelRatioF();
generateCornerPixmap();
}
@@ -245,7 +245,7 @@ void QSGSoftwareInternalRectangleNode::paint(QPainter *painter)
} else {
//Rounded Rects and Rects with Borders
//Avoids broken behaviors of QPainter::drawRect/roundedRect
- QPixmap pixmap = QPixmap(m_rect.width() * m_devicePixelRatio, m_rect.height() * m_devicePixelRatio);
+ QPixmap pixmap = QPixmap(qRound(m_rect.width() * m_devicePixelRatio), qRound(m_rect.height() * m_devicePixelRatio));
pixmap.fill(Qt::transparent);
pixmap.setDevicePixelRatio(m_devicePixelRatio);
QPainter pixmapPainter(&pixmap);
@@ -356,7 +356,7 @@ void QSGSoftwareInternalRectangleNode::paintRectangle(QPainter *painter, const Q
} else {
//blit 4 corners to border
- int scaledRadius = radius * m_devicePixelRatio;
+ int scaledRadius = qRound(radius * m_devicePixelRatio);
QRectF topLeftCorner(QPointF(rect.x(), rect.y()),
QPointF(rect.x() + radius, rect.y() + radius));
painter->drawPixmap(topLeftCorner, m_cornerPixmap, QRectF(0, 0, scaledRadius, scaledRadius));
@@ -416,7 +416,7 @@ void QSGSoftwareInternalRectangleNode::generateCornerPixmap()
//Generate new corner Pixmap
int radius = qFloor(qMin(qMin(m_rect.width(), m_rect.height()) * 0.5, m_radius));
- m_cornerPixmap = QPixmap(radius * 2 * m_devicePixelRatio, radius * 2 * m_devicePixelRatio);
+ m_cornerPixmap = QPixmap(qRound(radius * 2 * m_devicePixelRatio), qRound(radius * 2 * m_devicePixelRatio));
m_cornerPixmap.setDevicePixelRatio(m_devicePixelRatio);
m_cornerPixmap.fill(Qt::transparent);
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode_p.h b/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode_p.h
index f363e279e1..1f87424d2a 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode_p.h
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwareinternalrectanglenode_p.h
@@ -95,7 +95,7 @@ private:
bool m_cornerPixmapIsDirty;
QPixmap m_cornerPixmap;
- int m_devicePixelRatio;
+ qreal m_devicePixelRatio;
};
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarelayer.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarelayer.cpp
index bd5d8f72c0..b4301451d8 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarelayer.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarelayer.cpp
@@ -45,9 +45,9 @@
QT_BEGIN_NAMESPACE
QSGSoftwareLayer::QSGSoftwareLayer(QSGRenderContext *renderContext)
- : m_item(0)
+ : m_item(nullptr)
, m_context(renderContext)
- , m_renderer(0)
+ , m_renderer(nullptr)
, m_device_pixel_ratio(1)
, m_mirrorHorizontal(false)
, m_mirrorVertical(true)
@@ -203,7 +203,7 @@ void QSGSoftwareLayer::markDirtyTexture()
void QSGSoftwareLayer::invalidated()
{
delete m_renderer;
- m_renderer = 0;
+ m_renderer = nullptr;
}
void QSGSoftwareLayer::grab()
@@ -229,9 +229,6 @@ void QSGSoftwareLayer::grab()
if (m_pixmap.size() != m_size) {
m_pixmap = QPixmap(m_size);
m_pixmap.setDevicePixelRatio(m_device_pixel_ratio);
- // This fill here is wasteful, but necessary because it is the only way
- // to force a QImage based pixmap to have an alpha channel.
- m_pixmap.fill(Qt::transparent);
}
// Render texture.
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarepainternode.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarepainternode.cpp
index 34b0cd5b72..60ae06dd94 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarepainternode.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarepainternode.cpp
@@ -47,7 +47,7 @@ QSGSoftwarePainterNode::QSGSoftwarePainterNode(QQuickPaintedItem *item)
: QSGPainterNode()
, m_preferredRenderTarget(QQuickPaintedItem::Image)
, m_item(item)
- , m_texture(0)
+ , m_texture(nullptr)
, m_dirtyContents(false)
, m_opaquePainting(false)
, m_linear_filtering(false)
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarepixmaprenderer.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarepixmaprenderer.cpp
index ad6cf39425..303f98c801 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarepixmaprenderer.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarepixmaprenderer.cpp
@@ -79,16 +79,9 @@ void QSGSoftwarePixmapRenderer::render(QPaintDevice *target)
QElapsedTimer renderTimer;
// Setup background item
- setBackgroundSize(QSize(target->width(), target->height()));
+ setBackgroundRect(m_projectionRect);
setBackgroundColor(clearColor());
- QPainter painter(target);
- painter.setRenderHint(QPainter::Antialiasing);
- painter.setWindow(m_projectionRect);
- auto rc = static_cast<QSGSoftwareRenderContext *>(context());
- QPainter *prevPainter = rc->m_activePainter;
- rc->m_activePainter = &painter;
-
renderTimer.start();
buildRenderList();
qint64 buildRenderListTime = renderTimer.restart();
@@ -101,6 +94,19 @@ void QSGSoftwarePixmapRenderer::render(QPaintDevice *target)
optimizeRenderList();
qint64 optimizeRenderListTime = renderTimer.restart();
+ if (!isOpaque() && target->devType() == QInternal::Pixmap) {
+ // This fill here is wasteful, but necessary because it is the only way
+ // to force a QImage based pixmap to have an alpha channel.
+ static_cast<QPixmap *>(target)->fill(Qt::transparent);
+ }
+
+ QPainter painter(target);
+ painter.setRenderHint(QPainter::Antialiasing);
+ painter.setWindow(m_projectionRect);
+ auto rc = static_cast<QSGSoftwareRenderContext *>(context());
+ QPainter *prevPainter = rc->m_activePainter;
+ rc->m_activePainter = &painter;
+
QRegion paintedRegion = renderNodes(&painter);
qint64 renderTime = renderTimer.elapsed();
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes.cpp
index 77d21ec042..1463681fa3 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes.cpp
@@ -188,7 +188,7 @@ void QSGSoftwareNinePatchNode::paint(QPainter *painter)
painter->drawPixmap(m_bounds, m_pixmap, QRectF(0, 0, m_pixmap.width(), m_pixmap.height()));
else
QSGSoftwareHelpers::qDrawBorderPixmap(painter, m_bounds.toRect(), m_margins, m_pixmap, QRect(0, 0, m_pixmap.width(), m_pixmap.height()),
- m_margins, Qt::StretchTile, QSGSoftwareHelpers::QDrawBorderPixmap::DrawingHints(0));
+ m_margins, Qt::StretchTile, QSGSoftwareHelpers::QDrawBorderPixmap::DrawingHints(nullptr));
}
QRectF QSGSoftwareNinePatchNode::bounds() const
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes_p.h b/src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes_p.h
index 9f1913205b..114137fb55 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes_p.h
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarepublicnodes_p.h
@@ -133,6 +133,8 @@ public:
QRectF bounds() const;
+ bool isOpaque() const { return !m_pixmap.hasAlphaChannel(); }
+
private:
QPixmap m_pixmap;
QRectF m_bounds;
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenode.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenode.cpp
index cecc6c21ca..7fb531cca3 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenode.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenode.cpp
@@ -134,73 +134,58 @@ void QSGSoftwareRenderableNode::update()
{
// Update the Node properties
m_isDirty = true;
+ m_isOpaque = false;
QRectF boundingRect;
switch (m_nodeType) {
case QSGSoftwareRenderableNode::SimpleRect:
- if (m_handle.simpleRectNode->color().alpha() == 255 && !m_transform.isRotating())
+ if (m_handle.simpleRectNode->color().alpha() == 255)
m_isOpaque = true;
- else
- m_isOpaque = false;
boundingRect = m_handle.simpleRectNode->rect();
break;
case QSGSoftwareRenderableNode::SimpleTexture:
- if (!m_handle.simpleTextureNode->texture()->hasAlphaChannel() && !m_transform.isRotating())
+ if (!m_handle.simpleTextureNode->texture()->hasAlphaChannel())
m_isOpaque = true;
- else
- m_isOpaque = false;
boundingRect = m_handle.simpleTextureNode->rect();
break;
case QSGSoftwareRenderableNode::Image:
- // There isn't a way to tell, so assume it's not
- m_isOpaque = false;
+ m_isOpaque = !m_handle.imageNode->pixmap().hasAlphaChannel();
boundingRect = m_handle.imageNode->rect().toRect();
break;
case QSGSoftwareRenderableNode::Painter:
- if (m_handle.painterNode->opaquePainting() && !m_transform.isRotating())
+ if (m_handle.painterNode->opaquePainting())
m_isOpaque = true;
- else
- m_isOpaque = false;
boundingRect = QRectF(0, 0, m_handle.painterNode->size().width(), m_handle.painterNode->size().height());
break;
case QSGSoftwareRenderableNode::Rectangle:
- if (m_handle.rectangleNode->isOpaque() && !m_transform.isRotating())
+ if (m_handle.rectangleNode->isOpaque())
m_isOpaque = true;
- else
- m_isOpaque = false;
boundingRect = m_handle.rectangleNode->rect();
break;
case QSGSoftwareRenderableNode::Glyph:
// Always has alpha
- m_isOpaque = false;
-
boundingRect = m_handle.glpyhNode->boundingRect();
break;
case QSGSoftwareRenderableNode::NinePatch:
- // Difficult to tell, assume non-opaque
- m_isOpaque = false;
+ m_isOpaque = m_handle.ninePatchNode->isOpaque();
boundingRect = m_handle.ninePatchNode->bounds();
break;
case QSGSoftwareRenderableNode::SimpleRectangle:
- if (m_handle.simpleRectangleNode->color().alpha() == 255 && !m_transform.isRotating())
+ if (m_handle.simpleRectangleNode->color().alpha() == 255)
m_isOpaque = true;
- else
- m_isOpaque = false;
boundingRect = m_handle.simpleRectangleNode->rect();
break;
case QSGSoftwareRenderableNode::SimpleImage:
- if (!m_handle.simpleImageNode->texture()->hasAlphaChannel() && !m_transform.isRotating())
+ if (!m_handle.simpleImageNode->texture()->hasAlphaChannel())
m_isOpaque = true;
- else
- m_isOpaque = false;
boundingRect = m_handle.simpleImageNode->rect();
break;
@@ -211,10 +196,8 @@ void QSGSoftwareRenderableNode::update()
break;
#endif
case QSGSoftwareRenderableNode::RenderNode:
- if (m_handle.renderNode->flags().testFlag(QSGRenderNode::OpaqueRendering) && !m_transform.isRotating())
+ if (m_handle.renderNode->flags().testFlag(QSGRenderNode::OpaqueRendering))
m_isOpaque = true;
- else
- m_isOpaque = false;
boundingRect = m_handle.renderNode->rect();
break;
@@ -222,6 +205,9 @@ void QSGSoftwareRenderableNode::update()
break;
}
+ if (m_transform.isRotating())
+ m_isOpaque = false;
+
const QRectF transformedRect = m_transform.mapRect(boundingRect);
m_boundingRectMin = toRectMin(transformedRect);
m_boundingRectMax = toRectMax(transformedRect);
@@ -232,8 +218,9 @@ void QSGSoftwareRenderableNode::update()
m_boundingRectMin = QRect();
m_boundingRectMax = QRect();
} else {
- m_boundingRectMin = m_boundingRectMin.intersected(m_clipRegion.rects().constFirst());
- m_boundingRectMax = m_boundingRectMax.intersected(m_clipRegion.rects().constFirst());
+ const auto rects = m_clipRegion.begin();
+ m_boundingRectMin = m_boundingRectMin.intersected(rects[0]);
+ m_boundingRectMax = m_boundingRectMax.intersected(rects[0]);
}
}
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenodeupdater.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenodeupdater.cpp
index 666f1d0616..fabecfcbb8 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenodeupdater.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenodeupdater.cpp
@@ -83,7 +83,7 @@ void QSGSoftwareRenderableNodeUpdater::endVisit(QSGTransformNode *)
bool QSGSoftwareRenderableNodeUpdater::visit(QSGClipNode *node)
{
// Make sure to translate the clip rect into world coordinates
- if (m_clipState.count() == 0 || m_clipState.top().isNull()) {
+ if (m_clipState.count() == 0 || (m_clipState.count() == 1 && m_clipState.top().isNull())) {
m_clipState.push(m_transformState.top().map(QRegion(node->clipRect().toRect())));
m_hasClip = true;
} else {
@@ -97,7 +97,7 @@ bool QSGSoftwareRenderableNodeUpdater::visit(QSGClipNode *node)
void QSGSoftwareRenderableNodeUpdater::endVisit(QSGClipNode *)
{
m_clipState.pop();
- if (m_clipState.count() == 0 || m_clipState.top().isNull())
+ if (m_clipState.count() == 0 || (m_clipState.count() == 1 && m_clipState.top().isNull()))
m_hasClip = false;
}
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderer.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderer.cpp
index 85d04fe136..ffcee5f56e 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderer.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderer.cpp
@@ -112,7 +112,8 @@ void QSGSoftwareRenderer::render()
QElapsedTimer renderTimer;
setBackgroundColor(clearColor());
- setBackgroundSize(QSize(m_paintDevice->width() / m_paintDevice->devicePixelRatio(),
+ setBackgroundRect(QRect(0, 0,
+ m_paintDevice->width() / m_paintDevice->devicePixelRatio(),
m_paintDevice->height() / m_paintDevice->devicePixelRatio()));
// Build Renderlist
@@ -155,6 +156,7 @@ void QSGSoftwareRenderer::render()
m_flushRegion = renderNodes(&painter);
qint64 renderTime = renderTimer.elapsed();
+ painter.end();
if (m_backingStore != nullptr)
m_backingStore->endPaint();
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderloop.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderloop.cpp
index 3f0d1383b9..423f5f7321 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderloop.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarerenderloop.cpp
@@ -97,7 +97,6 @@ void QSGSoftwareRenderLoop::windowDestroyed(QQuickWindow *window)
if (m_windows.size() == 0) {
rc->invalidate();
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
}
}
diff --git a/src/quick/scenegraph/adaptations/software/qsgsoftwarethreadedrenderloop.cpp b/src/quick/scenegraph/adaptations/software/qsgsoftwarethreadedrenderloop.cpp
index 832b69d0cc..f8973af2fb 100644
--- a/src/quick/scenegraph/adaptations/software/qsgsoftwarethreadedrenderloop.cpp
+++ b/src/quick/scenegraph/adaptations/software/qsgsoftwarethreadedrenderloop.cpp
@@ -294,7 +294,7 @@ bool QSGSoftwareRenderThread::event(QEvent *e)
}
rc->invalidate();
QCoreApplication::processEvents();
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
+ QCoreApplication::sendPostedEvents(nullptr, QEvent::DeferredDelete);
if (wme->destroying)
delete wd->animationController;
}
@@ -456,7 +456,7 @@ void QSGSoftwareRenderThread::sync(bool inExpose)
// Process deferred deletes now, directly after the sync as deleteLater
// on the GUI must now also have resulted in SG changes and the delete
// is a safe operation.
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
+ QCoreApplication::sendPostedEvents(nullptr, QEvent::DeferredDelete);
}
if (!inExpose) {
@@ -523,7 +523,7 @@ void QSGSoftwareRenderThread::syncAndRender()
// rate of the current screen the window is on.
int blockTime = vsyncDelta - (int) renderThrottleTimer.elapsed();
if (blockTime > 0) {
- qCDebug(QSG_RASTER_LOG_RENDERLOOP) << "RT - blocking for " << blockTime << "ms";
+ qCDebug(QSG_RASTER_LOG_RENDERLOOP, "RT - blocking for %d ms", blockTime);
msleep(blockTime);
}
renderThrottleTimer.restart();
diff --git a/src/quick/scenegraph/compressedtexture/qsgcompressedatlastexture.cpp b/src/quick/scenegraph/compressedtexture/qsgcompressedatlastexture.cpp
new file mode 100644
index 0000000000..e868a4380e
--- /dev/null
+++ b/src/quick/scenegraph/compressedtexture/qsgcompressedatlastexture.cpp
@@ -0,0 +1,174 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qsgcompressedatlastexture_p.h"
+
+#include <QtCore/QVarLengthArray>
+#include <QtCore/QElapsedTimer>
+#include <QtCore/QtMath>
+
+#include <QtGui/QOpenGLContext>
+#include <QtGui/QGuiApplication>
+#include <QtGui/QScreen>
+#include <QtGui/QSurface>
+#include <QtGui/QWindow>
+#include <QtGui/QOpenGLFunctions>
+#include <QtGui/QOpenGLTexture>
+#include <QDebug>
+
+#include <private/qqmlglobal_p.h>
+#include <private/qquickprofiler_p.h>
+#include <private/qsgtexture_p.h>
+#include <private/qsgcompressedtexture_p.h>
+#include <private/qsgpkmhandler_p.h>
+
+QT_BEGIN_NAMESPACE
+
+static QElapsedTimer qsg_renderer_timer;
+
+namespace QSGCompressedAtlasTexture
+{
+
+Atlas::Atlas(const QSize &size, uint format)
+ : QSGAtlasTexture::AtlasBase(size)
+ , m_format(format)
+{
+}
+
+Atlas::~Atlas()
+{
+}
+
+Texture *Atlas::create(const QByteArray &data, int dataLength, int dataOffset, const QSize &size, const QSize &paddedSize)
+{
+ // No need to lock, as manager already locked it.
+ QRect rect = m_allocator.allocate(paddedSize);
+ if (rect.width() > 0 && rect.height() > 0) {
+ Texture *t = new Texture(this, rect, data, dataLength, dataOffset, size);
+ m_pending_uploads << t;
+ return t;
+ }
+ return nullptr;
+}
+
+void Atlas::generateTexture()
+{
+ QOpenGLFunctions *funcs = QOpenGLContext::currentContext()->functions();
+ funcs->glCompressedTexImage2D(GL_TEXTURE_2D, 0, m_format,
+ m_size.width(), m_size.height(), 0,
+ (m_size.width() * m_size.height()) / 2,
+ nullptr);
+}
+
+void Atlas::uploadPendingTexture(int i)
+{
+ Texture *texture = static_cast<Texture*>(m_pending_uploads.at(i));
+
+ const QRect &r = texture->atlasSubRect();
+
+ QOpenGLFunctions *funcs = QOpenGLContext::currentContext()->functions();
+ funcs->glCompressedTexSubImage2D(GL_TEXTURE_2D, 0,
+ r.x(), r.y(), r.width(), r.height(), m_format,
+ texture->sizeInBytes(),
+ texture->data().constData() + texture->dataOffset());
+
+ qCDebug(QSG_LOG_TIME_TEXTURE).nospace() << "compressed atlastexture uploaded in: " << qsg_renderer_timer.elapsed()
+ << "ms (" << texture->textureSize().width() << "x"
+ << texture->textureSize().height() << ")";
+
+ // TODO: consider releasing the data (as is done in the regular atlas)?
+ // The advantage of keeping this data around is that it makes it much easier
+ // to remove the texture from the atlas
+}
+
+Texture::Texture(Atlas *atlas, const QRect &textureRect, const QByteArray &data, int dataLength, int dataOffset, const QSize &size)
+ : QSGAtlasTexture::TextureBase(atlas, textureRect)
+ , m_nonatlas_texture(nullptr)
+ , m_data(data)
+ , m_size(size)
+ , m_dataLength(dataLength)
+ , m_dataOffset(dataOffset)
+{
+ float w = atlas->size().width();
+ float h = atlas->size().height();
+ QRect nopad = atlasSubRect();
+ // offset by half-pixel to prevent bleeding when scaling
+ m_texture_coords_rect = QRectF((nopad.x() + .5) / w,
+ (nopad.y() + .5) / h,
+ (nopad.width() - 1.) / w,
+ (nopad.height() - 1.) / h);
+}
+
+Texture::~Texture()
+{
+ delete m_nonatlas_texture;
+}
+
+bool Texture::hasAlphaChannel() const
+{
+ return QSGCompressedTexture::formatIsOpaque(static_cast<Atlas*>(m_atlas)->format());
+}
+
+QSGTexture *Texture::removedFromAtlas() const
+{
+ if (m_nonatlas_texture) {
+ m_nonatlas_texture->setMipmapFiltering(mipmapFiltering());
+ m_nonatlas_texture->setFiltering(filtering());
+ return m_nonatlas_texture;
+ }
+
+ if (!m_data.isEmpty()) {
+ QSGCompressedTexture::DataPtr texData(QSGCompressedTexture::DataPtr::create());
+ texData->data = m_data;
+ texData->size = m_size;
+ texData->format = static_cast<Atlas*>(m_atlas)->format();
+ texData->hasAlpha = hasAlphaChannel();
+ texData->dataLength = m_dataLength;
+ texData->dataOffset = m_dataOffset;
+ m_nonatlas_texture = new QSGCompressedTexture(texData);
+ m_nonatlas_texture->setMipmapFiltering(mipmapFiltering());
+ m_nonatlas_texture->setFiltering(filtering());
+ }
+
+ return m_nonatlas_texture;
+}
+
+}
+
+QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/compressedtexture/qsgcompressedatlastexture_p.h b/src/quick/scenegraph/compressedtexture/qsgcompressedatlastexture_p.h
new file mode 100644
index 0000000000..59e935b623
--- /dev/null
+++ b/src/quick/scenegraph/compressedtexture/qsgcompressedatlastexture_p.h
@@ -0,0 +1,119 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QSGCOMPRESSEDATLASTEXTURE_P_H
+#define QSGCOMPRESSEDATLASTEXTURE_P_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include <QtCore/QSize>
+
+#include <QtGui/qopengl.h>
+
+#include <QtQuick/QSGTexture>
+#include <QtQuick/private/qsgareaallocator_p.h>
+#include <QtQuick/private/qsgatlastexture_p.h>
+
+QT_BEGIN_NAMESPACE
+
+class QSGCompressedTextureFactory;
+
+namespace QSGCompressedAtlasTexture {
+
+class Texture;
+
+class Atlas : public QSGAtlasTexture::AtlasBase
+{
+public:
+ Atlas(const QSize &size, uint format);
+ ~Atlas();
+
+ void generateTexture() override;
+ void uploadPendingTexture(int i) override;
+
+ Texture *create(const QByteArray &data, int dataLength, int dataOffset, const QSize &size, const QSize &paddedSize);
+
+ uint format() const { return m_format; }
+
+private:
+ uint m_format;
+};
+
+class Texture : public QSGAtlasTexture::TextureBase
+{
+ Q_OBJECT
+public:
+ Texture(Atlas *atlas, const QRect &textureRect, const QByteArray &data, int dataLength, int dataOffset, const QSize &size);
+ ~Texture();
+
+ QSize textureSize() const override { return m_size; }
+ bool hasAlphaChannel() const override;
+ bool hasMipmaps() const override { return false; }
+
+ QRectF normalizedTextureSubRect() const override { return m_texture_coords_rect; }
+
+ QSGTexture *removedFromAtlas() const override;
+
+ const QByteArray &data() const { return m_data; }
+ int sizeInBytes() const { return m_dataLength; }
+ int dataOffset() const { return m_dataOffset; }
+
+private:
+ QRectF m_texture_coords_rect;
+ mutable QSGTexture *m_nonatlas_texture;
+ QByteArray m_data;
+ QSize m_size;
+ int m_dataLength;
+ int m_dataOffset;
+};
+
+}
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/quick/scenegraph/compressedtexture/qsgcompressedtexture.cpp b/src/quick/scenegraph/compressedtexture/qsgcompressedtexture.cpp
new file mode 100644
index 0000000000..839c562989
--- /dev/null
+++ b/src/quick/scenegraph/compressedtexture/qsgcompressedtexture.cpp
@@ -0,0 +1,246 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+
+#include "qsgcompressedtexture_p.h"
+#include <QOpenGLContext>
+#include <QOpenGLTexture>
+#include <QOpenGLFunctions>
+#include <QDebug>
+#include <QtQuick/private/qquickwindow_p.h>
+
+QT_BEGIN_NAMESPACE
+
+Q_LOGGING_CATEGORY(QSG_LOG_TEXTUREIO, "qt.scenegraph.textureio");
+
+bool QSGCompressedTextureData::isValid() const
+{
+ if (data.isNull() || size.isEmpty() || !format)
+ return false;
+ if (dataLength < 0 || dataOffset < 0 || dataOffset >= data.length())
+ return false;
+ if (dataLength > 0 && qint64(dataOffset) + qint64(dataLength) > qint64(data.length()))
+ return false;
+
+ return true;
+}
+
+int QSGCompressedTextureData::sizeInBytes() const
+{
+ if (!isValid())
+ return 0;
+ return dataLength > 0 ? dataLength : data.length() - dataOffset;
+}
+
+Q_QUICK_PRIVATE_EXPORT QDebug operator<<(QDebug dbg, const QSGCompressedTextureData *d)
+{
+ QDebugStateSaver saver(dbg);
+
+ dbg.nospace() << "QSGCompressedTextureData(";
+ if (d) {
+ dbg << d->logName << ' ';
+ dbg << static_cast<QOpenGLTexture::TextureFormat>(d->format)
+ << "[0x" << hex << d->format << dec << "]";
+ dbg.space() << (d->hasAlpha ? "with" : "no") << "alpha" << d->size
+ << "databuffer" << d->data.size() << "offset" << d->dataOffset << "length";
+ dbg.nospace() << d->dataLength << ")";
+ } else {
+ dbg << "null)";
+ }
+ return dbg;
+}
+
+QSGCompressedTexture::QSGCompressedTexture(const DataPtr& texData)
+ : m_textureData(texData)
+{
+ if (m_textureData) {
+ m_size = m_textureData->size;
+ m_hasAlpha = m_textureData->hasAlpha;
+ }
+}
+
+QSGCompressedTexture::~QSGCompressedTexture()
+{
+#if QT_CONFIG(opengl)
+ if (m_textureId) {
+ QOpenGLContext *ctx = QOpenGLContext::currentContext();
+ QOpenGLFunctions *funcs = ctx ? ctx->functions() : nullptr;
+ if (!funcs)
+ return;
+
+ funcs->glDeleteTextures(1, &m_textureId);
+ }
+#endif
+}
+
+int QSGCompressedTexture::textureId() const
+{
+#if QT_CONFIG(opengl)
+ if (!m_textureId) {
+ QOpenGLContext *ctx = QOpenGLContext::currentContext();
+ QOpenGLFunctions *funcs = ctx ? ctx->functions() : nullptr;
+ if (!funcs)
+ return 0;
+
+ funcs->glGenTextures(1, &m_textureId);
+ }
+#endif
+ return m_textureId;
+}
+
+QSize QSGCompressedTexture::textureSize() const
+{
+ return m_size;
+}
+
+bool QSGCompressedTexture::hasAlphaChannel() const
+{
+ return m_hasAlpha;
+}
+
+bool QSGCompressedTexture::hasMipmaps() const
+{
+ return false;
+}
+
+void QSGCompressedTexture::bind()
+{
+#if QT_CONFIG(opengl)
+ QOpenGLContext *ctx = QOpenGLContext::currentContext();
+ QOpenGLFunctions *funcs = ctx ? ctx->functions() : nullptr;
+ if (!funcs)
+ return;
+
+ if (!textureId())
+ return;
+
+ funcs->glBindTexture(GL_TEXTURE_2D, m_textureId);
+
+ if (m_uploaded)
+ return;
+
+ QByteArray logName(m_textureData ? m_textureData->logName : QByteArrayLiteral("(unset)"));
+
+ if (!m_textureData || !m_textureData->isValid()) {
+ qCDebug(QSG_LOG_TEXTUREIO, "Invalid texture data for %s", logName.constData());
+ funcs->glBindTexture(GL_TEXTURE_2D, 0);
+ return;
+ }
+
+ if (Q_UNLIKELY(QSG_LOG_TEXTUREIO().isDebugEnabled())) {
+ qCDebug(QSG_LOG_TEXTUREIO) << "Uploading texture" << m_textureData.data();
+ while (funcs->glGetError() != GL_NO_ERROR);
+ }
+
+ funcs->glCompressedTexImage2D(GL_TEXTURE_2D, 0, m_textureData->format,
+ m_size.width(), m_size.height(), 0, m_textureData->sizeInBytes(),
+ m_textureData->data.constData() + m_textureData->dataOffset);
+
+ if (Q_UNLIKELY(QSG_LOG_TEXTUREIO().isDebugEnabled())) {
+ GLuint error = funcs->glGetError();
+ if (error != GL_NO_ERROR) {
+ qCDebug(QSG_LOG_TEXTUREIO, "glCompressedTexImage2D failed for %s, error 0x%x", logName.constData(), error);
+ }
+ }
+
+ m_textureData.clear(); // Release this memory, not needed anymore
+
+ updateBindOptions(true);
+ m_uploaded = true;
+#endif // QT_CONFIG(opengl)
+}
+
+bool QSGCompressedTexture::formatIsOpaque(quint32 glTextureFormat)
+{
+ switch (glTextureFormat) {
+ case QOpenGLTexture::RGB_DXT1:
+ case QOpenGLTexture::R_ATI1N_UNorm:
+ case QOpenGLTexture::R_ATI1N_SNorm:
+ case QOpenGLTexture::RG_ATI2N_UNorm:
+ case QOpenGLTexture::RG_ATI2N_SNorm:
+ case QOpenGLTexture::RGB_BP_UNSIGNED_FLOAT:
+ case QOpenGLTexture::RGB_BP_SIGNED_FLOAT:
+ case QOpenGLTexture::R11_EAC_UNorm:
+ case QOpenGLTexture::R11_EAC_SNorm:
+ case QOpenGLTexture::RG11_EAC_UNorm:
+ case QOpenGLTexture::RG11_EAC_SNorm:
+ case QOpenGLTexture::RGB8_ETC2:
+ case QOpenGLTexture::SRGB8_ETC2:
+ case QOpenGLTexture::RGB8_ETC1:
+ case QOpenGLTexture::SRGB_DXT1:
+ return true;
+ break;
+ default:
+ return false;
+ }
+}
+
+QSGCompressedTextureFactory::QSGCompressedTextureFactory(const QSGCompressedTexture::DataPtr &texData)
+ : m_textureData(texData)
+{
+}
+
+QSGTexture *QSGCompressedTextureFactory::createTexture(QQuickWindow *window) const
+{
+ if (!m_textureData || !m_textureData->isValid())
+ return nullptr;
+
+ // attempt to atlas the texture
+ QSGRenderContext *context = QQuickWindowPrivate::get(window)->context;
+ QSGTexture *t = context->compressedTextureForFactory(this);
+ if (t)
+ return t;
+
+ return new QSGCompressedTexture(m_textureData);
+}
+
+int QSGCompressedTextureFactory::textureByteCount() const
+{
+ return m_textureData ? m_textureData->sizeInBytes() : 0;
+}
+
+
+QSize QSGCompressedTextureFactory::textureSize() const
+{
+ if (m_textureData && m_textureData->isValid())
+ return m_textureData->size;
+ return QSize();
+}
+
+QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/compressedtexture/qsgcompressedtexture_p.h b/src/quick/scenegraph/compressedtexture/qsgcompressedtexture_p.h
new file mode 100644
index 0000000000..aa87316809
--- /dev/null
+++ b/src/quick/scenegraph/compressedtexture/qsgcompressedtexture_p.h
@@ -0,0 +1,126 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QSGCOMPRESSEDTEXTURE_P_H
+#define QSGCOMPRESSEDTEXTURE_P_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include <QSGTexture>
+#include <QtQuick/private/qsgcontext_p.h>
+#include <QQuickTextureFactory>
+#include <QOpenGLFunctions>
+
+QT_BEGIN_NAMESPACE
+
+struct Q_QUICK_PRIVATE_EXPORT QSGCompressedTextureData
+{
+ QByteArray logName;
+ QByteArray data;
+ QSize size;
+ uint format = 0;
+ int dataOffset = 0;
+ int dataLength = 0;
+ bool hasAlpha = false;
+
+ bool isValid() const;
+ int sizeInBytes() const;
+};
+
+Q_QUICK_PRIVATE_EXPORT QDebug operator<<(QDebug, const QSGCompressedTextureData *);
+
+
+class Q_QUICK_PRIVATE_EXPORT QSGCompressedTexture : public QSGTexture
+{
+ Q_OBJECT
+public:
+ typedef QSharedPointer<QSGCompressedTextureData> DataPtr;
+
+ QSGCompressedTexture(const DataPtr& texData);
+ virtual ~QSGCompressedTexture();
+
+ int textureId() const override;
+ QSize textureSize() const override;
+ bool hasAlphaChannel() const override;
+ bool hasMipmaps() const override;
+
+ void bind() override;
+
+ const QSGCompressedTextureData *textureData();
+
+ static bool formatIsOpaque(quint32 glTextureFormat);
+
+protected:
+ DataPtr m_textureData;
+ QSize m_size;
+ mutable uint m_textureId = 0;
+ bool m_hasAlpha = false;
+ bool m_uploaded = false;
+};
+
+namespace QSGAtlasTexture {
+ class Manager;
+}
+
+class Q_QUICK_PRIVATE_EXPORT QSGCompressedTextureFactory : public QQuickTextureFactory
+{
+public:
+ QSGCompressedTextureFactory(const QSGCompressedTexture::DataPtr& texData);
+ QSGTexture *createTexture(QQuickWindow *) const override;
+ int textureByteCount() const override;
+ QSize textureSize() const override;
+
+protected:
+ QSGCompressedTexture::DataPtr m_textureData;
+private:
+ friend class QSGAtlasTexture::Manager;
+};
+
+QT_END_NAMESPACE
+
+#endif // QSGCOMPRESSEDTEXTURE_P_H
diff --git a/src/quick/scenegraph/compressedtexture/qsgktxhandler.cpp b/src/quick/scenegraph/compressedtexture/qsgktxhandler.cpp
new file mode 100644
index 0000000000..e3e4ca6824
--- /dev/null
+++ b/src/quick/scenegraph/compressedtexture/qsgktxhandler.cpp
@@ -0,0 +1,186 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qsgktxhandler_p.h"
+#include "qsgcompressedtexture_p.h"
+#include <QOpenGLTexture>
+#include <QtEndian>
+
+//#define KTX_DEBUG
+
+QT_BEGIN_NAMESPACE
+
+#define KTX_IDENTIFIER_LENGTH 12
+static const char ktxIdentifier[KTX_IDENTIFIER_LENGTH] = { '\xAB', 'K', 'T', 'X', ' ', '1', '1', '\xBB', '\r', '\n', '\x1A', '\n' };
+static const quint32 platformEndianIdentifier = 0x04030201;
+static const quint32 inversePlatformEndianIdentifier = 0x01020304;
+
+struct KTXHeader {
+ quint8 identifier[KTX_IDENTIFIER_LENGTH]; //Must match ktxIdentifier
+ quint32 endianness; //Either platformEndianIdentifier or inversePlatformEndianIdentifier, other values not allowed.
+ quint32 glType;
+ quint32 glTypeSize;
+ quint32 glFormat;
+ quint32 glInternalFormat;
+ quint32 glBaseInternalFormat;
+ quint32 pixelWidth;
+ quint32 pixelHeight;
+ quint32 pixelDepth;
+ quint32 numberOfArrayElements;
+ quint32 numberOfFaces;
+ quint32 numberOfMipmapLevels;
+ quint32 bytesOfKeyValueData;
+};
+
+static const int headerSize = sizeof(KTXHeader);
+
+// Currently unused, declared for future reference
+struct KTXKeyValuePairItem {
+ quint32 keyAndValueByteSize;
+ /*
+ quint8 keyAndValue[keyAndValueByteSize];
+ quint8 valuePadding[3 - ((keyAndValueByteSize + 3) % 4)];
+ */
+};
+
+struct KTXMipmapLevel {
+ quint32 imageSize;
+ /*
+ for each array_element in numberOfArrayElements*
+ for each face in numberOfFaces
+ for each z_slice in pixelDepth*
+ for each row or row_of_blocks in pixelHeight*
+ for each pixel or block_of_pixels in pixelWidth
+ Byte data[format-specific-number-of-bytes]**
+ end
+ end
+ end
+ Byte cubePadding[0-3]
+ end
+ end
+ quint8 mipPadding[3 - ((imageSize + 3) % 4)]
+ */
+};
+
+bool QSGKtxHandler::canRead(const QByteArray &suffix, const QByteArray &block)
+{
+ Q_UNUSED(suffix)
+
+ return (qstrncmp(block.constData(), ktxIdentifier, KTX_IDENTIFIER_LENGTH) == 0);
+}
+
+QQuickTextureFactory *QSGKtxHandler::read()
+{
+ if (!device())
+ return nullptr;
+
+ QByteArray buf = device()->readAll();
+ if (buf.size() < headerSize || !canRead(QByteArray(), buf)) {
+ qCDebug(QSG_LOG_TEXTUREIO, "Invalid KTX file %s", logName().constData());
+ return nullptr;
+ }
+
+ const KTXHeader *header = reinterpret_cast<const KTXHeader *>(buf.constData());
+ if (!checkHeader(*header)) {
+ qCDebug(QSG_LOG_TEXTUREIO, "Unsupported KTX file format in %s", logName().constData());
+ return nullptr;
+ }
+
+ QSGCompressedTexture::DataPtr texData(QSGCompressedTexture::DataPtr::create());
+
+ texData->size = QSize(decode(header->pixelWidth), decode(header->pixelHeight));
+ texData->format = decode(header->glInternalFormat);
+ texData->hasAlpha = !QSGCompressedTexture::formatIsOpaque(texData->format);
+
+ // For now, ignore any additional mipmap levels
+ int preambleSize = headerSize + decode(header->bytesOfKeyValueData);
+ if (buf.size() >= preambleSize + int(sizeof(KTXMipmapLevel))) {
+ texData->data = buf;
+ texData->dataOffset = preambleSize + sizeof(quint32); // for the imageSize
+ const KTXMipmapLevel *level = reinterpret_cast<const KTXMipmapLevel *>(buf.constData() + preambleSize);
+ texData->dataLength = decode(level->imageSize);
+ }
+
+ if (!texData->isValid()) {
+ qCDebug(QSG_LOG_TEXTUREIO, "Invalid values in header of KTX file %s", logName().constData());
+ return nullptr;
+ }
+
+ texData->logName = logName();
+#ifdef KTX_DEBUG
+ qDebug() << "KTX file handler read" << texData.data();
+#endif
+
+ return new QSGCompressedTextureFactory(texData);
+}
+
+bool QSGKtxHandler::checkHeader(const KTXHeader &header)
+{
+ if (header.endianness != platformEndianIdentifier && header.endianness != inversePlatformEndianIdentifier)
+ return false;
+ inverseEndian = (header.endianness == inversePlatformEndianIdentifier);
+#ifdef KTX_DEBUG
+ QMetaEnum tfme = QMetaEnum::fromType<QOpenGLTexture::TextureFormat>();
+ QMetaEnum ptme = QMetaEnum::fromType<QOpenGLTexture::PixelType>();
+ qDebug("Header of %s:", logName().constData());
+ qDebug(" glType: 0x%x (%s)", decode(header.glType), ptme.valueToKey(decode(header.glType)));
+ qDebug(" glTypeSize: %u", decode(header.glTypeSize));
+ qDebug(" glFormat: 0x%x (%s)", decode(header.glFormat), tfme.valueToKey(decode(header.glFormat)));
+ qDebug(" glInternalFormat: 0x%x (%s)", decode(header.glInternalFormat), tfme.valueToKey(decode(header.glInternalFormat)));
+ qDebug(" glBaseInternalFormat: 0x%x (%s)", decode(header.glBaseInternalFormat), tfme.valueToKey(decode(header.glBaseInternalFormat)));
+ qDebug(" pixelWidth: %u", decode(header.pixelWidth));
+ qDebug(" pixelHeight: %u", decode(header.pixelHeight));
+ qDebug(" pixelDepth: %u", decode(header.pixelDepth));
+ qDebug(" numberOfArrayElements: %u", decode(header.numberOfArrayElements));
+ qDebug(" numberOfFaces: %u", decode(header.numberOfFaces));
+ qDebug(" numberOfMipmapLevels: %u", decode(header.numberOfMipmapLevels));
+ qDebug(" bytesOfKeyValueData: %u", decode(header.bytesOfKeyValueData));
+#endif
+ return ((decode(header.glType) == 0) &&
+ (decode(header.glFormat) == 0) &&
+ (decode(header.pixelDepth) == 0) &&
+ (decode(header.numberOfFaces) == 1));
+}
+
+quint32 QSGKtxHandler::decode(quint32 val)
+{
+ return inverseEndian ? qbswap<quint32>(val) : val;
+}
+
+QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/compressedtexture/qsgktxhandler_p.h b/src/quick/scenegraph/compressedtexture/qsgktxhandler_p.h
new file mode 100644
index 0000000000..22f4db65b2
--- /dev/null
+++ b/src/quick/scenegraph/compressedtexture/qsgktxhandler_p.h
@@ -0,0 +1,78 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QSGKTXHANDLER_H
+#define QSGKTXHANDLER_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include "qsgtexturefilehandler_p.h"
+
+QT_BEGIN_NAMESPACE
+
+struct KTXHeader;
+
+class QSGKtxHandler : public QSGTextureFileHandler
+{
+public:
+ using QSGTextureFileHandler::QSGTextureFileHandler;
+
+ static bool canRead(const QByteArray &suffix, const QByteArray &block);
+
+ QQuickTextureFactory *read() override;
+
+private:
+ bool checkHeader(const KTXHeader &header);
+ quint32 decode(quint32 val);
+
+ bool inverseEndian = false;
+};
+
+QT_END_NAMESPACE
+
+#endif // QSGKTXHANDLER_H
diff --git a/src/quick/scenegraph/compressedtexture/qsgpkmhandler.cpp b/src/quick/scenegraph/compressedtexture/qsgpkmhandler.cpp
index bb8fce046d..618c0db045 100644
--- a/src/quick/scenegraph/compressedtexture/qsgpkmhandler.cpp
+++ b/src/quick/scenegraph/compressedtexture/qsgpkmhandler.cpp
@@ -38,172 +38,81 @@
****************************************************************************/
#include "qsgpkmhandler_p.h"
+#include "qsgcompressedtexture_p.h"
#include <QFile>
#include <QDebug>
#include <qendian.h>
#include <qopenglfunctions.h>
#include <qqmlfile.h>
+#include <QOpenGLTexture>
//#define ETC_DEBUG
-#ifndef GL_ETC1_RGB8_OES
- #define GL_ETC1_RGB8_OES 0x8d64
-#endif
-
-#ifndef GL_COMPRESSED_RGB8_ETC2
- #define GL_COMPRESSED_RGB8_ETC2 0x9274
-#endif
-
-#ifndef GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2
- #define GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2 0x9276
-#endif
-
-#ifndef GL_COMPRESSED_RGBA8_ETC2_EAC
- #define GL_COMPRESSED_RGBA8_ETC2_EAC 0x9278
-#endif
-
QT_BEGIN_NAMESPACE
static const int headerSize = 16;
static unsigned int typeMap[5] = {
- GL_ETC1_RGB8_OES,
- GL_COMPRESSED_RGB8_ETC2,
- 0, // unused
- GL_COMPRESSED_RGBA8_ETC2_EAC,
- GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2
+ QOpenGLTexture::RGB8_ETC1, // GL_ETC1_RGB8_OES,
+ QOpenGLTexture::RGB8_ETC2, // GL_COMPRESSED_RGB8_ETC2,
+ 0, // unused (obsolete)
+ QOpenGLTexture::RGBA8_ETC2_EAC, // GL_COMPRESSED_RGBA8_ETC2_EAC,
+ QOpenGLTexture::RGB8_PunchThrough_Alpha1_ETC2 // GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2
};
-QEtcTexture::QEtcTexture()
- : m_texture_id(0), m_uploaded(false)
-{
- initializeOpenGLFunctions();
-}
-
-QEtcTexture::~QEtcTexture()
-{
- if (m_texture_id)
- glDeleteTextures(1, &m_texture_id);
-}
-
-int QEtcTexture::textureId() const
-{
- if (m_texture_id == 0) {
- QEtcTexture *texture = const_cast<QEtcTexture*>(this);
- texture->glGenTextures(1, &texture->m_texture_id);
- }
- return m_texture_id;
-}
-
-bool QEtcTexture::hasAlphaChannel() const
-{
- return m_type == GL_COMPRESSED_RGBA8_ETC2_EAC ||
- m_type == GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2;
-}
-
-
-void QEtcTexture::bind()
+bool QSGPkmHandler::canRead(const QByteArray &suffix, const QByteArray &block)
{
- if (m_uploaded && m_texture_id) {
- glBindTexture(GL_TEXTURE_2D, m_texture_id);
- return;
- }
-
- if (m_texture_id == 0)
- glGenTextures(1, &m_texture_id);
- glBindTexture(GL_TEXTURE_2D, m_texture_id);
-
-#ifdef ETC_DEBUG
- qDebug() << "glCompressedTexImage2D, width: " << m_size.width() << "height" << m_size.height() <<
- "paddedWidth: " << m_paddedSize.width() << "paddedHeight: " << m_paddedSize.height();
-#endif
+ Q_UNUSED(suffix)
-#ifndef QT_NO_DEBUG
- while (glGetError() != GL_NO_ERROR) { }
-#endif
-
- QOpenGLContext *ctx = QOpenGLContext::currentContext();
- Q_ASSERT(ctx != 0);
- ctx->functions()->glCompressedTexImage2D(GL_TEXTURE_2D, 0, m_type,
- m_size.width(), m_size.height(), 0,
- (m_paddedSize.width() * m_paddedSize.height()) / 2,
- m_data.data() + headerSize);
-
-#ifndef QT_NO_DEBUG
- // Gracefully fail in case of an error...
- GLuint error = glGetError();
- if (error != GL_NO_ERROR) {
- qDebug () << "glCompressedTexImage2D for compressed texture failed, error: " << error;
- glBindTexture(GL_TEXTURE_2D, 0);
- glDeleteTextures(1, &m_texture_id);
- m_texture_id = 0;
- return;
- }
-#endif
-
- m_uploaded = true;
- updateBindOptions(true);
+ return block.startsWith("PKM ");
}
-class QEtcTextureFactory : public QQuickTextureFactory
-{
-public:
- QByteArray m_data;
- QSize m_size;
- QSize m_paddedSize;
- unsigned int m_type;
-
- QSize textureSize() const { return m_size; }
- int textureByteCount() const { return m_data.size(); }
-
- QSGTexture *createTexture(QQuickWindow *) const {
- QEtcTexture *texture = new QEtcTexture;
- texture->m_data = m_data;
- texture->m_size = m_size;
- texture->m_paddedSize = m_paddedSize;
- texture->m_type = m_type;
- return texture;
- }
-};
-
-QQuickTextureFactory *QSGPkmHandler::read(QIODevice *device)
+QQuickTextureFactory *QSGPkmHandler::read()
{
- QScopedPointer<QEtcTextureFactory> ret(new QEtcTextureFactory);
- ret->m_data = device->readAll();
- if (ret->m_data.isEmpty() || ret->m_data.size() < headerSize)
+ if (!device())
return nullptr;
- const char *rawData = ret->m_data.constData();
+ QSGCompressedTexture::DataPtr texData(QSGCompressedTexture::DataPtr::create());
- // magic number
- if (qstrncmp(rawData, "PKM ", 4) != 0)
+ texData->data = device()->readAll();
+ if (texData->data.size() < headerSize || !canRead(QByteArray(), texData->data)) {
+ qCDebug(QSG_LOG_TEXTUREIO, "Invalid PKM file %s", logName().constData());
return nullptr;
+ }
+
+ const char *rawData = texData->data.constData();
- // currently ignore version (rawData + 4)
+ // ignore version (rawData + 4 & 5)
// texture type
quint16 type = qFromBigEndian<quint16>(rawData + 6);
- static int typeCount = sizeof(typeMap)/sizeof(typeMap[0]);
- if (type >= typeCount)
+ if (type > sizeof(typeMap)/sizeof(typeMap[0])) {
+ qCDebug(QSG_LOG_TEXTUREIO, "Unknown compression format in PKM file %s", logName().constData());
return nullptr;
- ret->m_type = typeMap[type];
+ }
+ texData->format = typeMap[type];
+ texData->hasAlpha = !QSGCompressedTexture::formatIsOpaque(texData->format);
// texture size
- ret->m_paddedSize.setWidth(qFromBigEndian<quint16>(rawData + 8));
- ret->m_paddedSize.setHeight(qFromBigEndian<quint16>(rawData + 10));
- if ((ret->m_paddedSize.width() * ret->m_paddedSize.height()) / 2 > ret->m_data.size() - headerSize)
- return nullptr;
- ret->m_size.setWidth(qFromBigEndian<quint16>(rawData + 12));
- ret->m_size.setHeight(qFromBigEndian<quint16>(rawData + 14));
- if (ret->m_size.isEmpty())
+ const int bpb = (texData->format == QOpenGLTexture::RGBA8_ETC2_EAC) ? 16 : 8;
+ QSize paddedSize(qFromBigEndian<quint16>(rawData + 8), qFromBigEndian<quint16>(rawData + 10));
+ texData->dataLength = (paddedSize.width() / 4) * (paddedSize.height() / 4) * bpb;
+ QSize texSize(qFromBigEndian<quint16>(rawData + 12), qFromBigEndian<quint16>(rawData + 14));
+ texData->size = texSize;
+
+ texData->dataOffset = headerSize;
+
+ if (!texData->isValid()) {
+ qCDebug(QSG_LOG_TEXTUREIO, "Invalid values in header of PKM file %s", logName().constData());
return nullptr;
+ }
+ texData->logName = logName();
#ifdef ETC_DEBUG
- qDebug() << "requestTexture returning: " << ret->m_data.length() << "bytes; width: " << ret->m_size.width() << ", height: " << ret->m_size.height();
+ qDebug() << "PKM file handler read" << texData.data();
#endif
-
- return ret.take();
+ return new QSGCompressedTextureFactory(texData);
}
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/compressedtexture/qsgpkmhandler_p.h b/src/quick/scenegraph/compressedtexture/qsgpkmhandler_p.h
index eb6b2e46c0..6154c51b84 100644
--- a/src/quick/scenegraph/compressedtexture/qsgpkmhandler_p.h
+++ b/src/quick/scenegraph/compressedtexture/qsgpkmhandler_p.h
@@ -51,42 +51,18 @@
// We mean it.
//
-#include <QOpenGLFunctions>
-#include <QQuickImageProvider>
-#include <QtQuick/QSGTexture>
-#include <QUrl>
+#include "qsgtexturefilehandler_p.h"
QT_BEGIN_NAMESPACE
-class QSGPkmHandler
+class QSGPkmHandler : public QSGTextureFileHandler
{
public:
- QSGPkmHandler() {}
+ using QSGTextureFileHandler::QSGTextureFileHandler;
- QQuickTextureFactory *read(QIODevice *device);
-};
-
-class QEtcTexture : public QSGTexture, protected QOpenGLFunctions
-{
- Q_OBJECT
-public:
- QEtcTexture();
- ~QEtcTexture();
-
- void bind();
-
- QSize textureSize() const { return m_size; }
- int textureId() const;
-
- bool hasAlphaChannel() const;
- bool hasMipmaps() const { return false; }
+ static bool canRead(const QByteArray &suffix, const QByteArray &block);
- QByteArray m_data;
- QSize m_size;
- QSize m_paddedSize;
- GLuint m_texture_id;
- GLenum m_type;
- bool m_uploaded;
+ QQuickTextureFactory *read() override;
};
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/compressedtexture/qsgtexturefilehandler_p.h b/src/quick/scenegraph/compressedtexture/qsgtexturefilehandler_p.h
new file mode 100644
index 0000000000..8b831aebb9
--- /dev/null
+++ b/src/quick/scenegraph/compressedtexture/qsgtexturefilehandler_p.h
@@ -0,0 +1,83 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QSGTEXTUREFILEHANDLER_P_H
+#define QSGTEXTUREFILEHANDLER_P_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include <QLoggingCategory>
+
+QT_BEGIN_NAMESPACE
+
+Q_DECLARE_LOGGING_CATEGORY(QSG_LOG_TEXTUREIO)
+
+class QQuickTextureFactory;
+
+class QSGTextureFileHandler
+{
+public:
+ QSGTextureFileHandler(QIODevice *device, const QByteArray &logName = QByteArray())
+ : m_device(device)
+ {
+ m_logName = !logName.isEmpty() ? logName : QByteArrayLiteral("(unknown)");
+ }
+ virtual ~QSGTextureFileHandler() {}
+
+ virtual QQuickTextureFactory *read() = 0;
+ QIODevice *device() const { return m_device; }
+ QByteArray logName() const { return m_logName; }
+
+private:
+ QIODevice *m_device = nullptr;
+ QByteArray m_logName;
+};
+
+QT_END_NAMESPACE
+
+#endif // QSGTEXTUREFILEHANDLER_P_H
diff --git a/src/quick/scenegraph/coreapi/qsgabstractrenderer.cpp b/src/quick/scenegraph/coreapi/qsgabstractrenderer.cpp
index 3d4ce24716..fddac7ed71 100644
--- a/src/quick/scenegraph/coreapi/qsgabstractrenderer.cpp
+++ b/src/quick/scenegraph/coreapi/qsgabstractrenderer.cpp
@@ -97,7 +97,7 @@ QT_BEGIN_NAMESPACE
\internal
*/
QSGAbstractRendererPrivate::QSGAbstractRendererPrivate()
- : m_root_node(0)
+ : m_root_node(nullptr)
, m_clear_color(Qt::transparent)
, m_clear_mode(QSGAbstractRenderer::ClearColorBuffer | QSGAbstractRenderer::ClearDepthBuffer)
{
diff --git a/src/quick/scenegraph/coreapi/qsgabstractrenderer.h b/src/quick/scenegraph/coreapi/qsgabstractrenderer.h
index 304dc008d5..ab6fb4f317 100644
--- a/src/quick/scenegraph/coreapi/qsgabstractrenderer.h
+++ b/src/quick/scenegraph/coreapi/qsgabstractrenderer.h
@@ -62,7 +62,7 @@ public:
};
Q_DECLARE_FLAGS(ClearMode, ClearModeBit)
- virtual ~QSGAbstractRenderer();
+ ~QSGAbstractRenderer() override;
void setRootNode(QSGRootNode *node);
QSGRootNode *rootNode() const;
diff --git a/src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp b/src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp
index 0da35fba42..ba71551302 100644
--- a/src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp
+++ b/src/quick/scenegraph/coreapi/qsgbatchrenderer.cpp
@@ -144,7 +144,7 @@ ShaderManager::Shader *ShaderManager::prepareMaterial(QSGMaterial *material)
Q_QUICK_SG_PROFILE_START(QQuickProfiler::SceneGraphContextFrame);
QSGMaterialShader *s = material->createShader();
- QOpenGLContext *ctx = QOpenGLContext::currentContext();
+ QOpenGLContext *ctx = context->openglContext();
QSurfaceFormat::OpenGLContextProfile profile = ctx->format().profile();
QOpenGLShaderProgram *p = s->program();
@@ -155,10 +155,10 @@ ShaderManager::Shader *ShaderManager::prepareMaterial(QSGMaterial *material)
p->bindAttributeLocation(attr[i], i);
}
p->bindAttributeLocation("_qt_order", i);
- context->compileShader(s, material, qsgShaderRewriter_insertZAttributes(s->vertexShader(), profile), 0);
+ context->compileShader(s, material, qsgShaderRewriter_insertZAttributes(s->vertexShader(), profile), nullptr);
context->initializeShader(s);
if (!p->isLinked())
- return 0;
+ return nullptr;
shader = new Shader;
shader->program = s;
@@ -215,7 +215,7 @@ void ShaderManager::invalidated()
qDeleteAll(rewrittenShaders);
rewrittenShaders.clear();
delete blitProgram;
- blitProgram = 0;
+ blitProgram = nullptr;
}
void qsg_dumpShadowRoots(BatchRootInfo *i, int indent)
@@ -226,7 +226,7 @@ void qsg_dumpShadowRoots(BatchRootInfo *i, int indent)
QByteArray ind(indent + extraIndent + 10, ' ');
if (!i) {
- qDebug() << ind.constData() << "- no info";
+ qDebug("%s - no info", ind.constData());
} else {
qDebug() << ind.constData() << "- parent:" << i->parentRoot << "orders" << i->firstOrder << "->" << i->lastOrder << ", avail:" << i->availableOrders;
for (QSet<Node *>::const_iterator it = i->subRoots.constBegin();
@@ -280,7 +280,7 @@ Updater::Updater(Renderer *r)
void Updater::updateStates(QSGNode *n)
{
- m_current_clip = 0;
+ m_current_clip = nullptr;
m_added = 0;
m_transformChange = 0;
@@ -293,15 +293,15 @@ void Updater::updateStates(QSGNode *n)
qsg_dumpShadowRoots(sn);
if (Q_UNLIKELY(debug_build())) {
- qDebug() << "Updater::updateStates()";
+ qDebug("Updater::updateStates()");
if (sn->dirtyState & (QSGNode::DirtyNodeAdded << 16))
- qDebug() << " - nodes have been added";
+ qDebug(" - nodes have been added");
if (sn->dirtyState & (QSGNode::DirtyMatrix << 16))
- qDebug() << " - transforms have changed";
+ qDebug(" - transforms have changed");
if (sn->dirtyState & (QSGNode::DirtyOpacity << 16))
- qDebug() << " - opacity has changed";
+ qDebug(" - opacity has changed");
if (uint(sn->dirtyState) & uint(QSGNode::DirtyForceUpdate << 16))
- qDebug() << " - forceupdate";
+ qDebug(" - forceupdate");
}
if (Q_UNLIKELY(renderer->m_visualizeMode == Renderer::VisualizeChanges))
@@ -347,7 +347,7 @@ void Updater::visitNode(Node *n)
m_added = count;
m_force_update = force;
- n->dirtyState = 0;
+ n->dirtyState = nullptr;
}
void Updater::visitClipNode(Node *n)
@@ -473,7 +473,7 @@ void Updater::visitGeometryNode(Node *n)
if (e->root) {
BatchRootInfo *info = renderer->batchRootInfo(e->root);
- while (info != 0) {
+ while (info != nullptr) {
info->availableOrders--;
if (info->availableOrders < 0) {
renderer->m_rebuild |= Renderer::BuildRenderLists;
@@ -481,10 +481,10 @@ void Updater::visitGeometryNode(Node *n)
renderer->m_rebuild |= Renderer::BuildRenderListsForTaggedRoots;
renderer->m_taggedRoots << e->root;
}
- if (info->parentRoot != 0)
+ if (info->parentRoot != nullptr)
info = renderer->batchRootInfo(info->parentRoot);
else
- info = 0;
+ info = nullptr;
}
} else {
renderer->m_rebuild |= Renderer::FullRebuild;
@@ -680,12 +680,12 @@ void Batch::invalidate()
// the batch to do an early out..
cleanupRemovedElements();
Element *e = first;
- first = 0;
- root = 0;
+ first = nullptr;
+ root = nullptr;
while (e) {
- e->batch = 0;
+ e->batch = nullptr;
Element *n = e->nextInBatch;
- e->nextInBatch = 0;
+ e->nextInBatch = nullptr;
e = n;
}
}
@@ -756,7 +756,7 @@ Renderer::Renderer(QSGDefaultRenderContext *ctx)
, m_alphaRenderList(64)
, m_nextRenderOrder(0)
, m_partialRebuild(false)
- , m_partialRebuildRoot(0)
+ , m_partialRebuildRoot(nullptr)
, m_useDepthBuffer(true)
, m_opaqueBatches(16)
, m_alphaBatches(16)
@@ -768,17 +768,17 @@ Renderer::Renderer(QSGDefaultRenderContext *ctx)
, m_zRange(0)
, m_renderOrderRebuildLower(-1)
, m_renderOrderRebuildUpper(-1)
- , m_currentMaterial(0)
- , m_currentShader(0)
+ , m_currentMaterial(nullptr)
+ , m_currentShader(nullptr)
, m_currentStencilValue(0)
, m_clipMatrixId(0)
- , m_currentClip(0)
+ , m_currentClip(nullptr)
, m_currentClipType(NoClip)
, m_vertexUploadPool(256)
#ifdef QSG_SEPARATE_INDEX_BUFFER
, m_indexUploadPool(64)
#endif
- , m_vao(0)
+ , m_vao(nullptr)
, m_visualizeMode(VisualizeNothing)
{
initializeOpenGLFunctions();
@@ -805,8 +805,11 @@ Renderer::Renderer(QSGDefaultRenderContext *ctx)
m_batchVertexThreshold = qt_sg_envInt("QSG_RENDERER_BATCH_VERTEX_THRESHOLD", 1024);
if (Q_UNLIKELY(debug_build() || debug_render())) {
- qDebug() << "Batch thresholds: nodes:" << m_batchNodeThreshold << " vertices:" << m_batchVertexThreshold;
- qDebug() << "Using buffer strategy:" << (m_bufferStrategy == GL_STATIC_DRAW ? "static" : (m_bufferStrategy == GL_DYNAMIC_DRAW ? "dynamic" : "stream"));
+ qDebug("Batch thresholds: nodes: %d vertices: %d",
+ m_batchNodeThreshold, m_batchVertexThreshold);
+ qDebug("Using buffer strategy: %s",
+ (m_bufferStrategy == GL_STATIC_DRAW
+ ? "static" : (m_bufferStrategy == GL_DYNAMIC_DRAW ? "dynamic" : "stream")));
}
// If rendering with an OpenGL Core profile context, we need to create a VAO
@@ -913,7 +916,7 @@ void Renderer::unmap(Buffer *buffer, bool isIndexBuf)
glBufferData(target, buffer->size, buffer->data, m_bufferStrategy);
if (!m_context->hasBrokenIndexBufferObjects() && m_visualizeMode == VisualizeNothing) {
- buffer->data = 0;
+ buffer->data = nullptr;
}
}
@@ -941,7 +944,7 @@ void Renderer::removeBatchRootFromParent(Node *childRoot)
Q_ASSERT(parentInfo->subRoots.contains(childRoot));
parentInfo->subRoots.remove(childRoot);
- childInfo->parentRoot = 0;
+ childInfo->parentRoot = nullptr;
}
void Renderer::registerBatchRoot(Node *subRoot, Node *parentRoot)
@@ -1069,7 +1072,7 @@ void Renderer::nodeWasRemoved(Node *node)
if (e) {
e->removed = true;
m_elementsToDelete.add(e);
- e->node = 0;
+ e->node = nullptr;
if (e->root) {
BatchRootInfo *info = batchRootInfo(e->root);
info->availableOrders++;
@@ -1112,7 +1115,7 @@ void Renderer::nodeWasRemoved(Node *node)
void Renderer::turnNodeIntoBatchRoot(Node *node)
{
- if (Q_UNLIKELY(debug_change())) qDebug() << " - new batch root";
+ if (Q_UNLIKELY(debug_change())) qDebug(" - new batch root");
m_rebuild |= FullRebuild;
node->isBatchRoot = true;
node->becameBatchRoot = true;
@@ -1182,7 +1185,7 @@ void Renderer::nodeChanged(QSGNode *node, QSGNode::DirtyState state)
return;
}
if (node == rootNode())
- nodeWasAdded(node, 0);
+ nodeWasAdded(node, nullptr);
else
nodeWasAdded(node, m_nodes.value(node->parent()));
}
@@ -1435,7 +1438,7 @@ void Renderer::buildRenderListsForTaggedRoots()
}
}
m_partialRebuild = false;
- m_partialRebuildRoot = 0;
+ m_partialRebuildRoot = nullptr;
m_taggedRoots.clear();
m_nextRenderOrder = qMax(m_nextRenderOrder, maxRenderOrder);
@@ -2032,7 +2035,7 @@ Renderer::ClipType Renderer::updateStencilClip(const QSGClipNode *clip)
int vboSize = 0;
bool useVBO = false;
- QOpenGLContext *ctx = QOpenGLContext::currentContext();
+ QOpenGLContext *ctx = m_context->openglContext();
QSurfaceFormat::OpenGLContextProfile profile = ctx->format().profile();
if (!ctx->isOpenGLES() && profile == QSurfaceFormat::CoreProfile) {
@@ -2141,7 +2144,7 @@ Renderer::ClipType Renderer::updateStencilClip(const QSGClipNode *clip)
glBufferSubData(GL_ARRAY_BUFFER, 0, vertexByteSize, g->vertexData());
}
- pointer = 0;
+ pointer = nullptr;
}
glVertexAttribPointer(0, a->tupleSize, a->type, GL_FALSE, g->sizeOfVertex(), pointer);
@@ -2183,7 +2186,7 @@ void Renderer::updateClip(const QSGClipNode *clipList, const Batch *batch)
m_currentClip = clipList;
// updateClip sets another program, so force-reactivate our own
if (m_currentShader)
- setActiveShader(0, 0);
+ setActiveShader(nullptr, nullptr);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
if (batch->isOpaque)
@@ -2204,8 +2207,8 @@ void Renderer::updateClip(const QSGClipNode *clipList, const Batch *batch)
*/
void Renderer::setActiveShader(QSGMaterialShader *program, ShaderManager::Shader *shader)
{
- const char * const *c = m_currentProgram ? m_currentProgram->attributeNames() : 0;
- const char * const *n = program ? program->attributeNames() : 0;
+ const char * const *c = m_currentProgram ? m_currentProgram->attributeNames() : nullptr;
+ const char * const *n = program ? program->attributeNames() : nullptr;
int cza = m_currentShader ? m_currentShader->pos_order : -1;
int nza = shader ? shader->pos_order : -1;
@@ -2216,18 +2219,18 @@ void Renderer::setActiveShader(QSGMaterialShader *program, ShaderManager::Shader
bool was = c;
if (cza == i) {
was = true;
- c = 0;
+ c = nullptr;
} else if (c && !c[i]) { // end of the attribute array names
- c = 0;
+ c = nullptr;
was = false;
}
bool is = n;
if (nza == i) {
is = true;
- n = 0;
+ n = nullptr;
} else if (n && !n[i]) {
- n = 0;
+ n = nullptr;
is = false;
}
@@ -2243,7 +2246,7 @@ void Renderer::setActiveShader(QSGMaterialShader *program, ShaderManager::Shader
m_currentProgram->deactivate();
m_currentProgram = program;
m_currentShader = shader;
- m_currentMaterial = 0;
+ m_currentMaterial = nullptr;
if (m_currentProgram) {
m_currentProgram->program()->bind();
m_currentProgram->activate();
@@ -2295,7 +2298,7 @@ void Renderer::renderMergedBatch(const Batch *batch)
glBindBuffer(GL_ARRAY_BUFFER, batch->vbo.id);
- char *indexBase = 0;
+ char *indexBase = nullptr;
#ifdef QSG_SEPARATE_INDEX_BUFFER
const Buffer *indexBuf = &batch->ibo;
#else
@@ -2319,7 +2322,7 @@ void Renderer::renderMergedBatch(const Batch *batch)
setActiveShader(program, sms);
m_current_opacity = gn->inheritedOpacity();
- if (sms->lastOpacity != m_current_opacity) {
+ if (!qFuzzyCompare(sms->lastOpacity, float(m_current_opacity))) {
dirty |= QSGMaterialShader::RenderState::DirtyOpacity;
sms->lastOpacity = m_current_opacity;
}
@@ -2328,7 +2331,7 @@ void Renderer::renderMergedBatch(const Batch *batch)
#ifndef QT_NO_DEBUG
if (qsg_test_and_clear_material_failure()) {
- qDebug() << "QSGMaterial::updateState triggered an error (merged), batch will be skipped:";
+ qDebug("QSGMaterial::updateState triggered an error (merged), batch will be skipped:");
Element *ee = e;
while (ee) {
qDebug() << " -" << ee->node;
@@ -2391,7 +2394,7 @@ void Renderer::renderUnmergedBatch(const Batch *batch)
updateClip(gn->clipList(), batch);
glBindBuffer(GL_ARRAY_BUFFER, batch->vbo.id);
- char *indexBase = 0;
+ char *indexBase = nullptr;
#ifdef QSG_SEPARATE_INDEX_BUFFER
const Buffer *indexBuf = &batch->ibo;
#else
@@ -2449,7 +2452,7 @@ void Renderer::renderUnmergedBatch(const Batch *batch)
#ifndef QT_NO_DEBUG
if (qsg_test_and_clear_material_failure()) {
- qDebug() << "QSGMaterial::updateState() triggered an error (unmerged), batch will be skipped:";
+ qDebug("QSGMaterial::updateState() triggered an error (unmerged), batch will be skipped:");
qDebug() << " - offending node is" << e->node;
QSGNodeDumper::dump(rootNode());
qFatal("Aborting: scene graph is invalid...");
@@ -2494,18 +2497,21 @@ void Renderer::updateLineWidth(QSGGeometry *g)
if (g->drawingMode() == GL_LINE_STRIP || g->drawingMode() == GL_LINE_LOOP || g->drawingMode() == GL_LINES)
glLineWidth(g->lineWidth());
#if !defined(QT_OPENGL_ES_2)
- else if (!QOpenGLContext::currentContext()->isOpenGLES() && g->drawingMode() == GL_POINTS) {
- QOpenGLFunctions_1_0 *gl1funcs = 0;
- QOpenGLFunctions_3_2_Core *gl3funcs = 0;
- if (QOpenGLContext::currentContext()->format().profile() == QSurfaceFormat::CoreProfile)
- gl3funcs = QOpenGLContext::currentContext()->versionFunctions<QOpenGLFunctions_3_2_Core>();
- else
- gl1funcs = QOpenGLContext::currentContext()->versionFunctions<QOpenGLFunctions_1_0>();
- Q_ASSERT(gl1funcs || gl3funcs);
- if (gl1funcs)
- gl1funcs->glPointSize(g->lineWidth());
- else
- gl3funcs->glPointSize(g->lineWidth());
+ else {
+ QOpenGLContext *ctx = m_context->openglContext();
+ if (!ctx->isOpenGLES() && g->drawingMode() == GL_POINTS) {
+ QOpenGLFunctions_1_0 *gl1funcs = nullptr;
+ QOpenGLFunctions_3_2_Core *gl3funcs = nullptr;
+ if (ctx->format().profile() == QSurfaceFormat::CoreProfile)
+ gl3funcs = ctx->versionFunctions<QOpenGLFunctions_3_2_Core>();
+ else
+ gl1funcs = ctx->versionFunctions<QOpenGLFunctions_1_0>();
+ Q_ASSERT(gl1funcs || gl3funcs);
+ if (gl1funcs)
+ gl1funcs->glPointSize(g->lineWidth());
+ else
+ gl3funcs->glPointSize(g->lineWidth());
+ }
}
#endif
}
@@ -2540,10 +2546,10 @@ void Renderer::renderBatches()
bindable()->clear(clearMode());
m_current_opacity = 1;
- m_currentMaterial = 0;
- m_currentShader = 0;
- m_currentProgram = 0;
- m_currentClip = 0;
+ m_currentMaterial = nullptr;
+ m_currentShader = nullptr;
+ m_currentProgram = nullptr;
+ m_currentClip = nullptr;
bool renderOpaque = !debug_noopaque();
bool renderAlpha = !debug_noalpha();
@@ -2576,8 +2582,8 @@ void Renderer::renderBatches()
}
if (m_currentShader)
- setActiveShader(0, 0);
- updateStencilClip(0);
+ setActiveShader(nullptr, nullptr);
+ updateStencilClip(nullptr);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
glDepthMask(true);
@@ -2591,12 +2597,12 @@ void Renderer::deleteRemovedElements()
for (int i=0; i<m_opaqueRenderList.size(); ++i) {
Element **e = m_opaqueRenderList.data() + i;
if (*e && (*e)->removed)
- *e = 0;
+ *e = nullptr;
}
for (int i=0; i<m_alphaRenderList.size(); ++i) {
Element **e = m_alphaRenderList.data() + i;
if (*e && (*e)->removed)
- *e = 0;
+ *e = nullptr;
}
for (int i=0; i<m_elementsToDelete.size(); ++i) {
@@ -2611,6 +2617,8 @@ void Renderer::deleteRemovedElements()
void Renderer::render()
{
+ Q_ASSERT(m_context->openglContext() == QOpenGLContext::currentContext());
+
if (Q_UNLIKELY(debug_dump())) {
qDebug("\n");
QSGNodeDumper::dump(rootNode());
@@ -2655,12 +2663,12 @@ void Renderer::render()
m_rebuild |= BuildBatches;
if (Q_UNLIKELY(debug_build())) {
- qDebug() << "Opaque render lists" << (complete ? "(complete)" : "(partial)") << ":";
+ qDebug("Opaque render lists %s:", (complete ? "(complete)" : "(partial)"));
for (int i=0; i<m_opaqueRenderList.size(); ++i) {
Element *e = m_opaqueRenderList.at(i);
qDebug() << " - element:" << e << " batch:" << e->batch << " node:" << e->node << " order:" << e->order;
}
- qDebug() << "Alpha render list:" << (complete ? "(complete)" : "(partial)") << ":";
+ qDebug("Alpha render list %s:", complete ? "(complete)" : "(partial)");
for (int i=0; i<m_alphaRenderList.size(); ++i) {
Element *e = m_alphaRenderList.at(i);
qDebug() << " - element:" << e << " batch:" << e->batch << " node:" << e->node << " order:" << e->order;
@@ -2685,7 +2693,7 @@ void Renderer::render()
if (Q_UNLIKELY(debug_render())) timePrepareAlpha = timer.restart();
if (Q_UNLIKELY(debug_build())) {
- qDebug() << "Opaque Batches:";
+ qDebug("Opaque Batches:");
for (int i=0; i<m_opaqueBatches.size(); ++i) {
Batch *b = m_opaqueBatches.at(i);
qDebug() << " - Batch " << i << b << (b->needsUpload ? "upload" : "") << " root:" << b->root;
@@ -2693,7 +2701,7 @@ void Renderer::render()
qDebug() << " - element:" << e << " node:" << e->node << e->order;
}
}
- qDebug() << "Alpha Batches:";
+ qDebug("Alpha Batches:");
for (int i=0; i<m_alphaBatches.size(); ++i) {
Batch *b = m_alphaBatches.at(i);
qDebug() << " - Batch " << i << b << (b->needsUpload ? "upload" : "") << " root:" << b->root;
@@ -2731,7 +2739,7 @@ void Renderer::render()
int largestIBO = 0;
#endif
- if (Q_UNLIKELY(debug_upload())) qDebug() << "Uploading Opaque Batches:";
+ if (Q_UNLIKELY(debug_upload())) qDebug("Uploading Opaque Batches:");
for (int i=0; i<m_opaqueBatches.size(); ++i) {
Batch *b = m_opaqueBatches.at(i);
largestVBO = qMax(b->vbo.size, largestVBO);
@@ -2743,7 +2751,7 @@ void Renderer::render()
if (Q_UNLIKELY(debug_render())) timeUploadOpaque = timer.restart();
- if (Q_UNLIKELY(debug_upload())) qDebug() << "Uploading Alpha Batches:";
+ if (Q_UNLIKELY(debug_upload())) qDebug("Uploading Alpha Batches:");
for (int i=0; i<m_alphaBatches.size(); ++i) {
Batch *b = m_alphaBatches.at(i);
uploadBatch(b);
@@ -2807,11 +2815,11 @@ void Renderer::renderRenderNode(Batch *batch)
Q_ASSERT(batch->first->isRenderNode);
RenderNodeElement *e = (RenderNodeElement *) batch->first;
- setActiveShader(0, 0);
+ setActiveShader(nullptr, nullptr);
QSGNode *clip = e->renderNode->parent();
QSGRenderNodePrivate *rd = QSGRenderNodePrivate::get(e->renderNode);
- rd->m_clip_list = 0;
+ rd->m_clip_list = nullptr;
while (clip != rootNode()) {
if (clip->type() == QSGNode::ClipNodeType) {
rd->m_clip_list = static_cast<QSGClipNode *>(clip);
@@ -2875,8 +2883,8 @@ void Renderer::renderRenderNode(Batch *batch)
e->renderNode->render(&state);
- rd->m_matrix = 0;
- rd->m_clip_list = 0;
+ rd->m_matrix = nullptr;
+ rd->m_clip_list = nullptr;
if (changes & QSGRenderNode::ViewportState) {
QRect r = viewportRect();
@@ -2891,7 +2899,7 @@ void Renderer::renderRenderNode(Batch *batch)
if (changes & (QSGRenderNode::StencilState | QSGRenderNode::ScissorState)) {
glDisable(GL_SCISSOR_TEST);
- m_currentClip = 0;
+ m_currentClip = nullptr;
m_currentClipType = NoClip;
}
@@ -3061,7 +3069,7 @@ void Renderer::visualizeChanges(Node *n)
// This is because many changes don't propegate their dirty state to the
// parent so the node updater will not unset these states. They are
// not used for anything so, unsetting it should have no side effects.
- n->dirtyState = 0;
+ n->dirtyState = nullptr;
}
SHADOWNODE_TRAVERSE(n) {
@@ -3153,7 +3161,7 @@ void Renderer::visualizeOverdraw()
visualizeOverdraw_helper(m_nodes.value(rootNode()));
// Animate the view...
- QSurface *surface = QOpenGLContext::currentContext()->surface();
+ QSurface *surface = m_context->openglContext()->surface();
if (surface->surfaceClass() == QSurface::Window)
if (QQuickWindow *window = qobject_cast<QQuickWindow *>(static_cast<QWindow *>(surface)))
window->update();
diff --git a/src/quick/scenegraph/coreapi/qsgbatchrenderer_p.h b/src/quick/scenegraph/coreapi/qsgbatchrenderer_p.h
index 5c39242029..918f3ce82c 100644
--- a/src/quick/scenegraph/coreapi/qsgbatchrenderer_p.h
+++ b/src/quick/scenegraph/coreapi/qsgbatchrenderer_p.h
@@ -125,7 +125,6 @@ template <typename Type, int PageSize> class Allocator
{
public:
Allocator()
- : m_freePage(0)
{
pages.push_back(new AllocatorPage<Type, PageSize>());
}
@@ -209,7 +208,7 @@ public:
}
QVector<AllocatorPage<Type, PageSize> *> pages;
- int m_freePage;
+ int m_freePage = 0;
};
@@ -306,12 +305,7 @@ struct Buffer {
struct Element {
Element()
- : node(0)
- , batch(0)
- , nextInBatch(0)
- , root(0)
- , order(0)
- , boundsComputed(false)
+ : boundsComputed(false)
, boundsOutsideFloatRange(false)
, translateOnlyToRoot(false)
, removed(false)
@@ -332,14 +326,14 @@ struct Element {
}
void computeBounds();
- QSGGeometryNode *node;
- Batch *batch;
- Element *nextInBatch;
- Node *root;
+ QSGGeometryNode *node = nullptr;
+ Batch *batch = nullptr;
+ Element *nextInBatch = nullptr;
+ Node *root = nullptr;
Rect bounds; // in device coordinates
- int order;
+ int order = 0;
uint boundsComputed : 1;
uint boundsOutsideFloatRange : 1;
@@ -362,12 +356,12 @@ struct RenderNodeElement : public Element {
};
struct BatchRootInfo {
- BatchRootInfo() : parentRoot(0), lastOrder(-1), firstOrder(-1), availableOrders(0) { }
+ BatchRootInfo() {}
QSet<Node *> subRoots;
- Node *parentRoot;
- int lastOrder;
- int firstOrder;
- int availableOrders;
+ Node *parentRoot = nullptr;
+ int lastOrder = -1;
+ int firstOrder = -1;
+ int availableOrders = 0;
};
struct ClipBatchRootInfo : public BatchRootInfo
@@ -381,14 +375,13 @@ struct DrawSet
: vertices(v)
, zorders(z)
, indices(i)
- , indexCount(0)
{
}
- DrawSet() : vertices(0), zorders(0), indices(0), indexCount(0) {}
- int vertices;
- int zorders;
- int indices;
- int indexCount;
+ DrawSet() {}
+ int vertices = 0;
+ int zorders = 0;
+ int indices = 0;
+ int indexCount = 0;
};
enum BatchCompatibility
@@ -410,8 +403,8 @@ struct Batch
// pseudo-constructor...
void init() {
- first = 0;
- root = 0;
+ first = nullptr;
+ root = nullptr;
vertexCount = 0;
indexCount = 0;
isOpaque = false;
@@ -440,7 +433,9 @@ struct Batch
mutable uint uploadedThisFrame : 1; // solely for debugging purposes
Buffer vbo;
+#ifdef QSG_SEPARATE_INDEX_BUFFER
Buffer ibo;
+#endif
QDataBuffer<DrawSet> drawSets;
};
@@ -461,9 +456,9 @@ struct Node
void append(Node *child) {
Q_ASSERT(child);
Q_ASSERT(!hasChild(child));
- Q_ASSERT(child->m_parent == 0);
- Q_ASSERT(child->m_next == 0);
- Q_ASSERT(child->m_prev == 0);
+ Q_ASSERT(child->m_parent == nullptr);
+ Q_ASSERT(child->m_next == nullptr);
+ Q_ASSERT(child->m_prev == nullptr);
if (!m_child) {
child->m_next = child;
@@ -484,27 +479,27 @@ struct Node
// only child..
if (child->m_next == child) {
- m_child = 0;
+ m_child = nullptr;
} else {
if (m_child == child)
m_child = child->m_next;
child->m_next->m_prev = child->m_prev;
child->m_prev->m_next = child->m_next;
}
- child->m_next = 0;
- child->m_prev = 0;
- child->setParent(0);
+ child->m_next = nullptr;
+ child->m_prev = nullptr;
+ child->setParent(nullptr);
}
Node *firstChild() const { return m_child; }
Node *sibling() const {
Q_ASSERT(m_parent);
- return m_next == m_parent->m_child ? 0 : m_next;
+ return m_next == m_parent->m_child ? nullptr : m_next;
}
void setParent(Node *p) {
- Q_ASSERT(m_parent == 0 || p == 0);
+ Q_ASSERT(m_parent == nullptr || p == nullptr);
m_parent = p;
}
@@ -589,7 +584,7 @@ public:
float lastOpacity;
};
- ShaderManager(QSGDefaultRenderContext *ctx) : visualizeProgram(0), blitProgram(0), context(ctx) { }
+ ShaderManager(QSGDefaultRenderContext *ctx) : visualizeProgram(nullptr), blitProgram(nullptr), context(ctx) { }
~ShaderManager() {
qDeleteAll(rewrittenShaders);
qDeleteAll(stockShaders);
@@ -743,7 +738,9 @@ private:
ClipType m_currentClipType;
QDataBuffer<char> m_vertexUploadPool;
+#ifdef QSG_SEPARATE_INDEX_BUFFER
QDataBuffer<char> m_indexUploadPool;
+#endif
// For minimal OpenGL core profile support
QOpenGLVertexArrayObject *m_vao;
@@ -763,7 +760,10 @@ Batch *Renderer::newBatch()
m_batchPool.resize(size - 1);
} else {
b = new Batch();
- memset(&b->vbo, 0, sizeof(Buffer) * 2); // Clear VBO & IBO
+ memset(&b->vbo, 0, sizeof(Buffer));
+#ifdef QSG_SEPARATE_INDEX_BUFFER
+ memset(&b->ibo, 0, sizeof(Buffer));
+#endif
}
b->init();
return b;
diff --git a/src/quick/scenegraph/coreapi/qsggeometry.cpp b/src/quick/scenegraph/coreapi/qsggeometry.cpp
index 69a8c21ed2..226709094d 100644
--- a/src/quick/scenegraph/coreapi/qsggeometry.cpp
+++ b/src/quick/scenegraph/coreapi/qsggeometry.cpp
@@ -430,9 +430,9 @@ QSGGeometry::QSGGeometry(const QSGGeometry::AttributeSet &attributes,
, m_index_count(0)
, m_index_type(indexType)
, m_attributes(attributes)
- , m_data(0)
+ , m_data(nullptr)
, m_index_data_offset(-1)
- , m_server_data(0)
+ , m_server_data(nullptr)
, m_owns_data(false)
, m_index_usage_pattern(AlwaysUploadPattern)
, m_vertex_usage_pattern(AlwaysUploadPattern)
@@ -529,7 +529,7 @@ QSGGeometry::~QSGGeometry()
void *QSGGeometry::indexData()
{
return m_index_data_offset < 0
- ? 0
+ ? nullptr
: ((char *) m_data + m_index_data_offset);
}
@@ -541,7 +541,7 @@ void *QSGGeometry::indexData()
const void *QSGGeometry::indexData() const
{
return m_index_data_offset < 0
- ? 0
+ ? nullptr
: ((char *) m_data + m_index_data_offset);
}
@@ -768,6 +768,19 @@ void QSGGeometry::updateColoredRectGeometry(QSGGeometry *g, const QRectF &rect)
v[3].y = rect.bottom();
}
+/*!
+ \enum QSGGeometry::AttributeType
+
+ This enum identifies several attribute types.
+
+ \value UnknownAttribute Don't care
+ \value PositionAttribute Position
+ \value ColorAttribute Color
+ \value TexCoordAttribute Texture coordinate
+ \value TexCoord1Attribute Texture coordinate 1
+ \value TexCoord2Attribute Texture coordinate 2
+
+ */
/*!
\enum QSGGeometry::DataPattern
diff --git a/src/quick/scenegraph/coreapi/qsgmaterial.cpp b/src/quick/scenegraph/coreapi/qsgmaterial.cpp
index 07dc87a643..8557de1b1f 100644
--- a/src/quick/scenegraph/coreapi/qsgmaterial.cpp
+++ b/src/quick/scenegraph/coreapi/qsgmaterial.cpp
@@ -443,7 +443,12 @@ void QSGMaterialShader::compile()
otherwise returns \c false.
*/
+/*!
+ \fn bool QSGMaterialShader::RenderState::isCachedMaterialDataDirty() const
+ Returns \c true if the dirtyStates() contains the dirty cached material state,
+ otherwise returns \c false.
+ */
/*!
\fn QSGMaterialShader::RenderState::DirtyStates QSGMaterialShader::RenderState::dirtyStates() const
@@ -636,7 +641,7 @@ static void qt_print_material_count()
*/
QSGMaterial::QSGMaterial()
- : m_flags(0)
+ : m_flags(nullptr)
{
Q_UNUSED(m_reserved);
#ifndef QT_NO_DEBUG
diff --git a/src/quick/scenegraph/coreapi/qsgnode.cpp b/src/quick/scenegraph/coreapi/qsgnode.cpp
index 22d57001fc..9717862baa 100644
--- a/src/quick/scenegraph/coreapi/qsgnode.cpp
+++ b/src/quick/scenegraph/coreapi/qsgnode.cpp
@@ -114,6 +114,10 @@ static void qt_print_node_count()
\value DirtyOpacity The opacity of a QSGOpacityNode has changed.
\value DirtySubtreeBlocked The subtree has been blocked.
+ \omitvalue DirtyForceUpdate
+ \omitvalue DirtyUsePreprocess
+ \omitvalue DirtyPropagationMask
+
\sa QSGNode::markDirty()
*/
@@ -135,6 +139,8 @@ static void qt_print_node_count()
ownership over the opaque material and will delete it when the node is
destroyed or a material is assigned.
\value InternalReserved Reserved for internal use.
+
+ \omitvalue IsVisitableNode
*/
/*!
@@ -149,6 +155,8 @@ static void qt_print_node_count()
\value OpacityNodeType The type of QSGOpacityNode
\value RenderNodeType The type of QSGRenderNode
+ \omitvalue RootNodeType
+
\sa type()
*/
@@ -236,15 +244,8 @@ static void qt_print_node_count()
* Constructs a new node
*/
QSGNode::QSGNode()
- : m_parent(0)
- , m_type(BasicNodeType)
- , m_firstChild(0)
- , m_lastChild(0)
- , m_nextSibling(0)
- , m_previousSibling(0)
- , m_subtreeRenderableCount(0)
- , m_nodeFlags(OwnedByParent)
- , m_dirtyState(0)
+ : m_nodeFlags(OwnedByParent)
+ , m_dirtyState(nullptr)
{
init();
}
@@ -255,15 +256,15 @@ QSGNode::QSGNode()
* \internal
*/
QSGNode::QSGNode(NodeType type)
- : m_parent(0)
+ : m_parent(nullptr)
, m_type(type)
- , m_firstChild(0)
- , m_lastChild(0)
- , m_nextSibling(0)
- , m_previousSibling(0)
+ , m_firstChild(nullptr)
+ , m_lastChild(nullptr)
+ , m_nextSibling(nullptr)
+ , m_previousSibling(nullptr)
, m_subtreeRenderableCount(type == GeometryNodeType || type == RenderNodeType ? 1 : 0)
, m_nodeFlags(OwnedByParent)
- , m_dirtyState(0)
+ , m_dirtyState(nullptr)
{
init();
}
@@ -274,15 +275,15 @@ QSGNode::QSGNode(NodeType type)
* \internal
*/
QSGNode::QSGNode(QSGNodePrivate &dd, NodeType type)
- : m_parent(0)
+ : m_parent(nullptr)
, m_type(type)
- , m_firstChild(0)
- , m_lastChild(0)
- , m_nextSibling(0)
- , m_previousSibling(0)
+ , m_firstChild(nullptr)
+ , m_lastChild(nullptr)
+ , m_nextSibling(nullptr)
+ , m_previousSibling(nullptr)
, m_subtreeRenderableCount(type == GeometryNodeType || type == RenderNodeType ? 1 : 0)
, m_nodeFlags(OwnedByParent)
- , m_dirtyState(0)
+ , m_dirtyState(nullptr)
, d_ptr(&dd)
{
init();
@@ -380,17 +381,17 @@ void QSGNode::destroy()
{
if (m_parent) {
m_parent->removeChildNode(this);
- Q_ASSERT(m_parent == 0);
+ Q_ASSERT(m_parent == nullptr);
}
while (m_firstChild) {
QSGNode *child = m_firstChild;
removeChildNode(child);
- Q_ASSERT(child->m_parent == 0);
+ Q_ASSERT(child->m_parent == nullptr);
if (child->flags() & OwnedByParent)
delete child;
}
- Q_ASSERT(m_firstChild == 0 && m_lastChild == 0);
+ Q_ASSERT(m_firstChild == nullptr && m_lastChild == nullptr);
}
@@ -549,11 +550,11 @@ void QSGNode::removeChildNode(QSGNode *node)
next->m_previousSibling = previous;
else
m_lastChild = previous;
- node->m_previousSibling = 0;
- node->m_nextSibling = 0;
+ node->m_previousSibling = nullptr;
+ node->m_nextSibling = nullptr;
node->markDirty(DirtyNodeRemoved);
- node->m_parent = 0;
+ node->m_parent = nullptr;
}
@@ -566,13 +567,13 @@ void QSGNode::removeAllChildNodes()
while (m_firstChild) {
QSGNode *node = m_firstChild;
m_firstChild = node->m_nextSibling;
- node->m_nextSibling = 0;
+ node->m_nextSibling = nullptr;
if (m_firstChild)
- m_firstChild->m_previousSibling = 0;
+ m_firstChild->m_previousSibling = nullptr;
else
- m_lastChild = 0;
+ m_lastChild = nullptr;
node->markDirty(DirtyNodeRemoved);
- node->m_parent = 0;
+ node->m_parent = nullptr;
}
}
@@ -706,9 +707,9 @@ void qsgnode_set_description(QSGNode *node, const QString &description)
*/
QSGBasicGeometryNode::QSGBasicGeometryNode(NodeType type)
: QSGNode(type)
- , m_geometry(0)
- , m_matrix(0)
- , m_clip_list(0)
+ , m_geometry(nullptr)
+ , m_matrix(nullptr)
+ , m_clip_list(nullptr)
{
}
@@ -718,9 +719,9 @@ QSGBasicGeometryNode::QSGBasicGeometryNode(NodeType type)
*/
QSGBasicGeometryNode::QSGBasicGeometryNode(QSGBasicGeometryNodePrivate &dd, NodeType type)
: QSGNode(dd, type)
- , m_geometry(0)
- , m_matrix(0)
- , m_clip_list(0)
+ , m_geometry(nullptr)
+ , m_matrix(nullptr)
+ , m_clip_list(nullptr)
{
}
@@ -862,10 +863,6 @@ void QSGBasicGeometryNode::setGeometry(QSGGeometry *geometry)
QSGGeometryNode::QSGGeometryNode()
: QSGBasicGeometryNode(GeometryNodeType)
- , m_render_order(0)
- , m_material(0)
- , m_opaque_material(0)
- , m_opacity(1)
{
}
@@ -876,8 +873,8 @@ QSGGeometryNode::QSGGeometryNode()
QSGGeometryNode::QSGGeometryNode(QSGGeometryNodePrivate &dd)
: QSGBasicGeometryNode(dd, GeometryNodeType)
, m_render_order(0)
- , m_material(0)
- , m_opaque_material(0)
+ , m_material(nullptr)
+ , m_opaque_material(nullptr)
, m_opacity(1)
{
}
@@ -971,7 +968,7 @@ void QSGGeometryNode::setMaterial(QSGMaterial *material)
delete m_material;
m_material = material;
#ifndef QT_NO_DEBUG
- if (m_material != 0 && m_opaque_material == m_material)
+ if (m_material != nullptr && m_opaque_material == m_material)
qWarning("QSGGeometryNode: using same material for both opaque and translucent");
#endif
markDirty(DirtyMaterial);
@@ -1002,7 +999,7 @@ void QSGGeometryNode::setOpaqueMaterial(QSGMaterial *material)
delete m_opaque_material;
m_opaque_material = material;
#ifndef QT_NO_DEBUG
- if (m_opaque_material != 0 && m_opaque_material == m_material)
+ if (m_opaque_material != nullptr && m_opaque_material == m_material)
qWarning("QSGGeometryNode: using same material for both opaque and translucent");
#endif
@@ -1266,7 +1263,7 @@ QSGRootNode::QSGRootNode()
QSGRootNode::~QSGRootNode()
{
while (!m_renderers.isEmpty())
- m_renderers.constLast()->setRootNode(0);
+ m_renderers.constLast()->setRootNode(nullptr);
destroy(); // Must call destroy() here because markDirty() casts this to QSGRootNode.
}
@@ -1318,8 +1315,6 @@ void QSGRootNode::notifyNodeChange(QSGNode *node, DirtyState state)
*/
QSGOpacityNode::QSGOpacityNode()
: QSGNode(OpacityNodeType)
- , m_opacity(1)
- , m_combined_opacity(1)
{
}
diff --git a/src/quick/scenegraph/coreapi/qsgnode.h b/src/quick/scenegraph/coreapi/qsgnode.h
index f2708b2b96..854e284c9e 100644
--- a/src/quick/scenegraph/coreapi/qsgnode.h
+++ b/src/quick/scenegraph/coreapi/qsgnode.h
@@ -77,9 +77,7 @@ public:
TransformNodeType,
ClipNodeType,
OpacityNodeType,
-#ifndef qdoc
RootNodeType,
-#endif
RenderNodeType
};
@@ -96,9 +94,8 @@ public:
OwnsOpaqueMaterial = 0x00040000,
// Uppermost 8 bits are reserved for internal use.
-#ifndef qdoc
IsVisitableNode = 0x01000000
-#else
+#ifdef Q_CLANG_QDOC
InternalReserved = 0x01000000
#endif
};
@@ -113,7 +110,6 @@ public:
DirtyMaterial = 0x2000,
DirtyOpacity = 0x4000,
-#ifndef qdoc
DirtyForceUpdate = 0x8000,
DirtyUsePreprocess = UsePreprocess,
@@ -122,7 +118,6 @@ public:
| DirtyNodeAdded
| DirtyOpacity
| DirtyForceUpdate
-#endif
};
Q_DECLARE_FLAGS(DirtyState, DirtyStateBit)
@@ -173,13 +168,13 @@ private:
void init();
void destroy();
- QSGNode *m_parent;
- NodeType m_type;
- QSGNode *m_firstChild;
- QSGNode *m_lastChild;
- QSGNode *m_nextSibling;
- QSGNode *m_previousSibling;
- int m_subtreeRenderableCount;
+ QSGNode *m_parent = nullptr;
+ NodeType m_type = BasicNodeType;
+ QSGNode *m_firstChild = nullptr;
+ QSGNode *m_lastChild = nullptr;
+ QSGNode *m_nextSibling = nullptr;
+ QSGNode *m_previousSibling = nullptr;
+ int m_subtreeRenderableCount = 0;
Flags m_nodeFlags;
DirtyState m_dirtyState; // Obsolete, remove in Qt 6
@@ -195,7 +190,7 @@ void Q_QUICK_EXPORT qsgnode_set_description(QSGNode *node, const QString &descri
class Q_QUICK_EXPORT QSGBasicGeometryNode : public QSGNode
{
public:
- ~QSGBasicGeometryNode();
+ ~QSGBasicGeometryNode() override;
void setGeometry(QSGGeometry *geometry);
const QSGGeometry *geometry() const { return m_geometry; }
@@ -229,7 +224,7 @@ class Q_QUICK_EXPORT QSGGeometryNode : public QSGBasicGeometryNode
{
public:
QSGGeometryNode();
- ~QSGGeometryNode();
+ ~QSGGeometryNode() override;
void setMaterial(QSGMaterial *material);
QSGMaterial *material() const { return m_material; }
@@ -251,18 +246,18 @@ protected:
private:
friend class QSGNodeUpdater;
- int m_render_order;
- QSGMaterial *m_material;
- QSGMaterial *m_opaque_material;
+ int m_render_order = 0;
+ QSGMaterial *m_material = nullptr;
+ QSGMaterial *m_opaque_material = nullptr;
- qreal m_opacity;
+ qreal m_opacity = 1;
};
class Q_QUICK_EXPORT QSGClipNode : public QSGBasicGeometryNode
{
public:
QSGClipNode();
- ~QSGClipNode();
+ ~QSGClipNode() override;
void setIsRectangular(bool rectHint);
bool isRectangular() const { return m_is_rectangular; }
@@ -282,7 +277,7 @@ class Q_QUICK_EXPORT QSGTransformNode : public QSGNode
{
public:
QSGTransformNode();
- ~QSGTransformNode();
+ ~QSGTransformNode() override;
void setMatrix(const QMatrix4x4 &matrix);
const QMatrix4x4 &matrix() const { return m_matrix; }
@@ -300,7 +295,7 @@ class Q_QUICK_EXPORT QSGRootNode : public QSGNode
{
public:
QSGRootNode();
- ~QSGRootNode();
+ ~QSGRootNode() override;
private:
void notifyNodeChange(QSGNode *node, DirtyState state);
@@ -317,7 +312,7 @@ class Q_QUICK_EXPORT QSGOpacityNode : public QSGNode
{
public:
QSGOpacityNode();
- ~QSGOpacityNode();
+ ~QSGOpacityNode() override;
void setOpacity(qreal opacity);
qreal opacity() const { return m_opacity; }
@@ -328,8 +323,8 @@ public:
bool isSubtreeBlocked() const override;
private:
- qreal m_opacity;
- qreal m_combined_opacity;
+ qreal m_opacity = 1;
+ qreal m_combined_opacity = 1;
};
class Q_QUICK_EXPORT QSGNodeVisitor {
diff --git a/src/quick/scenegraph/coreapi/qsgnode_p.h b/src/quick/scenegraph/coreapi/qsgnode_p.h
index 84d5477085..f81128f51a 100644
--- a/src/quick/scenegraph/coreapi/qsgnode_p.h
+++ b/src/quick/scenegraph/coreapi/qsgnode_p.h
@@ -78,18 +78,14 @@ public:
class QSGBasicGeometryNodePrivate : public QSGNodePrivate
{
public:
- QSGBasicGeometryNodePrivate()
- : QSGNodePrivate()
- {}
+ QSGBasicGeometryNodePrivate() {}
};
class QSGGeometryNodePrivate: public QSGBasicGeometryNodePrivate
{
public:
- QSGGeometryNodePrivate()
- : QSGBasicGeometryNodePrivate()
- {}
+ QSGGeometryNodePrivate() {}
};
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/coreapi/qsgnodeupdater.cpp b/src/quick/scenegraph/coreapi/qsgnodeupdater.cpp
index d6d533307e..8bc9ded594 100644
--- a/src/quick/scenegraph/coreapi/qsgnodeupdater.cpp
+++ b/src/quick/scenegraph/coreapi/qsgnodeupdater.cpp
@@ -48,7 +48,7 @@ QT_BEGIN_NAMESPACE
QSGNodeUpdater::QSGNodeUpdater()
: m_combined_matrix_stack(64)
, m_opacity_stack(64)
- , m_current_clip(0)
+ , m_current_clip(nullptr)
, m_force_update(0)
{
m_opacity_stack.add(1);
@@ -60,7 +60,7 @@ QSGNodeUpdater::~QSGNodeUpdater()
void QSGNodeUpdater::updateStates(QSGNode *n)
{
- m_current_clip = 0;
+ m_current_clip = nullptr;
m_force_update = 0;
Q_ASSERT(m_opacity_stack.size() == 1); // The one we added in the constructr...
@@ -82,7 +82,7 @@ void QSGNodeUpdater::updateStates(QSGNode *n)
bool QSGNodeUpdater::isNodeBlocked(QSGNode *node, QSGNode *root) const
{
- while (node != root && node != 0) {
+ while (node != root && node != nullptr) {
if (node->isSubtreeBlocked())
return true;
node = node->parent();
diff --git a/src/quick/scenegraph/coreapi/qsgrenderer.cpp b/src/quick/scenegraph/coreapi/qsgrenderer.cpp
index 3ae79a933f..e1ba001d2d 100644
--- a/src/quick/scenegraph/coreapi/qsgrenderer.cpp
+++ b/src/quick/scenegraph/coreapi/qsgrenderer.cpp
@@ -132,8 +132,8 @@ QSGRenderer::QSGRenderer(QSGRenderContext *context)
, m_current_determinant(1)
, m_device_pixel_ratio(1)
, m_context(context)
- , m_node_updater(0)
- , m_bindable(0)
+ , m_node_updater(nullptr)
+ , m_bindable(nullptr)
, m_changed_emitted(false)
, m_is_rendering(false)
, m_is_preprocessing(false)
@@ -143,7 +143,7 @@ QSGRenderer::QSGRenderer(QSGRenderContext *context)
QSGRenderer::~QSGRenderer()
{
- setRootNode(0);
+ setRootNode(nullptr);
delete m_node_updater;
}
@@ -249,7 +249,7 @@ void QSGRenderer::renderScene(const QSGBindable &bindable)
m_is_rendering = false;
m_changed_emitted = false;
- m_bindable = 0;
+ m_bindable = nullptr;
qCDebug(QSG_LOG_TIME_RENDERER,
"time in renderer: total=%dms, preprocess=%d, updates=%d, binding=%d, rendering=%d",
diff --git a/src/quick/scenegraph/coreapi/qsgrenderer_p.h b/src/quick/scenegraph/coreapi/qsgrenderer_p.h
index ae8d9f75d2..8362ff54dc 100644
--- a/src/quick/scenegraph/coreapi/qsgrenderer_p.h
+++ b/src/quick/scenegraph/coreapi/qsgrenderer_p.h
@@ -168,12 +168,12 @@ class Q_QUICK_PRIVATE_EXPORT QSGNodeDumper : public QSGNodeVisitor {
public:
static void dump(QSGNode *n);
- QSGNodeDumper() : m_indent(0) {}
+ QSGNodeDumper() {}
void visitNode(QSGNode *n) override;
void visitChildren(QSGNode *n) override;
private:
- int m_indent;
+ int m_indent = 0;
};
diff --git a/src/quick/scenegraph/coreapi/qsgrendernode.cpp b/src/quick/scenegraph/coreapi/qsgrendernode.cpp
index a8954848d6..df3fa16a32 100644
--- a/src/quick/scenegraph/coreapi/qsgrendernode.cpp
+++ b/src/quick/scenegraph/coreapi/qsgrendernode.cpp
@@ -74,8 +74,8 @@ QSGRenderNode::~QSGRenderNode()
}
QSGRenderNodePrivate::QSGRenderNodePrivate()
- : m_matrix(0)
- , m_clip_list(0)
+ : m_matrix(nullptr)
+ , m_clip_list(nullptr)
, m_opacity(1)
{
}
@@ -119,7 +119,7 @@ QSGRenderNodePrivate::QSGRenderNodePrivate()
*/
QSGRenderNode::StateFlags QSGRenderNode::changedStates() const
{
- return 0;
+ return nullptr;
}
/*!
@@ -213,6 +213,22 @@ void QSGRenderNode::releaseResources()
}
/*!
+ \enum QSGRenderNode::StateFlag
+
+ This enum is a bit mask identifying several states.
+
+ \value DepthState Depth
+ \value StencilState Stencil
+ \value ScissorState Scissor
+ \value ColorState Color
+ \value BlendState Blend
+ \value CullState Cull
+ \value ViewportState View poirt
+ \value RenderTargetState Render target
+
+ */
+
+/*!
\enum QSGRenderNode::RenderingFlag
Possible values for the bitmask returned from flags().
@@ -251,7 +267,7 @@ void QSGRenderNode::releaseResources()
*/
QSGRenderNode::RenderingFlags QSGRenderNode::flags() const
{
- return 0;
+ return nullptr;
}
/*!
@@ -354,7 +370,7 @@ QSGRenderNode::RenderState::~RenderState()
*/
/*!
- \fn const QRegion *QSGRenderNode::clipRegion() const
+ \fn const QRegion *QSGRenderNode::RenderState::clipRegion() const
\return the current clip region or null for backends where clipping is
implemented via stencil or scissoring.
diff --git a/src/quick/scenegraph/coreapi/qsgrendernode.h b/src/quick/scenegraph/coreapi/qsgrendernode.h
index f6bc40d3ee..0fb83b080c 100644
--- a/src/quick/scenegraph/coreapi/qsgrendernode.h
+++ b/src/quick/scenegraph/coreapi/qsgrendernode.h
@@ -80,7 +80,7 @@ public:
};
QSGRenderNode();
- ~QSGRenderNode();
+ ~QSGRenderNode() override;
virtual StateFlags changedStates() const;
virtual void render(const RenderState *state) = 0;
diff --git a/src/quick/scenegraph/qsgadaptationlayer_p.h b/src/quick/scenegraph/qsgadaptationlayer_p.h
index ba146b884f..9c88b8272c 100644
--- a/src/quick/scenegraph/qsgadaptationlayer_p.h
+++ b/src/quick/scenegraph/qsgadaptationlayer_p.h
@@ -266,19 +266,19 @@ public:
Texture // for APIs with separate texture and sampler objects
};
struct InputParameter {
- InputParameter() : semanticIndex(0) { }
+ InputParameter() {}
// Semantics use the D3D keys (POSITION, TEXCOORD).
// Attribute name based APIs can map based on pre-defined names.
QByteArray semanticName;
- int semanticIndex;
+ int semanticIndex = 0;
};
struct Variable {
- Variable() : type(Constant), offset(0), size(0), bindPoint(0) { }
- VariableType type;
+ Variable() {}
+ VariableType type = Constant;
QByteArray name;
- uint offset; // for cbuffer members
- uint size; // for cbuffer members
- int bindPoint; // for textures and samplers; for register-based APIs
+ uint offset = 0; // for cbuffer members
+ uint size = 0; // for cbuffer members
+ int bindPoint = 0; // for textures and samplers; for register-based APIs
};
QByteArray blob; // source or bytecode
@@ -329,8 +329,8 @@ public:
};
struct ShaderData {
- ShaderData() : hasShaderCode(false) { }
- bool hasShaderCode;
+ ShaderData() {}
+ bool hasShaderCode = false;
QSGGuiThreadShaderEffectManager::ShaderInfo shaderInfo;
QVector<VariableData> varData;
};
@@ -373,7 +373,7 @@ public:
HighQualitySubPixelAntialiasing
};
- QSGGlyphNode() : m_ownerElement(0) {}
+ QSGGlyphNode() {}
virtual void setGlyphs(const QPointF &position, const QGlyphRun &glyphs) = 0;
virtual void setColor(const QColor &color) = 0;
@@ -394,7 +394,7 @@ public:
void accept(QSGNodeVisitorEx *visitor) override { if (visitor->visit(this)) visitor->visitChildren(this); visitor->endVisit(this); }
protected:
QRectF m_bounding_rect;
- QQuickItem *m_ownerElement;
+ QQuickItem *m_ownerElement = nullptr;
};
class Q_QUICK_PRIVATE_EXPORT QSGDistanceFieldGlyphConsumer
@@ -421,24 +421,24 @@ public:
};
struct TexCoord {
- qreal x;
- qreal y;
- qreal width;
- qreal height;
- qreal xMargin;
- qreal yMargin;
+ qreal x = 0;
+ qreal y = 0;
+ qreal width = -1;
+ qreal height = -1;
+ qreal xMargin = 0;
+ qreal yMargin = 0;
- TexCoord() : x(0), y(0), width(-1), height(-1), xMargin(0), yMargin(0) { }
+ TexCoord() {}
bool isNull() const { return width <= 0 || height <= 0; }
bool isValid() const { return width >= 0 && height >= 0; }
};
struct Texture {
- uint textureId;
+ uint textureId = 0;
QSize size;
- Texture() : textureId(0), size(QSize()) { }
+ Texture() : size(QSize()) { }
bool operator == (const Texture &other) const { return textureId == other.textureId; }
};
@@ -478,13 +478,13 @@ protected:
};
struct GlyphData {
- Texture *texture;
+ Texture *texture = nullptr;
TexCoord texCoord;
QRectF boundingRect;
QPainterPath path;
- quint32 ref;
+ quint32 ref = 0;
- GlyphData() : texture(0), ref(0) { }
+ GlyphData() {}
};
virtual void requestGlyphs(const QSet<glyph_t> &glyphs) = 0;
diff --git a/src/quick/scenegraph/qsgbasicglyphnode.cpp b/src/quick/scenegraph/qsgbasicglyphnode.cpp
index 38f650a82c..4559b7951c 100644
--- a/src/quick/scenegraph/qsgbasicglyphnode.cpp
+++ b/src/quick/scenegraph/qsgbasicglyphnode.cpp
@@ -44,7 +44,7 @@ QT_BEGIN_NAMESPACE
QSGBasicGlyphNode::QSGBasicGlyphNode()
: m_style(QQuickText::Normal)
- , m_material(0)
+ , m_material(nullptr)
, m_geometry(QSGGeometry::defaultAttributes_TexturedPoint2D(), 0)
{
m_geometry.setDrawingMode(QSGGeometry::DrawTriangles);
@@ -59,7 +59,7 @@ QSGBasicGlyphNode::~QSGBasicGlyphNode()
void QSGBasicGlyphNode::setColor(const QColor &color)
{
m_color = color;
- if (m_material != 0) {
+ if (m_material != nullptr) {
setMaterialColor(color);
markDirty(DirtyMaterial);
}
@@ -67,7 +67,7 @@ void QSGBasicGlyphNode::setColor(const QColor &color)
void QSGBasicGlyphNode::setGlyphs(const QPointF &position, const QGlyphRun &glyphs)
{
- if (m_material != 0)
+ if (m_material != nullptr)
delete m_material;
m_position = position;
diff --git a/src/quick/scenegraph/qsgcontext.cpp b/src/quick/scenegraph/qsgcontext.cpp
index fb66a6ebb1..d9ed25c099 100644
--- a/src/quick/scenegraph/qsgcontext.cpp
+++ b/src/quick/scenegraph/qsgcontext.cpp
@@ -363,13 +363,6 @@ void QSGRenderContext::registerFontengineForCleanup(QFontEngine *engine)
}
/*!
- Factory function for texture objects.
-
- If \a image is a valid image, the QSGTexture::setImage function
- will be called with \a image as argument.
- */
-
-/*!
Factory function for the scene graph renderers.
The renderers are used for the toplevel renderer and once for every
@@ -379,7 +372,7 @@ void QSGRenderContext::registerFontengineForCleanup(QFontEngine *engine)
QSGTexture *QSGRenderContext::textureForFactory(QQuickTextureFactory *factory, QQuickWindow *window)
{
if (!factory)
- return 0;
+ return nullptr;
m_mutex.lock();
QSGTexture *texture = m_textures.value(factory);
@@ -404,6 +397,20 @@ void QSGRenderContext::textureFactoryDestroyed(QObject *o)
m_mutex.unlock();
}
+/*!
+ Return the texture corresponding to a texture factory.
+
+ This may optionally manipulate the texture in some way; for example by returning
+ an atlased texture.
+
+ This function is not a replacement for textureForFactory; both should be used
+ for a single texture (this might atlas, while the other might cache).
+*/
+QSGTexture *QSGRenderContext::compressedTextureForFactory(const QSGCompressedTextureFactory *) const
+{
+ return nullptr;
+}
+
#include "qsgcontext.moc"
#include "moc_qsgcontext_p.cpp"
diff --git a/src/quick/scenegraph/qsgcontext_p.h b/src/quick/scenegraph/qsgcontext_p.h
index 84a2523f26..6d70d7ef6b 100644
--- a/src/quick/scenegraph/qsgcontext_p.h
+++ b/src/quick/scenegraph/qsgcontext_p.h
@@ -78,6 +78,7 @@ class QSGMaterial;
class QSGRenderLoop;
class QSGLayer;
class QQuickTextureFactory;
+class QSGCompressedTextureFactory;
class QSGContext;
class QQuickPaintedItem;
class QSGRendererInterface;
@@ -109,8 +110,8 @@ public:
MsaaAntialiasing
};
- explicit QSGContext(QObject *parent = 0);
- virtual ~QSGContext();
+ explicit QSGContext(QObject *parent = nullptr);
+ ~QSGContext() override;
virtual void renderContextInitialized(QSGRenderContext *renderContext);
virtual void renderContextInvalidated(QSGRenderContext *renderContext);
@@ -158,7 +159,7 @@ public:
};
QSGRenderContext(QSGContext *context);
- virtual ~QSGRenderContext();
+ ~QSGRenderContext() override;
QSGContext *sceneGraphContext() const { return m_sg; }
virtual bool isValid() const { return true; }
@@ -173,6 +174,7 @@ public:
virtual QSGTexture *createTexture(const QImage &image, uint flags = CreateTexture_Alpha) const = 0;
virtual QSGRenderer *createRenderer() = 0;
+ virtual QSGTexture *compressedTextureForFactory(const QSGCompressedTextureFactory *) const;
virtual void setAttachToGraphicsContext(bool attach) { Q_UNUSED(attach); }
diff --git a/src/quick/scenegraph/qsgcontextplugin.cpp b/src/quick/scenegraph/qsgcontextplugin.cpp
index 1c2550d197..31f1c4c722 100644
--- a/src/quick/scenegraph/qsgcontextplugin.cpp
+++ b/src/quick/scenegraph/qsgcontextplugin.cpp
@@ -74,8 +74,8 @@ struct QSGAdaptationBackendData
{
QSGAdaptationBackendData();
- bool tried;
- QSGContextFactoryInterface *factory;
+ bool tried = false;
+ QSGContextFactoryInterface *factory = nullptr;
QString name;
QSGContextFactoryInterface::Flags flags;
@@ -85,9 +85,7 @@ struct QSGAdaptationBackendData
};
QSGAdaptationBackendData::QSGAdaptationBackendData()
- : tried(false)
- , factory(nullptr)
- , flags(0)
+ : flags(nullptr)
{
// Fill in the table with the built-in adaptations.
builtIns.append(new QSGSoftwareAdaptation);
@@ -140,7 +138,9 @@ QSGAdaptationBackendData *contextFactory()
#ifdef Q_OS_HTML5
requestedBackend = QString::fromLocal8Bit("software");
#endif
+
if (!requestedBackend.isEmpty()) {
+ qCDebug(QSG_LOG_INFO, "Loading backend %s", qUtf8Printable(requestedBackend));
// First look for a built-in adaptation.
for (QSGContextFactoryInterface *builtInBackend : qAsConst(backendData->builtIns)) {
@@ -210,7 +210,7 @@ QQuickTextureFactory *QSGContext::createTextureFactoryFromImage(const QImage &im
QSGAdaptationBackendData *backendData = contextFactory();
if (backendData->factory)
return backendData->factory->createTextureFactoryFromImage(image);
- return 0;
+ return nullptr;
}
@@ -224,7 +224,7 @@ QSGRenderLoop *QSGContext::createWindowManager()
QSGAdaptationBackendData *backendData = contextFactory();
if (backendData->factory)
return backendData->factory->createWindowManager();
- return 0;
+ return nullptr;
}
void QSGContext::setBackend(const QString &backend)
diff --git a/src/quick/scenegraph/qsgcontextplugin_p.h b/src/quick/scenegraph/qsgcontextplugin_p.h
index 02d4b79b76..d37d4df270 100644
--- a/src/quick/scenegraph/qsgcontextplugin_p.h
+++ b/src/quick/scenegraph/qsgcontextplugin_p.h
@@ -87,13 +87,13 @@ class Q_QUICK_PRIVATE_EXPORT QSGContextPlugin : public QObject, public QSGContex
Q_OBJECT
Q_INTERFACES(QSGContextFactoryInterface:QFactoryInterface)
public:
- explicit QSGContextPlugin(QObject *parent = 0);
+ explicit QSGContextPlugin(QObject *parent = nullptr);
virtual ~QSGContextPlugin();
QStringList keys() const override = 0;
- QQuickTextureFactory *createTextureFactoryFromImage(const QImage &) override { return 0; }
- QSGRenderLoop *createWindowManager() override { return 0; }
+ QQuickTextureFactory *createTextureFactoryFromImage(const QImage &) override { return nullptr; }
+ QSGRenderLoop *createWindowManager() override { return nullptr; }
};
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/qsgdefaultcontext.cpp b/src/quick/scenegraph/qsgdefaultcontext.cpp
index be5fec9dab..9a0ac66690 100644
--- a/src/quick/scenegraph/qsgdefaultcontext.cpp
+++ b/src/quick/scenegraph/qsgdefaultcontext.cpp
@@ -149,20 +149,23 @@ void QSGDefaultContext::renderContextInitialized(QSGRenderContext *renderContext
dumped = true;
QSurfaceFormat format = openglRenderContext->openglContext()->format();
QOpenGLFunctions *funcs = QOpenGLContext::currentContext()->functions();
- qCDebug(QSG_LOG_INFO) << "R/G/B/A Buffers: " << format.redBufferSize() << format.greenBufferSize() << format.blueBufferSize() << format.alphaBufferSize();
- qCDebug(QSG_LOG_INFO) << "Depth Buffer: " << format.depthBufferSize();
- qCDebug(QSG_LOG_INFO) << "Stencil Buffer: " << format.stencilBufferSize();
- qCDebug(QSG_LOG_INFO) << "Samples: " << format.samples();
- qCDebug(QSG_LOG_INFO) << "GL_VENDOR: " << (const char *) funcs->glGetString(GL_VENDOR);
- qCDebug(QSG_LOG_INFO) << "GL_RENDERER: " << (const char *) funcs->glGetString(GL_RENDERER);
- qCDebug(QSG_LOG_INFO) << "GL_VERSION: " << (const char *) funcs->glGetString(GL_VERSION);
+ qCDebug(QSG_LOG_INFO, "R/G/B/A Buffers: %d %d %d %d", format.redBufferSize(),
+ format.greenBufferSize(), format.blueBufferSize(), format.alphaBufferSize());
+ qCDebug(QSG_LOG_INFO, "Depth Buffer: %d", format.depthBufferSize());
+ qCDebug(QSG_LOG_INFO, "Stencil Buffer: %d", format.stencilBufferSize());
+ qCDebug(QSG_LOG_INFO, "Samples: %d", format.samples());
+ qCDebug(QSG_LOG_INFO, "GL_VENDOR: %s", (const char*)funcs->glGetString(GL_VENDOR));
+ qCDebug(QSG_LOG_INFO, "GL_RENDERER: %s",
+ (const char*)funcs->glGetString(GL_RENDERER));
+ qCDebug(QSG_LOG_INFO, "GL_VERSION: %s", (const char*)funcs->glGetString(GL_VERSION));
QSet<QByteArray> exts = openglRenderContext->openglContext()->extensions();
QByteArray all;
for (const QByteArray &e : qAsConst(exts))
all += ' ' + e;
- qCDebug(QSG_LOG_INFO) << "GL_EXTENSIONS: " << all.constData();
- qCDebug(QSG_LOG_INFO) << "Max Texture Size: " << openglRenderContext->maxTextureSize();
- qCDebug(QSG_LOG_INFO) << "Debug context: " << format.testOption(QSurfaceFormat::DebugContext);
+ qCDebug(QSG_LOG_INFO, "GL_EXTENSIONS: %s", all.constData());
+ qCDebug(QSG_LOG_INFO, "Max Texture Size: %d", openglRenderContext->maxTextureSize());
+ qCDebug(QSG_LOG_INFO, "Debug context: %s",
+ format.testOption(QSurfaceFormat::DebugContext) ? "true" : "false");
}
m_mutex.unlock();
diff --git a/src/quick/scenegraph/qsgdefaultcontext_p.h b/src/quick/scenegraph/qsgdefaultcontext_p.h
index b2964bf403..6dfd197cf6 100644
--- a/src/quick/scenegraph/qsgdefaultcontext_p.h
+++ b/src/quick/scenegraph/qsgdefaultcontext_p.h
@@ -60,7 +60,7 @@ QT_BEGIN_NAMESPACE
class Q_QUICK_PRIVATE_EXPORT QSGDefaultContext : public QSGContext, public QSGRendererInterface
{
public:
- QSGDefaultContext(QObject *parent = 0);
+ QSGDefaultContext(QObject *parent = nullptr);
~QSGDefaultContext();
void renderContextInitialized(QSGRenderContext *renderContext) override;
diff --git a/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp b/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp
index 7789ef8fb1..ef189ba461 100644
--- a/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp
+++ b/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache.cpp
@@ -63,12 +63,12 @@ QSGDefaultDistanceFieldGlyphCache::QSGDefaultDistanceFieldGlyphCache(QOpenGLCont
: QSGDistanceFieldGlyphCache(c, font)
, m_maxTextureSize(0)
, m_maxTextureCount(3)
- , m_blitProgram(0)
+ , m_blitProgram(nullptr)
, m_blitBuffer(QOpenGLBuffer::VertexBuffer)
- , m_fboGuard(0)
+ , m_fboGuard(nullptr)
, m_funcs(c->functions())
#if !defined(QT_OPENGL_ES_2)
- , m_coreFuncs(0)
+ , m_coreFuncs(nullptr)
#endif
{
if (Q_LIKELY(m_blitBuffer.create())) {
@@ -89,7 +89,7 @@ QSGDefaultDistanceFieldGlyphCache::~QSGDefaultDistanceFieldGlyphCache()
for (int i = 0; i < m_textures.count(); ++i)
m_funcs->glDeleteTextures(1, &m_textures[i].texture);
- if (m_fboGuard != 0)
+ if (m_fboGuard != nullptr)
m_fboGuard->free();
delete m_blitProgram;
@@ -400,7 +400,7 @@ void QSGDefaultDistanceFieldGlyphCache::resizeTexture(TextureInfo *texInfo, int
m_funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0);
#endif
m_funcs->glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, oldWidth, oldHeight, 0,
- GL_RGBA, GL_UNSIGNED_BYTE, NULL);
+ GL_RGBA, GL_UNSIGNED_BYTE, nullptr);
m_funcs->glBindTexture(GL_TEXTURE_2D, 0);
m_funcs->glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0,
GL_TEXTURE_2D, tmp_texture, 0);
diff --git a/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache_p.h b/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache_p.h
index fe365495c2..76c0d20647 100644
--- a/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache_p.h
+++ b/src/quick/scenegraph/qsgdefaultdistancefieldglyphcache_p.h
@@ -91,10 +91,9 @@ private:
QSize size;
QRect allocatedArea;
QDistanceField image;
- int padding;
+ int padding = -1;
- TextureInfo(const QRect &preallocRect = QRect()) : texture(0), allocatedArea(preallocRect), padding(-1)
- { }
+ TextureInfo(const QRect &preallocRect = QRect()) : texture(0), allocatedArea(preallocRect) { }
};
void createTexture(TextureInfo * texInfo, int width, int height);
diff --git a/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp b/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
index 0169f097bc..dc473a6640 100644
--- a/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
+++ b/src/quick/scenegraph/qsgdefaultglyphnode_p.cpp
@@ -107,7 +107,7 @@ protected:
char const *const *QSGTextMaskShader::attributeNames() const
{
- static char const *const attr[] = { "vCoord", "tCoord", 0 };
+ static char const *const attr[] = { "vCoord", "tCoord", nullptr };
return attr;
}
@@ -141,13 +141,13 @@ void QSGTextMaskShader::updateState(const RenderState &state, QSGMaterial *newEf
{
QSGTextMaskMaterial *material = static_cast<QSGTextMaskMaterial *>(newEffect);
QSGTextMaskMaterial *oldMaterial = static_cast<QSGTextMaskMaterial *>(oldEffect);
- Q_ASSERT(oldEffect == 0 || newEffect->type() == oldEffect->type());
+ Q_ASSERT(oldEffect == nullptr || newEffect->type() == oldEffect->type());
bool updated = material->ensureUpToDate();
Q_ASSERT(material->texture());
- Q_ASSERT(oldMaterial == 0 || oldMaterial->texture());
+ Q_ASSERT(oldMaterial == nullptr || oldMaterial->texture());
if (updated
- || oldMaterial == 0
+ || oldMaterial == nullptr
|| oldMaterial->texture()->textureId() != material->texture()->textureId()) {
program()->setUniformValue(m_textureScale_id, QVector2D(1.0 / material->cacheTextureWidth(),
1.0 / material->cacheTextureHeight()));
@@ -190,7 +190,7 @@ void QSG8BitTextMaskShader::updateState(const RenderState &state, QSGMaterial *n
QSGTextMaskMaterial *material = static_cast<QSGTextMaskMaterial *>(newEffect);
QSGTextMaskMaterial *oldMaterial = static_cast<QSGTextMaskMaterial *>(oldEffect);
- if (oldMaterial == 0 || material->color() != oldMaterial->color() || state.isOpacityDirty()) {
+ if (oldMaterial == nullptr || material->color() != oldMaterial->color() || state.isOpacityDirty()) {
QVector4D color = qsg_premultiply(material->color(), state.opacity());
program()->setUniformValue(m_color_id, color);
}
@@ -282,7 +282,7 @@ void QSG24BitTextMaskShader::updateState(const RenderState &state, QSGMaterial *
QSGTextMaskMaterial *material = static_cast<QSGTextMaskMaterial *>(newEffect);
QSGTextMaskMaterial *oldMaterial = static_cast<QSGTextMaskMaterial *>(oldEffect);
- if (oldMaterial == 0 || material->color() != oldMaterial->color() || state.isOpacityDirty()) {
+ if (oldMaterial == nullptr || material->color() != oldMaterial->color() || state.isOpacityDirty()) {
QVector4D color = material->color();
if (useSRGB())
color = qt_sRGB_to_linear_RGB(color);
@@ -346,20 +346,20 @@ void QSGStyledTextShader::updateState(const RenderState &state,
QSGMaterial *newEffect,
QSGMaterial *oldEffect)
{
- Q_ASSERT(oldEffect == 0 || newEffect->type() == oldEffect->type());
+ Q_ASSERT(oldEffect == nullptr || newEffect->type() == oldEffect->type());
QSGStyledTextMaterial *material = static_cast<QSGStyledTextMaterial *>(newEffect);
QSGStyledTextMaterial *oldMaterial = static_cast<QSGStyledTextMaterial *>(oldEffect);
- if (oldMaterial == 0 || oldMaterial->styleShift() != material->styleShift())
+ if (oldMaterial == nullptr || oldMaterial->styleShift() != material->styleShift())
program()->setUniformValue(m_shift_id, material->styleShift());
- if (oldMaterial == 0 || material->color() != oldMaterial->color() || state.isOpacityDirty()) {
+ if (oldMaterial == nullptr || material->color() != oldMaterial->color() || state.isOpacityDirty()) {
QVector4D color = qsg_premultiply(material->color(), state.opacity());
program()->setUniformValue(m_color_id, color);
}
- if (oldMaterial == 0 || material->styleColor() != oldMaterial->styleColor() || state.isOpacityDirty()) {
+ if (oldMaterial == nullptr || material->styleColor() != oldMaterial->styleColor() || state.isOpacityDirty()) {
QVector4D styleColor = qsg_premultiply(material->styleColor(), state.opacity());
program()->setUniformValue(m_styleColor_id, styleColor);
}
@@ -367,9 +367,9 @@ void QSGStyledTextShader::updateState(const RenderState &state,
bool updated = material->ensureUpToDate();
Q_ASSERT(material->texture());
- Q_ASSERT(oldMaterial == 0 || oldMaterial->texture());
+ Q_ASSERT(oldMaterial == nullptr || oldMaterial->texture());
if (updated
- || oldMaterial == 0
+ || oldMaterial == nullptr
|| oldMaterial->texture()->textureId() != material->texture()->textureId()) {
program()->setUniformValue(m_textureScale_id, QVector2D(1.0 / material->cacheTextureWidth(),
1.0 / material->cacheTextureHeight()));
@@ -400,8 +400,8 @@ public:
};
QSGTextMaskMaterial::QSGTextMaskMaterial(const QRawFont &font, QFontEngine::GlyphFormat glyphFormat)
- : m_texture(0)
- , m_glyphCache(0)
+ : m_texture(nullptr)
+ , m_glyphCache(nullptr)
, m_font(font)
{
init(glyphFormat);
@@ -419,7 +419,7 @@ void QSGTextMaskMaterial::init(QFontEngine::GlyphFormat glyphFormat)
setFlag(Blending, true);
QOpenGLContext *ctx = const_cast<QOpenGLContext *>(QOpenGLContext::currentContext());
- Q_ASSERT(ctx != 0);
+ Q_ASSERT(ctx != nullptr);
// The following piece of code will read/write to the font engine's caches,
// potentially from different threads. However, this is safe because this
diff --git a/src/quick/scenegraph/qsgdefaultinternalimagenode.cpp b/src/quick/scenegraph/qsgdefaultinternalimagenode.cpp
index a5a6da06a7..5dd6eaa4ca 100644
--- a/src/quick/scenegraph/qsgdefaultinternalimagenode.cpp
+++ b/src/quick/scenegraph/qsgdefaultinternalimagenode.cpp
@@ -83,7 +83,6 @@ QSGMaterialShader *QSGSmoothTextureMaterial::createShader() const
}
SmoothTextureMaterialShader::SmoothTextureMaterialShader()
- : QSGTextureMaterialShader()
{
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/smoothtexture.vert"));
setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/qt-project.org/scenegraph/shaders/smoothtexture.frag"));
@@ -91,7 +90,7 @@ SmoothTextureMaterialShader::SmoothTextureMaterialShader()
void SmoothTextureMaterialShader::updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect)
{
- if (oldEffect == 0) {
+ if (oldEffect == nullptr) {
// The viewport is constant, so set the pixel size uniform only once.
QRect r = state.viewportRect();
program()->setUniformValue(m_pixelSizeLoc, 2.0f / r.width(), 2.0f / r.height());
@@ -106,7 +105,7 @@ char const *const *SmoothTextureMaterialShader::attributeNames() const
"multiTexCoord",
"vertexOffset",
"texCoordOffset",
- 0
+ nullptr
};
return attributes;
}
@@ -171,7 +170,7 @@ void QSGDefaultInternalImageNode::updateMaterialAntialiasing()
{
if (m_antialiasing) {
setMaterial(&m_smoothMaterial);
- setOpaqueMaterial(0);
+ setOpaqueMaterial(nullptr);
} else {
setMaterial(&m_materialO);
setOpaqueMaterial(&m_material);
diff --git a/src/quick/scenegraph/qsgdefaultinternalrectanglenode.cpp b/src/quick/scenegraph/qsgdefaultinternalrectanglenode.cpp
index e52dcaad52..fd0dcebd57 100644
--- a/src/quick/scenegraph/qsgdefaultinternalrectanglenode.cpp
+++ b/src/quick/scenegraph/qsgdefaultinternalrectanglenode.cpp
@@ -67,7 +67,6 @@ private:
};
SmoothColorMaterialShader::SmoothColorMaterialShader()
- : QSGMaterialShader()
{
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/smoothcolor.vert"));
setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/qt-project.org/scenegraph/shaders/smoothcolor.frag"));
@@ -81,7 +80,7 @@ void SmoothColorMaterialShader::updateState(const RenderState &state, QSGMateria
if (state.isMatrixDirty())
program()->setUniformValue(m_matrixLoc, state.combinedMatrix());
- if (oldEffect == 0) {
+ if (oldEffect == nullptr) {
// The viewport is constant, so set the pixel size uniform only once.
QRect r = state.viewportRect();
program()->setUniformValue(m_pixelSizeLoc, 2.0f / r.width(), 2.0f / r.height());
@@ -94,7 +93,7 @@ char const *const *SmoothColorMaterialShader::attributeNames() const
"vertex",
"vertexColor",
"vertexOffset",
- 0
+ nullptr
};
return attributes;
}
diff --git a/src/quick/scenegraph/qsgdefaultlayer.cpp b/src/quick/scenegraph/qsgdefaultlayer.cpp
index cd9c4a9a90..b2b123912f 100644
--- a/src/quick/scenegraph/qsgdefaultlayer.cpp
+++ b/src/quick/scenegraph/qsgdefaultlayer.cpp
@@ -90,15 +90,15 @@ namespace
QSGDefaultLayer::QSGDefaultLayer(QSGRenderContext *context)
: QSGLayer()
- , m_item(0)
+ , m_item(nullptr)
, m_device_pixel_ratio(1)
, m_format(GL_RGBA)
- , m_renderer(0)
- , m_fbo(0)
- , m_secondaryFbo(0)
+ , m_renderer(nullptr)
+ , m_fbo(nullptr)
+ , m_secondaryFbo(nullptr)
, m_transparentTexture(0)
#ifdef QSG_DEBUG_FBO_OVERLAY
- , m_debugOverlay(0)
+ , m_debugOverlay(nullptr)
#endif
, m_samples(0)
, m_mipmap(false)
@@ -122,13 +122,13 @@ QSGDefaultLayer::~QSGDefaultLayer()
void QSGDefaultLayer::invalidated()
{
delete m_renderer;
- m_renderer = 0;
+ m_renderer = nullptr;
delete m_fbo;
delete m_secondaryFbo;
- m_fbo = m_secondaryFbo = 0;
+ m_fbo = m_secondaryFbo = nullptr;
#ifdef QSG_DEBUG_FBO_OVERLAY
delete m_debugOverlay;
- m_debugOverlay = 0;
+ m_debugOverlay = nullptr;
#endif
if (m_transparentTexture) {
QOpenGLContext::currentContext()->functions()->glDeleteTextures(1, &m_transparentTexture);
@@ -204,7 +204,7 @@ void QSGDefaultLayer::setItem(QSGNode *item)
if (m_live && !m_item) {
delete m_fbo;
delete m_secondaryFbo;
- m_fbo = m_secondaryFbo = 0;
+ m_fbo = m_secondaryFbo = nullptr;
m_depthStencilBuffer.clear();
}
@@ -228,7 +228,7 @@ void QSGDefaultLayer::setSize(const QSize &size)
if (m_live && m_size.isNull()) {
delete m_fbo;
delete m_secondaryFbo;
- m_fbo = m_secondaryFbo = 0;
+ m_fbo = m_secondaryFbo = nullptr;
m_depthStencilBuffer.clear();
}
@@ -252,7 +252,7 @@ void QSGDefaultLayer::setLive(bool live)
if (m_live && (!m_item || m_size.isNull())) {
delete m_fbo;
delete m_secondaryFbo;
- m_fbo = m_secondaryFbo = 0;
+ m_fbo = m_secondaryFbo = nullptr;
m_depthStencilBuffer.clear();
}
@@ -295,7 +295,7 @@ void QSGDefaultLayer::grab()
if (!m_item || m_size.isNull()) {
delete m_fbo;
delete m_secondaryFbo;
- m_fbo = m_secondaryFbo = 0;
+ m_fbo = m_secondaryFbo = nullptr;
m_depthStencilBuffer.clear();
m_dirtyTexture = false;
return;
@@ -362,7 +362,7 @@ void QSGDefaultLayer::grab()
delete m_fbo;
delete m_secondaryFbo;
m_fbo = new QOpenGLFramebufferObject(m_size, format);
- m_secondaryFbo = 0;
+ m_secondaryFbo = nullptr;
funcs->glBindTexture(GL_TEXTURE_2D, m_fbo->texture());
updateBindOptions(true);
m_depthStencilBuffer = m_context->depthStencilBufferForFbo(m_fbo);
diff --git a/src/quick/scenegraph/qsgdefaultrendercontext.cpp b/src/quick/scenegraph/qsgdefaultrendercontext.cpp
index 95f3555994..7882496062 100644
--- a/src/quick/scenegraph/qsgdefaultrendercontext.cpp
+++ b/src/quick/scenegraph/qsgdefaultrendercontext.cpp
@@ -44,6 +44,7 @@
#include <QtQuick/private/qsgbatchrenderer_p.h>
#include <QtQuick/private/qsgrenderer_p.h>
#include <QtQuick/private/qsgatlastexture_p.h>
+#include <QtQuick/private/qsgcompressedtexture_p.h>
#include <QtQuick/private/qsgdefaultdistancefieldglyphcache_p.h>
QT_BEGIN_NAMESPACE
@@ -156,14 +157,14 @@ void QSGDefaultRenderContext::invalidate()
m_fontEnginesToClean.clear();
delete m_depthStencilManager;
- m_depthStencilManager = 0;
+ m_depthStencilManager = nullptr;
qDeleteAll(m_glyphCaches);
m_glyphCaches.clear();
if (m_gl->property(QSG_RENDERCONTEXT_PROPERTY) == QVariant::fromValue(this))
m_gl->setProperty(QSG_RENDERCONTEXT_PROPERTY, QVariant());
- m_gl = 0;
+ m_gl = nullptr;
if (m_sg)
m_sg->renderContextInvalidated(this);
@@ -210,7 +211,7 @@ QSharedPointer<QSGDepthStencilBuffer> QSGDefaultRenderContext::depthStencilBuffe
QSGDepthStencilBufferManager *QSGDefaultRenderContext::depthStencilBufferManager()
{
if (!m_gl)
- return 0;
+ return nullptr;
if (!m_depthStencilManager)
m_depthStencilManager = new QSGDepthStencilBufferManager(m_gl);
return m_depthStencilManager;
@@ -243,6 +244,14 @@ QSGRenderer *QSGDefaultRenderContext::createRenderer()
return new QSGBatchRenderer::Renderer(this);
}
+QSGTexture *QSGDefaultRenderContext::compressedTextureForFactory(const QSGCompressedTextureFactory *factory) const
+{
+ // The atlas implementation is only supported from the render thread
+ if (openglContext() && QThread::currentThread() == openglContext()->thread())
+ return m_atlasManager->create(factory);
+ return nullptr;
+}
+
/*!
Compile \a shader, optionally using \a vertexCode and \a fragmentCode as
replacement for the source code supplied by \a shader.
diff --git a/src/quick/scenegraph/qsgdefaultrendercontext_p.h b/src/quick/scenegraph/qsgdefaultrendercontext_p.h
index 2537a06988..eb62586a94 100644
--- a/src/quick/scenegraph/qsgdefaultrendercontext_p.h
+++ b/src/quick/scenegraph/qsgdefaultrendercontext_p.h
@@ -84,8 +84,9 @@ public:
QSGTexture *createTexture(const QImage &image, uint flags) const override;
QSGRenderer *createRenderer() override;
+ QSGTexture *compressedTextureForFactory(const QSGCompressedTextureFactory *factory) const override;
- virtual void compileShader(QSGMaterialShader *shader, QSGMaterial *material, const char *vertexCode = 0, const char *fragmentCode = 0);
+ virtual void compileShader(QSGMaterialShader *shader, QSGMaterial *material, const char *vertexCode = nullptr, const char *fragmentCode = nullptr);
virtual void initializeShader(QSGMaterialShader *shader);
void setAttachToGraphicsContext(bool attach) override;
diff --git a/src/quick/scenegraph/qsgdefaultspritenode.cpp b/src/quick/scenegraph/qsgdefaultspritenode.cpp
index 7fe6048d59..8761d99c1f 100644
--- a/src/quick/scenegraph/qsgdefaultspritenode.cpp
+++ b/src/quick/scenegraph/qsgdefaultspritenode.cpp
@@ -70,26 +70,18 @@ public:
return this - static_cast<const QQuickSpriteMaterial *>(other);
}
- QSGTexture *texture;
-
- float animT;
- float animX1;
- float animY1;
- float animX2;
- float animY2;
- float animW;
- float animH;
+ QSGTexture *texture = nullptr;
+
+ float animT = 0.0f;
+ float animX1 = 0.0f;
+ float animY1 = 0.0f;
+ float animX2 = 0.0f;
+ float animY2 = 0.0f;
+ float animW = 1.0f;
+ float animH = 1.0f;
};
QQuickSpriteMaterial::QQuickSpriteMaterial()
- : texture(0)
- , animT(0.0f)
- , animX1(0.0f)
- , animY1(0.0f)
- , animX2(0.0f)
- , animY2(0.0f)
- , animW(1.0f)
- , animH(1.0f)
{
setFlag(Blending, true);
}
@@ -103,7 +95,6 @@ class SpriteMaterialData : public QSGMaterialShader
{
public:
SpriteMaterialData()
- : QSGMaterialShader()
{
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/sprite.vert"));
setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/qt-project.org/scenegraph/shaders/sprite.frag"));
@@ -133,7 +124,7 @@ public:
static const char *attr[] = {
"vPos",
"vTex",
- 0
+ nullptr
};
return attr;
}
diff --git a/src/quick/scenegraph/qsgdistancefieldglyphnode.cpp b/src/quick/scenegraph/qsgdistancefieldglyphnode.cpp
index 32eda2d142..ae6336718e 100644
--- a/src/quick/scenegraph/qsgdistancefieldglyphnode.cpp
+++ b/src/quick/scenegraph/qsgdistancefieldglyphnode.cpp
@@ -46,12 +46,12 @@ QT_BEGIN_NAMESPACE
QSGDistanceFieldGlyphNode::QSGDistanceFieldGlyphNode(QSGRenderContext *context)
: m_glyphNodeType(RootGlyphNode)
, m_context(context)
- , m_material(0)
- , m_glyph_cache(0)
+ , m_material(nullptr)
+ , m_glyph_cache(nullptr)
, m_geometry(QSGGeometry::defaultAttributes_TexturedPoint2D(), 0)
, m_style(QQuickText::Normal)
, m_antialiasingMode(GrayAntialiasing)
- , m_texture(0)
+ , m_texture(nullptr)
, m_dirtyGeometry(false)
, m_dirtyMaterial(false)
{
@@ -80,7 +80,7 @@ QSGDistanceFieldGlyphNode::~QSGDistanceFieldGlyphNode()
void QSGDistanceFieldGlyphNode::setColor(const QColor &color)
{
m_color = color;
- if (m_material != 0) {
+ if (m_material != nullptr) {
m_material->setColor(color);
markDirty(DirtyMaterial);
} else {
@@ -113,7 +113,7 @@ void QSGDistanceFieldGlyphNode::setGlyphs(const QPointF &position, const QGlyphR
return;
if (m_glyph_cache != oldCache) {
- Q_ASSERT(ownerElement() != 0);
+ Q_ASSERT(ownerElement() != nullptr);
if (oldCache) {
oldCache->unregisterGlyphNode(this);
oldCache->unregisterOwnerElement(ownerElement());
@@ -181,7 +181,7 @@ void QSGDistanceFieldGlyphNode::updateGeometry()
// Remove previously created sub glyph nodes
// We assume all the children are sub glyph nodes
QSGNode *subnode = firstChild();
- QSGNode *nextNode = 0;
+ QSGNode *nextNode = nullptr;
while (subnode) {
nextNode = subnode->nextSibling();
delete subnode;
diff --git a/src/quick/scenegraph/qsgdistancefieldglyphnode_p.cpp b/src/quick/scenegraph/qsgdistancefieldglyphnode_p.cpp
index a67c659c99..aa58218505 100644
--- a/src/quick/scenegraph/qsgdistancefieldglyphnode_p.cpp
+++ b/src/quick/scenegraph/qsgdistancefieldglyphnode_p.cpp
@@ -61,37 +61,27 @@ protected:
void updateColor(const QVector4D &c);
void updateTextureScale(const QVector2D &ts);
- float m_fontScale;
- float m_matrixScale;
+ float m_fontScale = 1.0;
+ float m_matrixScale = 1.0;
- int m_matrix_id;
- int m_textureScale_id;
- int m_alphaMin_id;
- int m_alphaMax_id;
- int m_color_id;
+ int m_matrix_id = -1;
+ int m_textureScale_id = -1;
+ int m_alphaMin_id = -1;
+ int m_alphaMax_id = -1;
+ int m_color_id = -1;
QVector2D m_lastTextureScale;
QVector4D m_lastColor;
- float m_lastAlphaMin;
- float m_lastAlphaMax;
+ float m_lastAlphaMin = -1;
+ float m_lastAlphaMax = -1;
};
char const *const *QSGDistanceFieldTextMaterialShader::attributeNames() const {
- static char const *const attr[] = { "vCoord", "tCoord", 0 };
+ static char const *const attr[] = { "vCoord", "tCoord", nullptr };
return attr;
}
QSGDistanceFieldTextMaterialShader::QSGDistanceFieldTextMaterialShader()
- : QSGMaterialShader(),
- m_fontScale(1.0)
- , m_matrixScale(1.0)
- , m_matrix_id(-1)
- , m_textureScale_id(-1)
- , m_alphaMin_id(-1)
- , m_alphaMax_id(-1)
- , m_color_id(-1)
- , m_lastAlphaMin(-1)
- , m_lastAlphaMax(-1)
{
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/distancefieldtext.vert"));
setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/qt-project.org/scenegraph/shaders/distancefieldtext.frag"));
@@ -166,13 +156,13 @@ void QSGDistanceFieldTextMaterialShader::initialize()
void QSGDistanceFieldTextMaterialShader::updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect)
{
- Q_ASSERT(oldEffect == 0 || newEffect->type() == oldEffect->type());
+ Q_ASSERT(oldEffect == nullptr || newEffect->type() == oldEffect->type());
QSGDistanceFieldTextMaterial *material = static_cast<QSGDistanceFieldTextMaterial *>(newEffect);
QSGDistanceFieldTextMaterial *oldMaterial = static_cast<QSGDistanceFieldTextMaterial *>(oldEffect);
bool updated = material->updateTextureSize();
- if (oldMaterial == 0
+ if (oldMaterial == nullptr
|| material->color() != oldMaterial->color()
|| state.isOpacityDirty()) {
QVector4D color = material->color();
@@ -181,7 +171,7 @@ void QSGDistanceFieldTextMaterialShader::updateState(const RenderState &state, Q
}
bool updateRange = false;
- if (oldMaterial == 0
+ if (oldMaterial == nullptr
|| material->fontScale() != oldMaterial->fontScale()) {
m_fontScale = material->fontScale();
updateRange = true;
@@ -198,12 +188,12 @@ void QSGDistanceFieldTextMaterialShader::updateState(const RenderState &state, Q
Q_ASSERT(material->glyphCache());
if (updated
- || oldMaterial == 0
+ || oldMaterial == nullptr
|| oldMaterial->texture()->textureId != material->texture()->textureId) {
updateTextureScale(QVector2D(1.0 / material->textureSize().width(),
1.0 / material->textureSize().height()));
- QOpenGLFunctions *funcs = QOpenGLContext::currentContext()->functions();
+ QOpenGLFunctions *funcs = state.context()->functions();
funcs->glBindTexture(GL_TEXTURE_2D, material->texture()->textureId);
if (updated) {
@@ -218,8 +208,8 @@ void QSGDistanceFieldTextMaterialShader::updateState(const RenderState &state, Q
}
QSGDistanceFieldTextMaterial::QSGDistanceFieldTextMaterial()
- : m_glyph_cache(0)
- , m_texture(0)
+ : m_glyph_cache(nullptr)
+ , m_texture(nullptr)
, m_fontScale(1.0)
{
setFlag(Blending | RequiresDeterminant, true);
@@ -288,12 +278,11 @@ public:
protected:
void initialize() override;
- int m_styleColor_id;
+ int m_styleColor_id = -1;
};
DistanceFieldStyledTextMaterialShader::DistanceFieldStyledTextMaterialShader()
: QSGDistanceFieldTextMaterialShader()
- , m_styleColor_id(-1)
{
}
@@ -310,7 +299,7 @@ void DistanceFieldStyledTextMaterialShader::updateState(const RenderState &state
QSGDistanceFieldStyledTextMaterial *material = static_cast<QSGDistanceFieldStyledTextMaterial *>(newEffect);
QSGDistanceFieldStyledTextMaterial *oldMaterial = static_cast<QSGDistanceFieldStyledTextMaterial *>(oldEffect);
- if (oldMaterial == 0
+ if (oldMaterial == nullptr
|| material->styleColor() != oldMaterial->styleColor()
|| (state.isOpacityDirty())) {
QVector4D color = material->styleColor();
@@ -358,14 +347,12 @@ protected:
void updateOutlineAlphaRange(int dfRadius);
- int m_outlineAlphaMax0_id;
- int m_outlineAlphaMax1_id;
+ int m_outlineAlphaMax0_id = -1;
+ int m_outlineAlphaMax1_id = -1;
};
DistanceFieldOutlineTextMaterialShader::DistanceFieldOutlineTextMaterialShader()
: DistanceFieldStyledTextMaterialShader()
- , m_outlineAlphaMax0_id(-1)
- , m_outlineAlphaMax1_id(-1)
{
setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/qt-project.org/scenegraph/shaders/distancefieldoutlinetext.frag"));
}
@@ -398,7 +385,7 @@ void DistanceFieldOutlineTextMaterialShader::updateState(const RenderState &stat
QSGDistanceFieldOutlineTextMaterial *material = static_cast<QSGDistanceFieldOutlineTextMaterial *>(newEffect);
QSGDistanceFieldOutlineTextMaterial *oldMaterial = static_cast<QSGDistanceFieldOutlineTextMaterial *>(oldEffect);
- if (oldMaterial == 0
+ if (oldMaterial == nullptr
|| material->fontScale() != oldMaterial->fontScale()
|| state.isMatrixDirty())
updateOutlineAlphaRange(material->glyphCache()->distanceFieldRadius());
@@ -438,12 +425,11 @@ protected:
void updateShift(qreal fontScale, const QPointF& shift);
- int m_shift_id;
+ int m_shift_id = -1;
};
DistanceFieldShiftedStyleTextMaterialShader::DistanceFieldShiftedStyleTextMaterialShader()
: DistanceFieldStyledTextMaterialShader()
- , m_shift_id(-1)
{
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/distancefieldshiftedtext.vert"));
setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/qt-project.org/scenegraph/shaders/distancefieldshiftedtext.frag"));
@@ -462,7 +448,7 @@ void DistanceFieldShiftedStyleTextMaterialShader::updateState(const RenderState
QSGDistanceFieldShiftedStyleTextMaterial *material = static_cast<QSGDistanceFieldShiftedStyleTextMaterial *>(newEffect);
QSGDistanceFieldShiftedStyleTextMaterial *oldMaterial = static_cast<QSGDistanceFieldShiftedStyleTextMaterial *>(oldEffect);
- if (oldMaterial == 0
+ if (oldMaterial == nullptr
|| oldMaterial->fontScale() != material->fontScale()
|| oldMaterial->shift() != material->shift()
|| oldMaterial->textureSize() != material->textureSize()) {
@@ -516,14 +502,12 @@ public:
void updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect) override;
private:
- int m_fontScale_id;
- int m_vecDelta_id;
+ int m_fontScale_id = -1;
+ int m_vecDelta_id = -1;
};
QSGHiQSubPixelDistanceFieldTextMaterialShader::QSGHiQSubPixelDistanceFieldTextMaterialShader()
: QSGDistanceFieldTextMaterialShader()
- , m_fontScale_id(-1)
- , m_vecDelta_id(-1)
{
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/hiqsubpixeldistancefieldtext.vert"));
setShaderSourceFile(QOpenGLShader::Fragment, QStringLiteral(":/qt-project.org/scenegraph/shaders/hiqsubpixeldistancefieldtext.frag"));
@@ -550,19 +534,19 @@ void QSGHiQSubPixelDistanceFieldTextMaterialShader::deactivate()
void QSGHiQSubPixelDistanceFieldTextMaterialShader::updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect)
{
- Q_ASSERT(oldEffect == 0 || newEffect->type() == oldEffect->type());
+ Q_ASSERT(oldEffect == nullptr || newEffect->type() == oldEffect->type());
QSGDistanceFieldTextMaterial *material = static_cast<QSGDistanceFieldTextMaterial *>(newEffect);
QSGDistanceFieldTextMaterial *oldMaterial = static_cast<QSGDistanceFieldTextMaterial *>(oldEffect);
- if (oldMaterial == 0 || material->color() != oldMaterial->color()) {
+ if (oldMaterial == nullptr || material->color() != oldMaterial->color()) {
QVector4D c = material->color();
state.context()->functions()->glBlendColor(c.x(), c.y(), c.z(), 1.0f);
}
- if (oldMaterial == 0 || material->fontScale() != oldMaterial->fontScale())
+ if (oldMaterial == nullptr || material->fontScale() != oldMaterial->fontScale())
program()->setUniformValue(m_fontScale_id, GLfloat(material->fontScale()));
- if (oldMaterial == 0 || state.isMatrixDirty()) {
+ if (oldMaterial == nullptr || state.isMatrixDirty()) {
int viewportWidth = state.viewportRect().width();
QMatrix4x4 mat = state.combinedMatrix().inverted();
program()->setUniformValue(m_vecDelta_id, mat.column(0) * (qreal(2) / viewportWidth));
diff --git a/src/quick/scenegraph/qsgrenderloop.cpp b/src/quick/scenegraph/qsgrenderloop.cpp
index 58450d7a50..9e5cc27cd8 100644
--- a/src/quick/scenegraph/qsgrenderloop.cpp
+++ b/src/quick/scenegraph/qsgrenderloop.cpp
@@ -76,7 +76,7 @@ QT_BEGIN_NAMESPACE
extern bool qsg_useConsistentTiming();
extern Q_GUI_EXPORT QImage qt_gl_read_framebuffer(const QSize &size, bool alpha_format, bool include_alpha);
#if QT_CONFIG(opengl)
-/*!
+/*
expectations for this manager to work:
- one opengl context to render multiple windows
- OpenGL pipeline will not block for vsync in swap
@@ -88,7 +88,7 @@ extern Q_GUI_EXPORT QImage qt_gl_read_framebuffer(const QSize &size, bool alpha_
DEFINE_BOOL_CONFIG_OPTION(qmlNoThreadedRenderer, QML_BAD_GUI_RENDER_LOOP);
DEFINE_BOOL_CONFIG_OPTION(qmlForceThreadedRenderer, QML_FORCE_THREADED_RENDERER); // Might trigger graphics driver threading bugs, use at own risk
#endif
-QSGRenderLoop *QSGRenderLoop::s_instance = 0;
+QSGRenderLoop *QSGRenderLoop::s_instance = nullptr;
QSGRenderLoop::~QSGRenderLoop()
{
@@ -107,11 +107,11 @@ void QSGRenderLoop::cleanup()
QQuickWindowPrivate *wd = QQuickWindowPrivate::get(w);
if (wd->windowManager == s_instance) {
s_instance->windowDestroyed(w);
- wd->windowManager = 0;
+ wd->windowManager = nullptr;
}
}
delete s_instance;
- s_instance = 0;
+ s_instance = nullptr;
}
/*!
@@ -155,7 +155,7 @@ public:
void releaseResources(QQuickWindow *) override;
- QAnimationDriver *animationDriver() const override { return 0; }
+ QAnimationDriver *animationDriver() const override { return nullptr; }
QSGContext *sceneGraphContext() const override;
QSGRenderContext *createRenderContext(QSGContext *) const override { return rc; }
@@ -282,7 +282,7 @@ void QSGRenderLoop::handleContextCreationFailure(QQuickWindow *window,
}
#if QT_CONFIG(opengl)
QSGGuiThreadRenderLoop::QSGGuiThreadRenderLoop()
- : gl(0)
+ : gl(nullptr)
{
if (qsg_useConsistentTiming()) {
QUnifiedTimer::instance(true)->setConsistentTiming(true);
@@ -334,7 +334,7 @@ void QSGGuiThreadRenderLoop::windowDestroyed(QQuickWindow *window)
current = gl->makeCurrent(surface);
}
if (Q_UNLIKELY(!current))
- qCDebug(QSG_LOG_RENDERLOOP) << "cleanup without an OpenGL context";
+ qCDebug(QSG_LOG_RENDERLOOP, "cleanup without an OpenGL context");
#if QT_CONFIG(quick_shadereffect) && QT_CONFIG(opengl)
QQuickOpenGLShaderEffectMaterial::cleanupMaterialCache();
@@ -344,7 +344,7 @@ void QSGGuiThreadRenderLoop::windowDestroyed(QQuickWindow *window)
if (m_windows.size() == 0) {
rc->invalidate();
delete gl;
- gl = 0;
+ gl = nullptr;
} else if (gl && window == gl->surface() && current) {
gl->doneCurrent();
}
@@ -371,7 +371,7 @@ void QSGGuiThreadRenderLoop::renderWindow(QQuickWindow *window)
if (!gl->create()) {
const bool isEs = gl->isOpenGLES();
delete gl;
- gl = 0;
+ gl = nullptr;
handleContextCreationFailure(window, isEs);
} else {
cd->fireOpenGLContextCreated(gl);
diff --git a/src/quick/scenegraph/qsgthreadedrenderloop.cpp b/src/quick/scenegraph/qsgthreadedrenderloop.cpp
index 4a712d3cdd..8262708320 100644
--- a/src/quick/scenegraph/qsgthreadedrenderloop.cpp
+++ b/src/quick/scenegraph/qsgthreadedrenderloop.cpp
@@ -115,7 +115,7 @@
QT_BEGIN_NAMESPACE
-#define QSG_RT_PAD " (RT)"
+#define QSG_RT_PAD " (RT) %s"
static inline int qsgrl_animation_interval() {
qreal refreshRate = QGuiApplication::primaryScreen()->refreshRate();
@@ -167,7 +167,7 @@ template <typename T> T *windowFor(const QList<T> &list, QQuickWindow *window)
if (t.window == window)
return const_cast<T *>(&t);
}
- return 0;
+ return nullptr;
}
@@ -270,13 +270,13 @@ class QSGRenderThread : public QThread
public:
QSGRenderThread(QSGThreadedRenderLoop *w, QSGRenderContext *renderContext)
: wm(w)
- , gl(0)
- , animatorDriver(0)
+ , gl(nullptr)
+ , animatorDriver(nullptr)
, pendingUpdate(0)
, sleeping(false)
, syncResultedInChanges(false)
, active(false)
- , window(0)
+ , window(nullptr)
, stopEventProcessing(false)
{
sgrc = static_cast<QSGDefaultRenderContext *>(renderContext);
@@ -315,7 +315,7 @@ public:
public slots:
void sceneGraphChanged() {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "sceneGraphChanged";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "sceneGraphChanged");
syncResultedInChanges = true;
}
@@ -358,15 +358,15 @@ bool QSGRenderThread::event(QEvent *e)
switch ((int) e->type()) {
case WM_Obscure: {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "WM_Obscure";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "WM_Obscure");
Q_ASSERT(!window || window == static_cast<WMWindowEvent *>(e)->window);
mutex.lock();
if (window) {
QQuickWindowPrivate::get(window)->fireAboutToStop();
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- window removed";
- window = 0;
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- window removed");
+ window = nullptr;
}
waitCondition.wakeOne();
mutex.unlock();
@@ -374,7 +374,7 @@ bool QSGRenderThread::event(QEvent *e)
return true; }
case WM_RequestSync: {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "WM_RequestSync";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "WM_RequestSync");
WMSyncEvent *se = static_cast<WMSyncEvent *>(e);
if (sleeping)
stopEventProcessing = true;
@@ -383,33 +383,33 @@ bool QSGRenderThread::event(QEvent *e)
pendingUpdate |= SyncRequest;
if (se->syncInExpose) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- triggered from expose";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- triggered from expose");
pendingUpdate |= ExposeRequest;
}
if (se->forceRenderPass) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- repaint regardless";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- repaint regardless");
pendingUpdate |= RepaintRequest;
}
return true; }
case WM_TryRelease: {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "WM_TryRelease";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "WM_TryRelease");
mutex.lock();
wm->m_lockedForSync = true;
WMTryReleaseEvent *wme = static_cast<WMTryReleaseEvent *>(e);
if (!window || wme->inDestructor) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- setting exit flag and invalidating OpenGL";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- setting exit flag and invalidating OpenGL");
invalidateOpenGL(wme->window, wme->inDestructor, wme->fallbackSurface);
active = gl;
Q_ASSERT_X(!wme->inDestructor || !active, "QSGRenderThread::invalidateOpenGL()", "Thread's active state is not set to false when shutting down");
if (sleeping)
stopEventProcessing = true;
} else {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- not releasing because window is still active";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- not releasing because window is still active");
if (window) {
QQuickWindowPrivate *d = QQuickWindowPrivate::get(window);
if (d->renderer) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- requesting renderer to release cached resources";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- requesting renderer to release cached resources");
d->renderer->releaseCachedResources();
}
}
@@ -421,7 +421,7 @@ bool QSGRenderThread::event(QEvent *e)
}
case WM_Grab: {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "WM_Grab";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "WM_Grab");
WMGrabEvent *ce = static_cast<WMGrabEvent *>(e);
Q_ASSERT(ce->window);
Q_ASSERT(ce->window == window || !window);
@@ -429,41 +429,41 @@ bool QSGRenderThread::event(QEvent *e)
if (ce->window) {
gl->makeCurrent(ce->window);
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- sync scene graph";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- sync scene graph");
QQuickWindowPrivate *d = QQuickWindowPrivate::get(ce->window);
d->syncSceneGraph();
sgrc->endSync();
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- rendering scene graph";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- rendering scene graph");
QQuickWindowPrivate::get(ce->window)->renderSceneGraph(ce->window->size());
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- grabbing result";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- grabbing result");
bool alpha = ce->window->format().alphaBufferSize() > 0 && ce->window->color().alpha() != 255;
*ce->image = qt_gl_read_framebuffer(windowSize * ce->window->effectiveDevicePixelRatio(), alpha, alpha);
ce->image->setDevicePixelRatio(ce->window->effectiveDevicePixelRatio());
}
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- waking gui to handle result";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- waking gui to handle result");
waitCondition.wakeOne();
mutex.unlock();
return true;
}
case WM_PostJob: {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "WM_PostJob";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "WM_PostJob");
WMJobEvent *ce = static_cast<WMJobEvent *>(e);
Q_ASSERT(ce->window == window);
if (window) {
gl->makeCurrent(window);
ce->job->run();
delete ce->job;
- ce->job = 0;
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- job done";
+ ce->job = nullptr;
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- job done");
}
return true;
}
case WM_RequestRepaint:
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "WM_RequestPaint";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "WM_RequestPaint");
// When GUI posts this event, it is followed by a polishAndSync, so we mustn't
// exit the event loop yet.
pendingUpdate |= RepaintRequest;
@@ -477,13 +477,13 @@ bool QSGRenderThread::event(QEvent *e)
void QSGRenderThread::invalidateOpenGL(QQuickWindow *window, bool inDestructor, QOffscreenSurface *fallback)
{
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "invalidateOpenGL()";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "invalidateOpenGL()");
if (!gl)
return;
if (!window) {
- qCWarning(QSG_LOG_RENDERLOOP()) << "QSGThreadedRenderLoop:QSGRenderThread: no window to make current...";
+ qCWarning(QSG_LOG_RENDERLOOP, "QSGThreadedRenderLoop:QSGRenderThread: no window to make current...");
return;
}
@@ -493,7 +493,7 @@ void QSGRenderThread::invalidateOpenGL(QQuickWindow *window, bool inDestructor,
bool current = gl->makeCurrent(fallback ? static_cast<QSurface *>(fallback) : static_cast<QSurface *>(window));
if (Q_UNLIKELY(!current)) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- cleanup without an OpenGL context";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- cleanup without an OpenGL context");
}
QQuickWindowPrivate *dd = QQuickWindowPrivate::get(window);
@@ -506,7 +506,7 @@ void QSGRenderThread::invalidateOpenGL(QQuickWindow *window, bool inDestructor,
if (wipeSG) {
dd->cleanupNodesOnShutdown();
} else {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- persistent SG, avoiding cleanup";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- persistent SG, avoiding cleanup");
if (current)
gl->doneCurrent();
return;
@@ -514,29 +514,29 @@ void QSGRenderThread::invalidateOpenGL(QQuickWindow *window, bool inDestructor,
sgrc->invalidate();
QCoreApplication::processEvents();
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
+ QCoreApplication::sendPostedEvents(nullptr, QEvent::DeferredDelete);
if (inDestructor)
delete dd->animationController;
if (current)
gl->doneCurrent();
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- invalidating scene graph";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- invalidating scene graph");
if (wipeGL) {
delete gl;
- gl = 0;
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- invalidated OpenGL";
+ gl = nullptr;
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- invalidated OpenGL");
} else {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- persistent GL, avoiding cleanup";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- persistent GL, avoiding cleanup");
}
}
-/*!
+/*
Enters the mutex lock to make sure GUI is blocking and performs
sync, then wakes GUI.
*/
void QSGRenderThread::sync(bool inExpose)
{
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "sync()";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "sync()");
mutex.lock();
Q_ASSERT_X(wm->m_lockedForSync, "QSGRenderThread::sync()", "sync triggered on bad terms as gui is not already locked...");
@@ -554,7 +554,7 @@ void QSGRenderThread::sync(bool inExpose)
}
if (current) {
QQuickWindowPrivate *d = QQuickWindowPrivate::get(window);
- bool hadRenderer = d->renderer != 0;
+ bool hadRenderer = d->renderer != nullptr;
// If the scene graph was touched since the last sync() make sure it sends the
// changed signal.
if (d->renderer)
@@ -562,7 +562,7 @@ void QSGRenderThread::sync(bool inExpose)
d->syncSceneGraph();
sgrc->endSync();
if (!hadRenderer && d->renderer) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- renderer was created";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- renderer was created");
syncResultedInChanges = true;
connect(d->renderer, SIGNAL(sceneGraphChanged()), this, SLOT(sceneGraphChanged()), Qt::DirectConnection);
}
@@ -570,13 +570,13 @@ void QSGRenderThread::sync(bool inExpose)
// Process deferred deletes now, directly after the sync as
// deleteLater on the GUI must now also have resulted in SG changes
// and the delete is a safe operation.
- QCoreApplication::sendPostedEvents(0, QEvent::DeferredDelete);
+ QCoreApplication::sendPostedEvents(nullptr, QEvent::DeferredDelete);
} else {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- window has bad size, sync aborted";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- window has bad size, sync aborted");
}
if (!inExpose) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- sync complete, waking Gui";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- sync complete, waking Gui");
waitCondition.wakeOne();
mutex.unlock();
}
@@ -594,7 +594,7 @@ void QSGRenderThread::syncAndRender()
QElapsedTimer waitTimer;
waitTimer.start();
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "syncAndRender()";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "syncAndRender()");
syncResultedInChanges = false;
QQuickWindowPrivate *d = QQuickWindowPrivate::get(window);
@@ -605,7 +605,7 @@ void QSGRenderThread::syncAndRender()
pendingUpdate = 0;
if (syncRequested) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- updatePending, doing sync";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- updatePending, doing sync");
sync(exposeRequested);
}
#ifndef QSG_NO_RENDER_TIMING
@@ -616,14 +616,14 @@ void QSGRenderThread::syncAndRender()
QQuickProfiler::SceneGraphRenderLoopSync);
if (!syncResultedInChanges && !repaintRequested && sgrc->isValid()) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- no changes, render aborted";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- no changes, render aborted");
int waitTime = vsyncDelta - (int) waitTimer.elapsed();
if (waitTime > 0)
msleep(waitTime);
return;
}
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- rendering started";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- rendering started");
if (animatorDriver->isRunning()) {
@@ -653,10 +653,10 @@ void QSGRenderThread::syncAndRender()
} else {
Q_QUICK_SG_PROFILE_SKIP(QQuickProfiler::SceneGraphRenderLoopFrame,
QQuickProfiler::SceneGraphRenderLoopSync, 1);
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- window not ready, skipping render";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- window not ready, skipping render");
}
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- rendering done";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- rendering done");
// Though it would be more correct to put this block directly after
// fireFrameSwapped in the if (current) branch above, we don't do
@@ -664,7 +664,7 @@ void QSGRenderThread::syncAndRender()
// has started rendering with a bad window, causing makeCurrent to
// fail or if the window has a bad size.
if (exposeRequested) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "- wake Gui after initial expose";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "- wake Gui after initial expose");
waitCondition.wakeOne();
mutex.unlock();
}
@@ -692,31 +692,31 @@ void QSGRenderThread::postEvent(QEvent *e)
void QSGRenderThread::processEvents()
{
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "--- begin processEvents()";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "--- begin processEvents()");
while (eventQueue.hasMoreEvents()) {
QEvent *e = eventQueue.takeEvent(false);
event(e);
delete e;
}
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "--- done processEvents()";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "--- done processEvents()");
}
void QSGRenderThread::processEventsAndWaitForMore()
{
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "--- begin processEventsAndWaitForMore()";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "--- begin processEventsAndWaitForMore()");
stopEventProcessing = false;
while (!stopEventProcessing) {
QEvent *e = eventQueue.takeEvent(true);
event(e);
delete e;
}
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "--- done processEventsAndWaitForMore()";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "--- done processEventsAndWaitForMore()");
}
void QSGRenderThread::run()
{
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "run()";
- animatorDriver = sgrc->sceneGraphContext()->createAnimationDriver(0);
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "run()");
+ animatorDriver = sgrc->sceneGraphContext()->createAnimationDriver(nullptr);
animatorDriver->install();
if (QQmlDebugConnector::service<QQmlProfilerService>())
QQuickProfiler::registerAnimationCallback();
@@ -733,7 +733,7 @@ void QSGRenderThread::run()
QCoreApplication::processEvents();
if (active && (pendingUpdate == 0 || !window)) {
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "done drawing, sleep...";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "done drawing, sleep...");
sleeping = true;
processEventsAndWaitForMore();
sleeping = false;
@@ -742,10 +742,10 @@ void QSGRenderThread::run()
Q_ASSERT_X(!gl, "QSGRenderThread::run()", "The OpenGL context should be cleaned up before exiting the render thread...");
- qCDebug(QSG_LOG_RENDERLOOP) << QSG_RT_PAD << "run() completed";
+ qCDebug(QSG_LOG_RENDERLOOP, QSG_RT_PAD, "run() completed");
delete animatorDriver;
- animatorDriver = 0;
+ animatorDriver = nullptr;
sgrc->moveToThread(wm->thread());
moveToThread(wm->thread());
@@ -809,7 +809,7 @@ bool QSGThreadedRenderLoop::interleaveIncubation() const
void QSGThreadedRenderLoop::animationStarted()
{
- qCDebug(QSG_LOG_RENDERLOOP) << "- animationStarted()";
+ qCDebug(QSG_LOG_RENDERLOOP, "- animationStarted()");
startOrStopAnimationTimer();
for (int i=0; i<m_windows.size(); ++i)
@@ -818,7 +818,7 @@ void QSGThreadedRenderLoop::animationStarted()
void QSGThreadedRenderLoop::animationStopped()
{
- qCDebug(QSG_LOG_RENDERLOOP) << "- animationStopped()";
+ qCDebug(QSG_LOG_RENDERLOOP, "- animationStopped()");
startOrStopAnimationTimer();
}
@@ -826,7 +826,7 @@ void QSGThreadedRenderLoop::animationStopped()
void QSGThreadedRenderLoop::startOrStopAnimationTimer()
{
int exposedWindows = 0;
- const Window *theOne = 0;
+ const Window *theOne = nullptr;
for (int i=0; i<m_windows.size(); ++i) {
const Window &w = m_windows.at(i);
if (w.window->isVisible() && w.window->isExposed()) {
@@ -836,14 +836,14 @@ void QSGThreadedRenderLoop::startOrStopAnimationTimer()
}
if (m_animation_timer != 0 && (exposedWindows == 1 || !m_animation_driver->isRunning())) {
- qCDebug(QSG_LOG_RENDERLOOP) << "*** Stopping animation timer";
+ qCDebug(QSG_LOG_RENDERLOOP, "*** Stopping animation timer");
killTimer(m_animation_timer);
m_animation_timer = 0;
// If animations are running, make sure we keep on animating
if (m_animation_driver->isRunning())
maybePostPolishRequest(const_cast<Window *>(theOne));
} else if (m_animation_timer == 0 && exposedWindows != 1 && m_animation_driver->isRunning()) {
- qCDebug(QSG_LOG_RENDERLOOP) << "*** Starting animation timer";
+ qCDebug(QSG_LOG_RENDERLOOP, "*** Starting animation timer");
m_animation_timer = startTimer(qsgrl_animation_interval());
}
}
@@ -870,7 +870,7 @@ void QSGThreadedRenderLoop::hide(QQuickWindow *window)
}
-/*!
+/*
If the window is first hide it, then perform a complete cleanup
with releaseResources which will take down the GL context and
exit the rendering thread.
@@ -920,7 +920,7 @@ void QSGThreadedRenderLoop::exposureChanged(QQuickWindow *window)
}
}
-/*!
+/*
Will post an event to the render thread that this window should
start to render.
*/
@@ -930,7 +930,7 @@ void QSGThreadedRenderLoop::handleExposure(QQuickWindow *window)
Window *w = windowFor(m_windows, window);
if (!w) {
- qCDebug(QSG_LOG_RENDERLOOP) << "- adding window to list";
+ qCDebug(QSG_LOG_RENDERLOOP, "- adding window to list");
Window win;
win.window = window;
win.actualWindowFormat = window->format();
@@ -962,7 +962,7 @@ void QSGThreadedRenderLoop::handleExposure(QQuickWindow *window)
// Start render thread if it is not running
if (!w->thread->isRunning()) {
- qCDebug(QSG_LOG_RENDERLOOP) << "- starting render thread";
+ qCDebug(QSG_LOG_RENDERLOOP, "- starting render thread");
if (!w->thread->gl) {
w->thread->gl = new QOpenGLContext();
@@ -973,7 +973,7 @@ void QSGThreadedRenderLoop::handleExposure(QQuickWindow *window)
if (!w->thread->gl->create()) {
const bool isEs = w->thread->gl->isOpenGLES();
delete w->thread->gl;
- w->thread->gl = 0;
+ w->thread->gl = nullptr;
handleContextCreationFailure(w->window, isEs);
return;
}
@@ -981,7 +981,7 @@ void QSGThreadedRenderLoop::handleExposure(QQuickWindow *window)
QQuickWindowPrivate::get(w->window)->fireOpenGLContextCreated(w->thread->gl);
w->thread->gl->moveToThread(w->thread);
- qCDebug(QSG_LOG_RENDERLOOP) << "- OpenGL context created";
+ qCDebug(QSG_LOG_RENDERLOOP, "- OpenGL context created");
}
QQuickAnimatorController *controller = QQuickWindowPrivate::get(w->window)->animationController;
@@ -998,16 +998,16 @@ void QSGThreadedRenderLoop::handleExposure(QQuickWindow *window)
qFatal("Render thread failed to start, aborting application.");
} else {
- qCDebug(QSG_LOG_RENDERLOOP) << "- render thread already running";
+ qCDebug(QSG_LOG_RENDERLOOP, "- render thread already running");
}
polishAndSync(w, true);
- qCDebug(QSG_LOG_RENDERLOOP) << "- done with handleExposure()";
+ qCDebug(QSG_LOG_RENDERLOOP, "- done with handleExposure()");
startOrStopAnimationTimer();
}
-/*!
+/*
This function posts an event to the render thread to remove the window
from the list of windowses to render.
@@ -1029,7 +1029,7 @@ void QSGThreadedRenderLoop::handleObscurity(Window *w)
void QSGThreadedRenderLoop::handleUpdateRequest(QQuickWindow *window)
{
- qCDebug(QSG_LOG_RENDERLOOP) << "- polish and sync update request";
+ qCDebug(QSG_LOG_RENDERLOOP, "- polish and sync update request");
Window *w = windowFor(m_windows, window);
if (w)
polishAndSync(w);
@@ -1042,7 +1042,7 @@ void QSGThreadedRenderLoop::maybeUpdate(QQuickWindow *window)
maybeUpdate(w);
}
-/*!
+/*
Called whenever the QML scene has changed. Will post an event to
ourselves that a sync is needed.
*/
@@ -1065,7 +1065,7 @@ void QSGThreadedRenderLoop::maybeUpdate(Window *w)
// Call this function from the Gui thread later as startTimer cannot be
// called from the render thread.
if (current == w->thread) {
- qCDebug(QSG_LOG_RENDERLOOP) << "- on render thread";
+ qCDebug(QSG_LOG_RENDERLOOP, "- on render thread");
w->updateDuringSync = true;
return;
}
@@ -1073,7 +1073,7 @@ void QSGThreadedRenderLoop::maybeUpdate(Window *w)
maybePostPolishRequest(w);
}
-/*!
+/*
Called when the QQuickWindow should be explicitly repainted. This function
can also be called on the render thread when the GUI thread is blocked to
keep render thread animations alive.
@@ -1105,7 +1105,7 @@ void QSGThreadedRenderLoop::releaseResources(QQuickWindow *window)
releaseResources(w, false);
}
-/*!
+/*
* Release resources will post an event to the render thread to
* free up the SG and GL resources and exists the render thread.
*/
@@ -1123,15 +1123,15 @@ void QSGThreadedRenderLoop::releaseResources(Window *w, bool inDestructor)
// and the OpenGL resources.
// QOffscreenSurface must be created on the GUI thread, so we
// create it here and pass it on to QSGRenderThread::invalidateGL()
- QOffscreenSurface *fallback = 0;
+ QOffscreenSurface *fallback = nullptr;
if (!window->handle()) {
- qCDebug(QSG_LOG_RENDERLOOP) << "- using fallback surface";
+ qCDebug(QSG_LOG_RENDERLOOP, "- using fallback surface");
fallback = new QOffscreenSurface();
fallback->setFormat(w->actualWindowFormat);
fallback->create();
}
- qCDebug(QSG_LOG_RENDERLOOP) << "- posting release request to render thread";
+ qCDebug(QSG_LOG_RENDERLOOP, "- posting release request to render thread");
w->thread->postEvent(new WMTryReleaseEvent(window, inDestructor, fallback));
w->thread->waitCondition.wait(&w->thread->mutex);
delete fallback;
@@ -1161,7 +1161,7 @@ void QSGThreadedRenderLoop::polishAndSync(Window *w, bool inExpose)
QQuickWindow *window = w->window;
if (!w->thread || !w->thread->window) {
- qCDebug(QSG_LOG_RENDERLOOP) << "- not exposed, abort";
+ qCDebug(QSG_LOG_RENDERLOOP, "- not exposed, abort");
return;
}
@@ -1170,7 +1170,7 @@ void QSGThreadedRenderLoop::polishAndSync(Window *w, bool inExpose)
// The delivery of the event might have caused the window to stop rendering
w = windowFor(m_windows, window);
if (!w || !w->thread || !w->thread->window) {
- qCDebug(QSG_LOG_RENDERLOOP) << "- removed after event flushing, abort";
+ qCDebug(QSG_LOG_RENDERLOOP, "- removed after event flushing, abort");
return;
}
@@ -1196,13 +1196,13 @@ void QSGThreadedRenderLoop::polishAndSync(Window *w, bool inExpose)
emit window->afterAnimating();
- qCDebug(QSG_LOG_RENDERLOOP) << "- lock for sync";
+ qCDebug(QSG_LOG_RENDERLOOP, "- lock for sync");
w->thread->mutex.lock();
m_lockedForSync = true;
w->thread->postEvent(new WMSyncEvent(window, inExpose, w->forceRenderPass));
w->forceRenderPass = false;
- qCDebug(QSG_LOG_RENDERLOOP) << "- wait for sync";
+ qCDebug(QSG_LOG_RENDERLOOP, "- wait for sync");
if (profileFrames)
waitTime = timer.nsecsElapsed();
Q_QUICK_SG_PROFILE_RECORD(QQuickProfiler::SceneGraphPolishAndSync,
@@ -1210,7 +1210,7 @@ void QSGThreadedRenderLoop::polishAndSync(Window *w, bool inExpose)
w->thread->waitCondition.wait(&w->thread->mutex);
m_lockedForSync = false;
w->thread->mutex.unlock();
- qCDebug(QSG_LOG_RENDERLOOP) << "- unlock after sync";
+ qCDebug(QSG_LOG_RENDERLOOP, "- unlock after sync");
if (profileFrames)
syncTime = timer.nsecsElapsed();
@@ -1218,9 +1218,9 @@ void QSGThreadedRenderLoop::polishAndSync(Window *w, bool inExpose)
QQuickProfiler::SceneGraphPolishAndSyncSync);
if (m_animation_timer == 0 && m_animation_driver->isRunning()) {
- qCDebug(QSG_LOG_RENDERLOOP) << "- advancing animations";
+ qCDebug(QSG_LOG_RENDERLOOP, "- advancing animations");
m_animation_driver->advance();
- qCDebug(QSG_LOG_RENDERLOOP) << "- animations done..";
+ qCDebug(QSG_LOG_RENDERLOOP, "- animations done..");
// We need to trigger another sync to keep animations running...
maybePostPolishRequest(w);
emit timeToIncubate();
@@ -1247,7 +1247,7 @@ bool QSGThreadedRenderLoop::event(QEvent *e)
case QEvent::Timer: {
QTimerEvent *te = static_cast<QTimerEvent *>(e);
if (te->timerId() == m_animation_timer) {
- qCDebug(QSG_LOG_RENDERLOOP) << "- ticking non-visual timer";
+ qCDebug(QSG_LOG_RENDERLOOP, "- ticking non-visual timer");
m_animation_driver->advance();
emit timeToIncubate();
return true;
@@ -1286,25 +1286,25 @@ QImage QSGThreadedRenderLoop::grab(QQuickWindow *window)
if (!window->handle())
window->create();
- qCDebug(QSG_LOG_RENDERLOOP) << "- polishing items";
+ qCDebug(QSG_LOG_RENDERLOOP, "- polishing items");
QQuickWindowPrivate *d = QQuickWindowPrivate::get(window);
d->polishItems();
QImage result;
w->thread->mutex.lock();
m_lockedForSync = true;
- qCDebug(QSG_LOG_RENDERLOOP) << "- posting grab event";
+ qCDebug(QSG_LOG_RENDERLOOP, "- posting grab event");
w->thread->postEvent(new WMGrabEvent(window, &result));
w->thread->waitCondition.wait(&w->thread->mutex);
m_lockedForSync = false;
w->thread->mutex.unlock();
- qCDebug(QSG_LOG_RENDERLOOP) << "- grab complete";
+ qCDebug(QSG_LOG_RENDERLOOP, "- grab complete");
return result;
}
-/*!
+/*
* Posts a new job event to the render thread.
* Returns true if posting succeeded.
*/
diff --git a/src/quick/scenegraph/qsgwindowsrenderloop.cpp b/src/quick/scenegraph/qsgwindowsrenderloop.cpp
index e33f31f2ac..3b2737b8e1 100644
--- a/src/quick/scenegraph/qsgwindowsrenderloop.cpp
+++ b/src/quick/scenegraph/qsgwindowsrenderloop.cpp
@@ -64,7 +64,7 @@ QT_BEGIN_NAMESPACE
extern Q_GUI_EXPORT QImage qt_gl_read_framebuffer(const QSize &size, bool alpha_format, bool include_alpha);
-#define RLDEBUG(x) qCDebug(QSG_LOG_RENDERLOOP) << x;
+#define RLDEBUG(x) qCDebug(QSG_LOG_RENDERLOOP, x)
static QElapsedTimer qsg_render_timer;
#define QSG_LOG_TIME_SAMPLE(sampleName) \
@@ -78,7 +78,7 @@ static QElapsedTimer qsg_render_timer;
QSGWindowsRenderLoop::QSGWindowsRenderLoop()
- : m_gl(0)
+ : m_gl(nullptr)
, m_sg(QSGContext::createDefaultContext())
, m_updateTimer(0)
, m_animationTimer(0)
@@ -117,7 +117,7 @@ QSGWindowsRenderLoop::WindowData *QSGWindowsRenderLoop::windowData(QQuickWindow
if (wd.window == window)
return &wd;
}
- return 0;
+ return nullptr;
}
void QSGWindowsRenderLoop::maybePostUpdateTimer()
@@ -158,7 +158,7 @@ void QSGWindowsRenderLoop::stopped()
void QSGWindowsRenderLoop::show(QQuickWindow *window)
{
RLDEBUG("show");
- if (windowData(window) != 0)
+ if (windowData(window) != nullptr)
return;
// This happens before the platform window is shown, but after
@@ -178,7 +178,7 @@ void QSGWindowsRenderLoop::show(QQuickWindow *window)
if (!created) {
const bool isEs = m_gl->isOpenGLES();
delete m_gl;
- m_gl = 0;
+ m_gl = nullptr;
handleContextCreationFailure(window, isEs);
return;
}
@@ -243,7 +243,7 @@ void QSGWindowsRenderLoop::windowDestroyed(QQuickWindow *window)
current = m_gl->makeCurrent(surface);
}
if (Q_UNLIKELY(!current))
- qCDebug(QSG_LOG_RENDERLOOP) << "cleanup without an OpenGL context";
+ RLDEBUG("cleanup without an OpenGL context");
#if QT_CONFIG(quick_shadereffect) && QT_CONFIG(opengl)
QQuickOpenGLShaderEffectMaterial::cleanupMaterialCache();
@@ -253,7 +253,7 @@ void QSGWindowsRenderLoop::windowDestroyed(QQuickWindow *window)
if (m_windows.size() == 0) {
d->context->invalidate();
delete m_gl;
- m_gl = 0;
+ m_gl = nullptr;
} else if (m_gl && current) {
m_gl->doneCurrent();
}
@@ -272,7 +272,7 @@ bool QSGWindowsRenderLoop::anyoneShowing() const
void QSGWindowsRenderLoop::exposureChanged(QQuickWindow *window)
{
- if (windowData(window) == 0)
+ if (windowData(window) == nullptr)
return;
if (window->isExposed() && window->isVisible()) {
diff --git a/src/quick/scenegraph/scenegraph.pri b/src/quick/scenegraph/scenegraph.pri
index b5c72f521c..4fa3e7b6bf 100644
--- a/src/quick/scenegraph/scenegraph.pri
+++ b/src/quick/scenegraph/scenegraph.pri
@@ -1,4 +1,4 @@
-DEFINES += QSG_SEPARATE_INDEX_BUFFER
+# DEFINES += QSG_SEPARATE_INDEX_BUFFER
# DEFINES += QSG_DISTANCEFIELD_CACHE_DEBUG
# Core API
@@ -230,8 +230,15 @@ SOURCES += \
qtConfig(opengl(es1|es2)?) {
HEADERS += \
- $$PWD/compressedtexture/qsgpkmhandler_p.h
+ $$PWD/compressedtexture/qsgcompressedatlastexture_p.h \
+ $$PWD/compressedtexture/qsgcompressedtexture_p.h \
+ $$PWD/compressedtexture/qsgtexturefilehandler_p.h \
+ $$PWD/compressedtexture/qsgpkmhandler_p.h \
+ $$PWD/compressedtexture/qsgktxhandler_p.h
SOURCES += \
- $$PWD/compressedtexture/qsgpkmhandler.cpp
+ $$PWD/compressedtexture/qsgcompressedatlastexture.cpp \
+ $$PWD/compressedtexture/qsgcompressedtexture.cpp \
+ $$PWD/compressedtexture/qsgpkmhandler.cpp \
+ $$PWD/compressedtexture/qsgktxhandler.cpp
}
diff --git a/src/quick/scenegraph/util/qsgareaallocator.cpp b/src/quick/scenegraph/util/qsgareaallocator.cpp
index 67a9fa285a..cd270a1d63 100644
--- a/src/quick/scenegraph/util/qsgareaallocator.cpp
+++ b/src/quick/scenegraph/util/qsgareaallocator.cpp
@@ -72,8 +72,8 @@ struct QSGAreaAllocatorNode
QSGAreaAllocatorNode::QSGAreaAllocatorNode(QSGAreaAllocatorNode *parent)
: parent(parent)
- , left(0)
- , right(0)
+ , left(nullptr)
+ , right(nullptr)
, isOccupied(false)
{
}
@@ -86,14 +86,14 @@ QSGAreaAllocatorNode::~QSGAreaAllocatorNode()
bool QSGAreaAllocatorNode::isLeaf()
{
- Q_ASSERT((left != 0) == (right != 0));
+ Q_ASSERT((left != nullptr) == (right != nullptr));
return !left;
}
QSGAreaAllocator::QSGAreaAllocator(const QSize &size) : m_size(size)
{
- m_root = new QSGAreaAllocatorNode(0);
+ m_root = new QSGAreaAllocatorNode(nullptr);
}
QSGAreaAllocator::~QSGAreaAllocator()
@@ -179,13 +179,13 @@ bool QSGAreaAllocator::deallocateInNode(const QPoint &pos, QSGAreaAllocatorNode
void QSGAreaAllocator::mergeNodeWithNeighbors(QSGAreaAllocatorNode *node)
{
bool done = false;
- QSGAreaAllocatorNode *parent = 0;
- QSGAreaAllocatorNode *current = 0;
+ QSGAreaAllocatorNode *parent = nullptr;
+ QSGAreaAllocatorNode *current = nullptr;
QSGAreaAllocatorNode *sibling;
while (!done) {
Q_ASSERT(node->isLeaf());
Q_ASSERT(!node->isOccupied);
- if (node->parent == 0)
+ if (node->parent == nullptr)
return; // No neighbours.
SplitType splitType = SplitType(node->parent->splitType);
@@ -238,7 +238,7 @@ void QSGAreaAllocator::mergeNodeWithNeighbors(QSGAreaAllocatorNode *node)
}
sibling->parent = parent->parent;
*nodeRef = sibling;
- parent->left = parent->right = 0;
+ parent->left = parent->right = nullptr;
delete parent;
delete neighbor;
done = false;
@@ -276,7 +276,7 @@ void QSGAreaAllocator::mergeNodeWithNeighbors(QSGAreaAllocatorNode *node)
}
sibling->parent = parent->parent;
*nodeRef = sibling;
- parent->left = parent->right = 0;
+ parent->left = parent->right = nullptr;
delete parent;
delete neighbor;
done = false;
diff --git a/src/quick/scenegraph/util/qsgareaallocator_p.h b/src/quick/scenegraph/util/qsgareaallocator_p.h
index aa40ff0a6e..8bc05a5a5b 100644
--- a/src/quick/scenegraph/util/qsgareaallocator_p.h
+++ b/src/quick/scenegraph/util/qsgareaallocator_p.h
@@ -67,7 +67,7 @@ public:
QRect allocate(const QSize &size);
bool deallocate(const QRect &rect);
- bool isEmpty() const { return m_root == 0; }
+ bool isEmpty() const { return m_root == nullptr; }
QSize size() const { return m_size; }
private:
bool allocateInNode(const QSize &size, QPoint &result, const QRect &currentRect, QSGAreaAllocatorNode *node);
diff --git a/src/quick/scenegraph/util/qsgatlastexture.cpp b/src/quick/scenegraph/util/qsgatlastexture.cpp
index 22f0b13f46..7608a81ddc 100644
--- a/src/quick/scenegraph/util/qsgatlastexture.cpp
+++ b/src/quick/scenegraph/util/qsgatlastexture.cpp
@@ -44,6 +44,7 @@
#include <QtCore/QtMath>
#include <QtGui/QOpenGLContext>
+#include <QtGui/QOpenGLTexture>
#include <QtGui/QOpenGLFunctions>
#include <QtGui/QGuiApplication>
#include <QtGui/QScreen>
@@ -51,7 +52,10 @@
#include <QtGui/QWindow>
#include <QtGui/qpa/qplatformnativeinterface.h>
+#include <private/qqmlglobal_p.h>
#include <private/qsgtexture_p.h>
+#include <private/qsgcompressedtexture_p.h>
+#include <private/qsgcompressedatlastexture_p.h>
#include <private/qquickprofiler_p.h>
@@ -65,11 +69,13 @@ int qt_sg_envInt(const char *name, int defaultValue);
static QElapsedTimer qsg_renderer_timer;
+DEFINE_BOOL_CONFIG_OPTION(qsgEnableCompressedAtlas, QSG_ENABLE_COMPRESSED_ATLAS)
+
namespace QSGAtlasTexture
{
Manager::Manager()
- : m_atlas(0)
+ : m_atlas(nullptr)
{
QOpenGLContext *gl = QOpenGLContext::currentContext();
Q_ASSERT(gl);
@@ -99,7 +105,8 @@ Manager::Manager()
Manager::~Manager()
{
- Q_ASSERT(m_atlas == 0);
+ Q_ASSERT(m_atlas == nullptr);
+ Q_ASSERT(m_atlases.isEmpty());
}
void Manager::invalidate()
@@ -107,13 +114,21 @@ void Manager::invalidate()
if (m_atlas) {
m_atlas->invalidate();
m_atlas->deleteLater();
- m_atlas = 0;
+ m_atlas = nullptr;
+ }
+
+ QHash<unsigned int, QSGCompressedAtlasTexture::Atlas*>::iterator i = m_atlases.begin();
+ while (i != m_atlases.end()) {
+ i.value()->invalidate();
+ i.value()->deleteLater();
+ ++i;
}
+ m_atlases.clear();
}
QSGTexture *Manager::create(const QImage &image, bool hasAlphaChannel)
{
- Texture *t = 0;
+ Texture *t = nullptr;
if (image.width() < m_atlas_size_limit && image.height() < m_atlas_size_limit) {
if (!m_atlas)
m_atlas = new Atlas(m_atlas_size);
@@ -125,13 +140,147 @@ QSGTexture *Manager::create(const QImage &image, bool hasAlphaChannel)
return t;
}
-Atlas::Atlas(const QSize &size)
+QSGTexture *Manager::create(const QSGCompressedTextureFactory *factory)
+{
+ QSGTexture *t = nullptr;
+ if (!qsgEnableCompressedAtlas() || !factory->m_textureData || !factory->m_textureData->isValid())
+ return t;
+
+ // TODO: further abstract the atlas and remove this restriction
+ unsigned int format = factory->m_textureData->format;
+ switch (format) {
+ case QOpenGLTexture::RGB8_ETC1:
+ case QOpenGLTexture::RGB8_ETC2:
+ case QOpenGLTexture::RGBA8_ETC2_EAC:
+ case QOpenGLTexture::RGB8_PunchThrough_Alpha1_ETC2:
+ break;
+ default:
+ return t;
+ }
+
+ QSize size = factory->m_textureData->size;
+ if (size.width() < m_atlas_size_limit && size.height() < m_atlas_size_limit) {
+ QHash<unsigned int, QSGCompressedAtlasTexture::Atlas*>::iterator i = m_atlases.find(format);
+ if (i == m_atlases.end())
+ i = m_atlases.insert(format, new QSGCompressedAtlasTexture::Atlas(m_atlas_size, format));
+ // must be multiple of 4
+ QSize paddedSize(((size.width() + 3) / 4) * 4, ((size.height() + 3) / 4) * 4);
+ QByteArray data = factory->m_textureData->data;
+ t = i.value()->create(data, factory->m_textureData->sizeInBytes(), factory->m_textureData->dataOffset, size, paddedSize);
+ }
+ return t;
+}
+
+AtlasBase::AtlasBase(const QSize &size)
: m_allocator(size)
, m_texture_id(0)
, m_size(size)
- , m_atlas_transient_image_threshold(0)
, m_allocated(false)
{
+}
+
+AtlasBase::~AtlasBase()
+{
+ Q_ASSERT(!m_texture_id);
+}
+
+void AtlasBase::invalidate()
+{
+ if (m_texture_id && QOpenGLContext::currentContext())
+ QOpenGLContext::currentContext()->functions()->glDeleteTextures(1, &m_texture_id);
+ m_texture_id = 0;
+}
+
+int AtlasBase::textureId() const
+{
+ if (!m_texture_id) {
+ Q_ASSERT(QOpenGLContext::currentContext());
+ QOpenGLContext::currentContext()->functions()->glGenTextures(1, &const_cast<AtlasBase *>(this)->m_texture_id);
+ }
+
+ return m_texture_id;
+}
+
+void AtlasBase::bind(QSGTexture::Filtering filtering)
+{
+ QOpenGLFunctions *funcs = QOpenGLContext::currentContext()->functions();
+ if (!m_allocated) {
+ m_allocated = true;
+
+ while (funcs->glGetError() != GL_NO_ERROR) ;
+
+ funcs->glGenTextures(1, &m_texture_id);
+ funcs->glBindTexture(GL_TEXTURE_2D, m_texture_id);
+ funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
+ funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
+ funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+ funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+#if !defined(QT_OPENGL_ES_2)
+ if (!QOpenGLContext::currentContext()->isOpenGLES())
+ funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0);
+#endif
+ generateTexture();
+
+ GLenum errorCode = funcs->glGetError();
+ if (errorCode == GL_OUT_OF_MEMORY) {
+ qDebug("QSGTextureAtlas: texture atlas allocation failed, out of memory");
+ funcs->glDeleteTextures(1, &m_texture_id);
+ m_texture_id = 0;
+ } else if (errorCode != GL_NO_ERROR) {
+ qDebug("QSGTextureAtlas: texture atlas allocation failed, code=%x", errorCode);
+ funcs->glDeleteTextures(1, &m_texture_id);
+ m_texture_id = 0;
+ }
+ } else {
+ funcs->glBindTexture(GL_TEXTURE_2D, m_texture_id);
+ }
+
+ if (m_texture_id == 0)
+ return;
+
+ // Upload all pending images..
+ for (int i=0; i<m_pending_uploads.size(); ++i) {
+
+ bool profileFrames = QSG_LOG_TIME_TEXTURE().isDebugEnabled();
+ if (profileFrames)
+ qsg_renderer_timer.start();
+
+ Q_QUICK_SG_PROFILE_START(QQuickProfiler::SceneGraphTexturePrepare);
+
+ // Skip bind, convert, swizzle; they're irrelevant
+ Q_QUICK_SG_PROFILE_SKIP(QQuickProfiler::SceneGraphTexturePrepare,
+ QQuickProfiler::SceneGraphTexturePrepareStart, 3);
+
+ uploadPendingTexture(i);
+
+ Q_QUICK_SG_PROFILE_RECORD(QQuickProfiler::SceneGraphTexturePrepare,
+ QQuickProfiler::SceneGraphTexturePrepareUpload);
+
+ // Skip mipmap; unused
+ Q_QUICK_SG_PROFILE_SKIP(QQuickProfiler::SceneGraphTexturePrepare,
+ QQuickProfiler::SceneGraphTexturePrepareUpload, 1);
+ Q_QUICK_SG_PROFILE_REPORT(QQuickProfiler::SceneGraphTexturePrepare,
+ QQuickProfiler::SceneGraphTexturePrepareMipmap);
+ }
+
+ GLenum f = filtering == QSGTexture::Nearest ? GL_NEAREST : GL_LINEAR;
+ funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, f);
+ funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, f);
+
+ m_pending_uploads.clear();
+}
+
+void AtlasBase::remove(TextureBase *t)
+{
+ QRect atlasRect = t->atlasSubRect();
+ m_allocator.deallocate(atlasRect);
+ m_pending_uploads.removeOne(t);
+}
+
+Atlas::Atlas(const QSize &size)
+ : AtlasBase(size)
+ , m_atlas_transient_image_threshold(0)
+{
m_internalFormat = GL_RGBA;
m_externalFormat = GL_BGRA;
@@ -188,14 +337,6 @@ Atlas::Atlas(const QSize &size)
Atlas::~Atlas()
{
- Q_ASSERT(!m_texture_id);
-}
-
-void Atlas::invalidate()
-{
- if (m_texture_id && QOpenGLContext::currentContext())
- QOpenGLContext::currentContext()->functions()->glDeleteTextures(1, &m_texture_id);
- m_texture_id = 0;
}
Texture *Atlas::create(const QImage &image)
@@ -207,18 +348,7 @@ Texture *Atlas::create(const QImage &image)
m_pending_uploads << t;
return t;
}
- return 0;
-}
-
-
-int Atlas::textureId() const
-{
- if (!m_texture_id) {
- Q_ASSERT(QOpenGLContext::currentContext());
- QOpenGLContext::currentContext()->functions()->glGenTextures(1, &const_cast<Atlas *>(this)->m_texture_id);
- }
-
- return m_texture_id;
+ return nullptr;
}
static void swizzleBGRAToRGBA(QImage *image)
@@ -334,122 +464,70 @@ void Atlas::uploadBgra(Texture *texture)
}
}
-void Atlas::bind(QSGTexture::Filtering filtering)
+void Atlas::generateTexture()
{
QOpenGLFunctions *funcs = QOpenGLContext::currentContext()->functions();
- if (!m_allocated) {
- m_allocated = true;
-
- while (funcs->glGetError() != GL_NO_ERROR) ;
-
- funcs->glGenTextures(1, &m_texture_id);
- funcs->glBindTexture(GL_TEXTURE_2D, m_texture_id);
- funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
- funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
- funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
- funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
-#if !defined(QT_OPENGL_ES_2)
- if (!QOpenGLContext::currentContext()->isOpenGLES())
- funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0);
-#endif
- funcs->glTexImage2D(GL_TEXTURE_2D, 0, m_internalFormat, m_size.width(), m_size.height(), 0, m_externalFormat, GL_UNSIGNED_BYTE, 0);
+ funcs->glTexImage2D(GL_TEXTURE_2D, 0, m_internalFormat, m_size.width(), m_size.height(), 0, m_externalFormat, GL_UNSIGNED_BYTE, nullptr);
#if 0
- QImage pink(m_size.width(), m_size.height(), QImage::Format_ARGB32_Premultiplied);
- pink.fill(0);
- QPainter p(&pink);
- QLinearGradient redGrad(0, 0, m_size.width(), 0);
- redGrad.setColorAt(0, Qt::black);
- redGrad.setColorAt(1, Qt::red);
- p.fillRect(0, 0, m_size.width(), m_size.height(), redGrad);
- p.setCompositionMode(QPainter::CompositionMode_Plus);
- QLinearGradient blueGrad(0, 0, 0, m_size.height());
- blueGrad.setColorAt(0, Qt::black);
- blueGrad.setColorAt(1, Qt::blue);
- p.fillRect(0, 0, m_size.width(), m_size.height(), blueGrad);
- p.end();
-
- funcs->glTexImage2D(GL_TEXTURE_2D, 0, m_internalFormat, m_size.width(), m_size.height(), 0, m_externalFormat, GL_UNSIGNED_BYTE, pink.constBits());
+ QImage pink(m_size.width(), m_size.height(), QImage::Format_ARGB32_Premultiplied);
+ pink.fill(0);
+ QPainter p(&pink);
+ QLinearGradient redGrad(0, 0, m_size.width(), 0);
+ redGrad.setColorAt(0, Qt::black);
+ redGrad.setColorAt(1, Qt::red);
+ p.fillRect(0, 0, m_size.width(), m_size.height(), redGrad);
+ p.setCompositionMode(QPainter::CompositionMode_Plus);
+ QLinearGradient blueGrad(0, 0, 0, m_size.height());
+ blueGrad.setColorAt(0, Qt::black);
+ blueGrad.setColorAt(1, Qt::blue);
+ p.fillRect(0, 0, m_size.width(), m_size.height(), blueGrad);
+ p.end();
+
+ funcs->glTexImage2D(GL_TEXTURE_2D, 0, m_internalFormat, m_size.width(), m_size.height(), 0, m_externalFormat, GL_UNSIGNED_BYTE, pink.constBits());
#endif
+}
- GLenum errorCode = funcs->glGetError();
- if (errorCode == GL_OUT_OF_MEMORY) {
- qDebug("QSGTextureAtlas: texture atlas allocation failed, out of memory");
- funcs->glDeleteTextures(1, &m_texture_id);
- m_texture_id = 0;
- } else if (errorCode != GL_NO_ERROR) {
- qDebug("QSGTextureAtlas: texture atlas allocation failed, code=%x", errorCode);
- funcs->glDeleteTextures(1, &m_texture_id);
- m_texture_id = 0;
- }
+void Atlas::uploadPendingTexture(int i)
+{
+ Texture *t = static_cast<Texture*>(m_pending_uploads.at(i));
+ if (m_externalFormat == GL_BGRA &&
+ !m_use_bgra_fallback) {
+ uploadBgra(t);
} else {
- funcs->glBindTexture(GL_TEXTURE_2D, m_texture_id);
+ upload(t);
}
-
- if (m_texture_id == 0)
- return;
-
- // Upload all pending images..
- for (int i=0; i<m_pending_uploads.size(); ++i) {
-
- bool profileFrames = QSG_LOG_TIME_TEXTURE().isDebugEnabled();
- if (profileFrames)
- qsg_renderer_timer.start();
-
- Q_QUICK_SG_PROFILE_START(QQuickProfiler::SceneGraphTexturePrepare);
-
- // Skip bind, convert, swizzle; they're irrelevant
- Q_QUICK_SG_PROFILE_SKIP(QQuickProfiler::SceneGraphTexturePrepare,
- QQuickProfiler::SceneGraphTexturePrepareStart, 3);
-
- Texture *t = m_pending_uploads.at(i);
- if (m_externalFormat == GL_BGRA &&
- !m_use_bgra_fallback) {
- uploadBgra(t);
- } else {
- upload(t);
- }
- const QSize textureSize = t->textureSize();
- if (textureSize.width() > m_atlas_transient_image_threshold ||
- textureSize.height() > m_atlas_transient_image_threshold)
- t->releaseImage();
-
- qCDebug(QSG_LOG_TIME_TEXTURE).nospace() << "atlastexture uploaded in: " << qsg_renderer_timer.elapsed()
- << "ms (" << t->textureSize().width() << "x"
- << t->textureSize().height() << ")";
-
- Q_QUICK_SG_PROFILE_RECORD(QQuickProfiler::SceneGraphTexturePrepare,
- QQuickProfiler::SceneGraphTexturePrepareUpload);
-
- // Skip mipmap; unused
- Q_QUICK_SG_PROFILE_SKIP(QQuickProfiler::SceneGraphTexturePrepare,
- QQuickProfiler::SceneGraphTexturePrepareUpload, 1);
- Q_QUICK_SG_PROFILE_REPORT(QQuickProfiler::SceneGraphTexturePrepare,
- QQuickProfiler::SceneGraphTexturePrepareMipmap);
- }
-
- GLenum f = filtering == QSGTexture::Nearest ? GL_NEAREST : GL_LINEAR;
- funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, f);
- funcs->glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, f);
-
- m_pending_uploads.clear();
+ const QSize textureSize = t->textureSize();
+ if (textureSize.width() > m_atlas_transient_image_threshold ||
+ textureSize.height() > m_atlas_transient_image_threshold)
+ t->releaseImage();
+
+ qCDebug(QSG_LOG_TIME_TEXTURE, "atlastexture uploaded in: %lldms (%dx%d)",
+ qsg_renderer_timer.elapsed(),
+ t->textureSize().width(),
+ t->textureSize().height());
}
-void Atlas::remove(Texture *t)
+TextureBase::TextureBase(AtlasBase *atlas, const QRect &textureRect)
+ : m_allocated_rect(textureRect)
+ , m_atlas(atlas)
{
- QRect atlasRect = t->atlasSubRect();
- m_allocator.deallocate(atlasRect);
- m_pending_uploads.removeOne(t);
}
+TextureBase::~TextureBase()
+{
+ m_atlas->remove(this);
+}
+void TextureBase::bind()
+{
+ m_atlas->bind(filtering());
+}
Texture::Texture(Atlas *atlas, const QRect &textureRect, const QImage &image)
- : QSGTexture()
- , m_allocated_rect(textureRect)
+ : TextureBase(atlas, textureRect)
, m_image(image)
- , m_atlas(atlas)
- , m_nonatlas_texture(0)
+ , m_nonatlas_texture(nullptr)
, m_has_alpha(image.hasAlphaChannel())
{
float w = atlas->size().width();
@@ -463,16 +541,10 @@ Texture::Texture(Atlas *atlas, const QRect &textureRect, const QImage &image)
Texture::~Texture()
{
- m_atlas->remove(this);
if (m_nonatlas_texture)
delete m_nonatlas_texture;
}
-void Texture::bind()
-{
- m_atlas->bind(filtering());
-}
-
QSGTexture *Texture::removedFromAtlas() const
{
if (m_nonatlas_texture) {
@@ -508,7 +580,7 @@ QSGTexture *Texture::removedFromAtlas() const
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);
+ f->glCopyTexImage2D(GL_TEXTURE_2D, 0, static_cast<Atlas*>(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);
diff --git a/src/quick/scenegraph/util/qsgatlastexture_p.h b/src/quick/scenegraph/util/qsgatlastexture_p.h
index 3dee539547..14dc8f7958 100644
--- a/src/quick/scenegraph/util/qsgatlastexture_p.h
+++ b/src/quick/scenegraph/util/qsgatlastexture_p.h
@@ -61,10 +61,16 @@
QT_BEGIN_NAMESPACE
+namespace QSGCompressedAtlasTexture {
+ class Atlas;
+}
+class QSGCompressedTextureFactory;
+
namespace QSGAtlasTexture
{
class Texture;
+class TextureBase;
class Atlas;
class Manager : public QObject
@@ -76,93 +82,121 @@ public:
~Manager();
QSGTexture *create(const QImage &image, bool hasAlphaChannel);
+ QSGTexture *create(const QSGCompressedTextureFactory *factory);
void invalidate();
private:
Atlas *m_atlas;
+ // set of atlases for different compressed formats
+ QHash<unsigned int, QSGCompressedAtlasTexture::Atlas*> m_atlases;
QSize m_atlas_size;
int m_atlas_size_limit;
};
-class Atlas : public QObject
+class AtlasBase : public QObject
{
+ Q_OBJECT
public:
- Atlas(const QSize &size);
- ~Atlas();
+ AtlasBase(const QSize &size);
+ ~AtlasBase();
void invalidate();
int textureId() const;
void bind(QSGTexture::Filtering filtering);
+ void remove(TextureBase *t);
+
+ QSize size() const { return m_size; }
+
+protected:
+ virtual void generateTexture() = 0;
+ virtual void uploadPendingTexture(int i) = 0;
+
+protected:
+ QSGAreaAllocator m_allocator;
+ unsigned int m_texture_id;
+ QSize m_size;
+ QList<TextureBase *> m_pending_uploads;
+
+private:
+ bool m_allocated;
+};
+
+class Atlas : public AtlasBase
+{
+public:
+ Atlas(const QSize &size);
+ ~Atlas();
+
+ void generateTexture() override;
+ void uploadPendingTexture(int i) override;
+
void upload(Texture *texture);
void uploadBgra(Texture *texture);
Texture *create(const QImage &image);
- void remove(Texture *t);
-
- QSize size() const { return m_size; }
uint internalFormat() const { return m_internalFormat; }
uint externalFormat() const { return m_externalFormat; }
private:
- QSGAreaAllocator m_allocator;
- unsigned int m_texture_id;
- QSize m_size;
- QList<Texture *> m_pending_uploads;
-
uint m_internalFormat;
uint m_externalFormat;
int m_atlas_transient_image_threshold;
- uint m_allocated : 1;
uint m_use_bgra_fallback: 1;
-
uint m_debug_overlay : 1;
};
-class Texture : public QSGTexture
+class TextureBase : public QSGTexture
+{
+ Q_OBJECT
+public:
+ TextureBase(AtlasBase *atlas, const QRect &textureRect);
+ ~TextureBase();
+
+ int textureId() const override { return m_atlas->textureId(); }
+ bool isAtlasTexture() const override { return true; }
+
+ QRect atlasSubRect() const { return m_allocated_rect; }
+
+ void bind() override;
+
+protected:
+ QRect m_allocated_rect;
+ AtlasBase *m_atlas;
+};
+
+class Texture : public TextureBase
{
Q_OBJECT
public:
Texture(Atlas *atlas, const QRect &textureRect, const QImage &image);
~Texture();
- int textureId() const override { return m_atlas->textureId(); }
QSize textureSize() const override { return atlasSubRectWithoutPadding().size(); }
void setHasAlphaChannel(bool alpha) { m_has_alpha = alpha; }
bool hasAlphaChannel() const override { return m_has_alpha; }
bool hasMipmaps() const override { return false; }
- bool isAtlasTexture() const override { return true; }
QRectF normalizedTextureSubRect() const override { return m_texture_coords_rect; }
QRect atlasSubRect() const { return m_allocated_rect; }
QRect atlasSubRectWithoutPadding() const { return m_allocated_rect.adjusted(1, 1, -1, -1); }
- bool isTexture() const { return true; }
-
QSGTexture *removedFromAtlas() const override;
void releaseImage() { m_image = QImage(); }
const QImage &image() const { return m_image; }
- void bind() override;
-
private:
- QRect m_allocated_rect;
QRectF m_texture_coords_rect;
-
QImage m_image;
-
- Atlas *m_atlas;
-
mutable QSGPlainTexture *m_nonatlas_texture;
-
- uint m_has_alpha : 1;
+ bool m_has_alpha;
};
}
diff --git a/src/quick/scenegraph/util/qsgdefaultpainternode.cpp b/src/quick/scenegraph/util/qsgdefaultpainternode.cpp
index 9ffd1b4b08..981ea089be 100644
--- a/src/quick/scenegraph/util/qsgdefaultpainternode.cpp
+++ b/src/quick/scenegraph/util/qsgdefaultpainternode.cpp
@@ -78,11 +78,11 @@ QSGDefaultPainterNode::QSGDefaultPainterNode(QQuickPaintedItem *item)
, m_preferredRenderTarget(QQuickPaintedItem::Image)
, m_actualRenderTarget(QQuickPaintedItem::Image)
, m_item(item)
- , m_fbo(0)
- , m_multisampledFbo(0)
+ , m_fbo(nullptr)
+ , m_multisampledFbo(nullptr)
, m_geometry(QSGGeometry::defaultAttributes_TexturedPoint2D(), 4)
- , m_texture(0)
- , m_gl_device(0)
+ , m_texture(nullptr)
+ , m_gl_device(nullptr)
, m_fillColor(Qt::transparent)
, m_contentsScale(1.0)
, m_dirtyContents(false)
@@ -260,8 +260,8 @@ void QSGDefaultPainterNode::updateRenderTarget()
delete m_fbo;
delete m_multisampledFbo;
delete m_gl_device;
- m_fbo = m_multisampledFbo = 0;
- m_gl_device = 0;
+ m_fbo = m_multisampledFbo = nullptr;
+ m_gl_device = nullptr;
}
if (m_actualRenderTarget == QQuickPaintedItem::FramebufferObject ||
@@ -275,7 +275,7 @@ void QSGDefaultPainterNode::updateRenderTarget()
delete m_fbo;
delete m_multisampledFbo;
- m_fbo = m_multisampledFbo = 0;
+ m_fbo = m_multisampledFbo = nullptr;
if (m_gl_device)
m_gl_device->setSize(m_fboSize);
diff --git a/src/quick/scenegraph/util/qsgdepthstencilbuffer.cpp b/src/quick/scenegraph/util/qsgdepthstencilbuffer.cpp
index ba0207aca8..56508af152 100644
--- a/src/quick/scenegraph/util/qsgdepthstencilbuffer.cpp
+++ b/src/quick/scenegraph/util/qsgdepthstencilbuffer.cpp
@@ -43,7 +43,7 @@ QT_BEGIN_NAMESPACE
QSGDepthStencilBuffer::QSGDepthStencilBuffer(QOpenGLContext *context, const Format &format)
: m_functions(context)
- , m_manager(0)
+ , m_manager(nullptr)
, m_format(format)
, m_depthBuffer(0)
, m_stencilBuffer(0)
@@ -160,7 +160,7 @@ QSGDepthStencilBufferManager::~QSGDepthStencilBufferManager()
for (Hash::const_iterator it = m_buffers.constBegin(), cend = m_buffers.constEnd(); it != cend; ++it) {
QSGDepthStencilBuffer *buffer = it.value().data();
buffer->free();
- buffer->m_manager = 0;
+ buffer->m_manager = nullptr;
}
}
@@ -174,7 +174,7 @@ QSharedPointer<QSGDepthStencilBuffer> QSGDepthStencilBufferManager::bufferForFor
void QSGDepthStencilBufferManager::insertBuffer(const QSharedPointer<QSGDepthStencilBuffer> &buffer)
{
- Q_ASSERT(buffer->m_manager == 0);
+ Q_ASSERT(buffer->m_manager == nullptr);
Q_ASSERT(!m_buffers.contains(buffer->m_format));
buffer->m_manager = this;
m_buffers.insert(buffer->m_format, buffer.toWeakRef());
diff --git a/src/quick/scenegraph/util/qsgengine.cpp b/src/quick/scenegraph/util/qsgengine.cpp
index dffe199224..91fa46033c 100644
--- a/src/quick/scenegraph/util/qsgengine.cpp
+++ b/src/quick/scenegraph/util/qsgengine.cpp
@@ -157,7 +157,7 @@ QSGAbstractRenderer *QSGEngine::createRenderer() const
{
Q_D(const QSGEngine);
if (!d->sgRenderContext->isValid())
- return 0;
+ return nullptr;
QSGRenderer *renderer = d->sgRenderContext->createRenderer();
renderer->setCustomRenderMode(qgetenv("QSG_VISUALIZE"));
@@ -178,7 +178,7 @@ QSGTexture *QSGEngine::createTextureFromImage(const QImage &image, CreateTexture
{
Q_D(const QSGEngine);
if (!d->sgRenderContext->isValid())
- return 0;
+ return nullptr;
uint flags = 0;
if (options & TextureCanUseAtlas) flags |= QSGRenderContext::CreateTexture_Atlas;
if (!(options & TextureIsOpaque)) flags |= QSGRenderContext::CreateTexture_Alpha;
@@ -206,7 +206,7 @@ QSGTexture *QSGEngine::createTextureFromId(uint id, const QSize &size, CreateTex
texture->setTextureSize(size);
return texture;
}
- return 0;
+ return nullptr;
}
/*!
diff --git a/src/quick/scenegraph/util/qsgengine.h b/src/quick/scenegraph/util/qsgengine.h
index 514e6e8c2b..e9e01dc710 100644
--- a/src/quick/scenegraph/util/qsgengine.h
+++ b/src/quick/scenegraph/util/qsgengine.h
@@ -68,7 +68,7 @@ public:
Q_DECLARE_FLAGS(CreateTextureOptions, CreateTextureOption)
explicit QSGEngine(QObject *parent = nullptr);
- ~QSGEngine();
+ ~QSGEngine() override;
void initialize(QOpenGLContext *context);
void invalidate();
diff --git a/src/quick/scenegraph/util/qsgflatcolormaterial.cpp b/src/quick/scenegraph/util/qsgflatcolormaterial.cpp
index a0c71b5340..28f6113a60 100644
--- a/src/quick/scenegraph/util/qsgflatcolormaterial.cpp
+++ b/src/quick/scenegraph/util/qsgflatcolormaterial.cpp
@@ -77,13 +77,13 @@ FlatColorMaterialShader::FlatColorMaterialShader()
void FlatColorMaterialShader::updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect)
{
#if QT_CONFIG(opengl)
- Q_ASSERT(oldEffect == 0 || newEffect->type() == oldEffect->type());
+ Q_ASSERT(oldEffect == nullptr || newEffect->type() == oldEffect->type());
QSGFlatColorMaterial *oldMaterial = static_cast<QSGFlatColorMaterial *>(oldEffect);
QSGFlatColorMaterial *newMaterial = static_cast<QSGFlatColorMaterial *>(newEffect);
const QColor &c = newMaterial->color();
- if (oldMaterial == 0 || c != oldMaterial->color() || state.isOpacityDirty()) {
+ if (oldMaterial == nullptr || c != oldMaterial->color() || state.isOpacityDirty()) {
float opacity = state.opacity() * c.alphaF();
QVector4D v(c.redF() * opacity,
c.greenF() * opacity,
@@ -103,7 +103,7 @@ void FlatColorMaterialShader::updateState(const RenderState &state, QSGMaterial
char const *const *FlatColorMaterialShader::attributeNames() const
{
- static char const *const attr[] = { "vCoord", 0 };
+ static char const *const attr[] = { "vCoord", nullptr };
return attr;
}
diff --git a/src/quick/scenegraph/util/qsgimagenode.cpp b/src/quick/scenegraph/util/qsgimagenode.cpp
index c03c91d1cb..b154023247 100644
--- a/src/quick/scenegraph/util/qsgimagenode.cpp
+++ b/src/quick/scenegraph/util/qsgimagenode.cpp
@@ -168,7 +168,7 @@ QT_BEGIN_NAMESPACE
*/
/*!
- \fn QSGImageNode::TextureCoordinatesTransformMode textureCoordinatesTransform() const
+ \fn QSGImageNode::TextureCoordinatesTransformMode QSGImageNode::textureCoordinatesTransform() const
Returns the mode used to generate texture coordinates for this node.
*/
@@ -187,6 +187,15 @@ QT_BEGIN_NAMESPACE
\return \c true if the node takes ownership of the texture; otherwise \c false.
*/
+/*!
+ Updates the geometry \a g with the \a texture, the coordinates
+ in \a rect, and the texture coordinates from \a sourceRect.
+
+ \a g is assumed to be a triangle strip of four vertices of type
+ QSGGeometry::TexturedPoint2D.
+
+ \a texCoordMode is used for normalizing the \a sourceRect.
+ */
void QSGImageNode::rebuildGeometry(QSGGeometry *g,
QSGTexture *texture,
const QRectF &rect,
diff --git a/src/quick/scenegraph/util/qsgimagenode.h b/src/quick/scenegraph/util/qsgimagenode.h
index 0e053c307f..526f52b7e5 100644
--- a/src/quick/scenegraph/util/qsgimagenode.h
+++ b/src/quick/scenegraph/util/qsgimagenode.h
@@ -48,7 +48,7 @@ QT_BEGIN_NAMESPACE
class Q_QUICK_EXPORT QSGImageNode : public QSGGeometryNode
{
public:
- virtual ~QSGImageNode() { }
+ ~QSGImageNode() override { }
virtual void setRect(const QRectF &rect) = 0;
inline void setRect(qreal x, qreal y, qreal w, qreal h) { setRect(QRectF(x, y, w, h)); }
diff --git a/src/quick/scenegraph/util/qsgninepatchnode.h b/src/quick/scenegraph/util/qsgninepatchnode.h
index 8509cbd326..e76afd3c4a 100644
--- a/src/quick/scenegraph/util/qsgninepatchnode.h
+++ b/src/quick/scenegraph/util/qsgninepatchnode.h
@@ -48,7 +48,7 @@ QT_BEGIN_NAMESPACE
class Q_QUICK_EXPORT QSGNinePatchNode : public QSGGeometryNode
{
public:
- virtual ~QSGNinePatchNode() { }
+ ~QSGNinePatchNode() override { }
virtual void setTexture(QSGTexture *texture) = 0;
virtual void setBounds(const QRectF &bounds) = 0;
diff --git a/src/quick/scenegraph/util/qsgrectanglenode.h b/src/quick/scenegraph/util/qsgrectanglenode.h
index 8e0da1d9c7..ba52b65b07 100644
--- a/src/quick/scenegraph/util/qsgrectanglenode.h
+++ b/src/quick/scenegraph/util/qsgrectanglenode.h
@@ -47,7 +47,7 @@ QT_BEGIN_NAMESPACE
class Q_QUICK_EXPORT QSGRectangleNode : public QSGGeometryNode
{
public:
- virtual ~QSGRectangleNode() { }
+ ~QSGRectangleNode() override { }
virtual void setRect(const QRectF &rect) = 0;
inline void setRect(qreal x, qreal y, qreal w, qreal h) { setRect(QRectF(x, y, w, h)); }
diff --git a/src/quick/scenegraph/util/qsgshadersourcebuilder.cpp b/src/quick/scenegraph/util/qsgshadersourcebuilder.cpp
index e134a5d4d3..93fc213f2e 100644
--- a/src/quick/scenegraph/util/qsgshadersourcebuilder.cpp
+++ b/src/quick/scenegraph/util/qsgshadersourcebuilder.cpp
@@ -262,8 +262,8 @@ void QSGShaderSourceBuilder::addDefinition(const QByteArray &definition)
tok.initialize(input);
// First find #version, #extension's and "void main() { ... "
- const char *versionPos = 0;
- const char *extensionPos = 0;
+ const char *versionPos = nullptr;
+ const char *extensionPos = nullptr;
bool inSingleLineComment = false;
bool inMultiLineComment = false;
bool foundVersionStart = false;
@@ -325,8 +325,8 @@ void QSGShaderSourceBuilder::removeVersion()
tok.initialize(input);
// First find #version beginning and end (if present)
- const char *versionStartPos = 0;
- const char *versionEndPos = 0;
+ const char *versionStartPos = nullptr;
+ const char *versionEndPos = nullptr;
bool inSingleLineComment = false;
bool inMultiLineComment = false;
bool foundVersionStart = false;
@@ -361,7 +361,7 @@ void QSGShaderSourceBuilder::removeVersion()
t = tok.next();
}
- if (versionStartPos == 0)
+ if (versionStartPos == nullptr)
return;
// Construct a new shader string, inserting the definition
diff --git a/src/quick/scenegraph/util/qsgsimplematerial.cpp b/src/quick/scenegraph/util/qsgsimplematerial.cpp
index f29c58ad9e..376f7dce5c 100644
--- a/src/quick/scenegraph/util/qsgsimplematerial.cpp
+++ b/src/quick/scenegraph/util/qsgsimplematerial.cpp
@@ -173,17 +173,17 @@
/*!
- \fn char const *const *QSGSimpleMaterialShader::attributeNames() const
+ \fn template <typename State> char const *const *QSGSimpleMaterialShader<State>::attributeNames() const
\internal
*/
/*!
- \fn void QSGSimpleMaterialShader::initialize()
+ \fn template <typename State> void QSGSimpleMaterialShader<State>::initialize()
\internal
*/
/*!
- \fn void QSGSimpleMaterialShader::resolveUniforms()
+ \fn template <typename State> void QSGSimpleMaterialShader<State>::resolveUniforms()
Reimplement this function to resolve the location of named uniforms
in the shader program.
@@ -192,34 +192,34 @@
*/
/*!
- \fn const char *QSGSimpleMaterialShader::uniformMatrixName() const
+ \fn template <typename State> const char *QSGSimpleMaterialShader<State>::uniformMatrixName() const
Returns the name for the transform matrix uniform of this item.
The default value is \c qt_Matrix.
*/
/*!
- \fn const char *QSGSimpleMaterialShader::uniformOpacityName() const
+ \fn template <typename State> const char *QSGSimpleMaterialShader<State>::uniformOpacityName() const
Returns the name for the opacity uniform of this item.
The default value is \c qt_Opacity.
*/
/*!
- \fn void QSGSimpleMaterialShader::updateState(const RenderState &state, QSGMaterial *newMaterial, QSGMaterial *oldMaterial)
+ \fn template <typename State> void QSGSimpleMaterialShader<State>::updateState(const RenderState &state, QSGMaterial *newMaterial, QSGMaterial *oldMaterial)
\internal
*/
/*!
- \fn QList<QByteArray> QSGSimpleMaterialShader::attributes() const
+ \fn template <typename State> QList<QByteArray> QSGSimpleMaterialShader<State>::attributes() const
Returns a list of names, declaring the vertex attributes in the
vertex shader.
*/
/*!
- \fn void QSGSimpleMaterialShader::updateState(const State *newState, const State *oldState)
+ \fn template <typename State> void QSGSimpleMaterialShader<State>::updateState(const State *newState, const State *oldState)
Called whenever the state of this shader should be updated from
\a oldState to \a newState, typical for each new set of
diff --git a/src/quick/scenegraph/util/qsgsimplematerial.h b/src/quick/scenegraph/util/qsgsimplematerial.h
index b5b8815b4a..79180ca8e2 100644
--- a/src/quick/scenegraph/util/qsgsimplematerial.h
+++ b/src/quick/scenegraph/util/qsgsimplematerial.h
@@ -138,7 +138,7 @@ template <typename State>
class QSGSimpleMaterial : public QSGMaterial
{
public:
-#ifndef qdoc
+#ifndef Q_CLANG_QDOC
QSGSimpleMaterial(const State &aState, PtrShaderCreateFunc func)
: m_state(aState)
, m_func(func)
@@ -185,7 +185,7 @@ public:
QSGSimpleMaterialComparableMaterial(PtrShaderCreateFunc func)
: QSGSimpleMaterial<State>(func) {}
- int compare(const QSGMaterial *other) const {
+ int compare(const QSGMaterial *other) const override {
return QSGSimpleMaterialComparableMaterial<State>::state()->compare(static_cast<const QSGSimpleMaterialComparableMaterial<State> *>(other)->state());
}
};
@@ -207,7 +207,7 @@ Q_INLINE_TEMPLATE void QSGSimpleMaterialShader<State>::updateState(const RenderS
Q_UNUSED(state)
#endif
State *ns = static_cast<QSGSimpleMaterial<State> *>(newMaterial)->state();
- State *old = 0;
+ State *old = nullptr;
if (oldMaterial)
old = static_cast<QSGSimpleMaterial<State> *>(oldMaterial)->state();
updateState(ns, old);
diff --git a/src/quick/scenegraph/util/qsgsimpletexturenode.cpp b/src/quick/scenegraph/util/qsgsimpletexturenode.cpp
index 6ce37de7cb..0c49ca9aa5 100644
--- a/src/quick/scenegraph/util/qsgsimpletexturenode.cpp
+++ b/src/quick/scenegraph/util/qsgsimpletexturenode.cpp
@@ -47,8 +47,7 @@ class QSGSimpleTextureNodePrivate : public QSGGeometryNodePrivate
{
public:
QSGSimpleTextureNodePrivate()
- : QSGGeometryNodePrivate()
- , texCoordMode(QSGSimpleTextureNode::NoTransform)
+ : texCoordMode(QSGSimpleTextureNode::NoTransform)
, isAtlasTexture(false)
, ownsTexture(false)
{}
diff --git a/src/quick/scenegraph/util/qsgsimpletexturenode.h b/src/quick/scenegraph/util/qsgsimpletexturenode.h
index 09e4277c66..010463d3c6 100644
--- a/src/quick/scenegraph/util/qsgsimpletexturenode.h
+++ b/src/quick/scenegraph/util/qsgsimpletexturenode.h
@@ -52,7 +52,7 @@ class Q_QUICK_EXPORT QSGSimpleTextureNode : public QSGGeometryNode
{
public:
QSGSimpleTextureNode();
- ~QSGSimpleTextureNode();
+ ~QSGSimpleTextureNode() override;
void setRect(const QRectF &rect);
inline void setRect(qreal x, qreal y, qreal w, qreal h) { setRect(QRectF(x, y, w, h)); }
diff --git a/src/quick/scenegraph/util/qsgtexture.cpp b/src/quick/scenegraph/util/qsgtexture.cpp
index 4f11d95e70..fea92a5121 100644
--- a/src/quick/scenegraph/util/qsgtexture.cpp
+++ b/src/quick/scenegraph/util/qsgtexture.cpp
@@ -53,7 +53,7 @@
#endif
#include <private/qsgmaterialshader_p.h>
-#if defined(Q_OS_LINUX) && !defined(Q_OS_ANDROID) && !defined(__UCLIBC__)
+#if defined(Q_OS_LINUX) && !defined(Q_OS_ANDROID) && defined(__GLIBC__)
#define CAN_BACKTRACE_EXECINFO
#endif
@@ -399,7 +399,7 @@ QSGTexture::~QSGTexture()
QSGTexture *QSGTexture::removedFromAtlas() const
{
Q_ASSERT_X(!isAtlasTexture(), "QSGTexture::removedFromAtlas()", "Called on a non-atlas texture");
- return 0;
+ return nullptr;
}
/*!
diff --git a/src/quick/scenegraph/util/qsgtexture.h b/src/quick/scenegraph/util/qsgtexture.h
index 032129434e..7bd57a16e3 100644
--- a/src/quick/scenegraph/util/qsgtexture.h
+++ b/src/quick/scenegraph/util/qsgtexture.h
@@ -54,7 +54,7 @@ class Q_QUICK_EXPORT QSGTexture : public QObject
public:
QSGTexture();
- ~QSGTexture();
+ ~QSGTexture() override;
enum WrapMode {
Repeat,
diff --git a/src/quick/scenegraph/util/qsgtexture_p.h b/src/quick/scenegraph/util/qsgtexture_p.h
index 52dc6db2d0..18dd5eff68 100644
--- a/src/quick/scenegraph/util/qsgtexture_p.h
+++ b/src/quick/scenegraph/util/qsgtexture_p.h
@@ -83,7 +83,7 @@ class Q_QUICK_PRIVATE_EXPORT QSGPlainTexture : public QSGTexture
Q_OBJECT
public:
QSGPlainTexture();
- virtual ~QSGPlainTexture();
+ ~QSGPlainTexture() override;
void setOwnsTexture(bool owns) { m_owns_texture = owns; }
bool ownsTexture() const { return m_owns_texture; }
diff --git a/src/quick/scenegraph/util/qsgtexturematerial.cpp b/src/quick/scenegraph/util/qsgtexturematerial.cpp
index fbc8f27a63..7b1d5abb26 100644
--- a/src/quick/scenegraph/util/qsgtexturematerial.cpp
+++ b/src/quick/scenegraph/util/qsgtexturematerial.cpp
@@ -57,7 +57,6 @@ inline static bool isPowerOfTwo(int x)
QSGMaterialType QSGOpaqueTextureMaterialShader::type;
QSGOpaqueTextureMaterialShader::QSGOpaqueTextureMaterialShader()
- : QSGMaterialShader()
{
#if QT_CONFIG(opengl)
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/opaquetexture.vert"));
@@ -67,7 +66,7 @@ QSGOpaqueTextureMaterialShader::QSGOpaqueTextureMaterialShader()
char const *const *QSGOpaqueTextureMaterialShader::attributeNames() const
{
- static char const *const attr[] = { "qt_VertexPosition", "qt_VertexTexCoord", 0 };
+ static char const *const attr[] = { "qt_VertexPosition", "qt_VertexTexCoord", nullptr };
return attr;
}
@@ -80,7 +79,7 @@ void QSGOpaqueTextureMaterialShader::initialize()
void QSGOpaqueTextureMaterialShader::updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect)
{
- Q_ASSERT(oldEffect == 0 || newEffect->type() == oldEffect->type());
+ Q_ASSERT(oldEffect == nullptr || newEffect->type() == oldEffect->type());
QSGOpaqueTextureMaterial *tx = static_cast<QSGOpaqueTextureMaterial *>(newEffect);
QSGOpaqueTextureMaterial *oldTx = static_cast<QSGOpaqueTextureMaterial *>(oldEffect);
@@ -112,7 +111,7 @@ void QSGOpaqueTextureMaterialShader::updateState(const RenderState &state, QSGMa
t->setMipmapFiltering(tx->mipmapFiltering());
t->setAnisotropyLevel(tx->anisotropyLevel());
- if (oldTx == 0 || oldTx->texture()->textureId() != t->textureId())
+ if (oldTx == nullptr || oldTx->texture()->textureId() != t->textureId())
t->bind();
else
t->updateBindOptions();
@@ -169,7 +168,7 @@ void QSGOpaqueTextureMaterialShader::updateState(const RenderState &state, QSGMa
*/
QSGOpaqueTextureMaterial::QSGOpaqueTextureMaterial()
- : m_texture(0)
+ : m_texture(nullptr)
, m_filtering(QSGTexture::Nearest)
, m_mipmap_filtering(QSGTexture::None)
, m_horizontal_wrap(QSGTexture::ClampToEdge)
@@ -304,7 +303,17 @@ void QSGOpaqueTextureMaterial::setTexture(QSGTexture *texture)
The default vertical wrap mode is \c QSGTexture::ClampToEdge.
*/
+/*!
+ \fn void QSGOpaqueTextureMaterial::setAnisotropyLevel(QSGTexture::AnisotropyLevel level)
+
+ Sets this material's anistropy level to \a level.
+*/
+
+/*!
+ \fn QSGTexture::AnisotropyLevel QSGOpaqueTextureMaterial::anisotropyLevel() const
+ Returns this material's anistropy level.
+*/
/*!
\internal
@@ -388,7 +397,7 @@ QSGTextureMaterialShader::QSGTextureMaterialShader()
void QSGTextureMaterialShader::updateState(const RenderState &state, QSGMaterial *newEffect, QSGMaterial *oldEffect)
{
- Q_ASSERT(oldEffect == 0 || newEffect->type() == oldEffect->type());
+ Q_ASSERT(oldEffect == nullptr || newEffect->type() == oldEffect->type());
#if QT_CONFIG(opengl)
if (state.isOpacityDirty())
program()->setUniformValue(m_opacity_id, state.opacity());
diff --git a/src/quick/scenegraph/util/qsgtexturereader.cpp b/src/quick/scenegraph/util/qsgtexturereader.cpp
index 61729ada18..8af2c8e7cd 100644
--- a/src/quick/scenegraph/util/qsgtexturereader.cpp
+++ b/src/quick/scenegraph/util/qsgtexturereader.cpp
@@ -43,40 +43,71 @@
#if QT_CONFIG(opengl)
#include <private/qsgpkmhandler_p.h>
+#include <private/qsgktxhandler_p.h>
#endif
+#include <QFileInfo>
+
QT_BEGIN_NAMESPACE
-QSGTextureReader::QSGTextureReader()
+QSGTextureReader::QSGTextureReader(QIODevice *device, const QString &fileName)
+ : m_device(device), m_fileInfo(fileName)
{
+}
+QSGTextureReader::~QSGTextureReader()
+{
+ delete m_handler;
}
-QQuickTextureFactory *QSGTextureReader::read(QIODevice *device, const QByteArray &format)
+QQuickTextureFactory *QSGTextureReader::read()
{
#if QT_CONFIG(opengl)
- if (format == QByteArrayLiteral("pkm")) {
- QSGPkmHandler handler;
- return handler.read(device);
- }
+ if (!isTexture())
+ return nullptr;
+ return m_handler->read();
#else
- Q_UNUSED(device)
- Q_UNUSED(format)
-#endif
return nullptr;
+#endif
}
-bool QSGTextureReader::isTexture(QIODevice *device, const QByteArray &format)
+bool QSGTextureReader::isTexture()
{
#if QT_CONFIG(opengl)
- if (format == QByteArrayLiteral("pkm")) {
- return device->peek(4) == QByteArrayLiteral("PKM ");
+ if (!checked) {
+ checked = true;
+ if (!init())
+ return false;
+
+ QByteArray headerBlock = m_device->peek(64);
+ QByteArray suffix = m_fileInfo.suffix().toLower().toLatin1();
+ QByteArray logName = m_fileInfo.fileName().toUtf8();
+
+ // Currently the handlers are hardcoded; later maybe a list of plugins
+ if (QSGPkmHandler::canRead(suffix, headerBlock)) {
+ m_handler = new QSGPkmHandler(m_device, logName);
+ } else if (QSGKtxHandler::canRead(suffix, headerBlock)) {
+ m_handler = new QSGKtxHandler(m_device, logName);
+ }
+ // else if OtherHandler::canRead() ...etc.
}
+ return (m_handler != nullptr);
#else
- Q_UNUSED(device)
- Q_UNUSED(format)
-#endif
return false;
+#endif
+}
+
+QList<QByteArray> QSGTextureReader::supportedFileFormats()
+{
+ // Hardcoded for now
+ return {QByteArrayLiteral("pkm"), QByteArrayLiteral("ktx")};
+}
+
+bool QSGTextureReader::init()
+{
+ if (!m_device)
+ return false;
+ return m_device->isReadable();
}
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/util/qsgtexturereader_p.h b/src/quick/scenegraph/util/qsgtexturereader_p.h
index 7d2fc314a6..19e33bf5c3 100644
--- a/src/quick/scenegraph/util/qsgtexturereader_p.h
+++ b/src/quick/scenegraph/util/qsgtexturereader_p.h
@@ -52,19 +52,34 @@
//
#include <QString>
+#include <QFileInfo>
QT_BEGIN_NAMESPACE
class QIODevice;
class QQuickTextureFactory;
+class QSGTextureFileHandler;
class QSGTextureReader
{
public:
- QSGTextureReader();
+ QSGTextureReader(QIODevice *device, const QString &fileName = QString());
+ ~QSGTextureReader();
- static QQuickTextureFactory *read(QIODevice *device, const QByteArray &format);
- static bool isTexture(QIODevice *device, const QByteArray &format);
+ QQuickTextureFactory *read();
+ bool isTexture();
+
+ // TBD access function to params
+ // TBD ask for identified fmt
+
+ static QList<QByteArray> supportedFileFormats();
+
+private:
+ bool init();
+ QIODevice *m_device = nullptr;
+ QFileInfo m_fileInfo;
+ QSGTextureFileHandler *m_handler = nullptr;
+ bool checked = false;
};
QT_END_NAMESPACE
diff --git a/src/quick/scenegraph/util/qsgvertexcolormaterial.cpp b/src/quick/scenegraph/util/qsgvertexcolormaterial.cpp
index 42c589b14a..cb61430e2e 100644
--- a/src/quick/scenegraph/util/qsgvertexcolormaterial.cpp
+++ b/src/quick/scenegraph/util/qsgvertexcolormaterial.cpp
@@ -64,7 +64,6 @@ private:
QSGMaterialType QSGVertexColorMaterialShader::type;
QSGVertexColorMaterialShader::QSGVertexColorMaterialShader()
- : QSGMaterialShader()
{
#if QT_CONFIG(opengl)
setShaderSourceFile(QOpenGLShader::Vertex, QStringLiteral(":/qt-project.org/scenegraph/shaders/vertexcolor.vert"));
@@ -87,7 +86,7 @@ void QSGVertexColorMaterialShader::updateState(const RenderState &state, QSGMate
char const *const *QSGVertexColorMaterialShader::attributeNames() const
{
- static const char *const attr[] = { "vertexCoord", "vertexColor", 0 };
+ static const char *const attr[] = { "vertexCoord", "vertexColor", nullptr };
return attr;
}
diff --git a/src/quick/util/qquickanimation.cpp b/src/quick/util/qquickanimation.cpp
index bfac46adb9..a89f237499 100644
--- a/src/quick/util/qquickanimation.cpp
+++ b/src/quick/util/qquickanimation.cpp
@@ -91,7 +91,7 @@ QQuickAbstractAnimation::~QQuickAbstractAnimation()
{
Q_D(QQuickAbstractAnimation);
if (d->group)
- setGroup(0); //remove from group
+ setGroup(nullptr); //remove from group
delete d->animationInstance;
}
@@ -643,7 +643,7 @@ QAbstractAnimationJob* QQuickAbstractAnimation::transition(QQuickStateActions &a
Q_UNUSED(modified);
Q_UNUSED(direction);
Q_UNUSED(defaultTarget);
- return 0;
+ return nullptr;
}
void QQuickAbstractAnimationPrivate::animationFinished(QAbstractAnimationJob*)
@@ -838,7 +838,7 @@ void QQuickColorAnimation::setTo(const QColor &t)
}
QActionAnimation::QActionAnimation()
- : QAbstractAnimationJob(), animAction(0)
+ : QAbstractAnimationJob(), animAction(nullptr)
{
}
@@ -1666,13 +1666,13 @@ void QQuickRotationAnimation::setDirection(QQuickRotationAnimation::RotationDire
d->direction = direction;
switch(d->direction) {
case Clockwise:
- d->interpolator = reinterpret_cast<QVariantAnimation::Interpolator>(&_q_interpolateClockwiseRotation);
+ d->interpolator = reinterpret_cast<QVariantAnimation::Interpolator>(reinterpret_cast<void *>(&_q_interpolateClockwiseRotation));
break;
case Counterclockwise:
- d->interpolator = reinterpret_cast<QVariantAnimation::Interpolator>(&_q_interpolateCounterclockwiseRotation);
+ d->interpolator = reinterpret_cast<QVariantAnimation::Interpolator>(reinterpret_cast<void *>(&_q_interpolateCounterclockwiseRotation));
break;
case Shortest:
- d->interpolator = reinterpret_cast<QVariantAnimation::Interpolator>(&_q_interpolateShortestRotation);
+ d->interpolator = reinterpret_cast<QVariantAnimation::Interpolator>(reinterpret_cast<void *>(&_q_interpolateShortestRotation));
break;
default:
d->interpolator = QVariantAnimationPrivate::getInterpolator(d->interpolatorType);
@@ -1706,7 +1706,7 @@ void QQuickAnimationGroupPrivate::clear_animation(QQmlListProperty<QQuickAbstrac
if (q) {
while (q->d_func()->animations.count()) {
QQuickAbstractAnimation *firstAnim = q->d_func()->animations.at(0);
- firstAnim->setGroup(0);
+ firstAnim->setGroup(nullptr);
}
}
}
@@ -1715,7 +1715,7 @@ QQuickAnimationGroup::~QQuickAnimationGroup()
{
Q_D(QQuickAnimationGroup);
for (int i = 0; i < d->animations.count(); ++i)
- d->animations.at(i)->d_func()->group = 0;
+ d->animations.at(i)->d_func()->group = nullptr;
d->animations.clear();
}
@@ -1937,7 +1937,7 @@ void QQuickPropertyAnimationPrivate::convertVariant(QVariant &variant, int type)
}
QQuickBulkValueAnimator::QQuickBulkValueAnimator()
- : QAbstractAnimationJob(), animValue(0), fromSourced(0), m_duration(250)
+ : QAbstractAnimationJob(), animValue(nullptr), fromSourced(nullptr), m_duration(250)
{
}
@@ -2112,7 +2112,7 @@ void QQuickPropertyAnimation::setFrom(const QVariant &f)
return;
d->from = f;
d->fromIsDefined = f.isValid();
- emit fromChanged(f);
+ emit fromChanged();
}
/*!
@@ -2139,7 +2139,7 @@ void QQuickPropertyAnimation::setTo(const QVariant &t)
return;
d->to = t;
d->toIsDefined = t.isValid();
- emit toChanged(t);
+ emit toChanged();
}
/*!
@@ -2556,7 +2556,7 @@ void QQuickAnimationPropertyUpdater::setValue(qreal v)
if (deleted)
return;
}
- wasDeleted = 0;
+ wasDeleted = nullptr;
fromSourced = true;
}
diff --git a/src/quick/util/qquickanimation_p.h b/src/quick/util/qquickanimation_p.h
index e27871dcaa..2293f2597f 100644
--- a/src/quick/util/qquickanimation_p.h
+++ b/src/quick/util/qquickanimation_p.h
@@ -87,8 +87,8 @@ public:
AnyThread
};
- QQuickAbstractAnimation(QObject *parent=0);
- virtual ~QQuickAbstractAnimation();
+ QQuickAbstractAnimation(QObject *parent=nullptr);
+ ~QQuickAbstractAnimation() override;
enum Loops { Infinite = -2 };
Q_ENUM(Loops)
@@ -144,7 +144,7 @@ public:
virtual QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0);
+ QObject *defaultTarget = nullptr);
QAbstractAnimationJob* qtAnimation();
private Q_SLOTS:
@@ -166,8 +166,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPauseAnimation : public QQuickAbstractAnimati
Q_PROPERTY(int duration READ duration WRITE setDuration NOTIFY durationChanged)
public:
- QQuickPauseAnimation(QObject *parent=0);
- virtual ~QQuickPauseAnimation();
+ QQuickPauseAnimation(QObject *parent=nullptr);
+ ~QQuickPauseAnimation() override;
int duration() const;
void setDuration(int);
@@ -179,7 +179,7 @@ protected:
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
};
class QQuickScriptActionPrivate;
@@ -192,8 +192,8 @@ class QQuickScriptAction : public QQuickAbstractAnimation
Q_PROPERTY(QString scriptName READ stateChangeScriptName WRITE setStateChangeScriptName)
public:
- QQuickScriptAction(QObject *parent=0);
- virtual ~QQuickScriptAction();
+ QQuickScriptAction(QObject *parent=nullptr);
+ ~QQuickScriptAction() override;
QQmlScriptString script() const;
void setScript(const QQmlScriptString &);
@@ -205,7 +205,7 @@ protected:
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
};
class QQuickPropertyActionPrivate;
@@ -222,8 +222,8 @@ class QQuickPropertyAction : public QQuickAbstractAnimation
Q_PROPERTY(QVariant value READ value WRITE setValue NOTIFY valueChanged)
public:
- QQuickPropertyAction(QObject *parent=0);
- virtual ~QQuickPropertyAction();
+ QQuickPropertyAction(QObject *parent=nullptr);
+ ~QQuickPropertyAction() override;
QObject *target() const;
void setTargetObject(QObject *);
@@ -250,7 +250,7 @@ protected:
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
};
class QQuickPropertyAnimationPrivate;
@@ -270,8 +270,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPropertyAnimation : public QQuickAbstractAnim
Q_PROPERTY(QQmlListProperty<QObject> exclude READ exclude)
public:
- QQuickPropertyAnimation(QObject *parent=0);
- virtual ~QQuickPropertyAnimation();
+ QQuickPropertyAnimation(QObject *parent=nullptr);
+ ~QQuickPropertyAnimation() override;
virtual int duration() const;
virtual void setDuration(int);
@@ -300,17 +300,17 @@ public:
protected:
QQuickStateActions createTransitionActions(QQuickStateActions &actions,
QQmlProperties &modified,
- QObject *defaultTarget = 0);
+ QObject *defaultTarget = nullptr);
QQuickPropertyAnimation(QQuickPropertyAnimationPrivate &dd, QObject *parent);
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
Q_SIGNALS:
void durationChanged(int);
- void fromChanged(const QVariant &);
- void toChanged(const QVariant &);
+ void fromChanged();
+ void toChanged();
void easingChanged(const QEasingCurve &);
void propertiesChanged(const QString &);
void targetChanged();
@@ -325,8 +325,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickColorAnimation : public QQuickPropertyAnimati
Q_PROPERTY(QColor to READ to WRITE setTo)
public:
- QQuickColorAnimation(QObject *parent=0);
- virtual ~QQuickColorAnimation();
+ QQuickColorAnimation(QObject *parent=nullptr);
+ ~QQuickColorAnimation() override;
QColor from() const;
void setFrom(const QColor &);
@@ -340,12 +340,12 @@ class Q_QUICK_PRIVATE_EXPORT QQuickNumberAnimation : public QQuickPropertyAnimat
Q_OBJECT
Q_DECLARE_PRIVATE(QQuickPropertyAnimation)
- Q_PROPERTY(qreal from READ from WRITE setFrom)
- Q_PROPERTY(qreal to READ to WRITE setTo)
+ Q_PROPERTY(qreal from READ from WRITE setFrom NOTIFY fromChanged)
+ Q_PROPERTY(qreal to READ to WRITE setTo NOTIFY toChanged)
public:
- QQuickNumberAnimation(QObject *parent=0);
- virtual ~QQuickNumberAnimation();
+ QQuickNumberAnimation(QObject *parent=nullptr);
+ ~QQuickNumberAnimation() override;
qreal from() const;
void setFrom(qreal);
@@ -365,12 +365,12 @@ class Q_QUICK_PRIVATE_EXPORT QQuickVector3dAnimation : public QQuickPropertyAnim
Q_OBJECT
Q_DECLARE_PRIVATE(QQuickPropertyAnimation)
- Q_PROPERTY(QVector3D from READ from WRITE setFrom)
- Q_PROPERTY(QVector3D to READ to WRITE setTo)
+ Q_PROPERTY(QVector3D from READ from WRITE setFrom NOTIFY fromChanged)
+ Q_PROPERTY(QVector3D to READ to WRITE setTo NOTIFY toChanged)
public:
- QQuickVector3dAnimation(QObject *parent=0);
- virtual ~QQuickVector3dAnimation();
+ QQuickVector3dAnimation(QObject *parent=nullptr);
+ ~QQuickVector3dAnimation() override;
QVector3D from() const;
void setFrom(QVector3D);
@@ -385,13 +385,13 @@ class Q_QUICK_PRIVATE_EXPORT QQuickRotationAnimation : public QQuickPropertyAnim
Q_OBJECT
Q_DECLARE_PRIVATE(QQuickRotationAnimation)
- Q_PROPERTY(qreal from READ from WRITE setFrom)
- Q_PROPERTY(qreal to READ to WRITE setTo)
+ Q_PROPERTY(qreal from READ from WRITE setFrom NOTIFY fromChanged)
+ Q_PROPERTY(qreal to READ to WRITE setTo NOTIFY toChanged)
Q_PROPERTY(RotationDirection direction READ direction WRITE setDirection NOTIFY directionChanged)
public:
- QQuickRotationAnimation(QObject *parent=0);
- virtual ~QQuickRotationAnimation();
+ QQuickRotationAnimation(QObject *parent=nullptr);
+ ~QQuickRotationAnimation() override;
qreal from() const;
void setFrom(qreal);
@@ -419,7 +419,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickAnimationGroup : public QQuickAbstractAnimati
public:
QQuickAnimationGroup(QObject *parent);
- virtual ~QQuickAnimationGroup();
+ ~QQuickAnimationGroup() override;
QQmlListProperty<QQuickAbstractAnimation> animations();
friend class QQuickAbstractAnimation;
@@ -434,15 +434,15 @@ class QQuickSequentialAnimation : public QQuickAnimationGroup
Q_DECLARE_PRIVATE(QQuickAnimationGroup)
public:
- QQuickSequentialAnimation(QObject *parent=0);
- virtual ~QQuickSequentialAnimation();
+ QQuickSequentialAnimation(QObject *parent=nullptr);
+ ~QQuickSequentialAnimation() override;
protected:
ThreadingModel threadingModel() const override;
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
};
class Q_QUICK_PRIVATE_EXPORT QQuickParallelAnimation : public QQuickAnimationGroup
@@ -451,15 +451,15 @@ class Q_QUICK_PRIVATE_EXPORT QQuickParallelAnimation : public QQuickAnimationGro
Q_DECLARE_PRIVATE(QQuickAnimationGroup)
public:
- QQuickParallelAnimation(QObject *parent=0);
- virtual ~QQuickParallelAnimation();
+ QQuickParallelAnimation(QObject *parent=nullptr);
+ ~QQuickParallelAnimation() override;
protected:
ThreadingModel threadingModel() const override;
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
};
diff --git a/src/quick/util/qquickanimation_p_p.h b/src/quick/util/qquickanimation_p_p.h
index 7a1bd8ff13..c20ec65c24 100644
--- a/src/quick/util/qquickanimation_p_p.h
+++ b/src/quick/util/qquickanimation_p_p.h
@@ -102,7 +102,7 @@ public:
QActionAnimation();
QActionAnimation(QAbstractAnimationAction *action);
- ~QActionAnimation();
+ ~QActionAnimation() override;
int duration() const override;
void setAnimAction(QAbstractAnimationAction *action);
@@ -130,7 +130,7 @@ class Q_AUTOTEST_EXPORT QQuickBulkValueAnimator : public QAbstractAnimationJob
Q_DISABLE_COPY(QQuickBulkValueAnimator)
public:
QQuickBulkValueAnimator();
- ~QQuickBulkValueAnimator();
+ ~QQuickBulkValueAnimator() override;
void setAnimValue(QQuickBulkValueUpdater *value);
QQuickBulkValueUpdater *getAnimValue() const { return animValue; }
@@ -178,7 +178,7 @@ public:
: running(false), paused(false), alwaysRunToEnd(false),
/*connectedTimeLine(false), */componentComplete(true),
avoidPropertyValueSourceStart(false), disableUserControl(false),
- registered(false), loopCount(1), group(0), animationInstance(0) {}
+ registered(false), loopCount(1), group(nullptr), animationInstance(nullptr) {}
bool running:1;
bool paused:1;
@@ -237,7 +237,7 @@ class QQuickPropertyActionPrivate : public QQuickAbstractAnimationPrivate
Q_DECLARE_PUBLIC(QQuickPropertyAction)
public:
QQuickPropertyActionPrivate()
- : QQuickAbstractAnimationPrivate(), target(0) {}
+ : QQuickAbstractAnimationPrivate(), target(nullptr) {}
QObject *target;
QString propertyName;
@@ -265,8 +265,8 @@ class QQuickPropertyAnimationPrivate : public QQuickAbstractAnimationPrivate
Q_DECLARE_PUBLIC(QQuickPropertyAnimation)
public:
QQuickPropertyAnimationPrivate()
- : QQuickAbstractAnimationPrivate(), target(0), fromSourced(false), fromIsDefined(false), toIsDefined(false),
- defaultToInterpolatorType(0), interpolatorType(0), interpolator(0), duration(250), actions(0) {}
+ : QQuickAbstractAnimationPrivate(), target(nullptr), fromSourced(false), fromIsDefined(false), toIsDefined(false),
+ defaultToInterpolatorType(0), interpolatorType(0), interpolator(nullptr), duration(250), actions(nullptr) {}
QVariant from;
QVariant to;
@@ -306,8 +306,8 @@ public:
class Q_AUTOTEST_EXPORT QQuickAnimationPropertyUpdater : public QQuickBulkValueUpdater
{
public:
- QQuickAnimationPropertyUpdater() : interpolatorType(0), interpolator(0), prevInterpolatorType(0), reverse(false), fromSourced(false), fromDefined(false), wasDeleted(0) {}
- ~QQuickAnimationPropertyUpdater();
+ QQuickAnimationPropertyUpdater() : interpolatorType(0), interpolator(nullptr), prevInterpolatorType(0), reverse(false), fromSourced(false), fromDefined(false), wasDeleted(nullptr) {}
+ ~QQuickAnimationPropertyUpdater() override;
void setValue(qreal v) override;
diff --git a/src/quick/util/qquickanimationcontroller.cpp b/src/quick/util/qquickanimationcontroller.cpp
index cebb0391ae..63373541a6 100644
--- a/src/quick/util/qquickanimationcontroller.cpp
+++ b/src/quick/util/qquickanimationcontroller.cpp
@@ -49,7 +49,7 @@ class QQuickAnimationControllerPrivate : public QObjectPrivate, QAnimationJobCha
Q_DECLARE_PUBLIC(QQuickAnimationController)
public:
QQuickAnimationControllerPrivate()
- : progress(0.0), animation(0), animationInstance(0), finalized(false) {}
+ : progress(0.0), animation(nullptr), animationInstance(nullptr), finalized(false) {}
void animationFinished(QAbstractAnimationJob *job) override;
void animationCurrentTimeChanged(QAbstractAnimationJob *job, int currentTime) override;
@@ -197,7 +197,7 @@ void QQuickAnimationController::reload()
return;
if (!d->animation) {
- d->animationInstance = 0;
+ d->animationInstance = nullptr;
} else {
QQuickStateActions actions;
QQmlProperties properties;
@@ -223,7 +223,7 @@ void QQuickAnimationController::updateProgress()
d->animationInstance->setDisableUserControl();
d->animationInstance->start();
- QQmlAnimationTimer::unregisterAnimation(d->animationInstance);
+ QQmlAnimationTimer::instance()->unregisterAnimation(d->animationInstance);
d->animationInstance->setCurrentTime(d->progress * d->animationInstance->duration());
}
diff --git a/src/quick/util/qquickanimationcontroller_p.h b/src/quick/util/qquickanimationcontroller_p.h
index 43555ac1c1..d9ce377060 100644
--- a/src/quick/util/qquickanimationcontroller_p.h
+++ b/src/quick/util/qquickanimationcontroller_p.h
@@ -69,7 +69,7 @@ class Q_AUTOTEST_EXPORT QQuickAnimationController : public QObject, public QQmlP
Q_PROPERTY(QQuickAbstractAnimation *animation READ animation WRITE setAnimation NOTIFY animationChanged)
public:
- QQuickAnimationController(QObject *parent=0);
+ QQuickAnimationController(QObject *parent=nullptr);
~QQuickAnimationController();
qreal progress() const;
diff --git a/src/quick/util/qquickanimator.cpp b/src/quick/util/qquickanimator.cpp
index 5608326f8a..d1ff78f8bc 100644
--- a/src/quick/util/qquickanimator.cpp
+++ b/src/quick/util/qquickanimator.cpp
@@ -280,22 +280,22 @@ QAbstractAnimationJob *QQuickAnimator::transition(QQuickStateActions &actions,
if (d->defaultProperty.isValid() && propertyName() != d->defaultProperty.name()) {
qDebug() << Q_FUNC_INFO << "property name conflict...";
- return 0;
+ return nullptr;
}
// The animation system cannot handle backwards uncontrolled animations.
if (direction == Backward)
- return 0;
+ return nullptr;
QQuickAnimatorJob *job = createJob();
if (!job)
- return 0;
+ return nullptr;
d->apply(job, propertyName(), actions, modified, defaultTarget);
if (!job->target()) {
delete job;
- return 0;
+ return nullptr;
}
return job;
@@ -576,7 +576,7 @@ QQuickAnimatorJob *QQuickUniformAnimator::createJob() const
{
QString u = propertyName();
if (u.isEmpty())
- return 0;
+ return nullptr;
QQuickUniformAnimatorJob *job = new QQuickUniformAnimatorJob();
job->setUniform(u.toLatin1());
diff --git a/src/quick/util/qquickanimator_p.h b/src/quick/util/qquickanimator_p.h
index 92c66299dc..511cecda7f 100644
--- a/src/quick/util/qquickanimator_p.h
+++ b/src/quick/util/qquickanimator_p.h
@@ -94,8 +94,8 @@ protected:
TransitionDirection,
QObject *) override;
- QQuickAnimator(QQuickAnimatorPrivate &dd, QObject *parent = 0);
- QQuickAnimator(QObject *parent = 0);
+ QQuickAnimator(QQuickAnimatorPrivate &dd, QObject *parent = nullptr);
+ QQuickAnimator(QObject *parent = nullptr);
Q_SIGNALS:
void targetItemChanged(QQuickItem *);
@@ -110,7 +110,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickScaleAnimator : public QQuickAnimator
{
Q_OBJECT
public:
- QQuickScaleAnimator(QObject *parent = 0);
+ QQuickScaleAnimator(QObject *parent = nullptr);
protected:
QQuickAnimatorJob *createJob() const override;
QString propertyName() const override { return QStringLiteral("scale"); }
@@ -120,7 +120,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickXAnimator : public QQuickAnimator
{
Q_OBJECT
public:
- QQuickXAnimator(QObject *parent = 0);
+ QQuickXAnimator(QObject *parent = nullptr);
protected:
QQuickAnimatorJob *createJob() const override;
QString propertyName() const override { return QStringLiteral("x"); }
@@ -130,7 +130,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickYAnimator : public QQuickAnimator
{
Q_OBJECT
public:
- QQuickYAnimator(QObject *parent = 0);
+ QQuickYAnimator(QObject *parent = nullptr);
protected:
QQuickAnimatorJob *createJob() const override;
QString propertyName() const override { return QStringLiteral("y"); }
@@ -140,7 +140,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickOpacityAnimator : public QQuickAnimator
{
Q_OBJECT
public:
- QQuickOpacityAnimator(QObject *parent = 0);
+ QQuickOpacityAnimator(QObject *parent = nullptr);
protected:
QQuickAnimatorJob *createJob() const override;
QString propertyName() const override { return QStringLiteral("opacity"); }
@@ -157,7 +157,7 @@ public:
enum RotationDirection { Numerical, Shortest, Clockwise, Counterclockwise };
Q_ENUM(RotationDirection)
- QQuickRotationAnimator(QObject *parent = 0);
+ QQuickRotationAnimator(QObject *parent = nullptr);
void setDirection(RotationDirection dir);
RotationDirection direction() const;
@@ -179,7 +179,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickUniformAnimator : public QQuickAnimator
Q_PROPERTY(QString uniform READ uniform WRITE setUniform NOTIFY uniformChanged)
public:
- QQuickUniformAnimator(QObject *parent = 0);
+ QQuickUniformAnimator(QObject *parent = nullptr);
QString uniform() const;
void setUniform(const QString &);
diff --git a/src/quick/util/qquickanimatorcontroller.cpp b/src/quick/util/qquickanimatorcontroller.cpp
index 3f7347c01d..5cf8051922 100644
--- a/src/quick/util/qquickanimatorcontroller.cpp
+++ b/src/quick/util/qquickanimatorcontroller.cpp
@@ -123,8 +123,10 @@ static void qquickanimator_sync_before_start(QAbstractAnimationJob *job)
void QQuickAnimatorController::beforeNodeSync()
{
- for (const QSharedPointer<QAbstractAnimationJob> &toStop : qAsConst(m_rootsPendingStop))
+ for (const QSharedPointer<QAbstractAnimationJob> &toStop : qAsConst(m_rootsPendingStop)) {
toStop->stop();
+ m_animationRoots.remove(toStop.data());
+ }
m_rootsPendingStop.clear();
diff --git a/src/quick/util/qquickanimatorjob.cpp b/src/quick/util/qquickanimatorjob.cpp
index 43c8eb302a..6574f8f67e 100644
--- a/src/quick/util/qquickanimatorjob.cpp
+++ b/src/quick/util/qquickanimatorjob.cpp
@@ -250,8 +250,8 @@ void QQuickAnimatorProxyJob::syncBackCurrentValues()
}
QQuickAnimatorJob::QQuickAnimatorJob()
- : m_target(0)
- , m_controller(0)
+ : m_target(nullptr)
+ , m_controller(nullptr)
, m_from(0)
, m_to(0)
, m_value(0)
diff --git a/src/quick/util/qquickanimatorjob_p.h b/src/quick/util/qquickanimatorjob_p.h
index 777da2ee6c..74085526c0 100644
--- a/src/quick/util/qquickanimatorjob_p.h
+++ b/src/quick/util/qquickanimatorjob_p.h
@@ -194,7 +194,7 @@ public:
{
Helper()
: ref(1)
- , node(0)
+ , node(nullptr)
, ox(0)
, oy(0)
, dx(0)
diff --git a/src/quick/util/qquickapplication_p.h b/src/quick/util/qquickapplication_p.h
index 8ee203f0da..66a33489e4 100644
--- a/src/quick/util/qquickapplication_p.h
+++ b/src/quick/util/qquickapplication_p.h
@@ -72,7 +72,7 @@ class Q_AUTOTEST_EXPORT QQuickApplication : public QQmlApplication
Q_PROPERTY(QQmlListProperty<QQuickScreenInfo> screens READ screens NOTIFY screensChanged)
public:
- explicit QQuickApplication(QObject *parent = 0);
+ explicit QQuickApplication(QObject *parent = nullptr);
virtual ~QQuickApplication();
bool active() const;
Qt::LayoutDirection layoutDirection() const;
diff --git a/src/quick/util/qquickbehavior.cpp b/src/quick/util/qquickbehavior.cpp
index a562ebd937..8a4ff6a779 100644
--- a/src/quick/util/qquickbehavior.cpp
+++ b/src/quick/util/qquickbehavior.cpp
@@ -57,7 +57,7 @@ class QQuickBehaviorPrivate : public QObjectPrivate, public QAnimationJobChangeL
{
Q_DECLARE_PUBLIC(QQuickBehavior)
public:
- QQuickBehaviorPrivate() : animation(0), animationInstance(0), enabled(true), finalized(false)
+ QQuickBehaviorPrivate() : animation(nullptr), animationInstance(nullptr), enabled(true), finalized(false)
, blockRunningChanged(false) {}
void animationStateChanged(QAbstractAnimationJob *, QAbstractAnimationJob::State newState, QAbstractAnimationJob::State oldState) override;
diff --git a/src/quick/util/qquickbehavior_p.h b/src/quick/util/qquickbehavior_p.h
index b3fd2af400..f939597d15 100644
--- a/src/quick/util/qquickbehavior_p.h
+++ b/src/quick/util/qquickbehavior_p.h
@@ -72,7 +72,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickBehavior : public QObject, public QQmlPropert
Q_CLASSINFO("DeferredPropertyNames", "animation")
public:
- QQuickBehavior(QObject *parent=0);
+ QQuickBehavior(QObject *parent=nullptr);
~QQuickBehavior();
void setTarget(const QQmlProperty &) override;
diff --git a/src/quick/util/qquickfontloader.cpp b/src/quick/util/qquickfontloader.cpp
index 68e27c25fd..2da541304d 100644
--- a/src/quick/util/qquickfontloader.cpp
+++ b/src/quick/util/qquickfontloader.cpp
@@ -77,8 +77,8 @@ Q_SIGNALS:
void fontDownloaded(const QString&, QQuickFontLoader::Status);
private:
- int redirectCount;
- QNetworkReply *reply;
+ int redirectCount = 0;
+ QNetworkReply *reply = nullptr;
private Q_SLOTS:
void replyFinished();
@@ -91,13 +91,8 @@ public:
};
QQuickFontObject::QQuickFontObject(int _id)
- : QObject(0)
-#if QT_CONFIG(qml_network)
- ,redirectCount(0), reply(0)
-#endif
- ,id(_id)
+ : QObject(nullptr), id(_id)
{
-
}
#if QT_CONFIG(qml_network)
@@ -119,7 +114,7 @@ void QQuickFontObject::replyFinished()
QUrl url = reply->url().resolved(redirect.toUrl());
QNetworkAccessManager *manager = reply->manager();
reply->deleteLater();
- reply = 0;
+ reply = nullptr;
download(url, manager);
return;
}
@@ -138,7 +133,7 @@ void QQuickFontObject::replyFinished()
emit fontDownloaded(QString(), QQuickFontLoader::Error);
}
reply->deleteLater();
- reply = 0;
+ reply = nullptr;
}
}
#endif // qml_network
@@ -148,11 +143,11 @@ class QQuickFontLoaderPrivate : public QObjectPrivate
Q_DECLARE_PUBLIC(QQuickFontLoader)
public:
- QQuickFontLoaderPrivate() : status(QQuickFontLoader::Null) {}
+ QQuickFontLoaderPrivate() {}
QUrl url;
QString name;
- QQuickFontLoader::Status status;
+ QQuickFontLoader::Status status = QQuickFontLoader::Null;
};
static void q_QFontLoaderFontsStaticReset();
diff --git a/src/quick/util/qquickfontloader_p.h b/src/quick/util/qquickfontloader_p.h
index 29feecde4f..8d277f7cf7 100644
--- a/src/quick/util/qquickfontloader_p.h
+++ b/src/quick/util/qquickfontloader_p.h
@@ -72,7 +72,7 @@ public:
enum Status { Null = 0, Ready, Loading, Error };
Q_ENUM(Status)
- QQuickFontLoader(QObject *parent = 0);
+ QQuickFontLoader(QObject *parent = nullptr);
~QQuickFontLoader();
QUrl source() const;
diff --git a/src/quick/util/qquickfontmetrics_p.h b/src/quick/util/qquickfontmetrics_p.h
index ebabe51712..db2b7b6796 100644
--- a/src/quick/util/qquickfontmetrics_p.h
+++ b/src/quick/util/qquickfontmetrics_p.h
@@ -80,7 +80,7 @@ class Q_AUTOTEST_EXPORT QQuickFontMetrics : public QObject
Q_PROPERTY(qreal strikeOutPosition READ strikeOutPosition NOTIFY fontChanged)
Q_PROPERTY(qreal lineWidth READ lineWidth NOTIFY fontChanged)
public:
- explicit QQuickFontMetrics(QObject *parent = 0);
+ explicit QQuickFontMetrics(QObject *parent = nullptr);
~QQuickFontMetrics();
QFont font() const;
diff --git a/src/quick/util/qquickglobal.cpp b/src/quick/util/qquickglobal.cpp
index 5f8d2b94d3..7fa20636ec 100644
--- a/src/quick/util/qquickglobal.cpp
+++ b/src/quick/util/qquickglobal.cpp
@@ -419,7 +419,7 @@ public:
break;
}
- return 0;
+ return nullptr;
}
bool init(int type, QVariant& dst) override
@@ -863,8 +863,8 @@ void QQuick_initializeProviders()
void QQuick_deinitializeProviders()
{
QQml_removeValueTypeProvider(getValueTypeProvider());
- QQml_setColorProvider(0); // technically, another plugin may have overridden our providers
- QQml_setGuiProvider(0); // but we cannot handle that case in a sane way.
+ QQml_setColorProvider(nullptr); // technically, another plugin may have overridden our providers
+ QQml_setGuiProvider(nullptr); // but we cannot handle that case in a sane way.
}
QT_END_NAMESPACE
diff --git a/src/quick/util/qquickimageprovider.cpp b/src/quick/util/qquickimageprovider.cpp
index 6ee5b95dc7..1a13f6395a 100644
--- a/src/quick/util/qquickimageprovider.cpp
+++ b/src/quick/util/qquickimageprovider.cpp
@@ -108,7 +108,7 @@ QImage QQuickTextureFactory::image() const
QQuickTextureFactory *QQuickTextureFactory::textureFactoryForImage(const QImage &image)
{
if (image.isNull())
- return 0;
+ return nullptr;
QQuickTextureFactory *texture = QSGContext::createTextureFactoryFromImage(image);
if (texture)
return texture;
@@ -469,7 +469,7 @@ QQuickTextureFactory *QQuickImageProvider::requestTexture(const QString &id, QSi
Q_UNUSED(requestedSize);
if (d->type == Texture)
qWarning("ImageProvider supports Texture type but has not implemented requestTexture()");
- return 0;
+ return nullptr;
}
/*!
@@ -484,7 +484,7 @@ QQuickTextureFactory *QQuickImageProvider::requestTexture(const QString &id, QSi
*/
QQuickAsyncImageProvider::QQuickAsyncImageProvider()
: QQuickImageProvider(ImageResponse, ForceAsynchronousImageLoading)
- , d(0) // just as a placeholder in case we need it for the future
+ , d(nullptr) // just as a placeholder in case we need it for the future
{
Q_UNUSED(d);
}
@@ -515,15 +515,12 @@ class QQuickImageProviderOptionsPrivate : public QSharedData
{
public:
QQuickImageProviderOptionsPrivate()
- : autoTransform(QQuickImageProviderOptions::UsePluginDefaultTransform)
- , preserveAspectRatioCrop(false)
- , preserveAspectRatioFit(false)
{
}
- QQuickImageProviderOptions::AutoTransform autoTransform;
- bool preserveAspectRatioCrop;
- bool preserveAspectRatioFit;
+ QQuickImageProviderOptions::AutoTransform autoTransform = QQuickImageProviderOptions::UsePluginDefaultTransform;
+ bool preserveAspectRatioCrop = false;
+ bool preserveAspectRatioFit = false;
};
/*!
@@ -683,13 +680,15 @@ QSize QQuickImageProviderWithOptions::loadSize(const QSize &originalSize, const
return res;
const bool preserveAspectCropOrFit = options.preserveAspectRatioCrop() || options.preserveAspectRatioFit();
- const bool force_scale = (format == "svg" || format == "svgz");
+
+ if (!preserveAspectCropOrFit && (format == "svg" || format == "svgz") && !requestedSize.isEmpty())
+ return requestedSize;
qreal ratio = 0.0;
- if (requestedSize.width() && (preserveAspectCropOrFit || force_scale || requestedSize.width() < originalSize.width())) {
+ if (requestedSize.width() && (preserveAspectCropOrFit || requestedSize.width() < originalSize.width())) {
ratio = qreal(requestedSize.width()) / originalSize.width();
}
- if (requestedSize.height() && (preserveAspectCropOrFit || force_scale || requestedSize.height() < originalSize.height())) {
+ if (requestedSize.height() && (preserveAspectCropOrFit || requestedSize.height() < originalSize.height())) {
qreal hr = qreal(requestedSize.height()) / originalSize.height();
if (ratio == 0.0)
ratio = hr;
diff --git a/src/quick/util/qquickimageprovider.h b/src/quick/util/qquickimageprovider.h
index 681de4b6c2..4f8193789a 100644
--- a/src/quick/util/qquickimageprovider.h
+++ b/src/quick/util/qquickimageprovider.h
@@ -56,9 +56,10 @@ class QQuickWindow;
class Q_QUICK_EXPORT QQuickTextureFactory : public QObject
{
+ Q_OBJECT
public:
QQuickTextureFactory();
- virtual ~QQuickTextureFactory();
+ ~QQuickTextureFactory() override;
virtual QSGTexture *createTexture(QQuickWindow *window) const = 0;
virtual QSize textureSize() const = 0;
@@ -73,7 +74,7 @@ class Q_QUICK_EXPORT QQuickImageResponse : public QObject
Q_OBJECT
public:
QQuickImageResponse();
- virtual ~QQuickImageResponse();
+ ~QQuickImageResponse() override;
virtual QQuickTextureFactory *textureFactory() const = 0;
virtual QString errorString() const;
@@ -90,7 +91,7 @@ class Q_QUICK_EXPORT QQuickImageProvider : public QQmlImageProviderBase
friend class QQuickImageProviderWithOptions; // ### Qt 6 Remove
public:
QQuickImageProvider(ImageType type, Flags flags = Flags());
- virtual ~QQuickImageProvider();
+ ~QQuickImageProvider() override;
ImageType imageType() const override;
Flags flags() const override;
@@ -113,7 +114,7 @@ class Q_QUICK_EXPORT QQuickAsyncImageProvider : public QQuickImageProvider
{
public:
QQuickAsyncImageProvider();
- virtual ~QQuickAsyncImageProvider();
+ ~QQuickAsyncImageProvider() override;
#if QT_VERSION >= QT_VERSION_CHECK(6,0,0)
virtual QQuickImageResponse *requestImageResponse(const QString &id, const QSize &requestedSize, const QQuickImageProviderOptions &options) = 0;
diff --git a/src/quick/util/qquickpath.cpp b/src/quick/util/qquickpath.cpp
index 0323dc9286..56eafcd12a 100644
--- a/src/quick/util/qquickpath.cpp
+++ b/src/quick/util/qquickpath.cpp
@@ -256,7 +256,7 @@ bool QQuickPath::isClosed() const
QQmlListProperty<QQuickPathElement> QQuickPath::pathElements()
{
return QQmlListProperty<QQuickPathElement>(this,
- 0,
+ nullptr,
pathElements_append,
pathElements_count,
pathElements_at,
@@ -397,7 +397,12 @@ void QQuickPath::processPath()
d->_pointCache.clear();
d->prevBez.isValid = false;
- d->_path = createPath(QPointF(), QPointF(), d->_attributes, d->pathLength, d->_attributePoints, &d->closed);
+ if (d->isShapePath) {
+ // This path is a ShapePath, so avoid extra overhead
+ d->_path = createShapePath(QPointF(), QPointF(), d->pathLength, &d->closed);
+ } else {
+ d->_path = createPath(QPointF(), QPointF(), d->_attributes, d->pathLength, d->_attributePoints, &d->closed);
+ }
emit changed();
}
@@ -493,6 +498,42 @@ QPainterPath QQuickPath::createPath(const QPointF &startPoint, const QPointF &en
return path;
}
+QPainterPath QQuickPath::createShapePath(const QPointF &startPoint, const QPointF &endPoint, qreal &pathLength, bool *closed)
+{
+ Q_D(QQuickPath);
+
+ if (!d->componentComplete)
+ return QPainterPath();
+
+ QPainterPath path;
+
+ qreal startX = d->startX.isValid() ? d->startX.value : startPoint.x();
+ qreal startY = d->startY.isValid() ? d->startY.value : startPoint.y();
+ path.moveTo(startX, startY);
+
+ int index = 0;
+ for (QQuickCurve *curve : qAsConst(d->_pathCurves)) {
+ QQuickPathData data;
+ data.index = index;
+ data.endPoint = endPoint;
+ data.curves = d->_pathCurves;
+ curve->addToPath(path, data);
+ ++index;
+ }
+
+ if (closed) {
+ QPointF end = path.currentPosition();
+ *closed = startX == end.x() && startY == end.y();
+ }
+
+ // Note: Length of paths inside ShapePath is not used, so currently
+ // length is always 0. This avoids potentially heavy path.length()
+ //pathLength = path.length();
+ pathLength = 0;
+
+ return path;
+}
+
void QQuickPath::classBegin()
{
Q_D(QQuickPath);
diff --git a/src/quick/util/qquickpath_p.h b/src/quick/util/qquickpath_p.h
index d5474e2d30..6b9a40fe6d 100644
--- a/src/quick/util/qquickpath_p.h
+++ b/src/quick/util/qquickpath_p.h
@@ -78,7 +78,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathElement : public QObject
{
Q_OBJECT
public:
- QQuickPathElement(QObject *parent=0) : QObject(parent) {}
+ QQuickPathElement(QObject *parent=nullptr) : QObject(parent) {}
Q_SIGNALS:
void changed();
};
@@ -90,7 +90,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathAttribute : public QQuickPathElement
Q_PROPERTY(QString name READ name WRITE setName NOTIFY nameChanged)
Q_PROPERTY(qreal value READ value WRITE setValue NOTIFY valueChanged)
public:
- QQuickPathAttribute(QObject *parent=0) : QQuickPathElement(parent), _value(0) {}
+ QQuickPathAttribute(QObject *parent=nullptr) : QQuickPathElement(parent) {}
QString name() const;
@@ -105,7 +105,7 @@ Q_SIGNALS:
private:
QString _name;
- qreal _value;
+ qreal _value = 0;
};
class Q_QUICK_PRIVATE_EXPORT QQuickCurve : public QQuickPathElement
@@ -117,7 +117,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickCurve : public QQuickPathElement
Q_PROPERTY(qreal relativeX READ relativeX WRITE setRelativeX NOTIFY relativeXChanged)
Q_PROPERTY(qreal relativeY READ relativeY WRITE setRelativeY NOTIFY relativeYChanged)
public:
- QQuickCurve(QObject *parent=0) : QQuickPathElement(parent) {}
+ QQuickCurve(QObject *parent=nullptr) : QQuickPathElement(parent) {}
qreal x() const;
void setX(qreal x);
@@ -154,7 +154,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathLine : public QQuickCurve
{
Q_OBJECT
public:
- QQuickPathLine(QObject *parent=0) : QQuickCurve(parent) {}
+ QQuickPathLine(QObject *parent=nullptr) : QQuickCurve(parent) {}
void addToPath(QPainterPath &path, const QQuickPathData &) override;
};
@@ -163,7 +163,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathMove : public QQuickCurve
{
Q_OBJECT
public:
- QQuickPathMove(QObject *parent=0) : QQuickCurve(parent) {}
+ QQuickPathMove(QObject *parent=nullptr) : QQuickCurve(parent) {}
void addToPath(QPainterPath &path, const QQuickPathData &) override;
};
@@ -177,7 +177,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathQuad : public QQuickCurve
Q_PROPERTY(qreal relativeControlX READ relativeControlX WRITE setRelativeControlX NOTIFY relativeControlXChanged)
Q_PROPERTY(qreal relativeControlY READ relativeControlY WRITE setRelativeControlY NOTIFY relativeControlYChanged)
public:
- QQuickPathQuad(QObject *parent=0) : QQuickCurve(parent), _controlX(0), _controlY(0) {}
+ QQuickPathQuad(QObject *parent=nullptr) : QQuickCurve(parent) {}
qreal controlX() const;
void setControlX(qreal x);
@@ -202,8 +202,8 @@ Q_SIGNALS:
void relativeControlYChanged();
private:
- qreal _controlX;
- qreal _controlY;
+ qreal _controlX = 0;
+ qreal _controlY = 0;
QQmlNullableValue<qreal> _relativeControlX;
QQmlNullableValue<qreal> _relativeControlY;
};
@@ -221,7 +221,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathCubic : public QQuickCurve
Q_PROPERTY(qreal relativeControl2X READ relativeControl2X WRITE setRelativeControl2X NOTIFY relativeControl2XChanged)
Q_PROPERTY(qreal relativeControl2Y READ relativeControl2Y WRITE setRelativeControl2Y NOTIFY relativeControl2YChanged)
public:
- QQuickPathCubic(QObject *parent=0) : QQuickCurve(parent), _control1X(0), _control1Y(0), _control2X(0), _control2Y(0) {}
+ QQuickPathCubic(QObject *parent=nullptr) : QQuickCurve(parent) {}
qreal control1X() const;
void setControl1X(qreal x);
@@ -264,10 +264,10 @@ Q_SIGNALS:
void relativeControl2YChanged();
private:
- qreal _control1X;
- qreal _control1Y;
- qreal _control2X;
- qreal _control2Y;
+ qreal _control1X = 0;
+ qreal _control1Y = 0;
+ qreal _control2X = 0;
+ qreal _control2Y = 0;
QQmlNullableValue<qreal> _relativeControl1X;
QQmlNullableValue<qreal> _relativeControl1Y;
QQmlNullableValue<qreal> _relativeControl2X;
@@ -278,7 +278,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathCatmullRomCurve : public QQuickCurve
{
Q_OBJECT
public:
- QQuickPathCatmullRomCurve(QObject *parent=0) : QQuickCurve(parent) {}
+ QQuickPathCatmullRomCurve(QObject *parent=nullptr) : QQuickCurve(parent) {}
void addToPath(QPainterPath &path, const QQuickPathData &) override;
};
@@ -293,8 +293,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathArc : public QQuickCurve
Q_PROPERTY(qreal xAxisRotation READ xAxisRotation WRITE setXAxisRotation NOTIFY xAxisRotationChanged REVISION 2)
public:
- QQuickPathArc(QObject *parent=0)
- : QQuickCurve(parent), _radiusX(0), _radiusY(0), _useLargeArc(false), _direction(Clockwise), _xAxisRotation(0) {}
+ QQuickPathArc(QObject *parent=nullptr)
+ : QQuickCurve(parent) {}
enum ArcDirection { Clockwise, Counterclockwise };
Q_ENUM(ArcDirection)
@@ -324,11 +324,11 @@ Q_SIGNALS:
Q_REVISION(2) void xAxisRotationChanged();
private:
- qreal _radiusX;
- qreal _radiusY;
- bool _useLargeArc;
- ArcDirection _direction;
- qreal _xAxisRotation;
+ qreal _radiusX = 0;
+ qreal _radiusY = 0;
+ bool _useLargeArc = false;
+ ArcDirection _direction = Clockwise;
+ qreal _xAxisRotation = 0;
};
class Q_QUICK_PRIVATE_EXPORT QQuickPathAngleArc : public QQuickCurve
@@ -343,8 +343,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathAngleArc : public QQuickCurve
Q_PROPERTY(bool moveToStart READ moveToStart WRITE setMoveToStart NOTIFY moveToStartChanged)
public:
- QQuickPathAngleArc(QObject *parent=0)
- : QQuickCurve(parent), _centerX(0), _centerY(0), _radiusX(0), _radiusY(0), _startAngle(0), _sweepAngle(0), _moveToStart(true) {}
+ QQuickPathAngleArc(QObject *parent=nullptr)
+ : QQuickCurve(parent) {}
qreal centerX() const;
void setCenterX(qreal);
@@ -379,13 +379,13 @@ Q_SIGNALS:
void moveToStartChanged();
private:
- qreal _centerX;
- qreal _centerY;
- qreal _radiusX;
- qreal _radiusY;
- qreal _startAngle;
- qreal _sweepAngle;
- bool _moveToStart;
+ qreal _centerX = 0;
+ qreal _centerY = 0;
+ qreal _radiusX = 0;
+ qreal _radiusY = 0;
+ qreal _startAngle = 0;
+ qreal _sweepAngle = 0;
+ bool _moveToStart = true;
};
class Q_QUICK_PRIVATE_EXPORT QQuickPathSvg : public QQuickCurve
@@ -393,7 +393,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathSvg : public QQuickCurve
Q_OBJECT
Q_PROPERTY(QString path READ path WRITE setPath NOTIFY pathChanged)
public:
- QQuickPathSvg(QObject *parent=0) : QQuickCurve(parent) {}
+ QQuickPathSvg(QObject *parent=nullptr) : QQuickCurve(parent) {}
QString path() const;
void setPath(const QString &path);
@@ -412,7 +412,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPathPercent : public QQuickPathElement
Q_OBJECT
Q_PROPERTY(qreal value READ value WRITE setValue NOTIFY valueChanged)
public:
- QQuickPathPercent(QObject *parent=0) : QQuickPathElement(parent), _value(0) {}
+ QQuickPathPercent(QObject *parent=nullptr) : QQuickPathElement(parent) {}
qreal value() const;
void setValue(qreal value);
@@ -421,18 +421,18 @@ Q_SIGNALS:
void valueChanged();
private:
- qreal _value;
+ qreal _value = 0;
};
struct QQuickCachedBezier
{
- QQuickCachedBezier() : isValid(false) {}
+ QQuickCachedBezier() {}
QBezier bezier;
int element;
qreal bezLength;
qreal currLength;
qreal p;
- bool isValid;
+ bool isValid = false;
};
class QQuickPathPrivate;
@@ -448,8 +448,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPath : public QObject, public QQmlParserStatu
Q_CLASSINFO("DefaultProperty", "pathElements")
Q_INTERFACES(QQmlParserStatus)
public:
- QQuickPath(QObject *parent=0);
- ~QQuickPath();
+ QQuickPath(QObject *parent=nullptr);
+ ~QQuickPath() override;
QQmlListProperty<QQuickPathElement> pathElements();
@@ -467,7 +467,7 @@ public:
QStringList attributes() const;
qreal attributeAt(const QString &, qreal) const;
QPointF pointAt(qreal) const;
- QPointF sequentialPointAt(qreal p, qreal *angle = 0) const;
+ QPointF sequentialPointAt(qreal p, qreal *angle = nullptr) const;
void invalidateSequentialHistory() const;
Q_SIGNALS:
@@ -494,15 +494,15 @@ private Q_SLOTS:
private:
struct AttributePoint {
- AttributePoint() : percent(0), scale(1), origpercent(0) {}
+ AttributePoint() {}
AttributePoint(const AttributePoint &other)
: percent(other.percent), scale(other.scale), origpercent(other.origpercent), values(other.values) {}
AttributePoint &operator=(const AttributePoint &other) {
percent = other.percent; scale = other.scale; origpercent = other.origpercent; values = other.values; return *this;
}
- qreal percent; //massaged percent along the painter path
- qreal scale;
- qreal origpercent; //'real' percent along the painter path
+ qreal percent = 0; //massaged percent along the painter path
+ qreal scale = 1;
+ qreal origpercent = 0; //'real' percent along the painter path
QHash<QString, qreal> values;
};
@@ -512,8 +512,8 @@ private:
static void interpolate(QList<AttributePoint> &points, int idx, const QString &name, qreal value);
static void endpoint(QList<AttributePoint> &attributePoints, const QString &name);
- static QPointF forwardsPointAt(const QPainterPath &path, const qreal &pathLength, const QList<AttributePoint> &attributePoints, QQuickCachedBezier &prevBez, qreal p, qreal *angle = 0);
- static QPointF backwardsPointAt(const QPainterPath &path, const qreal &pathLength, const QList<AttributePoint> &attributePoints, QQuickCachedBezier &prevBez, qreal p, qreal *angle = 0);
+ static QPointF forwardsPointAt(const QPainterPath &path, const qreal &pathLength, const QList<AttributePoint> &attributePoints, QQuickCachedBezier &prevBez, qreal p, qreal *angle = nullptr);
+ static QPointF backwardsPointAt(const QPainterPath &path, const qreal &pathLength, const QList<AttributePoint> &attributePoints, QQuickCachedBezier &prevBez, qreal p, qreal *angle = nullptr);
private:
Q_DISABLE_COPY(QQuickPath)
@@ -521,8 +521,9 @@ private:
friend class QQuickPathAnimationUpdater;
public:
- QPainterPath createPath(const QPointF &startPoint, const QPointF &endPoint, const QStringList &attributes, qreal &pathLength, QList<AttributePoint> &attributePoints, bool *closed = 0);
- static QPointF sequentialPointAt(const QPainterPath &path, const qreal &pathLength, const QList<AttributePoint> &attributePoints, QQuickCachedBezier &prevBez, qreal p, qreal *angle = 0);
+ QPainterPath createPath(const QPointF &startPoint, const QPointF &endPoint, const QStringList &attributes, qreal &pathLength, QList<AttributePoint> &attributePoints, bool *closed = nullptr);
+ QPainterPath createShapePath(const QPointF &startPoint, const QPointF &endPoint, qreal &pathLength, bool *closed = nullptr);
+ static QPointF sequentialPointAt(const QPainterPath &path, const qreal &pathLength, const QList<AttributePoint> &attributePoints, QQuickCachedBezier &prevBez, qreal p, qreal *angle = nullptr);
};
QT_END_NAMESPACE
diff --git a/src/quick/util/qquickpath_p_p.h b/src/quick/util/qquickpath_p_p.h
index 8ce85dbf0f..9735d51264 100644
--- a/src/quick/util/qquickpath_p_p.h
+++ b/src/quick/util/qquickpath_p_p.h
@@ -72,7 +72,7 @@ public:
static QQuickPathPrivate* get(QQuickPath *path) { return path->d_func(); }
static const QQuickPathPrivate* get(const QQuickPath *path) { return path->d_func(); }
- QQuickPathPrivate() : pathLength(0), closed(false), componentComplete(true) { }
+ QQuickPathPrivate() {}
QPainterPath _path;
QList<QQuickPathElement*> _pathElements;
@@ -83,9 +83,10 @@ public:
mutable QQuickCachedBezier prevBez;
QQmlNullableValue<qreal> startX;
QQmlNullableValue<qreal> startY;
- qreal pathLength;
- bool closed;
- bool componentComplete;
+ qreal pathLength = 0;
+ bool closed = false;
+ bool componentComplete = true;
+ bool isShapePath = false;
};
QT_END_NAMESPACE
diff --git a/src/quick/util/qquickpathinterpolator.cpp b/src/quick/util/qquickpathinterpolator.cpp
index 838213042e..bb47ca0205 100644
--- a/src/quick/util/qquickpathinterpolator.cpp
+++ b/src/quick/util/qquickpathinterpolator.cpp
@@ -59,7 +59,7 @@ QT_BEGIN_NAMESPACE
*/
QQuickPathInterpolator::QQuickPathInterpolator(QObject *parent) :
- QObject(parent), _path(0), _x(0), _y(0), _angle(0), _progress(0)
+ QObject(parent), _path(nullptr), _x(0), _y(0), _angle(0), _progress(0)
{
}
diff --git a/src/quick/util/qquickpathinterpolator_p.h b/src/quick/util/qquickpathinterpolator_p.h
index 0fdb1a444f..60a9ff2e22 100644
--- a/src/quick/util/qquickpathinterpolator_p.h
+++ b/src/quick/util/qquickpathinterpolator_p.h
@@ -70,7 +70,7 @@ class Q_AUTOTEST_EXPORT QQuickPathInterpolator : public QObject
Q_PROPERTY(qreal y READ y NOTIFY yChanged)
Q_PROPERTY(qreal angle READ angle NOTIFY angleChanged)
public:
- explicit QQuickPathInterpolator(QObject *parent = 0);
+ explicit QQuickPathInterpolator(QObject *parent = nullptr);
QQuickPath *path() const;
void setPath(QQuickPath *path);
diff --git a/src/quick/util/qquickpixmapcache.cpp b/src/quick/util/qquickpixmapcache.cpp
index e218b84fff..4237ec3edf 100644
--- a/src/quick/util/qquickpixmapcache.cpp
+++ b/src/quick/util/qquickpixmapcache.cpp
@@ -244,8 +244,8 @@ public:
: refCount(1), inCache(false), pixmapStatus(QQuickPixmap::Error),
url(u), errorString(e), requestSize(s),
providerOptions(po), appliedTransform(QQuickImageProviderOptions::UsePluginDefaultTransform),
- textureFactory(0), reply(0), prevUnreferenced(0),
- prevUnreferencedPtr(0), nextUnreferenced(0)
+ textureFactory(nullptr), reply(nullptr), prevUnreferenced(nullptr),
+ prevUnreferencedPtr(nullptr), nextUnreferenced(nullptr)
{
declarativePixmaps.insert(pixmap);
}
@@ -254,8 +254,8 @@ public:
: refCount(1), inCache(false), pixmapStatus(QQuickPixmap::Loading),
url(u), requestSize(r),
providerOptions(po), appliedTransform(aTransform),
- textureFactory(0), reply(0), prevUnreferenced(0), prevUnreferencedPtr(0),
- nextUnreferenced(0)
+ textureFactory(nullptr), reply(nullptr), prevUnreferenced(nullptr), prevUnreferencedPtr(nullptr),
+ nextUnreferenced(nullptr)
{
declarativePixmaps.insert(pixmap);
}
@@ -265,8 +265,8 @@ public:
: refCount(1), inCache(false), pixmapStatus(QQuickPixmap::Ready),
url(u), implicitSize(s), requestSize(r),
providerOptions(po), appliedTransform(aTransform),
- textureFactory(texture), reply(0), prevUnreferenced(0),
- prevUnreferencedPtr(0), nextUnreferenced(0)
+ textureFactory(texture), reply(nullptr), prevUnreferenced(nullptr),
+ prevUnreferencedPtr(nullptr), nextUnreferenced(nullptr)
{
declarativePixmaps.insert(pixmap);
}
@@ -274,8 +274,8 @@ public:
QQuickPixmapData(QQuickPixmap *pixmap, QQuickTextureFactory *texture)
: refCount(1), inCache(false), pixmapStatus(QQuickPixmap::Ready),
appliedTransform(QQuickImageProviderOptions::UsePluginDefaultTransform),
- textureFactory(texture), reply(0), prevUnreferenced(0),
- prevUnreferencedPtr(0), nextUnreferenced(0)
+ textureFactory(texture), reply(nullptr), prevUnreferenced(nullptr),
+ prevUnreferencedPtr(nullptr), nextUnreferenced(nullptr)
{
if (texture)
requestSize = implicitSize = texture->textureSize();
@@ -287,7 +287,7 @@ public:
while (!declarativePixmaps.isEmpty()) {
QQuickPixmap *referencer = declarativePixmaps.first();
declarativePixmaps.remove(referencer);
- referencer->d = 0;
+ referencer->d = nullptr;
}
delete textureFactory;
}
@@ -414,10 +414,54 @@ static bool readImage(const QUrl& url, QIODevice *dev, QImage *image, QString *e
}
}
+static QStringList fromLatin1List(const QList<QByteArray> &list)
+{
+ QStringList res;
+ res.reserve(list.size());
+ for (const QByteArray &item : list)
+ res.append(QString::fromLatin1(item));
+ return res;
+}
+
+class BackendSupport
+{
+public:
+ BackendSupport()
+ {
+ delete QSGContext::createTextureFactoryFromImage(QImage()); // Force init of backend data
+ hasOpenGL = QQuickWindow::sceneGraphBackend().isEmpty(); // i.e. default
+ QList<QByteArray> list;
+ if (hasOpenGL)
+ list.append(QSGTextureReader::supportedFileFormats());
+ list.append(QImageReader::supportedImageFormats());
+ fileSuffixes = fromLatin1List(list);
+ }
+ bool hasOpenGL;
+ QStringList fileSuffixes;
+};
+Q_GLOBAL_STATIC(BackendSupport, backendSupport);
+
+static QString existingImageFileForPath(const QString &localFile)
+{
+ // Do nothing if given filepath exists or already has a suffix
+ QFileInfo fi(localFile);
+ if (!fi.suffix().isEmpty() || fi.exists())
+ return localFile;
+
+ QString tryFile = localFile + QStringLiteral(".xxxx");
+ const int suffixIdx = localFile.length() + 1;
+ for (const QString &suffix : backendSupport()->fileSuffixes) {
+ tryFile.replace(suffixIdx, 10, suffix);
+ if (QFileInfo::exists(tryFile))
+ return tryFile;
+ }
+ return localFile;
+}
+
QQuickPixmapReader::QQuickPixmapReader(QQmlEngine *eng)
-: QThread(eng), engine(eng), threadObject(0)
+: QThread(eng), engine(eng), threadObject(nullptr)
#if QT_CONFIG(qml_network)
-, accessManager(0)
+, accessManager(nullptr)
#endif
{
eventLoopQuitHack = new QObject;
@@ -436,7 +480,7 @@ QQuickPixmapReader::~QQuickPixmapReader()
// manually cancel all outstanding jobs.
for (QQuickPixmapReply *reply : qAsConst(jobs)) {
if (reply->data && reply->data->reply == reply)
- reply->data->reply = 0;
+ reply->data->reply = nullptr;
delete reply;
}
jobs.clear();
@@ -445,7 +489,7 @@ QQuickPixmapReader::~QQuickPixmapReader()
const auto cancelJob = [this](QQuickPixmapReply *reply) {
if (reply->loading) {
cancelled.append(reply);
- reply->data = 0;
+ reply->data = nullptr;
}
};
@@ -519,7 +563,7 @@ void QQuickPixmapReader::asyncResponseFinished(QQuickImageResponse *response)
QQuickPixmapReply *job = asyncResponses.take(response);
if (job) {
- QQuickTextureFactory *t = 0;
+ QQuickTextureFactory *t = nullptr;
QQuickPixmapReply::ReadError error = QQuickPixmapReply::NoError;
QString errorString;
if (!response->errorString().isEmpty()) {
@@ -618,7 +662,7 @@ void QQuickPixmapReader::processJobs()
const QUrl url = job->url;
QString localFile;
QQuickImageProvider::ImageType imageType = QQuickImageProvider::Invalid;
- QQuickImageProvider *provider = 0;
+ QQuickImageProvider *provider = nullptr;
if (url.scheme() == QLatin1String("image")) {
provider = static_cast<QQuickImageProvider *>(engine->imageProvider(imageProviderId(url)));
@@ -667,7 +711,7 @@ void QQuickPixmapReader::processJob(QQuickPixmapReply *runningJob, const QUrl &u
QString errorStr = QQuickPixmap::tr("Invalid image provider: %1").arg(url.toString());
mutex.lock();
if (!cancelled.contains(runningJob))
- runningJob->postReply(QQuickPixmapReply::Loading, errorStr, readSize, 0);
+ runningJob->postReply(QQuickPixmapReply::Loading, errorStr, readSize, nullptr);
mutex.unlock();
return;
}
@@ -769,18 +813,18 @@ void QQuickPixmapReader::processJob(QQuickPixmapReply *runningJob, const QUrl &u
QImage image;
QQuickPixmapReply::ReadError errorCode = QQuickPixmapReply::NoError;
QString errorStr;
- QFile f(localFile);
+ QFile f(existingImageFileForPath(localFile));
QSize readSize;
if (f.open(QIODevice::ReadOnly)) {
-
- // for now, purely use suffix information to determine whether we are working with a compressed texture
- QByteArray suffix = QFileInfo(f).suffix().toLower().toLatin1();
- if (QSGTextureReader::isTexture(&f, suffix)) {
- QQuickTextureFactory *factory = QSGTextureReader::read(&f, suffix);
+ QSGTextureReader texReader(&f, localFile);
+ if (backendSupport()->hasOpenGL && texReader.isTexture()) {
+ QQuickTextureFactory *factory = texReader.read();
if (factory) {
readSize = factory->textureSize();
} else {
errorStr = QQuickPixmap::tr("Error decoding: %1").arg(url.toString());
+ if (f.fileName() != localFile)
+ errorStr += QString::fromLatin1(" (%1)").arg(f.fileName());
errorCode = QQuickPixmapReply::Decoding;
}
mutex.lock();
@@ -789,8 +833,11 @@ void QQuickPixmapReader::processJob(QQuickPixmapReply *runningJob, const QUrl &u
mutex.unlock();
return;
} else {
- if (!readImage(url, &f, &image, &errorStr, &readSize, runningJob->requestSize, runningJob->providerOptions))
+ if (!readImage(url, &f, &image, &errorStr, &readSize, runningJob->requestSize, runningJob->providerOptions)) {
errorCode = QQuickPixmapReply::Loading;
+ if (f.fileName() != localFile)
+ errorStr += QString::fromLatin1(" (%1)").arg(f.fileName());
+ }
}
} else {
errorStr = QQuickPixmap::tr("Cannot open: %1").arg(url.toString());
@@ -853,7 +900,7 @@ void QQuickPixmapReader::cancel(QQuickPixmapReply *reply)
mutex.lock();
if (reply->loading) {
cancelled.append(reply);
- reply->data = 0;
+ reply->data = nullptr;
// XXX
if (threadObject) threadObject->processJobs();
} else {
@@ -887,7 +934,7 @@ void QQuickPixmapReader::run()
exec();
delete threadObject;
- threadObject = 0;
+ threadObject = nullptr;
}
class QQuickPixmapKey
@@ -940,7 +987,7 @@ Q_GLOBAL_STATIC(QQuickPixmapStore, pixmapStore);
QQuickPixmapStore::QQuickPixmapStore()
- : m_unreferencedPixmaps(0), m_lastUnreferencedPixmap(0), m_unreferencedCost(0), m_timerId(-1), m_destroying(false)
+ : m_unreferencedPixmaps(nullptr), m_lastUnreferencedPixmap(nullptr), m_unreferencedCost(0), m_timerId(-1), m_destroying(false)
{
}
@@ -983,9 +1030,9 @@ QQuickPixmapStore::~QQuickPixmapStore()
void QQuickPixmapStore::unreferencePixmap(QQuickPixmapData *data)
{
- Q_ASSERT(data->prevUnreferenced == 0);
- Q_ASSERT(data->prevUnreferencedPtr == 0);
- Q_ASSERT(data->nextUnreferenced == 0);
+ Q_ASSERT(data->prevUnreferenced == nullptr);
+ Q_ASSERT(data->prevUnreferencedPtr == nullptr);
+ Q_ASSERT(data->nextUnreferenced == nullptr);
data->nextUnreferenced = m_unreferencedPixmaps;
data->prevUnreferencedPtr = &m_unreferencedPixmaps;
@@ -1021,9 +1068,9 @@ void QQuickPixmapStore::referencePixmap(QQuickPixmapData *data)
if (m_lastUnreferencedPixmap == data)
m_lastUnreferencedPixmap = data->prevUnreferenced;
- data->nextUnreferenced = 0;
- data->prevUnreferencedPtr = 0;
- data->prevUnreferenced = 0;
+ data->nextUnreferenced = nullptr;
+ data->prevUnreferencedPtr = nullptr;
+ data->prevUnreferenced = nullptr;
m_unreferencedCost -= data->cost();
}
@@ -1032,12 +1079,12 @@ void QQuickPixmapStore::shrinkCache(int remove)
{
while ((remove > 0 || m_unreferencedCost > cache_limit) && m_lastUnreferencedPixmap) {
QQuickPixmapData *data = m_lastUnreferencedPixmap;
- Q_ASSERT(data->nextUnreferenced == 0);
+ Q_ASSERT(data->nextUnreferenced == nullptr);
- *data->prevUnreferencedPtr = 0;
+ *data->prevUnreferencedPtr = nullptr;
m_lastUnreferencedPixmap = data->prevUnreferenced;
- data->prevUnreferencedPtr = 0;
- data->prevUnreferenced = 0;
+ data->prevUnreferencedPtr = nullptr;
+ data->prevUnreferenced = nullptr;
if (!m_destroying) {
remove -= data->cost();
@@ -1054,7 +1101,7 @@ void QQuickPixmapStore::timerEvent(QTimerEvent *)
shrinkCache(removalCost);
- if (m_unreferencedPixmaps == 0) {
+ if (m_unreferencedPixmaps == nullptr) {
killTimer(m_timerId);
m_timerId = -1;
}
@@ -1071,7 +1118,7 @@ void QQuickPixmap::purgeCache()
}
QQuickPixmapReply::QQuickPixmapReply(QQuickPixmapData *d)
-: data(d), engineForReader(0), requestSize(d->requestSize), url(d->url), loading(false), providerOptions(d->providerOptions), redirectCount(0)
+: data(d), engineForReader(nullptr), requestSize(d->requestSize), url(d->url), loading(false), providerOptions(d->providerOptions), redirectCount(0)
{
if (finishedIndex == -1) {
finishedIndex = QMetaMethod::fromSignal(&QQuickPixmapReply::finished).methodIndex();
@@ -1094,10 +1141,10 @@ bool QQuickPixmapReply::event(QEvent *event)
data->pixmapStatus = (de->error == NoError) ? QQuickPixmap::Ready : QQuickPixmap::Error;
if (data->pixmapStatus == QQuickPixmap::Ready) {
data->textureFactory = de->textureFactory;
- de->textureFactory = 0;
+ de->textureFactory = nullptr;
data->implicitSize = de->implicitSize;
PIXMAP_PROFILE(pixmapLoadingFinished(data->url,
- data->textureFactory != 0 && data->textureFactory->textureSize().isValid() ?
+ data->textureFactory != nullptr && data->textureFactory->textureSize().isValid() ?
data->textureFactory->textureSize() :
(data->requestSize.isValid() ? data->requestSize : data->implicitSize)));
} else {
@@ -1106,7 +1153,7 @@ bool QQuickPixmapReply::event(QEvent *event)
data->removeFromCache(); // We don't continue to cache error'd pixmaps
}
- data->reply = 0;
+ data->reply = nullptr;
emit finished();
} else {
PIXMAP_PROFILE(pixmapStateChanged<QQuickProfiler::PixmapLoadingError>(url));
@@ -1142,8 +1189,8 @@ void QQuickPixmapData::release()
if (refCount == 0) {
if (reply) {
QQuickPixmapReply *cancelReply = reply;
- reply->data = 0;
- reply = 0;
+ reply->data = nullptr;
+ reply = nullptr;
QQuickPixmapReader::readerMutex.lock();
QQuickPixmapReader *reader = QQuickPixmapReader::existingInstance(cancelReply->engineForReader);
if (reader)
@@ -1245,22 +1292,23 @@ static QQuickPixmapData* createPixmapDataSync(QQuickPixmap *declarativePixmap, Q
QString localFile = QQmlFile::urlToLocalFileOrQrc(url);
if (localFile.isEmpty())
- return 0;
+ return nullptr;
- QFile f(localFile);
+ QFile f(existingImageFileForPath(localFile));
QSize readSize;
QString errorString;
if (f.open(QIODevice::ReadOnly)) {
- // for now, purely use suffix information to determine whether we are working with a compressed texture
- QByteArray suffix = QFileInfo(f).suffix().toLower().toLatin1();
- if (QSGTextureReader::isTexture(&f, suffix)) {
- QQuickTextureFactory *factory = QSGTextureReader::read(&f, suffix);
+ QSGTextureReader texReader(&f, localFile);
+ if (backendSupport()->hasOpenGL && texReader.isTexture()) {
+ QQuickTextureFactory *factory = texReader.read();
if (factory) {
*ok = true;
- return new QQuickPixmapData(declarativePixmap, factory);
+ return new QQuickPixmapData(declarativePixmap, url, factory, factory->textureSize(), requestSize, providerOptions, QQuickImageProviderOptions::UsePluginDefaultTransform);
} else {
errorString = QQuickPixmap::tr("Error decoding: %1").arg(url.toString());
+ if (f.fileName() != localFile)
+ errorString += QString::fromLatin1(" (%1)").arg(f.fileName());
}
} else {
QImage image;
@@ -1268,6 +1316,8 @@ static QQuickPixmapData* createPixmapDataSync(QQuickPixmap *declarativePixmap, Q
if (readImage(url, &f, &image, &errorString, &readSize, requestSize, providerOptions, &appliedTransform)) {
*ok = true;
return new QQuickPixmapData(declarativePixmap, url, QQuickTextureFactory::textureFactoryForImage(image), readSize, requestSize, providerOptions, appliedTransform);
+ } else if (f.fileName() != localFile) {
+ errorString += QString::fromLatin1(" (%1)").arg(f.fileName());
}
}
} else {
@@ -1284,18 +1334,18 @@ struct QQuickPixmapNull {
Q_GLOBAL_STATIC(QQuickPixmapNull, nullPixmap);
QQuickPixmap::QQuickPixmap()
-: d(0)
+: d(nullptr)
{
}
QQuickPixmap::QQuickPixmap(QQmlEngine *engine, const QUrl &url)
-: d(0)
+: d(nullptr)
{
load(engine, url);
}
QQuickPixmap::QQuickPixmap(QQmlEngine *engine, const QUrl &url, const QSize &size)
-: d(0)
+: d(nullptr)
{
load(engine, url, size);
}
@@ -1311,13 +1361,13 @@ QQuickPixmap::~QQuickPixmap()
if (d) {
d->declarativePixmaps.remove(this);
d->release();
- d = 0;
+ d = nullptr;
}
}
bool QQuickPixmap::isNull() const
{
- return d == 0;
+ return d == nullptr;
}
bool QQuickPixmap::isReady() const
@@ -1388,7 +1438,7 @@ QQuickTextureFactory *QQuickPixmap::textureFactory() const
if (d)
return d->textureFactory;
- return 0;
+ return nullptr;
}
QImage QQuickPixmap::image() const
@@ -1466,7 +1516,7 @@ void QQuickPixmap::load(QQmlEngine *engine, const QUrl &url, const QSize &reques
if (d) {
d->declarativePixmaps.remove(this);
d->release();
- d = 0;
+ d = nullptr;
}
QQuickPixmapKey key = { &url, &requestSize, providerOptions };
@@ -1538,7 +1588,7 @@ void QQuickPixmap::clear()
if (d) {
d->declarativePixmaps.remove(this);
d->release();
- d = 0;
+ d = nullptr;
}
}
@@ -1546,10 +1596,10 @@ void QQuickPixmap::clear(QObject *obj)
{
if (d) {
if (d->reply)
- QObject::disconnect(d->reply, 0, obj, 0);
+ QObject::disconnect(d->reply, nullptr, obj, nullptr);
d->declarativePixmaps.remove(this);
d->release();
- d = 0;
+ d = nullptr;
}
}
diff --git a/src/quick/util/qquickprofiler.cpp b/src/quick/util/qquickprofiler.cpp
index 402cd44ff0..bd9f04e562 100644
--- a/src/quick/util/qquickprofiler.cpp
+++ b/src/quick/util/qquickprofiler.cpp
@@ -47,12 +47,12 @@
QT_BEGIN_NAMESPACE
// instance will be set, unset in constructor. Allows static methods to be inlined.
-QQuickProfiler *QQuickProfiler::s_instance = 0;
+QQuickProfiler *QQuickProfiler::s_instance = nullptr;
quint64 QQuickProfiler::featuresEnabled = 0;
void QQuickProfiler::initialize(QObject *parent)
{
- Q_ASSERT(s_instance == 0);
+ Q_ASSERT(s_instance == nullptr);
s_instance = new QQuickProfiler(parent);
}
@@ -99,7 +99,7 @@ QQuickProfiler::~QQuickProfiler()
{
QMutexLocker lock(&m_dataMutex);
featuresEnabled = 0;
- s_instance = 0;
+ s_instance = nullptr;
}
void QQuickProfiler::startProfilingImpl(quint64 features)
diff --git a/src/quick/util/qquickprofiler_p.h b/src/quick/util/qquickprofiler_p.h
index 38027a6abf..d699ddf371 100644
--- a/src/quick/util/qquickprofiler_p.h
+++ b/src/quick/util/qquickprofiler_p.h
@@ -333,7 +333,7 @@ public:
static void initialize(QObject *parent);
- virtual ~QQuickProfiler();
+ ~QQuickProfiler() override;
signals:
void dataReady(const QVector<QQuickProfilerData> &data);
diff --git a/src/quick/util/qquickpropertychanges.cpp b/src/quick/util/qquickpropertychanges.cpp
index 4a9b4a95c1..a3a598621f 100644
--- a/src/quick/util/qquickpropertychanges.cpp
+++ b/src/quick/util/qquickpropertychanges.cpp
@@ -213,13 +213,15 @@ public:
class ExpressionChange {
public:
ExpressionChange(const QString &_name,
+ const QV4::CompiledData::Binding *_binding,
QQmlBinding::Identifier _id,
const QString& _expr,
const QUrl &_url,
int _line,
int _column)
- : name(_name), id(_id), expression(_expr), url(_url), line(_line), column(_column) {}
+ : name(_name), binding(_binding), id(_id), expression(_expr), url(_url), line(_line), column(_column) {}
QString name;
+ const QV4::CompiledData::Binding *binding;
QQmlBinding::Identifier id;
QString expression;
QUrl url;
@@ -281,19 +283,22 @@ void QQuickPropertyChangesPrivate::decodeBinding(const QString &propertyPrefix,
return;
}
- QQmlProperty prop = property(propertyName); //### better way to check for signal property?
-
- if (prop.type() & QQmlProperty::SignalProperty) {
- QQuickReplaceSignalHandler *handler = new QQuickReplaceSignalHandler;
- handler->property = prop;
- handler->expression.take(new QQmlBoundSignalExpression(object, QQmlPropertyPrivate::get(prop)->signalIndex(),
- QQmlContextData::get(qmlContext(q)), object, compilationUnit->runtimeFunctions.at(binding->value.compiledScriptIndex)));
- signalReplacements << handler;
- return;
+ if (propertyName.count() >= 3 &&
+ propertyName.at(0) == QLatin1Char('o') &&
+ propertyName.at(1) == QLatin1Char('n') &&
+ propertyName.at(2).isUpper()) {
+ QQmlProperty prop = property(propertyName);
+ if (prop.isSignalProperty()) {
+ QQuickReplaceSignalHandler *handler = new QQuickReplaceSignalHandler;
+ handler->property = prop;
+ handler->expression.take(new QQmlBoundSignalExpression(object, QQmlPropertyPrivate::get(prop)->signalIndex(),
+ QQmlContextData::get(qmlContext(q)), object, compilationUnit->runtimeFunctions.at(binding->value.compiledScriptIndex)));
+ signalReplacements << handler;
+ return;
+ }
}
- if (binding->type == QV4::CompiledData::Binding::Type_Script) {
- QString expression = binding->valueAsString(qmlUnit);
+ if (binding->type == QV4::CompiledData::Binding::Type_Script || binding->containsTranslations()) {
QUrl url = QUrl();
int line = -1;
int column = -1;
@@ -305,16 +310,23 @@ void QQuickPropertyChangesPrivate::decodeBinding(const QString &propertyPrefix,
column = ddata->columnNumber;
}
- expressions << ExpressionChange(propertyName, binding->value.compiledScriptIndex, expression, url, line, column);
+ QString expression;
+ QQmlBinding::Identifier id = QQmlBinding::Invalid;
+
+ if (!binding->containsTranslations()) {
+ expression = binding->valueAsString(qmlUnit);
+ id = binding->value.compiledScriptIndex;
+ }
+ expressions << ExpressionChange(propertyName, binding, id, expression, url, line, column);
return;
}
QVariant var;
switch (binding->type) {
case QV4::CompiledData::Binding::Type_Script:
- Q_UNREACHABLE();
case QV4::CompiledData::Binding::Type_Translation:
case QV4::CompiledData::Binding::Type_TranslationById:
+ Q_UNREACHABLE();
case QV4::CompiledData::Binding::Type_String:
var = binding->valueAsString(qmlUnit);
break;
@@ -395,7 +407,10 @@ QQmlProperty
QQuickPropertyChangesPrivate::property(const QString &property)
{
Q_Q(QQuickPropertyChanges);
- QQmlProperty prop(object, property, qmlContext(q));
+ QQmlContextData *context = nullptr;
+ if (QQmlData *ddata = QQmlData::get(q))
+ context = ddata->outerContext;
+ QQmlProperty prop = QQmlPropertyPrivate::create(object, property, context);
if (!prop.isValid()) {
qmlWarning(q) << QQuickPropertyChanges::tr("Cannot assign to non-existent property \"%1\"").arg(property);
return QQmlProperty();
@@ -415,9 +430,10 @@ QQuickPropertyChanges::ActionList QQuickPropertyChanges::actions()
ActionList list;
for (int ii = 0; ii < d->properties.count(); ++ii) {
+ QQmlProperty prop = d->property(d->properties.at(ii).first);
- QQuickStateAction a(d->object, d->properties.at(ii).first,
- qmlContext(this), d->properties.at(ii).second);
+ QQuickStateAction a(d->object, prop, d->properties.at(ii).first,
+ d->properties.at(ii).second);
if (a.property.isValid()) {
a.restore = restoreEntryValues();
@@ -426,7 +442,6 @@ QQuickPropertyChanges::ActionList QQuickPropertyChanges::actions()
}
for (int ii = 0; ii < d->signalReplacements.count(); ++ii) {
-
QQuickReplaceSignalHandler *handler = d->signalReplacements.at(ii);
if (handler->property.isValid()) {
@@ -452,14 +467,15 @@ QQuickPropertyChanges::ActionList QQuickPropertyChanges::actions()
QQmlContextData *context = QQmlContextData::get(qmlContext(this));
- QQmlBinding *newBinding = 0;
- if (e.id != QQmlBinding::Invalid) {
- QV4::Scope scope(QQmlEnginePrivate::getV4Engine(qmlEngine(this)));
+ QQmlBinding *newBinding = nullptr;
+ if (e.binding && e.binding->containsTranslations()) {
+ newBinding = QQmlBinding::createTranslationBinding(d->compilationUnit, e.binding, object(), context);
+ } else if (e.id != QQmlBinding::Invalid) {
+ QV4::Scope scope(qmlEngine(this)->handle());
QV4::Scoped<QV4::QmlContext> qmlContext(scope, QV4::QmlContext::create(scope.engine->rootContext(), context, object()));
newBinding = QQmlBinding::create(&QQmlPropertyPrivate::get(prop)->core,
d->compilationUnit->runtimeFunctions.at(e.id), object(), context, qmlContext);
}
-// QQmlBinding *newBinding = e.id != QQmlBinding::Invalid ? QQmlBinding::createBinding(e.id, object(), qmlContext(this)) : 0;
if (!newBinding)
newBinding = QQmlBinding::create(&QQmlPropertyPrivate::get(prop)->core,
e.expression, object(), context, e.url.toString(), e.line);
@@ -638,7 +654,7 @@ void QQuickPropertyChanges::changeExpression(const QString &name, const QString
}
// adding a new expression.
- expressionIterator.insert(ExpressionEntry(name, QQmlBinding::Invalid, expression, QUrl(), -1, -1));
+ expressionIterator.insert(ExpressionEntry(name, nullptr, QQmlBinding::Invalid, expression, QUrl(), -1, -1));
if (state() && state()->isStateActive()) {
if (hadValue) {
diff --git a/src/quick/util/qquickshortcut.cpp b/src/quick/util/qquickshortcut.cpp
index 2fe4962b1a..78dc855326 100644
--- a/src/quick/util/qquickshortcut.cpp
+++ b/src/quick/util/qquickshortcut.cpp
@@ -41,6 +41,7 @@
#include <QtQuick/qquickitem.h>
#include <QtQuick/qquickwindow.h>
+#include <QtQuick/qquickrendercontrol.h>
#include <QtQuick/private/qtquickglobal_p.h>
#include <QtGui/private/qguiapplication_p.h>
@@ -102,6 +103,8 @@ static bool qQuickShortcutContextMatcher(QObject *obj, Qt::ShortcutContext conte
if (QQuickItem *item = qobject_cast<QQuickItem *>(obj))
obj = item->window();
}
+ if (QWindow *renderWindow = QQuickRenderControl::renderWindowFor(qobject_cast<QQuickWindow *>(obj)))
+ obj = renderWindow;
return obj && obj == QGuiApplication::focusWindow();
default:
return false;
@@ -119,7 +122,8 @@ Q_QUICK_PRIVATE_EXPORT ContextMatcher qt_quick_shortcut_context_matcher()
Q_QUICK_PRIVATE_EXPORT void qt_quick_set_shortcut_context_matcher(ContextMatcher matcher)
{
- *ctxMatcher() = matcher;
+ if (!ctxMatcher.isDestroyed())
+ *ctxMatcher() = matcher;
}
QT_BEGIN_NAMESPACE
diff --git a/src/quick/util/qquicksmoothedanimation_p.h b/src/quick/util/qquicksmoothedanimation_p.h
index 2f0e3bc0d8..7bceba387c 100644
--- a/src/quick/util/qquicksmoothedanimation_p.h
+++ b/src/quick/util/qquicksmoothedanimation_p.h
@@ -73,7 +73,7 @@ public:
enum ReversingMode { Eased, Immediate, Sync };
Q_ENUM(ReversingMode)
- QQuickSmoothedAnimation(QObject *parent = 0);
+ QQuickSmoothedAnimation(QObject *parent = nullptr);
~QQuickSmoothedAnimation();
ReversingMode reversingMode() const;
@@ -91,7 +91,7 @@ public:
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
Q_SIGNALS:
void velocityChanged();
void reversingModeChanged();
diff --git a/src/quick/util/qquicksmoothedanimation_p_p.h b/src/quick/util/qquicksmoothedanimation_p_p.h
index a415fdb55f..7850562594 100644
--- a/src/quick/util/qquicksmoothedanimation_p_p.h
+++ b/src/quick/util/qquicksmoothedanimation_p_p.h
@@ -65,7 +65,7 @@ class QSmoothedAnimationTimer : public QTimer
{
Q_OBJECT
public:
- explicit QSmoothedAnimationTimer(QSmoothedAnimation *animation, QObject *parent = 0);
+ explicit QSmoothedAnimationTimer(QSmoothedAnimation *animation, QObject *parent = nullptr);
~QSmoothedAnimationTimer();
public Q_SLOTS:
void stopAnimation();
@@ -78,7 +78,7 @@ class Q_AUTOTEST_EXPORT QSmoothedAnimation : public QAbstractAnimationJob
{
Q_DISABLE_COPY(QSmoothedAnimation)
public:
- QSmoothedAnimation(QQuickSmoothedAnimationPrivate * = 0);
+ QSmoothedAnimation(QQuickSmoothedAnimationPrivate * = nullptr);
~QSmoothedAnimation();
qreal to;
@@ -98,7 +98,7 @@ public:
void init();
void prepareForRestart();
- void clearTemplate() { animationTemplate = 0; }
+ void clearTemplate() { animationTemplate = nullptr; }
protected:
void updateCurrentTime(int) override;
diff --git a/src/quick/util/qquickspringanimation.cpp b/src/quick/util/qquickspringanimation.cpp
index bf844589ba..4389d941fd 100644
--- a/src/quick/util/qquickspringanimation.cpp
+++ b/src/quick/util/qquickspringanimation.cpp
@@ -58,7 +58,7 @@ class Q_AUTOTEST_EXPORT QSpringAnimation : public QAbstractAnimationJob
{
Q_DISABLE_COPY(QSpringAnimation)
public:
- QSpringAnimation(QQuickSpringAnimationPrivate * = 0);
+ QSpringAnimation(QQuickSpringAnimationPrivate * = nullptr);
~QSpringAnimation();
int duration() const override;
@@ -94,7 +94,7 @@ public:
typedef QHash<QQmlProperty, QSpringAnimation*> ActiveAnimationHash;
typedef ActiveAnimationHash::Iterator ActiveAnimationHashIt;
- void clearTemplate() { animationTemplate = 0; }
+ void clearTemplate() { animationTemplate = nullptr; }
protected:
void updateCurrentTime(int time) override;
diff --git a/src/quick/util/qquickspringanimation_p.h b/src/quick/util/qquickspringanimation_p.h
index ffb2c41e6b..2014a4311a 100644
--- a/src/quick/util/qquickspringanimation_p.h
+++ b/src/quick/util/qquickspringanimation_p.h
@@ -73,7 +73,7 @@ class Q_AUTOTEST_EXPORT QQuickSpringAnimation : public QQuickNumberAnimation
Q_PROPERTY(qreal mass READ mass WRITE setMass NOTIFY massChanged)
public:
- QQuickSpringAnimation(QObject *parent=0);
+ QQuickSpringAnimation(QObject *parent=nullptr);
~QQuickSpringAnimation();
qreal velocity() const;
@@ -97,7 +97,7 @@ public:
QAbstractAnimationJob* transition(QQuickStateActions &actions,
QQmlProperties &modified,
TransitionDirection direction,
- QObject *defaultTarget = 0) override;
+ QObject *defaultTarget = nullptr) override;
Q_SIGNALS:
void modulusChanged();
diff --git a/src/quick/util/qquickstate.cpp b/src/quick/util/qquickstate.cpp
index 65e51feb81..be8300f531 100644
--- a/src/quick/util/qquickstate.cpp
+++ b/src/quick/util/qquickstate.cpp
@@ -52,8 +52,8 @@ QT_BEGIN_NAMESPACE
DEFINE_BOOL_CONFIG_OPTION(stateChangeDebug, STATECHANGE_DEBUG);
QQuickStateAction::QQuickStateAction()
-: restore(true), actionDone(false), reverseEvent(false), deletableToBinding(false), fromBinding(0), event(0),
- specifiedObject(0)
+: restore(true), actionDone(false), reverseEvent(false), deletableToBinding(false), fromBinding(nullptr), event(nullptr),
+ specifiedObject(nullptr)
{
}
@@ -61,18 +61,17 @@ QQuickStateAction::QQuickStateAction(QObject *target, const QString &propertyNam
const QVariant &value)
: restore(true), actionDone(false), reverseEvent(false), deletableToBinding(false),
property(target, propertyName, qmlEngine(target)), toValue(value),
- fromBinding(0), event(0),
+ fromBinding(nullptr), event(nullptr),
specifiedObject(target), specifiedProperty(propertyName)
{
if (property.isValid())
fromValue = property.read();
}
-QQuickStateAction::QQuickStateAction(QObject *target, const QString &propertyName,
- QQmlContext *context, const QVariant &value)
+QQuickStateAction::QQuickStateAction(QObject *target, const QQmlProperty &property, const QString &propertyName, const QVariant &value)
: restore(true), actionDone(false), reverseEvent(false), deletableToBinding(false),
- property(target, propertyName, context), toValue(value),
- fromBinding(0), event(0),
+ property(property), toValue(value),
+ fromBinding(nullptr), event(nullptr),
specifiedObject(target), specifiedProperty(propertyName)
{
if (property.isValid())
@@ -193,7 +192,7 @@ bool QQuickState::isNamed() const
bool QQuickState::isWhenKnown() const
{
Q_D(const QQuickState);
- return d->when != 0;
+ return d->when != nullptr;
}
/*!
@@ -363,7 +362,7 @@ void QQuickStateAction::deleteFromBinding()
{
if (fromBinding) {
QQmlPropertyPrivate::removeBinding(property);
- fromBinding = 0;
+ fromBinding = nullptr;
}
}
@@ -531,7 +530,7 @@ QQmlAbstractBinding *QQuickState::bindingInRevertList(QObject *target, const QSt
}
}
- return 0;
+ return nullptr;
}
bool QQuickState::isStateActive() const
diff --git a/src/quick/util/qquickstate_p.h b/src/quick/util/qquickstate_p.h
index ac720f4189..79874ee78e 100644
--- a/src/quick/util/qquickstate_p.h
+++ b/src/quick/util/qquickstate_p.h
@@ -69,8 +69,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickStateAction
public:
QQuickStateAction();
QQuickStateAction(QObject *, const QString &, const QVariant &);
- QQuickStateAction(QObject *, const QString &,
- QQmlContext *, const QVariant &);
+ QQuickStateAction(QObject *, const QQmlProperty &property, const QString &,
+ const QVariant &);
bool restore:1;
bool actionDone:1;
@@ -126,7 +126,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickStateOperation : public QObject
{
Q_OBJECT
public:
- QQuickStateOperation(QObject *parent = 0)
+ QQuickStateOperation(QObject *parent = nullptr)
: QObject(parent) {}
typedef QList<QQuickStateAction> ActionList;
@@ -136,7 +136,7 @@ public:
void setState(QQuickState *state);
protected:
- QQuickStateOperation(QObjectPrivate &dd, QObject *parent = 0);
+ QQuickStateOperation(QObjectPrivate &dd, QObject *parent = nullptr);
private:
Q_DECLARE_PRIVATE(QQuickStateOperation)
@@ -159,8 +159,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickState : public QObject
Q_CLASSINFO("DeferredPropertyNames", "changes")
public:
- QQuickState(QObject *parent=0);
- virtual ~QQuickState();
+ QQuickState(QObject *parent=nullptr);
+ ~QQuickState() override;
QString name() const;
void setName(const QString &);
diff --git a/src/quick/util/qquickstate_p_p.h b/src/quick/util/qquickstate_p_p.h
index eba1dabecf..f1bc24c558 100644
--- a/src/quick/util/qquickstate_p_p.h
+++ b/src/quick/util/qquickstate_p_p.h
@@ -178,8 +178,8 @@ private:
class QQuickRevertAction
{
public:
- QQuickRevertAction() : event(0) {}
- QQuickRevertAction(const QQmlProperty &prop) : property(prop), event(0) {}
+ QQuickRevertAction() : event(nullptr) {}
+ QQuickRevertAction(const QQmlProperty &prop) : property(prop), event(nullptr) {}
QQuickRevertAction(QQuickStateActionEvent *e) : event(e) {}
QQmlProperty property;
QQuickStateActionEvent *event;
@@ -192,7 +192,7 @@ class QQuickStateOperationPrivate : public QObjectPrivate
public:
QQuickStateOperationPrivate()
- : m_state(0) {}
+ : m_state(nullptr) {}
QQuickState *m_state;
};
@@ -203,7 +203,7 @@ class QQuickStatePrivate : public QObjectPrivate
public:
QQuickStatePrivate()
- : when(0), named(false), inState(false), group(0) {}
+ : when(nullptr), named(false), inState(false), group(nullptr) {}
typedef QList<QQuickSimpleAction> SimpleActionList;
@@ -233,7 +233,7 @@ public:
QList<OperationGuard> *list = static_cast<QList<OperationGuard> *>(prop->data);
QMutableListIterator<OperationGuard> listIterator(*list);
while(listIterator.hasNext())
- listIterator.next()->setState(0);
+ listIterator.next()->setState(nullptr);
list->clear();
}
static int operations_count(QQmlListProperty<QQuickStateOperation> *prop) {
diff --git a/src/quick/util/qquickstatechangescript_p.h b/src/quick/util/qquickstatechangescript_p.h
index a1315ae2ef..ff509a7cf5 100644
--- a/src/quick/util/qquickstatechangescript_p.h
+++ b/src/quick/util/qquickstatechangescript_p.h
@@ -66,7 +66,7 @@ class Q_AUTOTEST_EXPORT QQuickStateChangeScript : public QQuickStateOperation, p
Q_PROPERTY(QString name READ name WRITE setName)
public:
- QQuickStateChangeScript(QObject *parent=0);
+ QQuickStateChangeScript(QObject *parent=nullptr);
~QQuickStateChangeScript();
ActionList actions() override;
diff --git a/src/quick/util/qquickstategroup.cpp b/src/quick/util/qquickstategroup.cpp
index ebcbbf93ed..1b99baed9a 100644
--- a/src/quick/util/qquickstategroup.cpp
+++ b/src/quick/util/qquickstategroup.cpp
@@ -60,7 +60,7 @@ class QQuickStateGroupPrivate : public QObjectPrivate
Q_DECLARE_PUBLIC(QQuickStateGroup)
public:
QQuickStateGroupPrivate()
- : nullState(0), componentComplete(true),
+ : nullState(nullptr), componentComplete(true),
ignoreTrans(false), applyingState(false), unnamedCount(0) {}
QString currentState;
@@ -129,7 +129,7 @@ QQuickStateGroup::~QQuickStateGroup()
{
Q_D(const QQuickStateGroup);
for (int i = 0; i < d->states.count(); ++i)
- d->states.at(i)->setStateGroup(0);
+ d->states.at(i)->setStateGroup(nullptr);
}
QList<QQuickState *> QQuickStateGroup::states() const
@@ -194,7 +194,7 @@ void QQuickStateGroupPrivate::clear_states(QQmlListProperty<QQuickState> *list)
QQuickStateGroup *_this = static_cast<QQuickStateGroup *>(list->object);
_this->d_func()->setCurrentStateInternal(QString(), true);
for (int i = 0; i < _this->d_func()->states.count(); ++i) {
- _this->d_func()->states.at(i)->setStateGroup(0);
+ _this->d_func()->states.at(i)->setStateGroup(nullptr);
}
_this->d_func()->states.clear();
}
@@ -364,7 +364,7 @@ bool QQuickStateGroupPrivate::updateAutoState()
QQuickTransition *QQuickStateGroupPrivate::findTransition(const QString &from, const QString &to)
{
- QQuickTransition *highest = 0;
+ QQuickTransition *highest = nullptr;
int score = 0;
bool reversed = false;
bool done = false;
@@ -444,7 +444,7 @@ void QQuickStateGroupPrivate::setCurrentStateInternal(const QString &state,
applyingState = true;
- QQuickTransition *transition = ignoreTrans ? 0 : findTransition(currentState, state);
+ QQuickTransition *transition = ignoreTrans ? nullptr : findTransition(currentState, state);
if (stateChangeDebug()) {
qWarning() << this << "Changing state. From" << currentState << ". To" << state;
if (transition)
@@ -452,7 +452,7 @@ void QQuickStateGroupPrivate::setCurrentStateInternal(const QString &state,
<< transition->toState();
}
- QQuickState *oldState = 0;
+ QQuickState *oldState = nullptr;
if (!currentState.isEmpty()) {
for (int ii = 0; ii < states.count(); ++ii) {
if (states.at(ii)->name() == currentState) {
@@ -465,7 +465,7 @@ void QQuickStateGroupPrivate::setCurrentStateInternal(const QString &state,
currentState = state;
emit q->stateChanged(currentState);
- QQuickState *newState = 0;
+ QQuickState *newState = nullptr;
for (int ii = 0; ii < states.count(); ++ii) {
if (states.at(ii)->name() == currentState) {
newState = states.at(ii);
@@ -473,7 +473,7 @@ void QQuickStateGroupPrivate::setCurrentStateInternal(const QString &state,
}
}
- if (oldState == 0 || newState == 0) {
+ if (oldState == nullptr || newState == nullptr) {
if (!nullState) {
nullState = new QQuickState;
QQml_setParent_noEvent(nullState, q);
@@ -496,7 +496,7 @@ QQuickState *QQuickStateGroup::findState(const QString &name) const
return state;
}
- return 0;
+ return nullptr;
}
void QQuickStateGroup::removeState(QQuickState *state)
diff --git a/src/quick/util/qquickstategroup_p.h b/src/quick/util/qquickstategroup_p.h
index eebe3a9e56..7235066d99 100644
--- a/src/quick/util/qquickstategroup_p.h
+++ b/src/quick/util/qquickstategroup_p.h
@@ -67,7 +67,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickStateGroup : public QObject, public QQmlParse
Q_PROPERTY(QQmlListProperty<QQuickTransition> transitions READ transitionsProperty DESIGNABLE false)
public:
- QQuickStateGroup(QObject * = 0);
+ QQuickStateGroup(QObject * = nullptr);
virtual ~QQuickStateGroup();
QString state() const;
diff --git a/src/quick/util/qquickstyledtext.cpp b/src/quick/util/qquickstyledtext.cpp
index ae8719341d..762d49f2d2 100644
--- a/src/quick/util/qquickstyledtext.cpp
+++ b/src/quick/util/qquickstyledtext.cpp
@@ -695,7 +695,7 @@ void QQuickStyledTextPrivate::parseImageAttributes(const QChar *&ch, const QStri
image->size = image->pix->implicitSize();
} else {
delete image->pix;
- image->pix = 0;
+ image->pix = nullptr;
}
}
}
diff --git a/src/quick/util/qquickstyledtext_p.h b/src/quick/util/qquickstyledtext_p.h
index 2a2e234224..51f1b7d8f9 100644
--- a/src/quick/util/qquickstyledtext_p.h
+++ b/src/quick/util/qquickstyledtext_p.h
@@ -67,9 +67,7 @@ class QQmlContext;
class Q_AUTOTEST_EXPORT QQuickStyledTextImgTag
{
public:
- QQuickStyledTextImgTag()
- : position(0), offset(0.0), align(QQuickStyledTextImgTag::Bottom), pix(0)
- { }
+ QQuickStyledTextImgTag() { }
~QQuickStyledTextImgTag() { delete pix; }
@@ -82,10 +80,10 @@ public:
QUrl url;
QPointF pos;
QSize size;
- int position;
- qreal offset; // this offset allows us to compensate for flooring reserved space
- Align align;
- QQuickPixmap *pix;
+ int position = 0;
+ qreal offset = 0.0; // this offset allows us to compensate for flooring reserved space
+ Align align = QQuickStyledTextImgTag::Bottom;
+ QQuickPixmap *pix = nullptr;
};
class Q_AUTOTEST_EXPORT QQuickStyledText
diff --git a/src/quick/util/qquicksvgparser.cpp b/src/quick/util/qquicksvgparser.cpp
index 086c6d0b28..2bf9c121d3 100644
--- a/src/quick/util/qquicksvgparser.cpp
+++ b/src/quick/util/qquicksvgparser.cpp
@@ -126,7 +126,7 @@ static qreal toDouble(const QChar *&str)
val = -val;
} else {
bool ok = false;
- val = qstrtod(temp, 0, &ok);
+ val = qstrtod(temp, nullptr, &ok);
}
return val;
diff --git a/src/quick/util/qquicksystempalette_p.h b/src/quick/util/qquicksystempalette_p.h
index 086fb31993..9a3a520ed1 100644
--- a/src/quick/util/qquicksystempalette_p.h
+++ b/src/quick/util/qquicksystempalette_p.h
@@ -81,7 +81,7 @@ class Q_AUTOTEST_EXPORT QQuickSystemPalette : public QObject
Q_PROPERTY(QColor highlightedText READ highlightedText NOTIFY paletteChanged)
public:
- QQuickSystemPalette(QObject *parent=0);
+ QQuickSystemPalette(QObject *parent=nullptr);
~QQuickSystemPalette();
enum ColorGroup { Active = QPalette::Active, Inactive = QPalette::Inactive, Disabled = QPalette::Disabled };
diff --git a/src/quick/util/qquicktimeline.cpp b/src/quick/util/qquicktimeline.cpp
index b3f0caa2b3..ac9f75979e 100644
--- a/src/quick/util/qquicktimeline.cpp
+++ b/src/quick/util/qquicktimeline.cpp
@@ -57,7 +57,7 @@ struct Update {
Update(QQuickTimeLineValue *_g, qreal _v)
: g(_g), v(_v) {}
Update(const QQuickTimeLineCallback &_e)
- : g(0), v(0), e(_e) {}
+ : g(nullptr), v(0), e(_e) {}
QQuickTimeLineValue *g;
qreal v;
@@ -104,11 +104,11 @@ struct QQuickTimeLinePrivate
};
struct TimeLine
{
- TimeLine() : length(0), consumedOpLength(0), base(0.) {}
+ TimeLine() {}
QList<Op> ops;
- int length;
- int consumedOpLength;
- qreal base;
+ int length = 0;
+ int consumedOpLength = 0;
+ qreal base = 0.;
};
int length;
@@ -133,7 +133,7 @@ struct QQuickTimeLinePrivate
};
QQuickTimeLinePrivate::QQuickTimeLinePrivate(QQuickTimeLine *parent)
-: length(0), syncPoint(0), q(parent), clockRunning(false), prevTime(0), order(0), syncMode(QQuickTimeLine::LocalSync), syncAdj(0), updateQueue(0)
+: length(0), syncPoint(0), q(parent), clockRunning(false), prevTime(0), order(0), syncMode(QQuickTimeLine::LocalSync), syncAdj(0), updateQueue(nullptr)
{
}
@@ -326,9 +326,9 @@ QQuickTimeLine::~QQuickTimeLine()
for (QQuickTimeLinePrivate::Ops::Iterator iter = d->ops.begin();
iter != d->ops.end();
++iter)
- iter.key()->_t = 0;
+ iter.key()->_t = nullptr;
- delete d; d = 0;
+ delete d; d = nullptr;
}
/*!
@@ -514,7 +514,7 @@ void QQuickTimeLine::reset(QQuickTimeLineValue &timeLineValue)
return;
}
remove(&timeLineValue);
- timeLineValue._t = 0;
+ timeLineValue._t = nullptr;
}
int QQuickTimeLine::duration() const
@@ -666,7 +666,7 @@ void QQuickTimeLine::complete()
void QQuickTimeLine::clear()
{
for (QQuickTimeLinePrivate::Ops::const_iterator iter = d->ops.cbegin(), cend = d->ops.cend(); iter != cend; ++iter)
- iter.key()->_t = 0;
+ iter.key()->_t = nullptr;
d->ops.clear();
d->length = 0;
d->syncPoint = 0;
@@ -800,7 +800,7 @@ int QQuickTimeLinePrivate::advance(int t)
if (tl.ops.isEmpty()) {
iter = ops.erase(iter);
- v->_t = 0;
+ v->_t = nullptr;
} else {
if (tl.ops.first().type == Op::Pause && pauseTime != 0) {
int opPauseTime = tl.ops.first().length - tl.consumedOpLength;
@@ -826,7 +826,7 @@ int QQuickTimeLinePrivate::advance(int t)
v.e.d0(v.e.d1);
}
}
- updateQueue = 0;
+ updateQueue = nullptr;
} while(t);
return pauseTime;
@@ -854,7 +854,7 @@ void QQuickTimeLine::remove(QQuickTimeLineObject *v)
if (d->ops.isEmpty()) {
stop();
d->clockRunning = false;
- } else if (/*!GfxClock::isActive()*/ state() != Running) {
+ } else if (state() != Running) { // was !GfxClock::isActive()
stop();
d->prevTime = 0;
d->clockRunning = true;
@@ -913,7 +913,7 @@ void QQuickTimeLine::remove(QQuickTimeLineObject *v)
QQuickTimeLineObject::QQuickTimeLineObject()
-: _t(0)
+: _t(nullptr)
{
}
@@ -921,12 +921,12 @@ QQuickTimeLineObject::~QQuickTimeLineObject()
{
if (_t) {
_t->remove(this);
- _t = 0;
+ _t = nullptr;
}
}
QQuickTimeLineCallback::QQuickTimeLineCallback()
-: d0(0), d1(0), d2(0)
+: d0(nullptr), d1(nullptr), d2(nullptr)
{
}
diff --git a/src/quick/util/qquicktimeline_p_p.h b/src/quick/util/qquicktimeline_p_p.h
index ae1087487b..abb5369b7b 100644
--- a/src/quick/util/qquicktimeline_p_p.h
+++ b/src/quick/util/qquicktimeline_p_p.h
@@ -65,7 +65,7 @@ class Q_AUTOTEST_EXPORT QQuickTimeLine : public QObject, QAbstractAnimationJob
{
Q_OBJECT
public:
- QQuickTimeLine(QObject *parent = 0);
+ QQuickTimeLine(QObject *parent = nullptr);
~QQuickTimeLine();
enum SyncMode { LocalSync, GlobalSync };
@@ -152,7 +152,7 @@ public:
typedef void (*Callback)(void *);
QQuickTimeLineCallback();
- QQuickTimeLineCallback(QQuickTimeLineObject *b, Callback, void * = 0);
+ QQuickTimeLineCallback(QQuickTimeLineObject *b, Callback, void * = nullptr);
QQuickTimeLineCallback(const QQuickTimeLineCallback &o);
QQuickTimeLineCallback &operator=(const QQuickTimeLineCallback &o);
@@ -170,7 +170,7 @@ class QQuickTimeLineValueProxy : public QQuickTimeLineValue
{
public:
QQuickTimeLineValueProxy(T *cls, void (T::*func)(qreal), qreal v = 0.)
- : QQuickTimeLineValue(v), _class(cls), _setFunctionReal(func), _setFunctionInt(0)
+ : QQuickTimeLineValue(v), _class(cls), _setFunctionReal(func), _setFunctionInt(nullptr)
{
Q_ASSERT(_class);
}
diff --git a/src/quick/util/qquicktransition.cpp b/src/quick/util/qquicktransition.cpp
index 29690a4857..fd6415dffb 100644
--- a/src/quick/util/qquicktransition.cpp
+++ b/src/quick/util/qquicktransition.cpp
@@ -109,7 +109,7 @@ protected:
void updateState(QAbstractAnimationJob::State newState, QAbstractAnimationJob::State oldState) override;
};
-class QQuickTransitionPrivate : public QObjectPrivate, QAnimationJobChangeListener
+class QQuickTransitionPrivate : public QObjectPrivate
{
Q_DECLARE_PUBLIC(QQuickTransition)
public:
@@ -120,11 +120,8 @@ public:
{
}
- void removeStateChangeListener(QAbstractAnimationJob *anim)
- {
- if (anim)
- anim->removeAnimationChangeListener(this, QAbstractAnimationJob::StateChange);
- }
+ static QQuickTransitionPrivate *get(QQuickTransition *q) { return q->d_func(); }
+ void animationStateChanged(QAbstractAnimationJob::State newState);
QString fromState;
QString toState;
@@ -134,7 +131,6 @@ public:
bool reversible;
bool enabled;
protected:
- void animationStateChanged(QAbstractAnimationJob *, QAbstractAnimationJob::State, QAbstractAnimationJob::State) override;
static void append_animation(QQmlListProperty<QQuickAbstractAnimation> *list, QQuickAbstractAnimation *a);
static int animation_count(QQmlListProperty<QQuickAbstractAnimation> *list);
@@ -171,7 +167,16 @@ void QQuickTransitionPrivate::clear_animations(QQmlListProperty<QQuickAbstractAn
}
}
-void QQuickTransitionPrivate::animationStateChanged(QAbstractAnimationJob *, QAbstractAnimationJob::State newState, QAbstractAnimationJob::State)
+void QQuickTransitionInstance::animationStateChanged(QAbstractAnimationJob *, QAbstractAnimationJob::State newState, QAbstractAnimationJob::State)
+{
+ if (!m_transition)
+ return;
+
+ QQuickTransitionPrivate *transition = QQuickTransitionPrivate::get(m_transition);
+ transition->animationStateChanged(newState);
+}
+
+void QQuickTransitionPrivate::animationStateChanged(QAbstractAnimationJob::State newState)
{
Q_Q(QQuickTransition);
@@ -197,15 +202,16 @@ void ParallelAnimationWrapper::updateState(QAbstractAnimationJob::State newState
}
}
-QQuickTransitionInstance::QQuickTransitionInstance(QQuickTransitionPrivate *transition, QAbstractAnimationJob *anim)
+QQuickTransitionInstance::QQuickTransitionInstance(QQuickTransition *transition, QAbstractAnimationJob *anim)
: m_transition(transition)
, m_anim(anim)
{
+ anim->addAnimationChangeListener(this, QAbstractAnimationJob::StateChange);
}
QQuickTransitionInstance::~QQuickTransitionInstance()
{
- m_transition->removeStateChangeListener(m_anim);
+ removeStateChangeListener();
delete m_anim;
}
@@ -257,7 +263,7 @@ QQuickTransitionInstance *QQuickTransition::prepare(QQuickStateOperation::Action
int start = d->reversed ? d->animations.count() - 1 : 0;
int end = d->reversed ? -1 : d->animations.count();
- QAbstractAnimationJob *anim = 0;
+ QAbstractAnimationJob *anim = nullptr;
for (int i = start; i != end;) {
anim = d->animations.at(i)->transition(actions, after, direction, defaultTarget);
if (anim) {
@@ -270,8 +276,7 @@ QQuickTransitionInstance *QQuickTransition::prepare(QQuickStateOperation::Action
group->setDirection(d->reversed ? QAbstractAnimationJob::Backward : QAbstractAnimationJob::Forward);
- group->addAnimationChangeListener(d, QAbstractAnimationJob::StateChange);
- QQuickTransitionInstance *wrapper = new QQuickTransitionInstance(d, group);
+ QQuickTransitionInstance *wrapper = new QQuickTransitionInstance(this, group);
return wrapper;
}
diff --git a/src/quick/util/qquicktransition_p.h b/src/quick/util/qquicktransition_p.h
index d6f365f99e..c7d06b8832 100644
--- a/src/quick/util/qquicktransition_p.h
+++ b/src/quick/util/qquicktransition_p.h
@@ -53,6 +53,7 @@
#include "qquickstate_p.h"
#include <private/qabstractanimationjob_p.h>
+#include <private/qqmlguard_p.h>
#include <qqml.h>
#include <QtCore/qobject.h>
@@ -64,10 +65,10 @@ class QQuickTransitionPrivate;
class QQuickTransitionManager;
class QQuickTransition;
-class QQuickTransitionInstance
+class QQuickTransitionInstance : QAnimationJobChangeListener
{
public:
- QQuickTransitionInstance(QQuickTransitionPrivate *transition, QAbstractAnimationJob *anim);
+ QQuickTransitionInstance(QQuickTransition *transition, QAbstractAnimationJob *anim);
~QQuickTransitionInstance();
void start();
@@ -75,8 +76,16 @@ public:
bool isRunning() const;
+protected:
+ void animationStateChanged(QAbstractAnimationJob *, QAbstractAnimationJob::State, QAbstractAnimationJob::State) override;
+
+ void removeStateChangeListener()
+ {
+ m_anim->removeAnimationChangeListener(this, QAbstractAnimationJob::StateChange);
+ }
+
private:
- QQuickTransitionPrivate *m_transition;
+ QQmlGuard<QQuickTransition> m_transition;
QAbstractAnimationJob *m_anim;
friend class QQuickTransition;
};
@@ -96,7 +105,7 @@ class Q_QUICK_PRIVATE_EXPORT QQuickTransition : public QObject
Q_CLASSINFO("DeferredPropertyNames", "animations")
public:
- QQuickTransition(QObject *parent=0);
+ QQuickTransition(QObject *parent=nullptr);
~QQuickTransition();
QString fromState() const;
diff --git a/src/quick/util/qquicktransitionmanager.cpp b/src/quick/util/qquicktransitionmanager.cpp
index 714e6d62b6..a1367249c6 100644
--- a/src/quick/util/qquicktransitionmanager.cpp
+++ b/src/quick/util/qquicktransitionmanager.cpp
@@ -56,7 +56,7 @@ class QQuickTransitionManagerPrivate
{
public:
QQuickTransitionManagerPrivate()
- : state(0), transitionInstance(0) {}
+ : state(nullptr), transitionInstance(nullptr) {}
void applyBindings();
typedef QList<QQuickSimpleAction> SimpleActionList;
@@ -79,7 +79,7 @@ void QQuickTransitionManager::setState(QQuickState *s)
QQuickTransitionManager::~QQuickTransitionManager()
{
delete d->transitionInstance;
- delete d; d = 0;
+ delete d; d = nullptr;
}
bool QQuickTransitionManager::isRunning() const
@@ -274,7 +274,7 @@ void QQuickTransitionManager::cancel()
QQuickStateAction action = d->bindingsList[i];
if (action.toBinding && action.deletableToBinding) {
QQmlPropertyPrivate::removeBinding(action.property);
- action.toBinding = 0;
+ action.toBinding = nullptr;
action.deletableToBinding = false;
} else if (action.event) {
//### what do we do here?
diff --git a/src/quick/util/qquicktransitionmanager_p_p.h b/src/quick/util/qquicktransitionmanager_p_p.h
index 68daf6db3c..89317e1e07 100644
--- a/src/quick/util/qquicktransitionmanager_p_p.h
+++ b/src/quick/util/qquicktransitionmanager_p_p.h
@@ -66,7 +66,7 @@ public:
bool isRunning() const;
- void transition(const QList<QQuickStateAction> &, QQuickTransition *transition, QObject *defaultTarget = 0);
+ void transition(const QList<QQuickStateAction> &, QQuickTransition *transition, QObject *defaultTarget = nullptr);
void cancel();
diff --git a/src/quick/util/qquickvalidator_p.h b/src/quick/util/qquickvalidator_p.h
index ba188e947a..812e552d8e 100644
--- a/src/quick/util/qquickvalidator_p.h
+++ b/src/quick/util/qquickvalidator_p.h
@@ -62,7 +62,7 @@ class Q_AUTOTEST_EXPORT QQuickIntValidator : public QIntValidator
Q_OBJECT
Q_PROPERTY(QString locale READ localeName WRITE setLocaleName RESET resetLocaleName NOTIFY localeNameChanged)
public:
- QQuickIntValidator(QObject *parent = 0);
+ QQuickIntValidator(QObject *parent = nullptr);
QString localeName() const;
void setLocaleName(const QString &name);
@@ -77,7 +77,7 @@ class Q_AUTOTEST_EXPORT QQuickDoubleValidator : public QDoubleValidator
Q_OBJECT
Q_PROPERTY(QString locale READ localeName WRITE setLocaleName RESET resetLocaleName NOTIFY localeNameChanged)
public:
- QQuickDoubleValidator(QObject *parent = 0);
+ QQuickDoubleValidator(QObject *parent = nullptr);
QString localeName() const;
void setLocaleName(const QString &name);
diff --git a/src/quickwidgets/qquickwidget.cpp b/src/quickwidgets/qquickwidget.cpp
index 7c221850ab..6f3b685974 100644
--- a/src/quickwidgets/qquickwidget.cpp
+++ b/src/quickwidgets/qquickwidget.cpp
@@ -184,15 +184,15 @@ void QQuickWidgetPrivate::handleWindowChange()
}
QQuickWidgetPrivate::QQuickWidgetPrivate()
- : root(0)
- , component(0)
- , offscreenWindow(0)
- , offscreenSurface(0)
- , renderControl(0)
+ : root(nullptr)
+ , component(nullptr)
+ , offscreenWindow(nullptr)
+ , offscreenSurface(nullptr)
+ , renderControl(nullptr)
#if QT_CONFIG(opengl)
- , fbo(0)
- , resolvedFbo(0)
- , context(0)
+ , fbo(nullptr)
+ , resolvedFbo(nullptr)
+ , context(nullptr)
#endif
, resizeMode(QQuickWidget::SizeViewToRootObject)
, initialSize(0,0)
@@ -233,11 +233,11 @@ void QQuickWidgetPrivate::execute()
if (root) {
delete root;
- root = 0;
+ root = nullptr;
}
if (component) {
delete component;
- component = 0;
+ component = nullptr;
}
if (!source.isEmpty()) {
QML_MEMORY_SCOPE_URL(engine.data()->baseUrl().resolved(source));
@@ -489,7 +489,8 @@ QImage QQuickWidgetPrivate::grabFramebuffer()
*/
-/*! \fn void QQuickWidget::statusChanged(QQuickWidget::Status status)
+/*!
+ \fn void QQuickWidget::statusChanged(QQuickWidget::Status status)
This signal is emitted when the component's current \a status changes.
*/
@@ -499,7 +500,7 @@ QImage QQuickWidgetPrivate::grabFramebuffer()
*/
QQuickWidget::QQuickWidget(QWidget *parent)
-: QWidget(*(new QQuickWidgetPrivate), parent, 0)
+: QWidget(*(new QQuickWidgetPrivate), parent, nullptr)
{
setMouseTracking(true);
setFocusPolicy(Qt::StrongFocus);
@@ -527,7 +528,7 @@ QQuickWidget::QQuickWidget(const QUrl &source, QWidget *parent)
\sa Status, status(), errors()
*/
QQuickWidget::QQuickWidget(QQmlEngine* engine, QWidget *parent)
- : QWidget(*(new QQuickWidgetPrivate), parent, 0)
+ : QWidget(*(new QQuickWidgetPrivate), parent, nullptr)
{
setMouseTracking(true);
setFocusPolicy(Qt::StrongFocus);
@@ -543,7 +544,7 @@ QQuickWidget::~QQuickWidget()
// be a child of the QQuickWidgetPrivate, and will be destroyed by its dtor
Q_D(QQuickWidget);
delete d->root;
- d->root = 0;
+ d->root = nullptr;
}
/*!
@@ -587,7 +588,7 @@ void QQuickWidget::setContent(const QUrl& url, QQmlComponent *component, QObject
if (d->component && d->component->isError()) {
const QList<QQmlError> errorList = d->component->errors();
for (const QQmlError &error : errorList) {
- QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), 0).warning()
+ QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
<< error;
}
emit statusChanged(status());
@@ -796,7 +797,7 @@ void QQuickWidgetPrivate::updateSize()
void QQuickWidgetPrivate::updatePosition()
{
Q_Q(QQuickWidget);
- if (offscreenWindow == 0)
+ if (offscreenWindow == nullptr)
return;
const QPoint &pos = q->mapToGlobal(QPoint(0, 0));
@@ -870,7 +871,7 @@ void QQuickWidgetPrivate::createContext()
if (!context->create()) {
const bool isEs = context->isOpenGLES();
delete context;
- context = 0;
+ context = nullptr;
handleContextCreationFailure(offscreenWindow->requestedFormat(), isEs);
return;
}
@@ -896,10 +897,10 @@ void QQuickWidgetPrivate::createContext()
void QQuickWidgetPrivate::destroyContext()
{
delete offscreenSurface;
- offscreenSurface = 0;
+ offscreenSurface = nullptr;
#if QT_CONFIG(opengl)
delete context;
- context = 0;
+ context = nullptr;
#endif
}
@@ -935,7 +936,7 @@ void QQuickWidget::createFramebufferObject()
}
QOpenGLContext *shareWindowContext = QWidgetPrivate::get(window())->shareContext();
- if (shareWindowContext && context->shareContext() != shareWindowContext) {
+ if (shareWindowContext && context->shareContext() != shareWindowContext && !qGuiApp->testAttribute(Qt::AA_ShareOpenGLContexts)) {
context->setShareContext(shareWindowContext);
context->setScreen(shareWindowContext->screen());
if (!context->create())
@@ -1009,9 +1010,9 @@ void QQuickWidget::destroyFramebufferObject()
#if QT_CONFIG(opengl)
delete d->fbo;
- d->fbo = 0;
+ d->fbo = nullptr;
delete d->resolvedFbo;
- d->resolvedFbo = 0;
+ d->resolvedFbo = nullptr;
#endif
}
@@ -1032,7 +1033,7 @@ void QQuickWidget::continueExecute()
if (d->component->isError()) {
const QList<QQmlError> errorList = d->component->errors();
for (const QQmlError &error : errorList) {
- QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), 0).warning()
+ QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
<< error;
}
emit statusChanged(status());
@@ -1044,7 +1045,7 @@ void QQuickWidget::continueExecute()
if (d->component->isError()) {
const QList<QQmlError> errorList = d->component->errors();
for (const QQmlError &error : errorList) {
- QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), 0).warning()
+ QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
<< error;
}
emit statusChanged(status());
@@ -1077,7 +1078,7 @@ void QQuickWidgetPrivate::setRootObject(QObject *obj)
<< "Ensure your QML code is written for QtQuick 2, and uses a root that is or" << endl
<< "inherits from QtQuick's Item (not a Timer, QtObject, etc)." << endl;
delete obj;
- root = 0;
+ root = nullptr;
}
if (root) {
initialSize = rootObjectSize();
@@ -1247,11 +1248,12 @@ void QQuickWidget::mouseMoveEvent(QMouseEvent *e)
Q_QUICK_INPUT_PROFILE(QQuickProfiler::Mouse, QQuickProfiler::InputMouseMove, e->localPos().x(),
e->localPos().y());
- // Use the constructor taking localPos and screenPos. That puts localPos into the
- // event's localPos and windowPos, and screenPos into the event's screenPos. This way
- // the windowPos in e is ignored and is replaced by localPos. This is necessary
- // because QQuickWindow thinks of itself as a top-level window always.
- QMouseEvent mappedEvent(e->type(), e->localPos(), e->screenPos(), e->button(), e->buttons(), e->modifiers());
+ // Put localPos into the event's localPos and windowPos, and screenPos into the
+ // event's screenPos. This way the windowPos in e is ignored and is replaced by
+ // localPos. This is necessary because QQuickWindow thinks of itself as a
+ // top-level window always.
+ QMouseEvent mappedEvent(e->type(), e->localPos(), e->localPos(), e->screenPos(),
+ e->button(), e->buttons(), e->modifiers(), e->source());
QCoreApplication::sendEvent(d->offscreenWindow, &mappedEvent);
e->setAccepted(mappedEvent.isAccepted());
}
@@ -1265,12 +1267,12 @@ void QQuickWidget::mouseDoubleClickEvent(QMouseEvent *e)
// As the second mouse press is suppressed in widget windows we emulate it here for QML.
// See QTBUG-25831
- QMouseEvent pressEvent(QEvent::MouseButtonPress, e->localPos(), e->screenPos(), e->button(),
- e->buttons(), e->modifiers());
+ QMouseEvent pressEvent(QEvent::MouseButtonPress, e->localPos(), e->localPos(), e->screenPos(),
+ e->button(), e->buttons(), e->modifiers(), e->source());
QCoreApplication::sendEvent(d->offscreenWindow, &pressEvent);
e->setAccepted(pressEvent.isAccepted());
- QMouseEvent mappedEvent(e->type(), e->localPos(), e->screenPos(), e->button(), e->buttons(),
- e->modifiers());
+ QMouseEvent mappedEvent(e->type(), e->localPos(), e->localPos(), e->screenPos(),
+ e->button(), e->buttons(), e->modifiers(), e->source());
QCoreApplication::sendEvent(d->offscreenWindow, &mappedEvent);
}
@@ -1330,7 +1332,8 @@ void QQuickWidget::mousePressEvent(QMouseEvent *e)
Q_QUICK_INPUT_PROFILE(QQuickProfiler::Mouse, QQuickProfiler::InputMousePress, e->button(),
e->buttons());
- QMouseEvent mappedEvent(e->type(), e->localPos(), e->screenPos(), e->button(), e->buttons(), e->modifiers());
+ QMouseEvent mappedEvent(e->type(), e->localPos(), e->localPos(), e->screenPos(),
+ e->button(), e->buttons(), e->modifiers(), e->source());
QCoreApplication::sendEvent(d->offscreenWindow, &mappedEvent);
e->setAccepted(mappedEvent.isAccepted());
}
@@ -1342,7 +1345,8 @@ void QQuickWidget::mouseReleaseEvent(QMouseEvent *e)
Q_QUICK_INPUT_PROFILE(QQuickProfiler::Mouse, QQuickProfiler::InputMouseRelease, e->button(),
e->buttons());
- QMouseEvent mappedEvent(e->type(), e->localPos(), e->screenPos(), e->button(), e->buttons(), e->modifiers());
+ QMouseEvent mappedEvent(e->type(), e->localPos(), e->localPos(), e->screenPos(),
+ e->button(), e->buttons(), e->modifiers(), e->source());
QCoreApplication::sendEvent(d->offscreenWindow, &mappedEvent);
e->setAccepted(mappedEvent.isAccepted());
}
@@ -1392,6 +1396,28 @@ static Qt::WindowState resolveWindowState(Qt::WindowStates states)
return Qt::WindowNoState;
}
+static void remapInputMethodQueryEvent(QObject *object, QInputMethodQueryEvent *e)
+{
+ auto item = qobject_cast<QQuickItem *>(object);
+ if (!item)
+ return;
+
+ // Remap all QRectF values.
+ for (auto query : {Qt::ImCursorRectangle, Qt::ImAnchorRectangle, Qt::ImInputItemClipRectangle}) {
+ if (e->queries() & query) {
+ auto value = e->value(query);
+ if (value.canConvert<QRectF>())
+ e->setValue(query, item->mapRectToScene(value.toRectF()));
+ }
+ }
+ // Remap all QPointF values.
+ if (e->queries() & Qt::ImCursorPosition) {
+ auto value = e->value(Qt::ImCursorPosition);
+ if (value.canConvert<QPointF>())
+ e->setValue(Qt::ImCursorPosition, item->mapToScene(value.toPointF()));
+ }
+}
+
/*! \reimp */
bool QQuickWidget::event(QEvent *e)
{
@@ -1399,6 +1425,7 @@ bool QQuickWidget::event(QEvent *e)
switch (e->type()) {
+ case QEvent::Leave:
case QEvent::TouchBegin:
case QEvent::TouchEnd:
case QEvent::TouchUpdate:
@@ -1407,8 +1434,17 @@ bool QQuickWidget::event(QEvent *e)
return QCoreApplication::sendEvent(d->offscreenWindow, e);
case QEvent::InputMethod:
- case QEvent::InputMethodQuery:
return QCoreApplication::sendEvent(d->offscreenWindow->focusObject(), e);
+ case QEvent::InputMethodQuery:
+ {
+ bool eventResult = QCoreApplication::sendEvent(d->offscreenWindow->focusObject(), e);
+ // The result in focusObject are based on offscreenWindow. But
+ // the inputMethodTransform won't get updated because the focus
+ // is on QQuickWidget. We need to remap the value based on the
+ // widget.
+ remapInputMethodQueryEvent(d->offscreenWindow->focusObject(), static_cast<QInputMethodQueryEvent *>(e));
+ return eventResult;
+ }
case QEvent::WindowChangeInternal:
d->handleWindowChange();
@@ -1452,6 +1488,14 @@ bool QQuickWidget::event(QEvent *e)
case QEvent::ShortcutOverride:
return QCoreApplication::sendEvent(d->offscreenWindow, e);
+ case QEvent::Enter: {
+ QEnterEvent *enterEvent = static_cast<QEnterEvent *>(e);
+ QEnterEvent mappedEvent(enterEvent->localPos(), enterEvent->windowPos(),
+ enterEvent->screenPos());
+ const bool ret = QCoreApplication::sendEvent(d->offscreenWindow, &mappedEvent);
+ e->setAccepted(mappedEvent.isAccepted());
+ return ret;
+ }
default:
break;
}
@@ -1606,6 +1650,9 @@ QQuickWindow *QQuickWidget::quickWindow() const
return d->offscreenWindow;
}
+/*!
+ \reimp
+ */
void QQuickWidget::paintEvent(QPaintEvent *event)
{
Q_D(QQuickWidget);
@@ -1619,12 +1666,12 @@ void QQuickWidget::paintEvent(QPaintEvent *event)
QTransform transform;
transform.scale(devicePixelRatioF(), devicePixelRatioF());
//Paint only the updated areas
- const auto rects = d->updateRegion.rects();
- for (auto targetRect : rects) {
+ QRegion targetRegion;
+ d->updateRegion.swap(targetRegion);
+ for (auto targetRect : targetRegion) {
auto sourceRect = transform.mapRect(QRectF(targetRect));
painter.drawImage(targetRect, d->softwareImage, sourceRect);
}
- d->updateRegion = QRegion();
}
}
}
diff --git a/src/quickwidgets/qquickwidget.h b/src/quickwidgets/qquickwidget.h
index 8c9382e84b..3ddb0613ad 100644
--- a/src/quickwidgets/qquickwidget.h
+++ b/src/quickwidgets/qquickwidget.h
@@ -66,7 +66,7 @@ public:
explicit QQuickWidget(QWidget *parent = nullptr);
QQuickWidget(QQmlEngine* engine, QWidget *parent);
explicit QQuickWidget(const QUrl &source, QWidget *parent = nullptr);
- virtual ~QQuickWidget();
+ ~QQuickWidget() override;
QUrl source() const;
diff --git a/src/src.pro b/src/src.pro
index 42bf90e092..ff0e1e99bc 100644
--- a/src/src.pro
+++ b/src/src.pro
@@ -2,7 +2,7 @@ TEMPLATE = subdirs
CONFIG += ordered
include($$OUT_PWD/qml/qtqml-config.pri)
include($$OUT_PWD/quick/qtquick-config.pri)
-QT_FOR_CONFIG += network qml quick-private
+QT_FOR_CONFIG += qml quick-private
SUBDIRS += \
qml
@@ -21,4 +21,9 @@ SUBDIRS += \
imports \
qmldevtools
-qtConfig(localserver):qtConfig(qml-debug): SUBDIRS += qmldebug
+qmldevtools.depends = qml
+
+qtConfig(qml-network) {
+ QT_FOR_CONFIG += network
+ qtConfig(localserver):qtConfig(qml-debug): SUBDIRS += qmldebug
+}