A tool to generate inbetweens for animated sprites, written in godot-rust

Overview

Bitmapflow

ko-fi

Bitmapflow is a tool to help you generate inbetweens for animated sprites. In other words, it makes your animations smoother. It uses optical flow to try to guess how the pixels move between frames, and blends them accordingly. The results are far from perfect, and probably require some editing by hand afterwards, but sometimes it can produce decent results.

It supports loading and saving animated gifs, spritesheets and individual frames.

Example:

Example

Usage

You can download the executables here. (Windows only for now). You'll need to install the Visual Studio Redistributable first (unless you already have Visual Studio 2015 or newer installed). Other than that, it should work out of the box.

A video tutorial on how to use the program can be found here.

A short summary:

  1. Drag and drop your image into the program. It can be an animated gif, a spritesheet, or individual frames. If you don't have any sprites laying around you can find some in the examples folder in this repository.
  2. Tweak the parameters.
  3. Open the File menu to export the results as an animated gif, a spritesheet, or individual frames.

If you use big sprites with lots of frames, you may need to wait a while after tweaking the parameters for the processing to complete, since calculating optical flow can be quite CPU intensive.

A short explanation of the parameters follows.

Basic Parameters

  • Inbetweens: this decides how many inbetweens to generate. For example, if your input animation has 12 frames, and you generate 2 inbetweens, your output animation now has 36 frames. The more inbetweens you have, the smoother your animation gets.
  • Loop seamlessly: if enabled, the animation will loop seamlessly. Disable this for one-shot animations, like explosions.
  • Motion multiplier: if this value isn't 1x, it will exaggerate the motion if it's >1x, or diminish it if it's <1x. E.g. If you put it at 2x, the motion will go twice as fast; if it's 0.5x, the motion will be cut in half.
  • FPS: on the bottom right of the screen, you can change the speed of the input animation, in frames per second (FPS). The output animation will have a higher FPS, depending on the amount of inbetweens. E.g. If your input animation runs at 10 FPS, generating 1 inbetween means your output animation now runs at 20 FPS. Note that this parameter has no effect on the inbetween generation process, it's only used for displaying your sprite. (it does, however, affect the animation speed of exported gifs)

Advanced Parameters

  • Flow algorithm: You can decide which optical flow algorithm to use. The default is SimpleFlow, which works well in most cases. If it doesn't work for you, you can switch to DenseRLOF, which works better for some sprites. Both algorithms have different unique parameters to tweak, see below. Note that DenseRLOF seems a little unstable, it occasionally crashes for no reason (I'm using an external library, so I don't have any control over this).

I could explain all the advanced parameters in detail, but since they describe internal optical flow algorithm parameters, they require some background knowledge about the algorithm before they start to make sense. You can check the official documentation for SimpleFlow or the official documentation for DenseRLOF for more details.

You'll need to experiment a lot to find parameters that work well, although the default parameters seem to work decently for a lot of sprites. See my video tutorial on the subject.

Tips

The algorithm works best for sprites that only have movement in the two-dimensional plane. That means, things only move horizontally, vertically, or diagonally, not towards or away from the viewer.

Additionally, the algorithm assumes the brightness of pixels doesn't change between frames. That means, things like explosions, particle effects and blinking lights won't work that well, because they generally start bright and become dimmer over time.

Finally, if you feed pixel art into the program, make sure the pixel art isn't upscaled. It should be at its original resolution.

Compiling from source

If you want to dig through the source code and compile Bitmapflow yourself, you'll need to jump through some hoops. The program is written in Godot using godot-rust, so the project consists of two parts:

  1. The Godot project, found in the godot folder.
  2. The rust crate, found in the rust folder.

To get it to work, you'll need to install the following things on your system first:

  • Godot 3.2.3+
  • Cargo nightly 1.50+ (included in Rustup)
  • OpenCV 4.x (see the documentation of OpenCV-rust on how to get OpenCV)

I'm going to assume you're on Windows, but technically speaking this should work on other platforms as well, but the details and filenames will be different.

