문제

graph

I need a function like this. Horizontal value is the time, and vertical is the output. Starting at time 0, the value should be -1 or 1. Increasing the amount of time, the value should go to 1 and -1, decreasing the distance each time it "bounces".

I have done it in the past with hackish code: storing in a variable the target value, and every time the value reaches the target value, I do targetValue *= -.5, and so on.

Maybe there's a better implementation using a mathematical function out there that doesn't require doing this by hand. For me, it's like a trigonometric function but the final output is multiplied by 1 - (time / maxTime), and it's not a wave but lines.

도움이 되었습니까?

해결책 3

Since this was for the flickering effect for a game (so the character being hit starts to flicker slowly and then flickers more quickly), I ended up making a solution based on @Blender answer.

Wolfram Alpha Plot

The only difference is that apart from making the vertical bouncing separation smaller, it also makes the horizontal bouncing separation smaller.

The code in AS3 would be:

// flickerTime is a Number between 0 and max, in seconds.
// max is the amount in seconds that the flickering effect lasts
// 10 is a constant that can be changed if we want more or less flickers in that amount of time
var max:Number = 3;
var flick:Number = Math.cos(this.flickerTime * this.flickerTime * 10) * (max - this.flickerTime) / max;
this.visible = flick > 0;

다른 팁

If you're not interested in the exact shape, then targetValue *= -.5 is exactly what I would do, as long as the time increments between calls to the function which draws the graph are equal. The reason that I think that's a good choice is that it's the simplest choice that will do what you want. If the time increments are unequal you might want to have something proportional to -(time-Increment) instead of always -.5.

If the decrease of the "target value" is linear, as in your figure, then:

  • Normalize your time steps to 1 and let the number of normalized periods needed to get to 0 be n.
  • Start with targetValue = -1,
  • There are terser ways to write the code, but here is a clear version. It is written in SAS OPTMODEL code, but if you don't have access to OPTMODEL you should be able to translate it to any language easily:

    proc optmodel;
    num targetValue init -1;
    num n init 3;
    num series{ t in 1 .. 2*n + 1} = 
        if t = 1 then 
            targetValue
        else 
            -series[t - 1] + mod(t,2)* (1 / n);
    print series;
    quit;
    

If you use a product by a constant instead of a subtraction by a constant your series will reach 0 only in the limit.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top