summaryrefslogtreecommitdiffstats
path: root/src/gui/rhi
Commit message (Collapse)AuthorAgeFilesLines
* Use SPDX license identifiersLucie Gérard2022-05-1627-1026/+54
| | | | | | | | | | | | | Replace the current license disclaimer in files by a SPDX-License-Identifier. Files that have to be modified by hand are modified. License files are organized under LICENSES directory. Task-number: QTBUG-67283 Change-Id: Id880c92784c40f3bbde861c0d93f58151c18b9f1 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Lars Knoll <lars.knoll@qt.io> Reviewed-by: Jörg Bornemann <joerg.bornemann@qt.io>
* rhi: d3d: Fix not resetting the pipeline tracking between passesLaszlo Agocs2022-05-102-5/+2
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | Do what all other backends do. If we did not want to reset the pipeline tracking pointer, then more logic would be needed, in order not to end up in trouble with clients that do: loop: create a pipeline // [1] beginpass ... // use the pipeline endpass readback finish destroy the pipeline goto loop ...because we may get the exact same pipeline pointer (with a matching generation even since it's always 1 in this case) in the different passes, just because malloc decided to do so in [1]. This could be solved by checking the global resource id but won't do that now as no other backends do it either. This solves random broken rendering with the Qt Quick 3D lightmapper. The above outline is exactly what the UV rasterization stage does. Pick-to: 6.3 6.2 Change-Id: Id74a0a336634d99092181b09dd7137eaec355d48 Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* QtGui: replace remaining uses of QLatin1String with QLatin1StringViewSona Kurazyan2022-04-281-7/+7
| | | | | | Task-number: QTBUG-98434 Change-Id: I98c27030c783f968cbf38dc966ce486dc366b302 Reviewed-by: Edward Welbourne <edward.welbourne@qt.io>
* QtGui: use _L1 for for creating Latin-1 string literalsSona Kurazyan2022-04-281-2/+4
| | | | | | Task-number: QTBUG-98434 Change-Id: Idcb71c1d27125333a53b6bdd3e1af0d4c66617fa Reviewed-by: Edward Welbourne <edward.welbourne@qt.io>
* rhi: d3d11: fail early with a broken deviceLaszlo Agocs2022-04-263-2/+312
| | | | | | | | | | | | | | | | | | | | | | | Broken meaning not being functional with shader model 5. This can happen with certain virtual machines where there is an accelerated DXGI adapter which then only supports a feature level lower than 11_0, and so SM 5.0 shaders do not work. Similarly, GPUs from 2009 and earlier may have a similar driver setup. We do not particularly care about such devices, however we should make sure it can be recognized early on (i.e. in create()) that something is not right and fail the entire QRhi initialization. Otherwise no error will occur until attempting to create the first shader via a QRhiGraphicsPipeline and that's way too late. This way clients such as Qt Quick can make an effort to retry with some other settings, most notably the PreferSoftwareRenderer flag, in order to pick the sw rasterizer based adapter (WARP). Task-number: QTBUG-78648 Change-Id: Ia4a3a0bc1a09e2864d426d4d55978dc6f759127c Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Make QRhiRenderTarget's rp getter functional with swapchainsLaszlo Agocs2022-04-265-0/+5
| | | | | | | | | | | | | | | | | swapchain->currentFrameRenderTarget()->renderPassDescriptor() is not functional at the moment, it returns null. This is because no backend ensures that the internal renderpass descriptor object is exposed via that getter in a QRhiSwapChainRenderTarget. Whereas in a QRhiTextureRenderTarget this would work by design because there the setter must be called by the user. Fix this up, providing better API symmetry, and also reducing the need to pass along QRhiRenderPassDescriptor objects seprately alongside a QRhiRenderTarget in some places, e.g. in Qt Quick. Change-Id: I42c4e9aaee3202c1d23bd093d840af80c5f8cd0f Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Add a feature flag for non-fill polygon modesLaszlo Agocs2022-04-227-2/+23
| | | | | | | | It's one thing that this is not part of OpenGL ES, but it is optional even with Vulkan, with some mobile GPUs not offering the feature at all. Change-Id: I4e2c6642eccb0793e69074b4b6eeb2b7cef3516e Reviewed-by: Christian Strømme <christian.stromme@qt.io>
* rhi: vulkan: Enable feature for line polygon modeLaszlo Agocs2022-04-211-0/+2
| | | | | | | | | | Turns out there is a fillModeNonSolid in VkPhysicalDeviceFeatures, so to be true to the spec we need to enable that when setting the polygonMode in a QRhiGraphicsPipeline to something other than the default Fill. This way the validation layer won't bark at us. Change-Id: I41f561a1796ba1d45229dc20bf1fb7bae3c43f48 Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* Use the QSurface for QRhiGles2InitParams::fallbackSurfaceJiDe Zhang2022-04-122-8/+10
| | | | | | | | | | There is no need to limit the type to QOffscreenSurface here, QRhi does not depend on the behavior in QOffscreenSurface. Users can use the custom offscreen QSurface types if needed. Task-number: QTBUG-102257 Change-Id: I47a064496f8c5f1986a0e11ec748ea32a03b903e Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* Add support for the HDRExtendedSrgbLinear color space on MetalLars Knoll2022-04-112-0/+43
| | | | | | | | | | | | | Request 16 bit floating point backbuffers and set the color space of the CAMetalLayer to kCGColorSpaceExtendedLinearSRGB if we set up the swap chain to use extended SRGB. Unfortunately the required CAMetalLayer.wantsExtendedDynamicRangeContent property is not yet available on iOS, so for now this is a macOS only feature. Change-Id: I28ab12cc0b829eded721061da2679be8e31d6b9d Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* rhi: Add explicit subclass for RTs from swapchainsLaszlo Agocs2022-04-0512-84/+128
| | | | | | | | | | | | | | | | | | | | | | | | | | We want to enable gaining access to the underlying resource(s) by inspecting a QRhiRenderTarget. This is not currently possible for swapchains since there is nothing that references the actual QRhiSwapChain. To clean this up, make an explicit, new QRhiSwapChainRenderTarget subclass. Thus the logic already used in a couple of places to examine the resources attached to a QRhiTextureRenderTarget can now work with swapchain render targets too, by branching based on the resourceType(). This eliminates the somewhat odd setup where a "RenderTarget" resource is QRhiRenderTarget corresponding (but not exposing!) a swapchain, whereas a "TextureRenderTarget" is a QRhiTextureRenderTarget which is a subclass of QRhiRenderTarget. Now we correctly have an (abstract) base and two subclasses, one for each type of render targets. Besides, it allows us to clean up the oddly named Q...ReferenceRenderTarget classes in the backends, which initially tried to indicate that this "render target" merely references (or, in practice, is) a swapchain. We can now have a nice and symmetrical Q...SwapChainRenderTarget and Q...TextureRenderTarget naming scheme. Change-Id: Ib07e9be99a316eec67b94de0860e08f5f4638959 Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: d3d11/vulkan: Allow passing in an array range overrideLaszlo Agocs2022-03-246-6/+62
| | | | | | | | | | | | | | | | | | Only (straightforwardly) implementable with modern APIs, and only really exists to handle special platform cases, such as when a video framework gives us a D3D texture array with D3D11_BIND_DECODER | D3D11_BIND_SHADER_RESOURCE which is only possible to use as a shader resource if the SRV selects a single array layer. Has no effect on the normal usage of texture arrays, where all array layers are exposed, and it is the shader that selects the layer when sampling or loading via the sampler2DArray. That continues to be the standard way to work with texture arrays. Change-Id: I0a656b605da21f50239b38abb83067e0208c1dbe Reviewed-by: Piotr Srebrny <piotr.srebrny@qt.io> Reviewed-by: Christian Strømme <christian.stromme@qt.io>
* Misc: Do not depend on transitive includesFabian Kosmale2022-03-171-0/+1
| | | | | | | | As a drive-by, remove superfluous includes from qnetworkmanagerservice.h and obey the coding conventions for includes in a few more places. Change-Id: I65b68c0cef7598d06a125e97637040392d4be9ff Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
* Gui: Do not depend on transitive includesFabian Kosmale2022-03-172-0/+3
| | | | | Change-Id: I27321235d9c8428de0cff1e22a618299b9e5a97f Reviewed-by: Marc Mutz <marc.mutz@qt.io>
* QShader: fix memory leak in detach()David Faure2022-03-152-18/+18
| | | | | | | | | | | | | | | | | qAtomicDetach() does d = new T(*d); which calls the copy constructor. Since there was no copy constructor declared for QShaderPrivate, the compiler generated one which copied the refcount over, instead of setting it to 1 in the detached instance. As a result, the destructor didn't delete the QShaderPrivate. Nothing was calling this constructor that takes a pointer, so clearly this was a typo for a copy constructor. Detected in an ASAN build, the qsb tool exited in error. Pick-to: 6.3 6.2 5.15 Change-Id: Idbe659b52d2600ac7c11b09142a6aa5b25310df9 Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* Fix deprecated use of QBA/Q*String::countMårten Nordheim2022-03-151-3/+3
| | | | | | | 'Use size() or length() instead' Change-Id: I284fce29727c4c1ec9ea38a4e8ea13a9e0af5390 Reviewed-by: Sona Kurazyan <sona.kurazyan@qt.io>
* wasm: prevent WebGL vertex attribute errorsMorten Johan Sørvig2022-03-141-0/+8
| | | | | | | | | | | | | | WebGL is stricter than OpenGL ES and require that unused vertex attribute arrays are disabled. This prevents errors such as: WebGL: INVALID_OPERATION: drawElements: no buffer is bound to enabled attribute Pick-to: 6.3 Change-Id: I68384a9f6954b6a1960ba6e8afd1fdbdfefe2335 Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io> Reviewed-by: Lorn Potter <lorn.potter@gmail.com>
* Fix deprecated uses of QScopedPointerMårten Nordheim2022-03-081-3/+5
| | | | | | | | | By changing it to unique_ptr. Pick-to: 6.2 6.3 Change-Id: I91abb69445b537d4c95983ae735341882352b29d Reviewed-by: Marc Mutz <marc.mutz@qt.io> Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
* Make sure all qtbase private headers include at least one otherThiago Macieira2022-02-242-3/+4
| | | | | | | | | | See script in qtbase/util/includeprivate for the rules. Since these files are being touched anyway, I also ran the updatecopyright.pl script too. Change-Id: Ib056b47dde3341ef9a52ffff13ef677e471674b6 Reviewed-by: Marc Mutz <marc.mutz@qt.io>
* Convert string tables in QShaderDescription to use string literals [2/2]Marc Mutz2022-02-091-79/+81
| | | | | | | | | | | Avoid allocating all these strings on load. Part 2: JSON keys. Pick-to: 6.3 6.2 Change-Id: I1724a58d700509c3af90ad1b87cb1bccae1075b8 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io> Reviewed-by: Christian Strømme <christian.stromme@qt.io>
* rhi: Add the long-pending probe() helper, with backing for MetalLaszlo Agocs2022-02-094-0/+62
| | | | | | | | | | | | | | | | | | | | | There is a TODO for this in Qt Quick from the 6.0 times. To decide upfront if Metal can be expected to function, or if a fallback to OpenGL needs to be triggered (especially important with macOS virtual machines, where, unlike any real macOS system, Metal may not be present at all), the scenegraph calls create() and then drops the result. The idea to make this less wasteful was back then to add a dedicated probing function which can, possibly, perform the checks in a more lightweight manner than full initialization. Implement this now, focusing on Metal. Brought to attention by QTBUG-100441: printing warnings about not having an MTLDevice is confusing in a Metal-less macOS VM, because it is not an actual error, only part of the probing at scenegraph initialization. We can now avoid printing confusing warnings there. Change-Id: Ie52c36af9224bedc3f5e4c23edb486d961c9f216 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* Convert string tables in QShaderDescription to use string literals [1/2]Christian Strømme2022-02-051-123/+123
| | | | | | | | | Avoid allocating all these strings on load. Part 1: tables. Pick-to: 6.3 6.2 Change-Id: Ibf7af9aea0088efe68b247c68022b98143634616 Reviewed-by: Marc Mutz <marc.mutz@qt.io> Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
* rhi: d3d11: Switch the default swap effect and scaling modeLaszlo Agocs2022-02-012-26/+48
| | | | | | | | | | | | | | | | | | | | | | [ChangeLog][QtGui][QRhi] With Direct3D 11 the default swap effect is now DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL combined with DXGI_SCALING_NONE. This should provide a better (less "jumpy") resizing experience for Qt Quick content in particular, because the stretch effect for size-mismatched present is not ideal for user interfaces. We'd rather want to keep the size as-is and have the white border on the right/bottom (which we will have anyway, inevitably). This is also closer to what one gets with OpenGL (though that may depend on the driver as well). For Vulkan on Windows, the behavior will remain very similar to what DXGI_SCALING_STRETCH does, depending on the implementation probably, because the Vulkan spec fails to address the handling of scaling modes for size-mismatched presents. To get the old D3D behavior, i.e. FLIP_DISCARD+SCALING_STRETCH, set the environment variable QT_D3D_FLIP_DISCARD to a non-zero value. Pick-to: 6.3 Fixes: QTBUG-99637 Change-Id: Ic8a219fbf3cdb6458b7ec9149bf27e771d9f7ddd Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: d3d11: switch to uuidof everywhereLaszlo Agocs2022-02-011-9/+9
| | | | | | | | | | | | | | There seems to be bizarre issues with IID_* as they are not always exported or are in a different library depending on the SDK and where dxguid.lib comes from. If not mistaken, we don't need these symbols at all because in C++ one can use __uuidof instead (which would not be possible in C code and there the IID_ objects are necessary). Pick-to: 6.3 Change-Id: I04712382630768a742bb5f42cc5fca9ad10ff719 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Christian Strømme <christian.stromme@qt.io> Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Code quality - remove defaults from switch enumsBen Fletcher2022-02-012-28/+11
| | | | | | | | | | | | | On code review of previous RHI patches it was noted that many switch on enum statements contain a default. This is discouraged as it prevents the compiler from automatically identifying switch statements that do not cover all enum cases. This patch addresses rhi base classes. Further patches required for specific backend implementations. Change-Id: Ib2bb30c66fd214b65a4ca7b787c7c610f3c313f5 Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* rhi: d3d11: Try uuidof instead of IID_* to help old MinGWLaszlo Agocs2022-02-011-1/+1
| | | | | | | Fixes: QTBUG-100294 Pick-to: 6.3 Change-Id: Iee90355ecd48a753f9a7ec53e7f5758e3d12eddf Reviewed-by: Christian Strømme <christian.stromme@qt.io>
* rhi: Add the basic infrastructure for geometry shader supportBen Fletcher2022-01-319-7/+68
| | | | | | | | | | | | | | | | | | | | | .. but this will only be supported on Vulkan, OpenGL 3.2+, and Open GL ES 3.2+ for the time being. The situation is: - Vulkan is working. qsb accepts .geom files already, and QShader has existing geometry shader support. - OpenGL 3.2 and OpenGL ES 3.2 are working. - D3D11 is not working. D3D11 supports geometry shaders, but SPIRV- Cross does not support translating geometry shaders to HLSL. - Metal is not working. Metal does not directly support geometry shaders. Change-Id: Ieb7c44c58b8be5f2e2197bf5133cf6847e6c132d Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* rhi: Add support for polygon fill modeBen Fletcher2022-01-318-1/+103
| | | | | | | | | | | | | | | | | Support for Polygon Mode (Triangle Fill Mode in Metal, Fill Mode in D3D) in the RHI graphics pipeline. Options are Fill and Line Status: OpenGL - ok Vulkan - ok Metal - ok D3D11 - ok OpenGL ES - does not support glPolygonMode. Change-Id: I20b7ef416624700c3dc8d1cbe6474f4ca3889db8 Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* rhi: Fix tessellation support for OpenGLBen Fletcher2022-01-282-7/+11
| | | | | | | | | Added shader stage mapping for tessellation stages. Manual test rhi/tessellation now works for OpenGL. Change-Id: I7906b21e9d6e20883f17729f077dba57aa29f4fd Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* rhi: Make sure pixelSize() to a texture rt is always up to dateLaszlo Agocs2022-01-256-0/+27
| | | | | | | | | This is an issue for QQuickWindow in practice, although it is not hit by our current tests. Pick-to: 6.3 Change-Id: Ia73704c1af6a82b2689ce7b844d3b0eb9a17ec18 Reviewed-by: Christian Strømme <christian.stromme@qt.io>
* rhi: d3d: Fix up non-vsynced presentationLaszlo Agocs2022-01-192-24/+48
| | | | | | | | | | | | | | | Doing Present(0, 0) is not necessarily sufficient to get rid of blocking. It may very well start blocking after a few frames. This does not apply to a non-flip-discard swapchain (when running with QT_D3D_NO_FLIP=1), but for flip-discard we should also try using DXGI_SWAP_CHAIN_FLAG_ALLOW_TEARING and DXGI_PRESENT_ALLOW_TEARING in case a swap interval of 0 is wanted. Pick-to: 6.3 Fixes: QTBUG-99949 Change-Id: I9cb13b139ba04e41b4f25b94bcd3d1e973496414 Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* QRhiGles2: replace two QSet<int> with QDuplicateTrackerMarc Mutz2022-01-182-8/+9
| | | | | | | | | | Apart from a more fitting, minimal, API, QDuplicateTracker also transparently uses C++17 pmr::monotonic_buffer_resource to avoid, or at least reduce, memory allocations. Pick-to: 6.3 Change-Id: Ied2574734949b2dadc1bcbaa9d1e3c0ed98ba50a Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* rhi: Add the basic infrastructure for tessellation supportLaszlo Agocs2022-01-139-48/+218
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | ...but this will only be supported with Vulkan and OpenGL 4.0+ and OpenGL ES 3.2+ for the time being. Taking the Vulkan model as our standard, the situation is the following: - Vulkan is ok, qsb secretly accepts .tesc and .tese files as input already (plus QShader already has the necessary plumbing when it comes to enums and such) To switch the tessellation domain origin to bottom left we require Vulkan 1.1 (don't bother with VK_KHR_maintenance2 on top of 1.0 at this point since 1.1 or 1.2 implementations should be common by now). The change is essential to allow the same evaluation shader to work with both OpenGL and Vulkan: this way we can use the same shader source, declaring the tessellation winding order as CCW, with both APIs. - OpenGL 4.0 and OpenGL ES 3.2 (or ES 3.1 with the Android extension pack, but we won't bother with checking that for now) can be made working without much complications, though we need to be careful when it comes to gathering and setting uniforms so that we do not leave the new tessellation stages out. We will stick to the Vulkan model in the sense that the inner and outer tessellation levels must be specified from the control shader, and cannot be specified from the host side, even though OpenGL would allow this. (basically the same story as with point size in vertex shaders) - D3D11 would be no problem API-wise, and we could likely implement the support for hull and domain shader stages in the backend, but SPIRV-Cross does not support translating tessellation shaders to HLSL. Attempting to feed in a .tesc or .tese file to qsb with --hlsl specified will always fail. One issue here is how hull shaders are structured, with the patchconstantfunc attribute specifying a separate function computing the patch constant data. With GLSL there is a single entry point in the tessellation control shader, which then performs both the calculations on the control points as well as the constant data (such as, the inner and outer tessellation factors). One option here is to inject handwritten HLSL shaders in the .qsb files using qsb's replace (-r) mode, but this is not exactly a viable universal solution. - Metal uses a different tessellation pipeline involving compute shaders. This needs more investigation but probably not something we can prioritize in practice. SPIRV-Cross does support this, generating a compute shader for control and a (post-)vertex shader for evaluation, presumably in order to enable MoltenVK to function when it comes to tessellation, but it is not clear yet how usable this is for us. Change-Id: Ic953c63850bda5bc912c7ac354425041b43157ef Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Add queries for vertex input/output limitsLaszlo Agocs2022-01-128-1/+70
| | | | | | | | | | Mainly because we do have legacy code in the Qt 5 graphical effects that tries to dynamically determine the max number of varyings. Make it easier to port such code. Change-Id: I846cab2c2fe7b4cd473b5ced0146ca36f1c8169b Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Christian Strømme <christian.stromme@qt.io>
* rhi: Improve the handling of HDR capable texture formatsLaszlo Agocs2022-01-117-32/+73
| | | | | | | | | | | Add some sort of autotest for both RGBA16F and the new RGB10A2. The latter is introduced particularly because ideally we should have a texture format that corresponds to the D3D/Vulkan swapchain color buffer format with HDR10. Change-Id: I1e1bbb7c7e32cb3db89275900811c0bcaeac39d6 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Add some docs for the hdr info queriesLaszlo Agocs2022-01-111-0/+55
| | | | | Change-Id: I9b3b62ac83642a7d3e474c991e572877b9e46ca5 Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: gl: Prevent breaking with ES when querying the sampler mapping tableLaszlo Agocs2022-01-072-17/+17
| | | | | | | | Send the full QShaderVersion down the line, not just the version number. Change-Id: I895d552fc47e0eb4ca92f32f117cd5a1d4d9015a Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Returns mapping tables by value from QShaderLaszlo Agocs2022-01-075-31/+26
| | | | | | | | | As these are QList and QHash. All existing usages are based on this anyway, no value in being able to indicate "not available" - an empty container fulfills the same role. Change-Id: I8059025fa7a4acb6fc674cd98b16fcafa19ed85d Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: gl: Do not just rely on GL_COMPRESSED_TEXTURE_FORMATSLaszlo Agocs2022-01-062-56/+104
| | | | | | | Pick-to: 6.3 6.2 Task-number: QTBUG-98937 Change-Id: I64f2783ae64ad3ef77a389999ded4c9ba2c46ee5 Reviewed-by: Eirik Aavitsland <eirik.aavitsland@qt.io>
* rhi: Add support for separate image and sampler objectsLaszlo Agocs2022-01-067-134/+507
| | | | | | | | | | | | | | | | | | | | | For Direct 3D, Metal, and Vulkan this is natively supported. (and makes no difference in particular for D3D and Metal because they do not have the legacy combined image sampler concept anyways) With OpenGL it will work too, but this relies on SPIR-Cross magic and is still using a combined sampler (e.g. a sampler2D) in the GLSL shader. The GL backend walks back and forth in the mapping tables from the shader baker in order to make this work, which is presumably slightly more expensive than combined image samplers. Do note that combined image samplers (i.e. sampler2D in the shader and QRhiShaderResourceBinding::sampledTexture() in code) continue to be the primary, recommended way for any user of the rhi for the time being. Change-Id: I194721bc657b1ffbcc1bb79e6eadebe569a25087 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* rhi: Expose HDR output info in a saner wayLaszlo Agocs2022-01-065-48/+72
| | | | | | | | | | Don't bother with exposing the IDXGIOutput6. Instead, report the values, just the ones that matter for tonemapping or transfer functions in a cross-platform way that's also prepared for Metal's different way of doing things. Change-Id: I28c7b6144f8267a9d3d44eff1e40697fb543385f Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Drop the profiler for nowLaszlo Agocs2022-01-0416-1173/+153
| | | | | | | | | | | | | | | | | | | | | | | | | | | The system we inherited from the original Qt 5.14 introduction of QRhi is a text stream based solution where resource creation and frame timings are sent in a comma-separated format to a QIODevice. This, while useful to get insights about the number of resources at a given time, is not actively helpful. The frameworks built on top (Qt Quick, Qt Quick 3D) are expected to provide solutions for logging timings in a different way (e.g. via the QML Profiler). Similarly, tracking active resources and generating statistics from that is better handled on a higher level. The unique bits, such as the Vulkan memory allocator statistics and the GPU frame timestamps, are converted into APIs in QRhi. This way a user of QRhi can query it at any time and do whatever it sees fit with the data. When it comes to the GPU timestamps, that has a somewhat limited value due to the heavy asynchronousness, hence the callback based API. Nonetheless, this is still useful since it is the only means of reporting some frame timing data (an approx. elapsed milliseconds for a frame) from the GPU side. Change-Id: I67cd58b81aaa7e343c11731f9aa5b4804c2a1823 Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
* rhi: Enable exposing separate image and sampler objects from the shaderLaszlo Agocs2022-01-036-13/+210
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Adds the following in a QShader/QShaderDescription: - a list of separate images - a list of separate samplers - a list of "combined_sampler_uniform_name" -> [ separate_texture_binding, separate_sampler_binding ] mappings (relevant for GLSL only) On the QShader (and qsb/QShaderBaker) level not having separate image (texture) and sampler objects exposed in the reflection info is not entirely future proof. Right now we benefit strongly from the fact that Vulkan/SPIR-V supports both combined and separate images/samplers, while for HLSL and MSL SPIRV-Cross translates combined image samplers to separate texture and sampler objects, but it is not given that relying on combined image samplers will always be possible in the long run; it is mostly a legacy OpenGL thing that just happens to be supported in Vulkan/SPIR-V due to some benefits with certain implementations/hw, but is not something present in any newer APIs. In addition, before this patch, attempting to run a shader with separate textures and samplers through qsb will just fail for GLSL, even though SPIRV-Cross does have the ability to generate a "fake" combined sampler for each separate texture+sampler combination. Take this into use. This also involves generating and exposing a combined_name->[separate_texture_binding,separate_sampler_binding] mapping table for GLSL, not unlike we have the native binding map for HLSL and MSL. A user (such as, the GL backend of QRhi) would then use this table to recognize what user-provided texture+sampler binding point numbers correspond to which auto-generated sampler2Ds in the GL program. Take the following example: layout(binding = 1) uniform texture2D sepTex; layout(binding = 2) uniform sampler sepSampler; layout(binding = 3) uniform sampler sepSampler2; Inn the reflection info (QShaderDescription) this (assuming a corresponding qtshadertools patch in place) now gives one entry in separateImages() and two in separateSamplers(). Assuming sepTex is used both with sepSampler and sepSampler2, the GLSL output and mapping table from QShaderBaker will have two auto-generated sampler2Ds (and no 'texture2D' or 'sampler'). One immediate benefit is that it is now possible to create a shader that relies only on separate images and samplers, feed it into qsb, generate all the possible targets, and then also feed the SPIR-V binary into a tool or library such as Tint (e.g. to generate WGSL) that canot deal with combined image samplers. Change-Id: I9b19847ea5854837b45d3a23edc788c48502aa15 Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Add the basics for HDR swapchainsLaszlo Agocs2022-01-0313-47/+328
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | ...backed by support in the backends for D3D11 and Vulkan. Expose only what works in practice: scRGB with RGBA16F and HDR10 with RGB10A2 (or A2BGRA10 etc.). For general use, e.g. to render 2D/3D content, scRGB (i.e. extended sRGB linear) should be chosen because that is a linear space. On Windows with a HDR10 display (and an NVIDIA card) both of these are known to work, as long as Use HDR is enabled in the Settings for the display on which the window is created. When requesting a HDR format and it is not supported, we will fall back to the default SDR RGBA8/BGRA8 format. However, the behavior seems to be a bit weird with Vulkan and NVIDIA at least when there is a HDR display but Use HDR is set to Off: this seems to enable HDR mode for the lifetime of the window (with the usual set of black screens while switching over the entire display). Not sure why the driver does this. With D3D/DXGI, with fewer abstractions in the way, we can check upfront properly, so that will nicely fall back to the defaults regardless of why HDR is not available. Support can also be checked in advance via QRhiSwapChain::isFormatSupported() as long as the QWindow is available. (though with Vulkan, as said above, this also seems to ignore the Use HDR setting of Windows) Complications, such as moving a window from one screen to another, are currently not known how they behave. To be seen how this is handled by the Windows compositor. (from 1903 and up it is said to be able to automatically downconvert scRGB to SDR so perhaps moving from a HDR to a non-HDR screen would work - remains to be seen if this needs something more involved) When it comes to other platforms and potential future support: - based on its docs Android 8+ may support scRGB with Vulkan as-is on a suitable device/display, as long as the application declares android:colorMode="wideColorGamut" in the manifest. - for Metal the layer can be made EDR enabled and then e.g. MTLPixelFormatRGBA16Float/kCGColorSpaceExtendedLinearSRGB should work. However, this won't be added unless we can test it. - Linux is unknown. If one needs access to display specific values such as the min/max luminance when implementing tonemapping or a transfer function, that needs platform/API specific approaches, and sadly the kind of data exposed seems to vary, potentially making it difficult to maintain a single cross-platform logic. With D3D one can get the DXGI_OUTPUT_DESC1 from the IDXGIOutput6. This has the min/max luminances in nits and a bunch of other things. For convenience the output object is now exposed from the swapchain's nativeHandles() whenever the D3D backend is used at run time. For Metal one would presumably access maximumExtendedDynamicRangeColorComponentValue and co. in the NSScreen. Elsewhere one needs to rely on platform/winsys specific approaches, if there are any. Remains to be seen longer term if/how this needs/can be better supported. Change-Id: I2e61a0e062282d4bfdfba39655941c0f9a795112 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: Auto-rebuild rt by tracking attachment id and generationLaszlo Agocs2021-12-1011-2/+162
| | | | | | | | | | | | | | | | | | | | | | | Unlike the shader resource binding lists that automatically recognize in setShaderResources() when a referenced QRhiResource has been rebuilt in the meantime (create() was called i.e. there may be completely different native objects underneath), QRhiTextureRenderTarget has no such thing. This leads to an asymmetric API and requires also rebuilding the rt whenever an attachment is rebuilt: rt = rhi->newTextureRenderTarget({ { texture } }) rt->create() cb->beginPass(rt, ...) texture->setPixelSize(...) texture->create() rt->create() // this should not be needed cb->beginPass(rt, ...) Avoid having to do that second rt->create(). Change-Id: If14eaa7aac3530950498bbdf834324d0741a7c4d Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* Callbacks for begin/end of a frame on OpenGLEskil Abrahamsen Blomfeldt2021-12-081-0/+6
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | The background for this is that when running Wayland, the Mesa driver has an issue which makes it crash if we call eglDestroySurface() while we are rendering to it. This is not according to the documentation, and it only seems to happen on Mesa and only on Wayland, so it is probably related to something in the Wayland implementation in the driver. Since this driver is very popular, we want to work around it, which can easily be done using existing locking mechanisms in the Qt Wayland QPA plugin. But in order to do so, we need reliable callbacks for the start and end of a frame. The RHI already has this, so we just need to channel the information to the QPA plugin. Having beginFrame/endFrame hooks in the QPlatformOpenGLContext could be useful in other cases as well, especially knowing that there are OpenGL implementations that require some extra thread protection. QPlatformSurface would be a more general location for these hooks, but since the issue is only seen on OpenGL and multi-threading is handled more explicitly in other APIs, we don't want to expose this API in a more general location than necessary. Task-number: QTBUG-92249 Change-Id: I97ce7d4f744c4b28eec457e919d1c9652ff00079 Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io> Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@qt.io>
* Restrict clang warning disabler to affected versionsEdward Welbourne2021-12-021-0/+2
| | | | | | | | | | | Apparently -Wdeprecated-copy got added between clang 9 and 11. Versions without it warn about the attempt to suppress this option's warnings. This follows-up on commit 8662fbdd7e0c8c5b089a3c9871ae0cd71790858e Change-Id: I7fe9258cfe8a79d24c1f8b331a56468415b25cdb Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
* rhi: metal: Ignore baseInstance if not supportedLaszlo Agocs2021-11-261-3/+9
| | | | | | | | | | | | | | | | | | | | | | A previous patch already introduced calling the correct variant of drawIndexedPrimitives, but it was not done for drawPrimitives. When base vertex and instance is not supported (e.g. on the iOS simulator), it does not mean that the value cannot be other than 0, but rather that the version of the function taking this arguments must not be called at all, otherwise a Metal failure occurs. The docs and logic is all in place, just add it to draw() as well. Amends 213755a86622ae8b3ed3d7ad34a6aecd051b2b03 which fixed this for indexed draw calls. Now we also prevent aborting Qt Quick applications that trigger non-indexed draw calls. Change-Id: Icb4313ffd2d3a77a73f7b5f49d7ce63c935254d3 Pick-to: 6.2 Task-number: QTBUG-95795 Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* rhi: gl: Optimize context/surface changesLaszlo Agocs2021-11-262-12/+24
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | When there is a context with a surface current, keep on using that whenever ensureContext() is called without specifying a QWindow. Consider the following sequence: <component A> beginOffscreenFrame render to texture 1 endOffscreenFrame <component B> beginOffscreenFrame render to texture 2 endOffscreenFrame <component C> beginFrame (with swapchain) render something using texture 1 and 2 endFrame repeat all over again, continuously (in practice this is what a top level widget with QOpenGLWidgets and/or QQuickWidgets in it would lead to with the QRhi migration in place) Besides being more readable, the new version recognizes that resource and offscreen operations do not need one specific surface (like the one QOffscreenSurface every GL backend of QRhi has), but are functional with any surface (or with surfaceless even) as long as the context is correct. Thus with the above example we can work with only ever making the one QWindow current. Change-Id: I633071cae88f02e1d45e445ee55c8a58f9ec5a8c Pick-to: 6.2 Fixes: QTBUG-96405 Reviewed-by: Andy Nichols <andy.nichols@qt.io>
* d3d11rhi: remove leftover of pre-win10 codeYuhang Zhao2021-11-261-3/+1
| | | | | | | | | Amends commit 1e085b9e15abeb45bbbf7995818fcd9c94bfefe1 Task-number: QTBUG-84432 Pick-to: 6.2 Change-Id: Id48fb6c2a9c7d24f1525975c6c154dbc323bbc25 Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>