与 OpacityMask 相反
Opposite for OpacityMask
它用另一个项目遮盖源项目,因此只有在遮罩不透明的情况下,源才可见。如何使源仅在蒙版透明的地方可见?
目前是用着色器完成的,但我想替换它。
不能反转mask,因为它由多个图像组成:单个反转图像的总和与总和的反转不同。
没有 Qt 制作的组件可以满足您的需要。 OpacityMask
最接近您的需要。您可以在官方存储库或您机器上的此路径中查看其代码 here:Qt_folder/Qt_version/Qt_kit/qml/QtGraphicalEffects/OpacityMask.qml。这样您就可以轻松浏览所有QtGraphicalEffects组件的源代码。
使用 ShaderEffect
是完成任务的不错选择。
正如 GrecKo 所指出的,OpacityMask
对象中已经有一个 invert
属性。它将在 Qt 5.7 中可用,但代码已在上面的 link 中可用。您可以等待更新或下载组件并在您的项目中使用它。
如果你喜欢使用 QML 项目(矩形),你可以使用以下代码:
import QtQuick 2.6
Item {
anchors.fill: parent
Image {
anchors.fill: parent
source: "http://i.imgur.com/R3yMj0y.jpg"
fillMode: Image.PreserveAspectCrop
focus: true
Keys.onRightPressed: _mask.maskX += 100
Keys.onLeftPressed: _mask.maskX -= 100
Keys.onUpPressed: _mask.maskY -= 100
Keys.onDownPressed: _mask.maskY += 100
MouseArea {
anchors.fill: parent
hoverEnabled: true
onPositionChanged: {
_mask.maskX = mouseX;
_mask.maskY = mouseY;
}
}
}
Rectangle {
id: _bk
anchors.fill: parent
color: "#33000000"
visible: false
layer.enabled: true
layer.smooth: true
}
Rectangle {
id: _mask
anchors.fill: parent
color: "transparent"
visible: true
property int maskX: 0
property int maskY: 0
Rectangle {
id: circle
width: 100; height: 100
x: _mask.maskX-50; y: _mask.maskY-50
radius: 50
color: "#000"
Behavior on x { NumberAnimation { duration: 400; easing.type: Easing.OutBack; easing.overshoot: 1.4 } }
Behavior on y { NumberAnimation { duration: 400; easing.type: Easing.OutBack; easing.overshoot: 1.4 } }
}
layer.enabled: true
layer.samplerName: "maskSource"
layer.effect: ShaderEffect {
property variant source: _bk
fragmentShader: "
varying highp vec2 qt_TexCoord0;
uniform highp float qt_Opacity;
uniform lowp sampler2D source;
uniform lowp sampler2D maskSource;
void main(void) {
gl_FragColor = texture2D(source, qt_TexCoord0.st) * (1.0-texture2D(maskSource, qt_TexCoord0.st).a) * qt_Opacity;
}
"
}
}
Rectangle {
id: _mask2
anchors.fill: parent
color: "transparent"
visible: true
Rectangle {
id: circle2
width: 150; height: 150
x: _mask.maskX-75; y: _mask.maskY-75
radius: 75
color: "#000"
Behavior on x { NumberAnimation { duration: 550; easing.type: Easing.OutBack; easing.overshoot: 2.4 } }
Behavior on y { NumberAnimation { duration: 550; easing.type: Easing.OutBack; easing.overshoot: 2.4 } }
}
layer.enabled: true
layer.samplerName: "maskSource"
layer.effect: ShaderEffect {
property variant source: _bk
fragmentShader: "
varying highp vec2 qt_TexCoord0;
uniform highp float qt_Opacity;
uniform lowp sampler2D source;
uniform lowp sampler2D maskSource;
void main(void) {
gl_FragColor = texture2D(source, qt_TexCoord0.st) * (1.0-texture2D(maskSource, qt_TexCoord0.st).a) * qt_Opacity;
}
"
}
}
Rectangle {
id: _mask3
anchors.fill: parent
color: "transparent"
visible: true
Rectangle {
id: circle3
width: 220; height: 220
x: _mask.maskX-110; y: _mask.maskY-110
radius: 110
color: "#000"
Behavior on x { NumberAnimation { duration: 650; easing.type: Easing.OutBack; easing.overshoot: 3.0 } }
Behavior on y { NumberAnimation { duration: 650; easing.type: Easing.OutBack; easing.overshoot: 3.0 } }
}
layer.enabled: true
layer.samplerName: "maskSource"
layer.effect: ShaderEffect {
property variant source: _bk
fragmentShader: "
varying highp vec2 qt_TexCoord0;
uniform highp float qt_Opacity;
uniform lowp sampler2D source;
uniform lowp sampler2D maskSource;
void main(void) {
gl_FragColor = texture2D(source, qt_TexCoord0.st) * (1.0-texture2D(maskSource, qt_TexCoord0.st).a) * qt_Opacity;
}
"
}
}
}
它用另一个项目遮盖源项目,因此只有在遮罩不透明的情况下,源才可见。如何使源仅在蒙版透明的地方可见?
目前是用着色器完成的,但我想替换它。
不能反转mask,因为它由多个图像组成:单个反转图像的总和与总和的反转不同。
没有 Qt 制作的组件可以满足您的需要。 OpacityMask
最接近您的需要。您可以在官方存储库或您机器上的此路径中查看其代码 here:Qt_folder/Qt_version/Qt_kit/qml/QtGraphicalEffects/OpacityMask.qml。这样您就可以轻松浏览所有QtGraphicalEffects组件的源代码。
使用 ShaderEffect
是完成任务的不错选择。
正如 GrecKo 所指出的,OpacityMask
对象中已经有一个 invert
属性。它将在 Qt 5.7 中可用,但代码已在上面的 link 中可用。您可以等待更新或下载组件并在您的项目中使用它。
如果你喜欢使用 QML 项目(矩形),你可以使用以下代码:
import QtQuick 2.6
Item {
anchors.fill: parent
Image {
anchors.fill: parent
source: "http://i.imgur.com/R3yMj0y.jpg"
fillMode: Image.PreserveAspectCrop
focus: true
Keys.onRightPressed: _mask.maskX += 100
Keys.onLeftPressed: _mask.maskX -= 100
Keys.onUpPressed: _mask.maskY -= 100
Keys.onDownPressed: _mask.maskY += 100
MouseArea {
anchors.fill: parent
hoverEnabled: true
onPositionChanged: {
_mask.maskX = mouseX;
_mask.maskY = mouseY;
}
}
}
Rectangle {
id: _bk
anchors.fill: parent
color: "#33000000"
visible: false
layer.enabled: true
layer.smooth: true
}
Rectangle {
id: _mask
anchors.fill: parent
color: "transparent"
visible: true
property int maskX: 0
property int maskY: 0
Rectangle {
id: circle
width: 100; height: 100
x: _mask.maskX-50; y: _mask.maskY-50
radius: 50
color: "#000"
Behavior on x { NumberAnimation { duration: 400; easing.type: Easing.OutBack; easing.overshoot: 1.4 } }
Behavior on y { NumberAnimation { duration: 400; easing.type: Easing.OutBack; easing.overshoot: 1.4 } }
}
layer.enabled: true
layer.samplerName: "maskSource"
layer.effect: ShaderEffect {
property variant source: _bk
fragmentShader: "
varying highp vec2 qt_TexCoord0;
uniform highp float qt_Opacity;
uniform lowp sampler2D source;
uniform lowp sampler2D maskSource;
void main(void) {
gl_FragColor = texture2D(source, qt_TexCoord0.st) * (1.0-texture2D(maskSource, qt_TexCoord0.st).a) * qt_Opacity;
}
"
}
}
Rectangle {
id: _mask2
anchors.fill: parent
color: "transparent"
visible: true
Rectangle {
id: circle2
width: 150; height: 150
x: _mask.maskX-75; y: _mask.maskY-75
radius: 75
color: "#000"
Behavior on x { NumberAnimation { duration: 550; easing.type: Easing.OutBack; easing.overshoot: 2.4 } }
Behavior on y { NumberAnimation { duration: 550; easing.type: Easing.OutBack; easing.overshoot: 2.4 } }
}
layer.enabled: true
layer.samplerName: "maskSource"
layer.effect: ShaderEffect {
property variant source: _bk
fragmentShader: "
varying highp vec2 qt_TexCoord0;
uniform highp float qt_Opacity;
uniform lowp sampler2D source;
uniform lowp sampler2D maskSource;
void main(void) {
gl_FragColor = texture2D(source, qt_TexCoord0.st) * (1.0-texture2D(maskSource, qt_TexCoord0.st).a) * qt_Opacity;
}
"
}
}
Rectangle {
id: _mask3
anchors.fill: parent
color: "transparent"
visible: true
Rectangle {
id: circle3
width: 220; height: 220
x: _mask.maskX-110; y: _mask.maskY-110
radius: 110
color: "#000"
Behavior on x { NumberAnimation { duration: 650; easing.type: Easing.OutBack; easing.overshoot: 3.0 } }
Behavior on y { NumberAnimation { duration: 650; easing.type: Easing.OutBack; easing.overshoot: 3.0 } }
}
layer.enabled: true
layer.samplerName: "maskSource"
layer.effect: ShaderEffect {
property variant source: _bk
fragmentShader: "
varying highp vec2 qt_TexCoord0;
uniform highp float qt_Opacity;
uniform lowp sampler2D source;
uniform lowp sampler2D maskSource;
void main(void) {
gl_FragColor = texture2D(source, qt_TexCoord0.st) * (1.0-texture2D(maskSource, qt_TexCoord0.st).a) * qt_Opacity;
}
"
}
}
}