从元素中删除类而不影响正在进行的css转换

时间:2016-11-27 17:32:46

标签: javascript jquery css css-transitions transition

好吧,我有一种情况,我基本上建立了一个小的通知下拉框,当用户做某事时发生,最后它转换到opacity: 0;状态。

但是,因为用户可能会点击其他会再次触发此通知框的内容,我试图找到一种方法将其重置为正常状态,而不会影响任何正在进行的转换并尝试通过< em> CSS 而不是 JavaScript

CodePen: http://codepen.io/gutterboy/pen/WoEydg

HTML:

<a href="#">Open Notify Window</a>

<div id="top_notify" class="top-notify">
    <div class="container-fluid">
        <div class="row">
            <div class="content col-xs-12">
                <div class="alert" role="alert"></div>
            </div>
        </div>
    </div>
</div>

SCSS:

body {
    text-align: center;
    padding-top: 150px;
}

.top-notify {
    position: fixed;
    top: 0;
    width: 100%;
    z-index: 9999;

    .content {
        text-align: center;
        background-color: transparent;
        transform-style: preserve-3d;
    }

    .alert {
        display: inline-block;
        transform: translateY(-100%);
        min-width: 250px;
        max-width: 500px;
        border-top-left-radius: 0;
        border-top-right-radius: 0;

        &.visible {
            transform: translateY(0%);
            transition: 0.8s 0s, opacity 1s 3.8s;
            opacity: 0;
        }

    }

}

JS:

$('a').on('click', function(e){
    e.preventDefault();
    myFunc();
});

function myFunc() {

    // Set file to prepare our data
    var loadUrl = "https://crossorigin.me/http://codepen.io/gutterboy/pen/ObjExz.html";

    // Run request

    getAjaxData(loadUrl, null, 'POST', 'html')

            .done(function(response) {

                var alert_el = $('#top_notify').find('.alert');

                // Update msg in alert box
                alert_el.text(response);
                alert_el.addClass('alert-success');

                // Slide in alert box
                alert_el.addClass('visible');

            })

            .fail(function() {
                alert('Problem!!');
            });

    // End

}

function getAjaxData(loadUrl, dataObject, action, type) {

    return jQuery.ajax({
        type: action,
        url: loadUrl,
        data: dataObject,
        dataType: type
    });

}

我知道我可以通过在JS中执行此操作将其重置为正常状态:

$('#top_notify').find('.alert').removeClass().addClass('alert'); // The classes it ends up with vary

...但是这样做会在转换完成之前删除类,淡出不透明度并且它会立即消失。

我知道我可以在JS中做一个延迟来抵消CSS延迟,但这样做并不是一个非常好的方法,因为你有两个不同的地方的时间。

有什么方法可以在通过CSS完成动画的同时实现这一点,或者我必须转向使用jQuery的animate,这样我可以在动画完成后运行重置程序吗?

1 个答案:

答案 0 :(得分:1)

好的,我提出了一个简单的解决方案,想出了一个令人费解的一个哈哈。

我应该首先提出的简单解决方案是删除ajax调用之前添加的任何其他类;我过于专注于在ajax区域内进行,当然这不起作用,但在我开始玩其他解决方案之前,我从未尝试过。

任何方式,简单的解决方案只是移动此代码:

 var alert_el = $('#top_notify').find('.alert');

...高于ajax来电,而不是在其中。

然后直接在其下添加:

alert_el.removeClass('visible alert-success alert-info alert-danger alert-warning');

完整的功能代码为:

function myFunc() {

    // Set file to prepare our data
    var loadUrl = "https://crossorigin.me/http://codepen.io/gutterboy/pen/ObjExz.html";

    var alert_el = $('#top_notify').find('.alert');

    alert_el.removeClass('visible alert-success alert-info alert-danger alert-warning');

    // Run request

    getAjaxData(loadUrl, null, 'POST', 'html')

            .done(function(response) {

                // Update msg in alert box
                alert_el.text(response);
                alert_el.addClass('alert-success');

                // Slide in alert box
                alert_el.addClass('visible');

            })

            .fail(function() {
                alert('Problem!!');
            });

    // End

}

CodePen: http://codepen.io/gutterboy/pen/xRXbXy

我提出的另一个解决方案,虽然现在不是真的需要,我想我会发布它,以防它在将来为我(或其他人)派上用场。

动画完成后没有删除visible类(因为我不知道在完成动作时提醒JS)但visible类 - 如果使用此方法我将更改其名称 - 不会添加任何新样式,它只会运行动画。

我是这样做的:

JavaScript仍然与上面的解决方案相同,它都在CSS中。

<强> TLDR;