Getting it to work:

  1. Go to the rust folder and run cargo build --release.
  2. After a while this should produce a DLL file called bitmapflow_rust.dll in the rust/target/release folder (On Linux this file will be called libbitmapflow_rust.so). Copy this file to the godot folder.
  3. Now open Godot and run the project in the godot folder.

That's all.

FAQ

On Windows, the program crashes after the splash screen, or I get an error about vcruntime140.dll not being found. What to do?

I get some weird OpenCV error about sizes or something after loading my sprite?

  • Try reducing the "layers" parameter in the Advanced parameters section, or click the big Reset button at the bottom of the sidebar. If that doesn't work, your sprite may be too small. Try using a bigger sprite. Also try using SimpleFlow instead of DenseRLOF, it's more versatile and breaks less often.

License

The code is licensed under MIT. The included example sprites (in the examples folder) are licensed as follows:

Comments
  • Vergen crate requires a nightly Rust compiler

    Vergen crate requires a nightly Rust compiler

    The vergen crate used for version information seems to require a nightly compiler (as of version 1.50), and when everything using it was commented out it builds fine on stable Rust. Just wanted to mention it in case anyone faces the same issue :)

    I haven't tested it with 1.51 yet, but maybe a mention about this in the README would help?

    (Tested on Linux)

    opened by Technohacker 2
  • 1.0.2 official Linux release fails to run on Fedora 33

    1.0.2 official Linux release fails to run on Fedora 33

    OS: Fedora 33 x86_64 Bitmapflow version: 1.0.2 official

    After extracting all files from the archive and adding the +x executable permission to bitmapflow.x86_64 (which is missing by default), I get this in the terminal:

    Godot Engine v3.2.3.stable.official - https://godotengine.org
    OpenGL ES 3.0 Renderer: GeForce GTX 1080/PCIe/SSE2
     
    ERROR: open_dynamic_library: Condition "!p_library_handle" is true. Returned: ERR_CANT_OPEN
       At: drivers/unix/os_unix.cpp:426.
    ERROR: get_symbol: No valid library handle, can't get symbol from GDNative object
       At: modules/gdnative/gdnative.cpp:501.
    ERROR: init_library: No nativescript_init in "res://libbitmapflow_rust.so" found
       At: modules/gdnative/nativescript/nativescript.cpp:1506.
    ERROR: start: Condition "!valid_type" is true. Continuing.
       At: main/main.cpp:1766.
    ERROR: start: Condition "!valid_type" is true. Continuing.
       At: main/main.cpp:1766.
    ERROR: start: Condition "!valid_type" is true. Continuing.
       At: main/main.cpp:1766.
    ERROR: start: Condition "!valid_type" is true. Continuing.
       At: main/main.cpp:1766.
    ERROR: start: Condition "!valid_type" is true. Continuing.
       At: main/main.cpp:1766.
    ERROR: start: Condition "!valid_type" is true. Continuing.
       At: main/main.cpp:1766.
    zsh: segmentation fault (core dumped)  ./bitmapflow.x86_64
    

    gdb full backtrace:

    #0  0x000000000044a984 in Variant::call_ptr(StringName const&, Variant const**, int, Variant*, Variant::CallError&) [clone .cold.492] ()
    No symbol table info available.
    #1  0x0000000000000000 in ?? ()
    No symbol table info available.
    
    opened by Calinou 7
  • Feedback

    Feedback

    Hello,

    I'm amazed by how good this technology is and I see massive potential in an area that leaves creative freedom in designing animations to the user: animation transitions.

    In games, 2D animations stutter from one action to the other, where sudden stops in movement can look unnatural when there is no blending or inbetweening happening on the pixel level. Since blending can't really be done in 2D (at least what I know of), a good approach would be to let the computer calculate the inbetween frames (between finished animations, not the animations themselves) to "supplement" the sprite sheet instead of replacing what is in it, already. The final step would be to seemlessly integrate this as a datastructure into existing engines, where you don't even have to do the bookkeeping of which frames should go between what actions.

    That way you don't go against the principles of animation (scale, stretch, tension, suspense) and leave the necessary control to the artist.

    What do you think about this idea?

    opened by NovemberDev 1
  • Build issues on Mac

    Build issues on Mac

    Hello, I thought I'd try to build the project on Mac, and I got through the dependencies and all that, however when trying to run cargo build --release I can't seem to get it past the open-cv step.

    Not sure if this is a failure on my part of not setting up the open-cv dependencies correctly or what, but the log doesn't really seem to tell me anything clear.. would love some input if you have an idea of how to fix it 😄

    bitmapflow_osx_build.log

    I had tried to document my steps here as well:

    https://gist.github.com/corjohnson/49d77b9f3e14478c29d8b30d6e9f9814

    opened by corjohnson 2
  • DenseRLOF breaks if the sprite image is too small

    DenseRLOF breaks if the sprite image is too small

    It will gobble up RAM until it crashes. This is an issue in opencv-rust so there is not much to do about this, except maybe adding a minimum sprite size.

    opened by Bauxitedev 1
  • Enable link-time optimization when building Rust library for production

    Enable link-time optimization when building Rust library for production

    This decreases the compiled library size and improves performance.

    codegen-units is also set to 1 to further optimize the compiled library.

    There's more advice here: https://likebike.com/posts/How_To_Write_Fast_Rust_Code.html

    Note: I haven't tried to run the Godot project as a whole with these changes. It's likely that it will work as-is, but I recommend cloning this branch locally to test before merging.

    Preview

    Linux x86_64 (rustc nightly from 2021-03-26). Both libraries had their debug symbols removed by running strip on them.

    Before (LTO disabled, codegen-units = 16)

    2,672,984 target/release/libbitmapflow_rust.so
    

    After (LTO enabled, codegen-units = 16)

    2,132,240 target/release/libbitmapflow_rust.so
    

    After (LTO enabled, codegen-units = 1) – this PR

    2,066,704 target/release/libbitmapflow_rust.so
    
    opened by Calinou 8
