与OpacityMask相反

时间:2016-05-30 20:12:54

标签: qt qml qt5 opacitymask

它使用另一个项目屏蔽源项目,因此只有在蒙版不透明的情况下,源才可见。如何只在面具透明的地方看到源?

目前已完成着色器,但我想替换它。

无法反转蒙版,因为它由多个图像组成:单独反转图像的总和与总和的反转不同。

2 个答案:

答案 0 :(得分:2)

Qt没有可以做你需要的组件。 OpacityMask最接近您的需求。您可以在此路径中的官方存储库或计算机上查看其代码here Qt_folder / Qt_version / Qt_kit / qml / QtGraphicalEffects / OpacityMask.qml 。这样您就可以轻松浏览所有QtGraphicalEffects组件的源代码。

使用ShaderEffect是完成任务的不错选择。

正如GrecKo所指出,invert对象中已存在OpacityMask属性。它将在Qt 5.7中提供,但代码已在上面的链接中提供。您可以等待更新或下载组件并在项目中使用它。

答案 1 :(得分:0)

如果您想使用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;
                }
            "
        }
    }
}

Opacity Mask using QML Item (Rectangle)