【11】qml弹出层,禁止事件穿透

最近在写弹出层时遇到事件穿透,刚好找到这篇文章得以解决,在这分享一下。核心思路:一个mask层,一个最顶层,都用rectangle,禁止事件穿透。

Rectangle {
    id: root
    width: 100
    height: 200
    color: 'lightblue'
    z:100
    transformOrigin: Item.Center  // 无效
 
    // 公有属性
    property bool showMask : false;
    property string animationType : 'none';
    property int duration : 500
    property int easingType : Easing.OutBounce
 
 
    // 私有属性
    property int innerX;
    property int innerY;
    property int innerWidth;
    property int innerHeight;
    property double innerOpacity;
 
    //------------------------------
    // 事件
    //------------------------------
    // 属性备份一下,避免动画对属性进行变更
    Component.onCompleted: {
        save();
    }
 
    function show()
    {
        reset();
        switch (animationType)
        {
            case "fade":     animFadeIn.start(); break;
            case "focus":    animFocusIn.start(); break;
            case "width":    animWidthIncrease.start(); break;
            case "height":   animHeightIncrease.start(); break;
            case "size":     animBig.start(); break;
            case "flyDown":  animInDown.start(); break;
            case "flyUp":    animInUp.start(); break;
            case "flyLeft":  animInLeft.start(); break;
            case "flyRight": animInRight.start(); break;
            default:         this.visible = true;
        }
    }
 
    function hide()
    {
        switch (animationType)
        {
            case "fade":    connector.target = animFadeOut;
                            animFadeOut.start(); break;
            case "focus":   connector.target = animFocusOut;       
                            animFocusOut.start(); break;
            case "width":   connector.target = animWidthDecrease;  
                            animWidthDecrease.start();   break;
            case "height":  connector.target = animHeightDecrease; 
                            animHeightDecrease.start();  break;
            case "size":    connector.target = animSmall;            
                           animSmall.start();   break;
            case "flyDown": connector.target = animOutUp;          
                          animOutUp.start();   break;
            case "flyUp":   connector.target = animOutDown;        
                          animOutDown.start(); break;
            case "flyLeft": connector.target = animOutRight;       
                          animOutRight.start();break;
            case "flyRight":connector.target = animOutLeft;        
                          animOutLeft.start(); break;
            default:        close();
        }
    }
 
    // 动画结束后调用的脚本
    Connections{
        id: connector
        target: animInDown
        onStopped: close()
    }
    //------------------------------
    // 辅助方法
    //------------------------------
    function getRoot(item)
    {
        return (item.parent !== null) ? getRoot(item.parent) : item;
    }
 
    function save()
    {
        innerX = root.x;
        innerY = root.y;
        innerWidth = root.width;
        innerHeight = root.height;
        innerOpacity = root.opacity;
        console.log("x=" + innerX + " y="+innerY + " w=" + innerWidth + " h="+innerHeight);
    }
 
    function reset()
    {
        root.x = innerX;
        root.y = innerY;
        root.width = innerWidth
        root.height = innerHeight;
        root.opacity = innerOpacity;
        root.scale = 1;
 
        connector.target = null;
        mask.visible = showMask;
        root.visible = true;
    }
 
    // 立即关闭
    function close()
    {
        mask.visible = false;
        root.visible = false;
        log();
    }
 
    function log()
    {
        console.log("x=" + x + " y="+y + " w=" + width + " h="+height);
    }
    //------------------------------
    // 遮罩
    //------------------------------
    // 禁止事件穿透
    MouseArea{
        anchors.fill: parent;
        onPressed:{
             mouse.accepted = true
        }
        drag.target: root  // root可拖动
    }
 
    // 灯箱遮罩层
    Mask{
        id: mask
        visible: false
    }
 
    //------------------------------
    // 动画
    //------------------------------
    // fadeIn/fadeOut
    PropertyAnimation {
        id:animFadeIn
        target: root
        duration: root.duration
        easing.type: root.easingType
        property: 'opacity';
        from: 0;
        to: root.innerOpacity
    }
    PropertyAnimation {
        id: animFadeOut
        target: root
        duration: root.duration
        easing.type: root.easingType
        property: 'opacity';
        from: root.innerOpacity;
        to: 0
    }
    ...
}

效果图:


3956112-84fd4e1ddcfc2ebb.gif

原文链接:
http://www.cnblogs.com/surfsky/p/3998391.html

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值