Releases(v1.0.2)
  • v1.0.2(Apr 16, 2021)

    Changelog

    • Official Linux support added (NOTE: only tested on Ubuntu for now)
    • Loop frames are now added at the end instead of the beginning
    • Add spritesheet optimization: attempt to find most square resolution when saving spritesheet
    • Small fixes

    How to use it

    Windows

    Simply download and extract the Bitmapflow_windows_v1.0.2.zip file and run Bitmapflow.exe. If it crashes right after the splash screen, download the Visual Studio Redistributable first and install it.

    Linux

    Simply download and extract the Bitmapflow_linux_v1.0.2.zip file and run bitmapflow.x86_64. The program depends on OpenCV 4.2, so make sure you have that installed, e.g. on Ubuntu: sudo apt install libopencv-contrib4.2 libopencv-dev.

    If it refuses to run for some reason, ensure the file is executable by running:

    chmod +x bitmapflow.x86_64

    (Note: the Linux build was only tested on Ubuntu, if you're on another distro YMMV)

    Source code(tar.gz)
    Source code(zip)
    Bitmapflow_linux_v1.0.2.zip(16.81 MB)
    Bitmapflow_windows_v1.0.2.zip(24.34 MB)
  • v1.0.1(Apr 2, 2021)

    Changelog

    • Fix load/save images on separate drive, fixes #3
    • Add proper error handling when images fail to load
    • Add check for properly extracted zip file
    • Fix bug in remembering file path when loading separate frames
    • Fix NaN numbox bug crashing the program on Linux if you drag the FPS numbox (note: Linux release is not done yet, coming soon)

    Windows

    How to use it

    Simply download and extract the Bitmapflow.zip file and run Bitmapflow.exe. If it crashes right after the splash screen, download the Visual Studio Redistributable first and install it.

    Source code(tar.gz)
    Source code(zip)
    Bitmapflow_windows_v1.0.1.zip(24.34 MB)
  • v1.0.0(Mar 25, 2021)

Owner
I make games and other stuff. Obsessed with Godot at the moment.
null
🎨 Procedurally generate 2D sprites

sprite (Executable) Run On Linux you need the gtk-rs dependencies to compile: cargo install sprite sprite This should produce the following window: s

Thomas Versteeg 68 Nov 25, 2022
Plugin to generate flowfields from tilemaps in the Godot Engine!

Godot Tilemap Flowfields RTS-Style optimized path-finding for crowds of agents. Built for the Godot game engine, written with performance in mind in R

Arne Winter 18 Jan 10, 2023
A Rust library for blitting 2D sprites

blit A Rust library for blitting 2D sprites Documentation Usage Add this to your Cargo.toml:

Thomas Versteeg 23 Dec 6, 2022
Materials for sprites in Bevy

bevy_sprite_material Materials for sprites in Bevy This bevy plugin changes the bevy_sprite implementation using a material. You might be interested i

Félix Lescaudey de Maneville 6 Aug 21, 2022
Use sprites in a 3d bevy scene.

bevy_sprite3d Use 2d sprites in a 3d bevy scene. This is a pretty common setup in other engines (unity, godot, etc). Useful for: 2d games using bevy's

null 46 Apr 24, 2023
Explicitly set sprite layers for sprites in Bevy games.

extol_sprite_layer lets you specify the drawing order for sprites in your Bevy game using a separate component rather than via the z-coordinate of you

Ash 5 May 2, 2023
A CLI tool to manage your godot-rust projects

ftw A CLI tool to manage your godot-rust project! Table of contents General Information Setup Usage Contact General Information This is a tool to help

Michael Angelo Calimlim 77 Dec 13, 2022
An artisanally made PSD Importer for Godot, written in Rust

PSD Importer for Godot Speed up your import workflow ✨ An artisanally made PSD Importer for Godot 3.5, written in Rust. ✨ Getting Started | ?? Documen

Bram Dingelstad 4 Jan 26, 2023
compare gdnative rust based physics against Godot built-in physics

Godot vs. Rapier Rapier is an open source physics framework written in Rust. This project pits godots built-in physics against Rapier. It uses godot-r

Stephan Dilly 75 Nov 17, 2022
An egui backend for godot-rust

Godot Egui An egui backend for godot-rust. Rationale Godot has a perfectly valid GUI system, so why egui? Here are my personal reasons: Simplicity: No

null 109 Jan 4, 2023
jlang--godot bridge, built in rust

jlang-rs-gd J is an extremely high-level mathematical notation and programming language. Godot is a game / gui / multimedia engine. jlang-rs-gd lets y

tangentstorm 2 Feb 15, 2022
GDDB is a superfast in-memory database designed for use in Godot

GDDB GDDB is a superfast in-memory database designed for use in Godot. This database aims to provide an easy frontend to an efficient in-memory databa

Richard Patching 5 Dec 4, 2022
A Godot 3.4 binding for Live2D

godot-cubism A Godot 3.4 binding for cubism-rs which itself is a binding for the native cubism sdk. Usage var factory = load("path_to_your_native_scri

null 16 Dec 23, 2022
A crate for using Bevy with the Godot Engine.

bevy_godot A crate for using Bevy with the Godot Engine. This crate is in active development and is not ready for production use. Features Godot Scene

Abby Bryant 63 Dec 17, 2022
A direct ecs to low-level server implementation for Godot 4.1

godot_ecs What if Godot 4.1 and Bevy got married? Well, you'd get one interesting duo of data driven goodness. In Development This crate is not produc

null 5 Oct 6, 2023
An extendable system made up of autonomous execution services known as nodes organized in a tree of processes. Inspired by Godot!

NodeTree NodeTree is a framework to create large scalable programs and games through a tree of processes. Each process is fully autonomous and is capa

LunaticWyrm 3 Apr 10, 2024
Generate rust command line executables from gRPC protobuf services.

Rust template repository. An opinionated starting point for rust projects such as systemd services command line tools client programs server programs

Kris Nóva 8 Sep 18, 2022
Decryption tool for assets.pie from Teenage Mutant Ninja Turtles: The Cowabunga Collection. This tool was made in its entirety by SowwyItsAnAlt.

Cowabunga Decryption tool for assets.pie from Teenage Mutant Ninja Turtles: The Cowabunga Collection. This tool was made in its entirety by SowwyItsAn

Masquerade 8 Dec 22, 2022
A Rust port of alien, a tool that converts software packages between Linux package managers.

alien A Rust port of alien, a tool that converts software packages to work from one package manager to the next. Currently, the tool supports converti

Leah 3 Jan 19, 2023