Repository navigation
OpenBone v0.2.0
·
1 commit
to 0e6dd73d39504dd533e520bdd1b0160b5ab79eed
since this release
Native runtimes for C++ (Godot, Cocos2d-x, SDL2, SFML, OpenGL, Unreal), C# (Unity, MonoGame), Java (libGDX, Android), Swift, Flutter and Haxe, all checked against a shared conformance suite; sound in the engine integrations; desktop installers for Windows, macOS and Linux; WebM video export; and the rest of the Spine-style rigging tools.
Native runtimes
- GLFW / OpenGL 3.3 sample (
runtimes/cpp/engines/glfw): the WebGL2 renderer's shader and blending in plain OpenGL (two-colour tint, premultiplied pages, all blend modes, stencil clipping), mouse input, and a hidden-window--out frame.pngmode. - Sound in more runtimes: the Swift
OpenBoneView/OpenBonePlayer(newOpenBoneAudio, AVFoundation;OpenBoneDocumentgainsaudioAssets,audioBuses,audioMaster), the libGDX module (OpenBoneAudio), the AndroidOpenBoneView(SoundPool / MediaPlayer,SoundSource) and the SDL2 and SFML samples play the document's sounds (on by default,isAudioEnabled/--muteto opt out; audio callbacks still get every command), on shared, unit-tested gain / voice / fade logic (OpenBoneAudioMixer, JavaAudioMixer,engines/common/openbone_audio.hpp). Unreal still only emits audio commands. - MonoGame integration (
runtimes/csharp/monogame):OpenBone.MonoGamefor MonoGame 3.8 DesktopGL —OpenBoneRenderer(DrawUserIndexedPrimitives, premultiplied blend modes, stencil clipping, two-colour tint through a GLSL effect built in code with aBasicEffectfallback, optional SpriteFont text),OpenBoneMonoGame(load, animations or state machine, mouse / touch → listeners, events) andOpenBoneSoundPlayer(SoundEffectInstancewith bus × master volume, log2 pitch, loops and fades), a DesktopGL knight sample and window-less tests (also in CI). - Haxe runtime (
runtimes/haxe): a pure Haxe 4.3 port of the runtime with no dependencies (.obone/.obonbloading, skins and skin bones, every constraint in custom order, sliders, physics, particles, sequences, packed/trimmed/polygon atlases, text templates, the draw list, state machines with listeners and bindings, events, audio commands) and JS number semantics on every target. All 82 conformance cases pass on the JS target (scripts run on its JavaScript engine throughJsScriptHost); on eval and Python the 6 scripted state-machine cases are skipped and the other 76 pass. - The Flutter plugin moved from
runtimes/darttoruntimes/flutter/openbone: Flutter 3.47's Swift Package Manager support fails when a plugin's folder name differs from its package name (flutter#186881). - Java runtime on Gradle 9.9 and Android Gradle Plugin 9.5 (Kotlin 2.4 through the Kotlin Android plugin), without Gradle 10 deprecations.
- Swift Package Manager for the Flutter plugin on iOS and macOS (
runtimes/flutter/openbone/darwin/openbone/Package.swift, with iOS and macOS sharing onedarwin/folder and podspec), so Flutter no longer warns thatopenbonelacks SPM support; the podspecs stay for CocoaPods. - Sound in the native engine integrations: the Flutter
OpenBoneWidget(newOpenBoneAudio, flutter_soloud; the plugin now needs Flutter 3.41+) and the Cocos2d-xOpenBoneNode(cocos2d::AudioEngine) play the document's sounds, like the GodotOpenBoneSprite. The C API gainsob_document_audio_asset,ob_document_audio_busandob_document_audio_master, and the DartOpenBoneDocumentexposesaudioAssets,audioBusesandaudioMaster. The Flutter example bundles its sounds. - C++ runtime (
runtimes/cpp): a native C++17 port of the runtime with no engine dependencies —.obone/.obonbloading, skins and skin bones, every attachment, animation mixing, IK/transform/path/physics in constraint order, sliders, particles, text templates, the draw list (clipping, sequences, packed/trimmed/polygon atlases, two-colour tint), state machines with listeners and bindings, events, audio commands, and scripts in embedded QuickJS. Passes all conformance cases (CTest). A stable C API (openbone.h,libopenbone) for FFI, a Godot 4 GDExtension (OpenBoneSprite, checked in headless Godot), SDL2 and SFML sample renderers, an Unreal Engine 5 plugin (as source) and a Cocos2d-x 4.0 node (built and run on Linux; it now binds its textures through the program state). - C# runtime (
runtimes/csharp):OpenBone.Runtimefor .NET Standard 2.1 / .NET 8, a native port of the runtime (.oboneand.obonbloading, skins and skin bones, every attachment, mixing, constraints in custom order, sliders, physics, particles, text templates, the draw list, state machines with listeners and bindings, events and audio commands) that passes every case of the conformance suite (dotnet test). Scripts run in Jint (OpenBone.Scripting.Jint) with the sameobAPI and limits as the QuickJS host. - Unity package (
runtimes/csharp/unity/com.openbone.runtime): ScriptedImporter for.obone/.obonb, OpenBone Animation and OpenBone State Machine components (UnityEvents, EventSystem or mouse pointer input), a mesh generator with blend modes, stencil clipping, two-colour tint and premultiplied pages (OpenBone/Skeletonshader), and an AudioSource bridge. Built withruntimes/csharp/unity/build-package.py; tested in Unity 6 (6000.6.8f1) with every example; it now declares itscom.unity.uguidependency, imports art and sounds in any import order, clamps texture edges, and hasStageBoundsfor framing a camera on the document's stage. - Java runtime (
runtimes/java): a Java 11 port of the runtime with no dependencies (.obone/.obonbloading, skins and skin bones, every constraint in custom order, sliders, physics, particles, sequences, packed atlases, text templates, draw list, state machines, bindings, events, audio commands), state machine scripts in QuickJS (openbone-scripting), a libGDX renderer with an LWJGL3 sample (openbone-gdx), and a Kotlin Android library withOpenBoneView(openbone-android). JUnit runs all 82 conformance cases on the JVM; an instrumented test runs them on Android. - Swift runtime (
runtimes/swift): a SwiftPM package that compiles the C++ runtime from source and wraps its C API —OpenBoneDocument/OpenBoneInstance(.obone/.obonb, skins, animation tracks, state-machine inputs, triggers and pointer, event / audio / state / log callbacks, bones, slots, zero-copy or copied draw list), ARC-owned handles.OpenBoneView(Metal, UIKit and AppKit) and SwiftUIOpenBonePlayerdraw it with blend modes, stencil clipping, two-colour tint, premultiplied pages, particles and CoreText text, and send touches / the mouse to listeners; plus a SwiftUI sample.swift testruns all 82 conformance cases (checked on Linux; the views have not yet been run on Apple hardware). The C API gainsob_instance_slot_count/ob_instance_slot/ob_instance_find_slot. - Flutter / Dart runtime (
runtimes/flutter/openbone): theopenboneFlutter FFI plugin wraps the C++ runtime's C API withdart:ffi(ffigen bindings) and buildslibopenbonefor Android, Linux and Windows (CMake) and iOS/macOS (CocoaPods). Pure-DartOpenBoneDocument/OpenBoneInstance(skins, tracks, state machine inputs, triggers and pointer, event / audio-command / state streams, draw list; native memory freed bydisposeor finalizers) andOpenBoneWidget+OpenBoneController(Ticker-driven,Canvas.drawVerticeswith blend modes, clipping, two-colour tint and premultiplied pages, gestures → listeners).flutter testruns all 82 conformance cases; the example runs on Linux desktop and an Android emulator (iOS, macOS and Windows not built yet). C API additions: slot accessors (ob_instance_slot_count/ob_instance_slot/ob_instance_find_slot, shared with the Swift package) andob_particle_dot_alpha; CMake optionsOPENBONE_BUILD_STATIC,OPENBONE_INSTALL.
Editor and rigging
- Dopesheet: multi-key selection (Shift/Ctrl-click, Shift-drag box, Ctrl/⌘+A), drag and arrow-key nudge of the selection, copy / cut / paste at the playhead (across animations), scale in time, curve and delete for all selected keys. New ops
transformKeys,pasteKeys,deleteKeys(also MCP tools). - Compensate (
J, toolbar ⇲ Comp): transform a bone while its child bones keep their place. - Linked meshes (
addLinkedMesh): share another mesh's geometry and weights with a different image, optionally following its deform keys. - Runtime fixes ahead of the native ports: full-weight rotation keys set the keyed value; draw-order keys keep unlisted slots in place (like Spine); blend states report their stronger animation's progress (exit times, on complete); transitions to deleted states are skipped; constraint results written to world transforms survive later constraints (
syncApplied); physics stretch uses the world rest length; additive sliders mix their colour and constraint keys; fully transparent shapes aren't drawn; no NaN from text-driven bindings or short deform keys. - Skin bones and skin constraints:
SkinData.bones/constraints; anything a skin lists is active only while a skin listing it is set (inactive bones and their children are not posed or drawn, inactive constraints are skipped). OpsaddToSkin,removeFromSkin; Inspector "Only in skins" on bones and constraints. - Inherit timeline:
{target: "bone", property: "inherit"}with steppednormal | onlyTranslation | noRotation | noScalekeys; keyable from the Inspector's Inherit field in Animate mode. - Constraint order: optional
orderon every constraint, applied as one sorted list (default unchanged: IK, transform, path, physics). OpsetConstraintOrder; Inspector "Constraint order" list with ↑↓. - Reference scale:
skeleton.referenceScale(default 100). Physics gravity and wind and IK softness scale with the skeleton's size relative to it, so a rescaled rig behaves the same. Document inspector "Ref. scale". - Two-colour tint: a keyable
darkslot colour, drawn by every renderer and runtime: Canvas2D, WebGL2, PixiJS (two-colour mesh shader), Phaser (a two-colour pipeline), Three.js (aDARKmaterial variant) and CanvasKit (a colour-matrix filter per run of equally tinted items). Engine-kit batches carry a per-vertexdarkchannel only when a slot in them uses one, so documents without it draw exactly as before. - Folders for slots, skins, animations, events, constraints and state machines (optional
folderpath; opssetFolder,renameFolder): grouped, collapsible lists with drag into folders, new / rename / delete folder. New Events list in the left panel. - Import data (☰ Menu → Import from project…, op
importData): copy animations and skins from another project by bone/slot name, with the images, sounds and events they use, or bring in its whole skeleton under a new root bone; conflicts rename, replace or skip. - Weight tools: lock bones while painting (locked weights stay, the others renormalise; also Smooth / Auto / Prune / Direct), and
swapWeights(Weights panel → Swap…) to trade two bones' weights on a mesh or its selected vertices.
Export and art pipeline
- Desktop installers: the Desktop installers workflow builds the Tauri app for Windows (
.msi, NSIS.exe), macOS (universal.dmg) and Linux (.deb,.rpm,.AppImage) and attaches them to a draft GitHub Release for eachv*tag (or keeps them as artifacts on a manual run). Optional macOS signing and notarization through repository secrets; installer metadata (publisher, category, descriptions, licence) in the Tauri config. Seedocs/releasing.md. - WebM video export: VP9 (VP8 as fallback) with Opus sound through WebCodecs and
webm-muxer(MIT); with a transparent background the video keeps its alpha channel where the browser's encoder supports it (Chrome, Edge), otherwise the background is filled with the document's colour and the dialog says so. - Texture atlas: premultiplied alpha (pages stored as rgb × a, recorded as
atlas.premultipliedAlpha; render-webgl, Pixi, Three.js, CanvasKit and Phaser upload them as they are with the matching blend, Canvas2D converts them back), whitespace stripping (each image packed by its visible bounds; meshes keep what their uvs cover, particle images stay whole) and polygon packing (region attachments draw a tight convex outline,region.polygon, instead of the full quad). In the Export dialog's Texture atlas settings,pack_atlas/export_fileand thesetAtlasop. One packing path (buildAtlasin render-canvas) for the editor, MCP server and CLI. - Live art reloading: ☰ Menu → Watch art for changes watches the folders the project's images and sounds come from (desktop, via tauri-plugin-fs), or a folder picked with Watch folder… (web: File System Access API, checked while the editor tab is in front). Changed files replace the art in place, sizes included (region attachments scale with their image), with a toast and no undo steps. New op
updateImage;DocumentStore.applyQuietapplies an op without an undo step. - CLI batch export:
openbone export <files or globs> --format json|obonb|atlas|png|jpeg|gif|apng|psd|avi|mov|spritesheet|web --out <dir>with--animation,--skin,--scale,--fpsand the atlas options. It runs the sameexportFilecode as the MCPexport_filetool. Newatlasformat: runtime JSON plus its atlas pages as PNG files in a ZIP. - Photoshop (
.psd) import: layers become slots and regions in place; groups can become bones.
Tooling, CI and docs
- CI (
.github/workflows): GitHub Actions run the web tests and build, and every native runtime against the conformance suite when its files change — C++ on Linux, macOS and Windows plus Godot (headless), SDL2 and SFML; C# and the Unity compile check; Java, libGDX and the Android library; Swift on Linux and macOS plus an iOS build; Flutter tests on Linux and macOS and the example built for Linux, Android, macOS, iOS and Windows. - About dialog (☰ Menu → About OpenBone): version, build, credits for the open-source tools OpenBone is built with.
pnpm version:set/pnpm version:checkkeep every package, the Tauri app and the desktop crate on one version.- Conformance suite (
conformance/,pnpm conformance): reference poses, draw lists, events, audio and state-machine traces from the TypeScript runtime for every example plus focused rigs and packed atlases, checked by a drift test;docs/runtime-spec.mdspecifies the evaluation rules for ports to other languages.
Installing
Download the installer for your system below. The macOS app is signed and notarized; the others are not code-signed yet:
- Windows: if SmartScreen appears, choose More info then Run anyway.
- Linux AppImage: on newer Ubuntu install
libfuse2, or run it with--appimage-extract-and-run.