基本上使用多个CSS动画来控制效果运行时期间的不同状态; CodePen在底部。

.visible类中的更改以及一些@keyframes的添加。

.visible class:

&.visible {
    animation: slideDown 0.8s 0s, keepThere 3s 0.8s, fadeAway 1s 3.8s;
}

正如你所看到的,我们已经摆脱了任何额外的样式 - 这意味着当动画完成时,它基本上重置恢复正常,这就是我们想要的。

现在,让我们分解这段代码:

我们在这里运行3种不同的动画,重要的是要注意它们不要一个接一个地运行 - 这意味着它们不会等到一个完成直到它开始下一个动画,因此我们需要包含delay设置。

首先,我们从slideDown动画开始:

slideDown 0.8s 0s

如果您不熟悉CSS中的动画,那么基本上它的作用是在0s开始运行之前设置延迟并且动画运行0.8s,这就是动画:

@keyframes slideDown {
    0% {
        transform: translateY(-100%);
    }
    100% {
        transform: translateY(0%);
    }
}

所以,非常简单,只需将transform-100%向下滑动到0%,此动画将在我们调用此动画时设置0.8s。< / p>

现在,我想让它可见 3秒,然后开始消失,但我们遇到了问题;一旦动画结束,它就会回到它的标准样式,在我们的例子中它意味着它会随着它回到transform: translateY(-100%)而消失,因为我们在.visible类中没有额外的样式,并且我们无法在那里添加任何额外的样式,因为我们无法重置它回到它的原始状态(风格明智)。

但我们该怎么办? fadeAway动画不会再开始3秒,而且此刻它没有任何消失的东西(确实如此,但是你不能将其视为&#39} ; s隐藏)。

解决方法是添加另一个动画 - 在技术上并没有真正动画任何动画,只是在fadeAway动画开始之前让它保持可见。

我们到达的地方:

keepThere 3s 0.8s

现在,记住我们fadeAway动画的设置是:fadeAway 1s 3.8s这意味着我们在此动画开始之前有 3秒,因此我们无法控制任何造型与它。

这就是这些参数值的来源 - 我们将延迟设置为0.8s,以便keepThere动画在slideDown动画完成之前不会启动;然后我们设置3s的持续时间来计算等待时间,直到fadeAway动画开始,这是keepThere动画:

@keyframes keepThere {
    0%, 100% {
        transform: translateY(0%);
    }
}

由于它具有相同的开始和结束样式,我们将它组合成0%, 100%的一个选择器,正如您所看到的,这就像它所说的那样,使元素在{{{ 1}}直到我们可以使用3s动画来控制样式。

我想技术上你可以将这个功能组合到fadeAway动画中,如果你想在%等于 3秒的情况下进行数学计算,那么就知道何时开始淡化元素。

最后我们有fadeAway动画:

fadeAway

正如我们上面所讨论的,我们已经知道为什么我们将fadeAway 1s 3.8s设置为delay3.8s偏移量以允许0.8s动画运行并且额外的slideDown延迟,因为我们希望元素可以显示多长时间,直到它开始消失为止,当然淡化需要3s才能完成。

这个动画是:

1s

现在,由于@keyframes fadeAway { 0%, 100% { transform: translateY(0%); } 0% { opacity: 1; } 100% { opacity: 0; } } 动画已经完成,我们必须确保元素可见,以便淡入淡出有一些可见的东西实际消失,这就是我们确保包含样式的原因keepThere作为从头到尾的值;之后,我认为它的作用非常明显。

把它们放在一起然后得到:

transform: translateY(0%);

CodePen: http://codepen.io/gutterboy/pen/QGqwBg

然后当然能够再次运行它必须重新添加类,因此这是在每次运行开始时(在ajax调用之前)删除.top-notify { position: fixed; top: 0; width: 100%; z-index: 9999; .content { text-align: center; background-color: transparent; transform-style: preserve-3d; } .alert { display: inline-block; transform: translateY(-100%); min-width: 250px; max-width: 500px; border-top-left-radius: 0; border-top-right-radius: 0; &.visible { animation: slideDown 0.8s 0s, keepThere 3s 0.8s, fadeAway 1s 3.8s; } } } @keyframes slideDown { 0% { transform: translateY(-100%); } 100% { transform: translateY(0%); } } @keyframes keepThere { 0%, 100% { transform: translateY(0%); } } @keyframes fadeAway { 0%, 100% { transform: translateY(0%); } 0% { opacity: 1; } 100% { opacity: 0; } } 类的目的然后当它在ajax调用期间重新添加时,再次运行

感谢@Nathaniel Flick分享链接,让我沿着这条道路开始:)

嗯,希望这对于某人看起来很方便,因为我不再使用该选项ha!