如何在计时器不再使用时打破计时器

时间:2015-09-04 21:10:46

标签: javascript timer setinterval

在javascript中不再使用计时器时,我有移除计时器的问题吗?

假设我们有一个变量tm用于计时器并使用window.setInterval设置它,当它仍在运行时我们用新的setInterval替换它,怎么可能摆脱第一个setInterval?

示例代码

var tm = setInterval(function(){
    console.log('tm1')
}, 10);

tm = setInterval(function(){
    console.log('tm2')
}, 10)

这是真正的问题

motion:function(ele,cssStart,cssEnd,duration,tangent, easing,loop, complete){
    if(ele==null||typeof cssEnd !== 'string') throw new TypeError();
    if(!$hd.isElement(ele) || !$hd(ele).isExists()) throw new TypeError();

    var validRules = /(left|top|width|color|height|background-color|margin-left|margin-right|margin-top|margin-botom|border-color|padding-left|padding-right|padding-top|border-bottom-width|border-top-width|border-left-width|border-right-width|border-bottom-color|border-top-color|border-left-color|border-right-color|padding-bottom|border-width|opacity|font-size)\s?(?=:).[^;]*(?=;?)/gim;

    // filtering css input
    cssEnd = cssEnd.replace(/\s{2,}|\n|\t/gim,'').replace(/\s?(:)\s?/gi,'$1').match(validRules);
    cssStart = !cssStart?[]:cssStart.replace(/\s{2,}|\n|\t/gim,'').replace(/\s(:)\s/gi,'$1').match(validRules);
    if(!cssEnd) throw new Error('invalid css rules, please refer to the documentation about the valid css rules for animation');

    // creating properties
    var _cssEnd = [],
    _paused = false,
    _cssStart = [],
    _tm = null,     
    _step,
    _complete = typeof complete ==='function'?complete:null,
    _loop = 0,
    _easing = typeof easing ==='string'?easing.match(/^easein|easeout|easeinout$/)?easing:'easein':'easein',
    _tangent = typeof tangent ==='string'?tangent in hd.classes.motionTangents ? tangent:'linear':'linear';

    this.ele = $hd(ele),
    this.duration = isNaN(duration)?1:parseFloat(duration),
    this.loop = isNaN(loop)?0:parseInt(loop),
    this.isPlaying = false;
    this.complete = false;

    // verifying the css rules of the end point
    var verify = function(cssStart, cssEnd){
        for (var i = 0; i < cssEnd.length; i++) {
            var colorPattern = /#[a-z0-9]+|rgba?\s?\(([0-9]{1,3}\s?,\s?)+((([0-9]+)?(\.)?([0-9]+))+)?\)/gi,
             name = cssEnd[i].replace(/^([a-z0-9-]+)\s?(?=:).*/gi,'$1'),
            value = cssEnd[i].replace(/^[a-z0-9-]+\s?:(.*)/gi,'$1'),
            startIndex = $hd(cssStart).inspectData(name+':',false),
            startValue = !startIndex.length?this.ele.getcss(name):cssStart[startIndex].replace(/^[a-z0-9-]+:(.*)/gi,'$1');

            if(value=='') continue;
            // parsing values
            if(name.match(/color/i)){
                //if color
                // validate the color

                if(!value.match(colorPattern)) continue;
                if(value.match(/#[a-z0-9]+/ig)){
                    // if hex then convert to rgb
                    var rgb = $hd(value).hex2rgb(),
                    value = !rgb?null:rgb;
                    if(!value) continue;
                }

                // verifying cssStart's value

                startValue = !startValue.match(colorPattern)?this.ele.getcss(name):startValue;
                if(!startValue.match(colorPattern)) continue;
                if(startValue.match(/#[a-z0-9]+/ig)){
                    // if hex then convert to rgb
                    var rgb = $hd(startValue).hex2rgb(),
                    startValue = rgb==null?null:rgb;
                }

                // if browser doesn't support rgba then convert the value to rgb
                value = !$hd.supports.rgba && value.match(/rgba/i)?value.replace(/(.*)a\s?(\((\d{1,3},)(\d{1,3},)(\d{1,3})).*/i,'$1$2)'):value;
                startValue = !$hd.supports.rgba && startValue.match(/rgba/i)?startValue.replace(/(.*)a\s?(\((\d{1,3},)(\d{1,3},)(\d{1,3})).*/i,'$1$2)'):startValue;             

                // compare and convert the value of both to object
                var colora = value.match(/[0-9]{1,3}/g),
                colorb = startValue.match(/[0-9]{1,3}/g);

                if(colora.length > colorb.length){
                    colorb.push(this.ele.getcss('opacity'))
                }else if(colorb.length>colora.length){
                    colora.push(colorb[colorb.length-1])
                }
                _cssEnd.push({
                    type:'color',
                    name:name,
                    value:{
                        r:parseInt(colora[0]),
                        g:parseInt(colora[1]),
                        b:parseInt(colora[2]),
                        a:colora[3]?parseFloat(colora[3]):null
                    }
                });
                _cssStart.push({
                    type:'color',
                    name:name,
                    value:{
                        r:parseInt(colorb[0]),
                        g:parseInt(colorb[1]),
                        b:parseInt(colorb[2]),
                        a:colorb[3]?parseFloat(colorb[3]):null
                    }
                });

            }else{
                value = parseFloat(value),
                startValue = parseFloat((isNaN(parseFloat(startValue))?parseFloat(this.ele.getcss(name)):startValue));
                if(isNaN(value)) continue;
                if(isNaN(startValue)) startValue = 0;
                _cssEnd.push({
                    type:'unit',
                    name:name,
                    value:parseFloat(value)
                });
                _cssStart.push({
                    type:'unit',
                    name:name,
                    value:parseFloat(startValue)
                });
            }

        }
    };

    verify.apply(this,[cssStart,cssEnd]);

    // clearing the arguments
    cssStart = complete = cssEnd = duration = tangent = loop = ele = verify = null;

    if($hd(_cssEnd).isEmpty()) throw new Error('MotionClass::invalid css rules');// raise error if cssEnd is empty
    var _pauseTime = 0;

    this.play = function(){
        if(this.isPlaying) return;
        if(!this.ele.isExists() || !this.ele.visible()) {
            this.stop();
            return;
        }

        this.isPlaying = true;
        _paused = false;

        if( $hd(_cssEnd).inspectData('left',true,true).length|| 
            $hd(_cssEnd).inspectData('top',true, true).length)
                this.ele.css('position:absolute');

        var st = new Date() - _pauseTime;

        _tm = window.setInterval(function(){
            if(!this.ele.isExists() || !this.ele.visible()) {
                this.stop();
                return;
            }
            var pg, delta,
            timePassed = new Date() - st;
            pg = timePassed / (this.duration*1000);

            if (pg > 1) pg = 1;

            if(_easing === 'easeout'){
                delta = 1 - hd.classes.motionTangents[_tangent](1 - pg);
            }else if(_easing==='easeinout'){
                if (pg <= 0.5) {
                    // the first half of animation will easing in
                    delta= hd.classes.motionTangents[_tangent](2 * pg) / 2
                } else {
                    // the rest of animation will easing out
                    delta= (2 - hd.classes.motionTangents[_tangent](2 * (1 - pg))) / 2
                }
            }else{
                delta = hd.classes.motionTangents[_tangent](pg);
            }
            // the movement
            _step.call(this,delta);


            if(_paused){
                window.clearInterval(_tm);
                _tm=null;
                _pauseTime = timePassed;
                this.isPlaying = false;
                return;
            }

            if (pg == 1) {
                _pauseTime =0;
                if(_loop>=this.loop){
                    this.complete = true;
                    this.stop();            
                    if(_complete)_complete.call(null,this);
                }else{
                    _loop++;
                    st = new Date(),
                    timePassed =  new Date() - st,
                    pg = 0;
                }
            }

        }.bind(this),15);
    };

    _step = function(delta){
        var styles = '';
        for(var i=0;i<_cssEnd.length;i++){
            var name = _cssEnd[i].name, 
            svalue =_cssStart[i].value, 
            value = _cssEnd[i].value;

            if(_cssEnd[i].type == 'color'){                 
                styles += name+':'+(value.a !=null?'rgba(':'rgb(')
                + Math.max(Math.min(parseInt((delta * (value.r-svalue.r)) + svalue.r, 10), 255), 0) + ',' 
                + Math.max(Math.min(parseInt((delta * (value.g-svalue.g)) + svalue.g, 10), 255), 0) + ',' 
                + Math.max(Math.min(parseInt((delta * (value.b-svalue.b)) + svalue.b, 10), 255), 0)
                + (value.a ==null?'':',' + $hd(parseFloat((value.a-svalue.a)*delta+svalue.a)).round(1)) +') !important;';
            }else{
                styles += name+':'+ $hd(parseFloat((value-svalue)*delta+svalue)).round(2) + (name.match(/opacity/i)?'':'px')+ '!important;';    
            }           
            this.ele.css(styles);   
        }           
    };

    this.stop = function(){
        this.isPlaying = false;
        window.clearInterval(_tm);
        _tm=null;
        _loop = 0;
    };

    this.pause = function(){
        _paused = true;
    };
}

这个问题是如何出现的;

var color = 'rgba('+($(1).randomize(0,255)+',')+
                                ($(1).randomize(0,255)+',')+
                                ($(1).randomize(0,255)+',')+
                                '1)';
            var bcolor = 'rgb('+($(1).randomize(0,255)+',')+
                                ($(1).randomize(0,255)+',')+
                                ($(1).randomize(0,255)+',')+
                                ')';
            var motion = new hd.classes.motion(box,'',('height:'+($(1).randomize(10,50))+
                    'px;border-color:'+bcolor+
                    ';background-color:'+color+
                    ';left :'+((e.x || e.clientX)-(box.rectangle().width/2))+
                    ';top : '+((e.y || e.clientY)-(box.rectangle().height/2))+
                    ';border-top-width:'+($(1).randomize(0,50))),
                    2,'circle','easeinout',1, function(e){
                        status.html('Idle');
                    });
                motion.play();

当变量运动被动作类(动画)引用时,如果用新的动作类(动画)替换第一动作的计时器,如何可以停止

1 个答案:

答案 0 :(得分:0)

真的很简单! clearInterval(tm)。如果您将它们称为不同的名称,您将能够区分它们。