
Security News
Axios Maintainer Confirms Social Engineering Attack Behind npm Compromise
Axios compromise traced to social engineering, showing how attacks on maintainers can bypass controls and expose the broader software supply chain.
A simple tweening library.
A tween is a representation of a timeline of a single animation. In the basic case, it emits values from 0 to 1, according to the provided easing function.
For example, we can animate “fade in” appearance of an object by rapidly changing its opacity style from zero (invisible) to one (fully visible). A tween would then emit values from 0 to 1 for each frame of the animation, eg. 0, 0.25, 0.5 and 1 in case the animation is linear and needs to be done in four frames.
$ yarn add neewt
tween(duration, easing, { onStart, onUpdate, onEnd })tween(delay, duration, easing, { onStart, onUpdate, onEnd })Creates a tween and immediately schedules it to run, unless delay is specified. Unless the duration is 0, the animation will kick off in the next animation frame (ie. asynchronously). All tweens you create are executed under the same requestAnimationFrame call, so there's usually no need for optimizing for less tweens, except in extreme cases.
It returns a Tween which can be optionally stored somewhere and passed to finishTween.
delay: numberIf not specified, 0 is assumed. Until this many milliseconds has passed since the tween was created, it won't run. This affects when onStart is run.
duration: numberHow long the tween will run, in milliseconds.
Note that this can never be exactly precise because the animations frames are triggered at around 16ms. The library handles that no overshoot is ever visible, and when the tween ends, the value 1 will be emitted (instead of something like 1.001 which would be more correct in terms of the timeline, but probably not what the visual result should be).
If 0 is given, the update will happen synchronously and the tween will be immediately marked as finished. If you need an instantaneous asynchronous animation, use a different small number for duration (such as 1).
easing: (t: number) => numberEasing describes the way the animation accelerates. Mathematically, the simplest way to move an object from point A to point B is to give it a constant velocity. However, this is rarely how things move in the real world; which is why animations are rarely created this way.
A more natural way for the object to move from A to B is to start slowly, accelerate and reach the maximum speed somewhere along the way, and then decelerate before reaching its destination. This type of easing is usually called ease-in-out, and is often accompanied by words like quad and cubic which describes the acceleration/deceleration rates more accurately.
Two more easing functions are commonly used for simple transitions: ease-in and ease-out, which are similar to the previous but one-sided. Ease-in animation will start slowly, and then accelerate right all the way, even in the its final moments. This type of easing is usually used when the object is moving away from the screen; we see it flying out of the screen in full speed, because we assume that its resting position is somewhere far off, outside the edges of the screen. Similarly, objects which enter the screen are coming in from far away, and thus when they first appear within the screen boundaries, they have their full velocity, slowly decelerating as they approach their resting place on the screen (which is ease-out function).
Mathematically, an easing function is a function which transform a linear change from 0 to 1 into a different type of change. So, the linear easing function would be a simple identity function: (t: number) => t. The quadratic ease in function is a basic parabola: (t: number) => t * t. Neewt comes with a few built-in easing functions, all exported under the name easing.
onUpdate: (v: number) => voidAs explained, the purpose of the tween is to rapidly fire numbers which the consumer can use to create an illusion of some sort of movement by rapidly re-drawing slightly different images. This is the function where the consumer defines how the tween affects the animation.
For example, one could move the object from (0, 0) to (0, 300) with the following update function:
onUpdate: v => {
object.setPosition(0, v * 300)
}
onStart: () => voidA function called when the tween starts, taking delay into account.
It's tempting to think that this hook is useless because the animation starts when the tween is created; however in most cases this is not true. When you specify a non-zero duration as the first argument to the tween function, it only schedules the animation to run in the next frame. Although this is “close enough” for most cases, it could case unexpected flashes if you want to make your object visible before animating it in.
object.setVisibility(true)
tween(300, easing.linear, {
onUpdate: v => object.setOpacity(v),
})
// Too early. The object is fully visible for one frame, before opacity is set to 0.
Above code will case a one-frame flicked in whcih the object is fully visible, before becoming completely invisible when the onUpdate is called for the first time. To avoid this, use the onStart hook.
tween(300, easing.linear, {
onStart: () => object.setVisibility(true),
onUpdate: v => object.setOpacity(v),
})
// Object is set to visible and its opacity is set to 0 at the same frame.
onEnd: (endReason, tween) => voidA hook to call when the animation ends. You can run some clean-up code, unfreeze the Ui, or run the next animation in sequence here. It's entirely up to you.
The hook will provide the reason for ending as an enumeration EndReason, which you can use to know whether the tween ended naturally or its end was forced via finishTween.
You'll also get the Tween reference that you can use to, for example, remove the tween from a set of currently running tweens.
finishTween(tween)Creating a tween with tween will result in a Tween object, which can be stored somewhere in case the situation calls for the need to cancel the animation prematurely, causing the tween to cease firing values and emitting the final 1 immediately, thus placing the animation in its final position.
If the tween has already finished, nothing will happen (so you don't have to check for this case when calling the function). But if you need to know whether the function call actually stopped the tween, you can look at its return value: true means that tween was ended prematurely, while false means that the call didn't do anything because the tween has already been completed (naturally or via a finishTween call).
easingFour easing functions are currently available for convenient use when providing it as the second argument to tween function.
t => t,t => t * t,t => t * (2 - t) andt => t < .5 ? 2 * t * t : -1 + (4 - 2 * t) * t.Of course, creating your own easing function is available, as they are simple JavaScript functions which accept a number and return a number.
Internally, easing is not a regular object, but a so-called “exotic object” created as the result of a re-exported namespace import. This means that only the functions you use will be a part of the final bundle if you use a common solution for tree-shaking your code such as Rollup. Thus, you do not have to worry that you will bloat your code with the rest just by using one of them, while still keeping all the easing functions easily accessible without importing each one separately.
EndReasonAn enumeration used in the onEnd hook which allows the consumer to differentiate between natural ending of the tween and a forced one via a finishTween function call.
It defines two values:
Natural andForced.TweenA type which represents the tween from the consumer's perspective. Returned by tween when creating it, and used by finishTween as the argument in order to reference it.
It purposely hides the implementation details of what it actually is. Thus, it should not be used in any other contexts, as its shape is an implementation detail which can change at any update without warnings for a breaking change.
The page is empty for one second. Then, a red rectangle appears for one second.
const object = document.createElement('div')
object.style.backgroundColor = `red`
object.style.width = `100px`
object.style.height = `100px`
object.hidden = true
setTimeout(() => {
tween(1000, easing.easeOutQuad, {
onStart: () => object.hidden = false,
onUpdate: v => object.style.opacity = `${v}`,
})
}, 1000)
It's probably simpler than XYZ. Instead of providing a full out-of-the-box solution for very complex cases, it comes with the bare minimum, allowing full control by the consumer. It's by no means an animation framework, but a simple utility library.
It's "tween", reversed.
I don't have a “testing area” set up. You'll have to build the project with
yarn buildand useyarn linkto test it out in a different project.
Because I'm lazy yet confident; a bad combination. I'd appreciate a PR for it.
Probably, as long as you provide a reference to another easing library or animation framework (any language or platform) which also uses it. Just open an issue with relevant info.
FAQs
A very simple tweening library.
We found that neewt demonstrated a not healthy version release cadence and project activity because the last version was released a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Security News
Axios compromise traced to social engineering, showing how attacks on maintainers can bypass controls and expose the broader software supply chain.

Security News
Node.js has paused its bug bounty program after funding ended, removing payouts for vulnerability reports but keeping its security process unchanged.

Security News
The Axios compromise shows how time-dependent dependency resolution makes exposure harder to detect and contain.