Alpha 2D Skeletal Animation - Animation States

Nux

GameMaker Staff
GameMaker Dev.

- A bare-bones, pure GML, modular animation runtime for GMS2 -
Nuxii 2D Skeletal Animation Runtime​


Downloads:

Download the most recent runtime (to be added in the near future once everything is wrapped up)
Marketplace(?)
GitHub
Direct
TBA

Introduction:
Hi, this began as a personal project which I've decided to share with others who are interested and might find use in my work. Additionally, it would be a learning experience for me to release and manage a project.

I am thinking of releasing this as free and open source, but we will have to see due to current circumstances.


Description:
The runtime includes a vast range of scripts for constructing your own skeletons and animations, as well as scripts for automatically decoding atlas and armature files from your favourite skeletal animation software into structures for use with your game. These scripts include: sk_armature_build_dragonbones(json,armatureNameOrID) & sk_armature_build_spine(json,armatureNameOrID) for your armature files; and sk_atlas_build_dragonbones(json,scale), sk_atlas_build_libgdx(libgdx,scale), and sk_atlas_build_spriter(json,scale) for your atlas files.

Additionally, there are scripts included for accessing, managing, and rendering these armatures. For example, calling sk_armature_updateWorldTransform(myArmature) will convert applied transformations of bones into world transformations. Then, once you are happy with your final pose, you can use vertex_bake_armature(myArmature,myAtlas,myVbuff), to bake your armature pose onto a vertex buffer in the "full fat" format (calling this function also returns the ID of the texture page to render from, which needs to be stored for when you submit your vertex buffer).



Demo for viewing and benchmarking armatures

Supported Formats:
  • DragonBones JSON Armature and Texture atlas support for version 5.5
  • Spine JSON Skeleton and Libgdx Texture atlas support (See below of a list of supported features)
  • Spriter SCON Entity and Texture atlas support

Features:
  • Entirely script-oriented; no overhead from objects
  • Add, edit, and remove data procedurally without the need for a skeletal animation software.
  • Manipulate bones, slots, and other armature data at runtime
  • Child bones and attachments are skewed naturally with non-uniform scales
  • Supports transformation & inverse kinematics (IK) constraints
  • IK constraint support for non-uniform parent scales
  • Supports multiple skins per armature
  • Supports multiple skins to be applied at once
  • Override specific attachments in a skin with the attachment remap stack*
  • Translate, scale, shear, and rotation transformations for bones and attachments
  • Supports the use of events
  • Supports the use point attachments
  • Supports the use of multiple attachments per slot for frame-by-frame animation
  • Supports full timeline support for bones, slots, constraints, events, and draw order frames
  • Interpolate between animation keyframes linearly or quadratically
  • Mix multiple animations with a selection of existing "mix modes"
  • Bones and constraints are cached into a single iterable list to improve performance and make nested constraints possible
  • Bake your final armatures directly onto vertex buffers to allow multiple sprites to be rendered from a single skeleton structure
  • Debug Scripts for bones, armatures, and atlas' with a range of debug arguments to help you figure out what's wrong in this cruel, cruel world...
  • Contains an abundance of helper scripts to improve usability of runtime features
  • Includes physics constraints for fancy jiggle bone movements that fluidly interact with your animations and movement at runtime
  • Includes hierarchy constraints for quick and easy dynamic reparenting of bones
  • Native animator to automatically handle the mixing of animations
* For example, having a skin ignore the attachments of certain body parts so you don't have multiple skins for each body part.

Planned Additions:
  • HTML documentation of script descriptions and applications
  • Optimisation improvements
  • Asymmetry handler for maintaining asymmetric features of an armature when flipping (such as different coloured arms)
  • Multi-page texture atlases


Support for Spine Essential

Unsupported Features: (items from this list may be implemented if desired)
  • Mesh attachments
  • Clipping attachments
  • Bounding box attachments
  • Path attachments
  • Path constraints
  • Tint black slots (two colour slots)
  • Bezier curves



An Example of proceedural animation by manipulating a bone's IK end effector.

Limitations:
  • All sprites must be located on the same texture atlas in order to be attached



DragonBones Dragon rendered in Gamemaker Studio 2.


Change Log (legacy docs, find future commits in the project GitHub):
In-Dev Version 0:
21/05/2018 23:49 - Added support for non-shearing inheritance (similar to how Spriter inherits bone scale)
21/05/2018 23:49 - Added a new type of image: The "Symbol", taking inspiration from flash animation programs.
21/05/2018 17:58 - Converted system from ds_lists into a more robust and efficient hybrid of arrays and data structures.
14/05/2018 21:46 - Updated DragonBones importer to version 5.6, which now includes IK constraint timelines.
14/05/2018 21:46 - Fixed a bug with timelines where first frames were being mixed prematurely.
14/05/2018 16:44 - Implemented limited support for Spine runtime.
14/05/2018 16:44 - Revamped drawOrder timeline so its more robust and stores more information with minimal additional overhead.
12/05/2018 21:51 - Implemented support for the libgdx texture atlas format (the .atlas files Spine uses!)
12/05/2018 19:07 - Polished physics constraint code.
12/05/2018 19:07 - Physics constraints now support rigid bodies and soft bodies.
12/05/2018 19:07 - Revamped the way inheritance works, fixing various constraint issues.
12/05/2018 00:39 - Added physics constraint which allows for jiggle bones that interact procedurally with animation movement.
11/05/2018 21:24 - Added hierarchy constraint to automate the dynamic re-parenting of bones.
11/05/2018 21:24 - Major cleanup and refactoring.
04/05/2018 20:32 - Added individual procedures for handling dynamic re-parenting of bones.
04/05/2018 20:32 - Fixed bugs with constraints not correcting applied transforms.
04/05/2018 15:36 - Added procedure to correct applied transforms using world transform.
04/05/2018 15:36 - Removed dynamic re-parenting from sk_bone_updateWorldTransform_ext, since it causes more problems than it solves.
04/05/2018 15:36 - Cleanup.
26/04/2018 22:05 - Minor efficiency improvements.
26/04/2018 18:57 - Implemented binary search.
26/04/2018 18:57 - Changed the way keyframes of a timeline are located, instead of getting the next frame, the current frame is obtained instead.
26/04/2018 18:57 - Fixed bug with timelines where the first keyframe was never being obtained, meanign some events were unable to be thrown.
26/04/2018 18:57 - Added attachment remaps and stacks to skin structures - these work in the same way as character maps in Spriter.
25/04/2018 20:35 - Revamped the way events are stored, managed, and thrown during animations. See Appendix #6.
25/04/2018 20:35 - Updated the dragonbones importer to import event and draw order timeline data.
25/04/2018 00:54 - Implemented transform constraint timeline.
25/04/2018 00:54 - Implemented draw order timeline.
25/04/2018 00:54 - Implemented update order timeline.
25/04/2018 00:54 - Fixed a bug with transformation constraints where they would transform incorrectly.
25/04/2018 00:54 - Updated the way attachments are stored in slots, so they are only obtained when required from a nested ds_map.
25/04/2018 00:54 - Added calling script attribute to custom events to define a script to call.
23/04/2018 16:05 - General cleanup and improvements.
22/04/2018 12:59 - Added custom "plane" attachments, which use a matrix instead of a region.
22/04/2018 12:59 - Added point attachments.
22/04/2018 12:59 - Added transformation constraints.
22/04/2018 12:59 - Preparation for spriter support.
18/04/2018 00:49 - Reconverted system from arrays to ds_lists. See Appendix #5.
17/04/2018 17:23 - Added shear transforms.
17/04/2018 17:23 - Revamped bone inheritance and transform modes.
17/04/2018 17:23 - Major Preparation for point attachments and transform constraints.
12/04/2018 14:05 - Minor preparation for mesh and clipping attachments, etc...
12/04/2018 14:05 - Implemented the Spriter texture atlas format.
11/04/2018 23:49 - Added support for cropped pages and pages not of a power of two. See Appendix #4.
10/04/2018 23:13 - Added support for rotated regions in atlas' (90 degrees counter clockwise).
02/04/2018 23:08 - Added slot attribute: attachmentFinal. See Appendix #3.
02/04/2018 23:08 - Moved slots to the armature cache; cutting the minimum number of loops per process in half!
02/04/2018 23:08 - Added Event timeline.
02/04/2018 23:08 - Added IK weight and bend timelines.
02/04/2018 23:08 - Decomposed the Atlas and Armature structures into a format where data is independent of where it is stored. See Appendix #2.
02/04/2018 23:08 - Converted system from static data to dynamically defined data. See Appendix #1.
02/04/2018 23:08 - [REDACTED] Converted system from ds_lists to arrays, this should hopefully result in a performance boost.
26/03/2018 15:59 - Added support for un-inherited scales for single bone systems.
26/03/2018 00:55 - Fixed a bug where IK constraints were getting erroneous solutions with non-uniform scales.

Appendix:
  1. This allows you to create and remove bones and other skeleton data on the fly.

  2. This makes these structures become more of an organised store of data with a few nifty functions to make your life easier, compared to the previous where each were practically the foundation of the entire system.
    However, all this can even now be avoided if you desire by creating the skeleton data manually, for example: making a simple bone system that animates without requiring the overhead of the armature and atlas.

  3. This can be altered after calling 'sk_armature_updateWorldTransform' to set the visible attachment for this slot (this is overwritten every step so its not permanent; if you want permanent, consider setting the attachment to the slots display list using 'sk_slot_add_attachment').

  4. This does not include sprites created using sprite_add (and other sister functions).

  5. The reason for this is due to arrays seeming to offer no performance gain at the expense of convenience; I ran some benchmarks and everything points towards lists being faster than arrays at runtime and startup. Results: https://pastebin.com/9MgzJQtE

  6. Events are no longer managed manually by passing a ds_list to the animation proceedure; you now tell the event what script to execute like so:
    Code:
    var myEvent = sk_armature_find_event(myArmature,"myEvent");
    sk_event_setScript(myEvent,myScript);
    ...and each time the event is thrown, it executes this script with the arguments being the data defined in your animation software:
    Code:
    argument0 <- boneData (this is a DragonBones specific attribute, but can be manipulated at runtime if you use an alternate piece of software)
    argument1 <- string
    argument2 <- real
    argument3 <- int
    argument4 <- sound
    ...I believe this to be a more intuitive than constantly polling for a specific event by checking whether it exists within the supplied ds_list.
 
Last edited:

Nux

GameMaker Staff
GameMaker Dev.
@hippyman Aha yes, I've heard the outcry.
@RichHopelessComposer Thanks, do you know how many armatures were on screen? Were you using the VM or YYC executable?

Also, quick bug fix: I managed to fix that one problem with IK Constraints producing wrong solutions for non-uniform scales; You can see the leg is now able to find a solution to the end effector, even though it is distorted and skewed!

Everything should be ship-shape now, only efficiency problems. So, I may even release this sooner now that issue is off my mind.

EDIT: As of 11/06/2018, this has been redacted due to some oversights.

EDIT: As of 20/10/2018, this has been fixed and is fully functional!
 
Last edited:

DukeSoft

Member
Nice! A free and open-source alternative to Spine. Oh, and it supports IK (which spine doesn't). +1000 kudo's for you!
 
  • Like
Reactions: Nux

Bingdom

Googledom
VM - Can get about 7 before fps drops below 60fps.
YYC - Can get about 26 before fps drops below 60fps.

1.5Ghz Dual core

It looks great. Keep up the great work. (Woo! Another widely useable open source(?) project being worked on like TheSnidr!)
 
Last edited:

DukeSoft

Member
I'm sorry for not updating this in a week; I've been trying to convert the system into a more modular framework where you can create skeleton data through constructors, and converting the system from using lists to arrays. However, everything is falling apart, I'm really stressed out with personal life and I want to cry.

Exhibit A:


I want to update this more frequently because I don't want to disappoint anyone, but right now it just isn't happening - I'm sorry.
Don't worry! You're not obliged to make anything :) Every second you put in is valued by people. No-one is allowed to be demanding, so do it only if you have the energy and time ^_^
 

Nux

GameMaker Staff
GameMaker Dev.
Currently, I am considering adding spine and spriter support, since this is most likely what most people will be using.

Also, I've added support for IK and event timelines, and (hopefully) made some efficiency improvements by cutting down the number of loops.

Another important change has to do with how data is stored; armature data can now be dynamically removed and added without causing issues (if done correctly using the supplied scripts), meaning that you don't necessarily need to build an armature, or own a skeletal animation software to use this runtime; you can create armatures at runtime, or not use them at all. For example: if you want to have the benefits of using inverse kinematics without the overhead of an armature, you can just create two bones and an IK constraint, then update and draw them manually (there are some kinks you will have to deal with, such as updating the world transforms of both bones before applying the constraint, but these will be detailed in the help file)! Of course, this applies to all skeleton data: Slots, Skins, Animations/Timelines, Attachments, ... ; you want it? I got it.

I've updated the OP to reflect these recent changes. You can find details of these changes in the Change Log section of the OP.

@Nux: Ah, sorry, I was just in "viewing" mode. I got nine dragon models on the screen before dipping below 60fps, using the VM version.
VM - Can get about 7 before fps drops below 60fps.
YYC - Can get about 26 before fps drops below 60fps.

1.5Ghz Dual core
Okay, thank you, guys! I don't think those numbers are very impressive currently, so I think I have a long way to go in terms of efficiency it seems. If anyone has any ideas on how that could be improved when I release this publicly (and you examine my horrible horrible spaghetti code) then I would really appreciate it.

Nice! A free and open-source alternative to Spine. Oh, and it supports IK (which spine doesn't). +1000 kudo's for you!
I think it's very silly to hide such a great feature behind a major paywall. Unless the runtime gamemaker uses just flatout doesn't support IK, then that's a surprise.

@maru_th_undrtkr @Niels Thanks!
 
Last edited:

Nux

GameMaker Staff
GameMaker Dev.
Sorry for not updating this as frequently as I'd like, but I am working on this in the background (you can see a list of changes in the change log section). A couple updates on whats happening:
  • Spriter support is on its way, I've figured out how to get bone re-parenting to work in a way I feel is suitable, that being with a thing I've called a "hierarchy constraint", which is similar to a slot and its attachments; but with a bone and bone parents. It's completely keyable and allows for some pretty interesting stuff transformation constraints aren't able to do. One disadvantage of this is that no runtime except spriter will ever support this feature... however, you are able to create it and add it to your armatures at runtime; I would like to create a custom format which can be loaded along side an existing format to do this automatically, so you don't need to hard code it.

  • I've refactored my code from my last post and have reached a point I am happy with the system and feel it is stable enough for release. I'm still suffering with major efficiency problems because ds_lists are slow as hell to access, hopefully this will change with the introduction of lightweight objects (please). I want to get atleast one other format supported before I release, however; it's getting close!

  • Another major feature I've prototyped is a physics constraint which will allow for jiggle bones that interact with your animations at runtime, see the bottom of this post for an example of it in action. Just like hierarchy constraints (which allow for dynamic reparenting of bones), you will have to define these constraints at runtime if you want to use them - I've already established by ideas for a secondary format to alleviate this (see the end sentence of the first bullet point).

  • Finally, here's a rundown of the most important changes to date I haven't mentioned in detail previously:
    Code:
    04/05/2018 20:32 - Added individual procedures for handling dynamic re-parenting of bones.
    04/05/2018 15:36 - Added procedure to correct applied transforms using world transform.
    26/04/2018 18:57 - Changed the way keyframes of a timeline are located, instead of getting the next frame, the current frame is obtained instead.
    26/04/2018 18:57 - Added attachment remaps and stacks to skin structures - these work in the same way as character maps in Spriter.
    25/04/2018 20:35 - Revamped the way events are stored, managed, and thrown during animations. See Appendix #6.
    25/04/2018 20:35 - Updated the dragonbones importer to import event and draw order timeline data.
    25/04/2018 00:54 - Implemented transform constraint timeline.
    25/04/2018 00:54 - Implemented draw order timeline.
    25/04/2018 00:54 - Implemented update order timeline.
    25/04/2018 00:54 - Updated the way attachments are stored in slots, so they are only obtained when required from a nested ds_map.
    22/04/2018 12:59 - Added custom "plane" attachments, which use a matrix instead of a region.
    22/04/2018 12:59 - Added point attachments.
    22/04/2018 12:59 - Added transformation constraints.
    17/04/2018 17:23 - Added shear transforms.
    12/04/2018 14:05 - Implemented the Spriter texture atlas format.
    11/04/2018 23:49 - Added support for cropped pages and pages not of a power of two. See Appendix #4.
    10/04/2018 23:13 - Added support for rotated regions in atlas' (90 degrees counter clockwise).
    02/04/2018 23:08 - Added Event timeline.
    02/04/2018 23:08 - Added IK weight and bend timelines.


Physics Constraints

P.S. if you haven't heard of transformation constraints, this is the kind of weird stuff they are able to do.
 

Nux

GameMaker Staff
GameMaker Dev.
I have a somewhat major update today: I've put aside Spriter support for now to work on a basic Spine implementation over the last couple of days (it shed some light on some bugs with the runtime prior which i've now fixed), and currently supports most of the Spine Essential features and some of the more basic Spine Pro features (IK constraints and transformation constraints); someday I'd like to support FFD and path constraints, but It's just not within my personal abilities at the moment, but I have considered it. Here's a little teaser of the current implementation:


Spine "Spineboy Raptor" skeleton loaded into Gamemaker Studio 2
FFD, Paths, tint black, and bezier curves are not currently supported.
IK constraints, transformation constraints, and keyable draw orders are, however, supported.

Anywhere you don't see a skin is because meshes aren't supported, and hence are not loaded. However, It should still give you can idea of what is currently possible with the runtime implementation.

If you'd prefer to see what Spine Essential skeletons look like, then here is an alternate .gif of Spineboy in a running pose.

About Spriter support: the SCON texture atlas format is (and has been for several weeks) supported, so you will be able to preview your spriter atlas' in the demo with the new atlas debug feature that displays the UV coordinates, orientation, origin, and name of each region in the atlas.


Spriter atlas being viewed in the Demo application showing the regions (blue), orientations (yellow), and origins (green) of each region in the atlas.

On another note: I am worried about performance issues on the VM, because I can only get around 20 incredibly basic armatures on screen at once before dipping below 60 fps (and my machine is fairly powerful). So I'm wondering if there's any quicker way of storing and accessing data than with lists/arrays, or is this just a sink people will have to deal with? I would consider deactivated objects if they weren't so messy; every day those lightweight objects on the roadmap get more and more appealing.

Finally, I'm going to update the demos for both the VM and YYC in the OP for anyone interested to test and submit feedback for ... and probably start to produce a basic document and wrap up for the first beta release (probably on GitHub, which I have no experience with, so that will be entertaining). I'll edit this post when I've done those.

EDIT: I've added a new Demo to the OP which now includes spine essential support, as well as a few bug fixes regarding the dragonbones importer.
 
Last edited:

Nux

GameMaker Staff
GameMaker Dev.
Heya, sorry about the huge pause; I've been busy. Anyhow, I've got a quick update regarding Spriter, a basic implementation of sprite animation is complete*. Something different with my implementation than the official runtimes provided by BrashMonkey is that sprite animations are able to be mixed, so long as the sprites share the same name between animations. Other things which are supported include: Character maps, dynamic re-parenting of sprites, and looping animations.

Also, I'm going to be creating a GitHub repository soon for those who want to get a sneak peek, or even use the runtime before full release, so keep an eye out for that!

Other than that, the looming stress of university applications and finance is over, so hopefully future updates will speed up.

*no pivot transformations yet, unfortunately, because the way the data is stored seems really temporary and static; I'd prefer to find a better solution than complicate my existing code with such a niche feature
 

Nux

GameMaker Staff
GameMaker Dev.
I've got around to creating a github repository for this project, so anybody who's avid to take a look can check it out. Feel free to clone it in its current state and use it as is (it should be stable).

In other news, I'm going to be revamping hierarchy constraints to be more hierarchical compared to re-parenting. This will make bone support for Spriter a breeze - because of its dynamic reparenting features.
 

Nux

GameMaker Staff
GameMaker Dev.
Quick update! The Spriter implementation now supports depth ordering of sprites!


Spriter Entity showcasing two Garfields in a binary orbit.
Oh, and I'm thinking of moving the change log to the github repo, and reserving this thread purely for showcasing and updates. So if that happens, you know where to look!
 
Last edited:

Nux

GameMaker Staff
GameMaker Dev.
Here it is! Spriter support is now complete (for the most part), and it even supports dynamic re-parenting of bones like in Spriter, something I've been personally excited for. However, there are a hand full of features which aren't supported (yet), including:
  • Changing the pivot of a sprite other than what's defined as the default.
  • Nested entities.
  • Most of their experimental features like skins and ffd.
BUT, like I've stated in my previous post, one thing that is superior with this system is that you can interpolate between sprite animations and/or mix those together. Additionally, because this system contains scripts for performing Inverse Kinematics and other useful manipulation on your bones, you can still use those with this system at runtime to create procedural animation.


Spriter Adventure Platformer character rendered in GMS2.

If you want early access, go to the GitHub and download the project file. Otherwise, I'm probably going to get around to creating a marketplace extension once some other important features are added. (Animation states, physics constraints, documentation, ...)
 

Nux

GameMaker Staff
GameMaker Dev.
Physics! That's right, I've recently revamped physics constraints so that they support slack chain physics between an anchor and an end effector. These can be used to simulate fabric, tails, and other soft bodies that can procedurally interact with your animations.


Use physics constraints to add chains between two extremities.
Additionally, I've added a couple of global variables which you can change to apply external horizontal and vertical movement to your physics constraints, so not only can these systems interact seamlessly with your animations, but also your players movement in the game world; which could result in a more immersive realistic experience if executed correctly ... or just some silly fun.


Use physics constraints to procedurally simulate the movement of tails towards an end effector.
 

Joe Ellis

Member
This is really impressive, and you can see how much work has gone into it
Is this just a collection of scripts that enables all this stuff, or have you an editor prog for it? If you haven't you definitely should, it will be less work than making the thing in the first place and, well, it would just be amazing

The chain stuff is really cool

You could actually make money from this cus no one has actually made a full 2d skeletal animation system for gamemaker as an extension, not being a heartless business KuϞ*, but loads of people could find this useful and say it was $5, thats nothing for most people, and you get something for all your hard work
 
Last edited:
  • Like
Reactions: Nux

Nux

GameMaker Staff
GameMaker Dev.
This is really impressive, and you can see how much work has gone into it
Is this just a collection of scripts that enables all this stuff, or have you an editor prog for it? If you haven't you definitely should, it will be less work than making the thing in the first place and, well, it would just be amazing

The chain stuff is really cool

You could actually make money from this cus no one has actually made a full 2d skeletal animation system for gamemaker as an extension, not being a heartless business KuϞ*, but loads of people could find this useful and say it was $5, thats nothing for most people, and you get something for all your hard work
First of all, thank you!

This is a full skeletal animation runtime built from the ground up by me, and doesn't leech of the existing Spine implementation GameMaker has. Currently, I have no plans of making an editor for this (although I would like to make one, it's just not my priority right now); I'd much rather support the existing export formats of other editors, be they by a company or an individual* - so to answer your question: No editor is required and everything is done through scripts.

I actually got the inspiration for the "chain stuff" from a game called 'Rain World', and a very crude early prototype of dynamic hair I made 6 months ago. I think that procedural animation can be really beautiful if done right; Hopefully, when I get Free Form Deformation (FFD) implemented, this feature will be enhanced since you would be able to simulate soft body physics, for exmaple: a skirt swaying when your character runs *hint* *hint*.

I did think about offering this for a price (which would help me out a lot), but I'd like to offer it for free for now so people can test it and give feedback; maybe I'll put a price tag on it in the future when it's more feature rich. If not, I could always put a paid version on the marketplace for those who want to pay and have the added premium of having the project in their library for easy importing.



*I've been considering finding someone who has something similar that they offer for free (or at a low price), to see if they'd like me to add support for their software, but most I've stumbled across haven't been updated in years.
 
Last edited:

Nux

GameMaker Staff
GameMaker Dev.
Slow progress recently because of university stuff, but I'm back in the flow.


YOU'VE DOOMED US ALL

The three main things I'm working on are:
  1. The animation state object, which will be used to automatically blend and mix animations.
  2. Properties: so skeleton data can be accessed and manipulated more intuitively, for example sk_bone_x(bone,[x]) where "x" is an optional argument that will determine whether the script acts as a function (returns the value currently held in "x"), or as a procedure (perform an action on the data record such as overwriting the data with the newly supplied value).
  3. Documentation, which you can get a preview on the GitHub here and here.
Once these are complete I'm going to start pushing towards a full release on the marketplace.
 

Nux

GameMaker Staff
GameMaker Dev.
I've recently been working on a Visual Basic tool for managing and manipulating GameMaker extensions, which you can take a look at here. Now, why am I telling you this? Because this means that I can now quick and easily convert the project file into a standalone extension, with all the scripts and macros contained within that. This will keep your projects squeaky clean, and when I release a new update it's as quick and easy as deleting the previous extension and importing the new version.

Other things I want to quickly gloss over: Documentation is going to be revamped to only cover the most important functions, Properties are complete, and I've totally changed the way timelines are applied.
 

Joe Ellis

Member
Wow that sounds so good! I've avoided building my scripts into a .gml extension for this reason, I have recently been reading from .object files and shaders to get variables but this is really cool how you've made something that actually makes the gm files
 
  • Like
Reactions: Nux

Nux

GameMaker Staff
GameMaker Dev.
Drum roll.

After a months of inactivity, where I've been occupied with my university application and a client, I have something of interest to show! If you want to know what I've changed over that time, here you go:
  1. Timelines have been revamped to allow for a future experimental animation feature which should improve the performance of animations by pre-calculating which frames to apply, opposed to searching for them each frame.
  2. Point attachments have been stripped of redundant scripts, now only containing scripts for transforming their local transforms into world space using a parent bone.
  3. The entire structure engine was revamped to allow for polymorphism, so no more switch statements; most things are abstracted.
  4. The armature has been revamped to not expose any of its nested lists in case a user deletes them, causing errors.
  5. Animation states have been implemented! (See below)
...That's right, these data structures will allow you to automatically blend and mix between animations smoothly without much effort. This is useful for player characters which change animations a lot, but can also be used for other things such as to sway a tree between two stationary poses at random intervals.


An animation state smoothly blending between multiple animations.

The code that you need to use to set animations is also simple to use, simply having to play the animation and specify whether you want it to loop or freeze on the final frame:


Finally, activity may slow down even more in a week since I'm moving into new accommodation and will be without this PC until December. I will be carrying a smaller PC, but whether I make progress whilst at university is another story; We will see.
 
Last edited:

Nux

GameMaker Staff
GameMaker Dev.
In the last couple of days I've had an epiphany how to do non-uniform scaling IK constraints (since Spine supports it, it's probably crucial to some people). So, I present you non-uniform scaled IK:


(Unoriginally) using the animation state in my previous post, IK chains where the parent bone has non-uniform scales now find end solutions!
...notice how the forearms distort when the arm bends, that's what made this problem especially difficult. This is a throwback to one of my first posts where I thought I found a solution to this problem, but it turned out to be invalid. Anyway, here it is in its full glory!


Also, @Bingdom has been helping out with the documentation in his free time, so a few things are getting improved currently.

P.s. For those of you interested in how this was done: Circle-ellipse intersection, and a lot of gymnastics with equations / avoiding complex numbers.
 

Joe Ellis

Member
Its always good when you work out something like this, I've had a few things in the past where I think I've worked something out and then turns out to be invalid, but its just a good feeling when you actually get it
I have no idea what this thing is though, well I've got a rough idea but I've never done it
I know what non uniform scaling means though, does it make the vertices or sections get more scaled the closer they are to the bone or something?
 

Nux

GameMaker Staff
GameMaker Dev.
does it make the vertices or sections get more scaled the closer they are to the bone or something?
When something is scaled non-uniformly, its xscale != yscale. (i.e. 1x1 would be uniform, 1x2, would not.) The effect this has on the skeleton is it shears the child bones (notice how the forearm's pixels form strange angles) so the transformation matrix no longer has axes which are orthogonal to each other.

When scales are uniform IK is a breeze because the lengths of your bones will never change, but when a circle is sheared it becomes an ellipse. This causes lots of issues because you can no longer perform IK the "traditional" way (algebraically using trigonometric functions), it requires a more geometric approach to solve; the algebra then becomes the grunt work, because the solution is held back by that initial realisation.
 

Joe Ellis

Member
When something is scaled non-uniformly, its xscale != yscale. (i.e. 1x1 would be uniform, 1x2, would not.) The effect this has on the skeleton is it shears the child bones (notice how the forearm's pixels form strange angles) so the transformation matrix no longer has axes which are orthogonal to each other.

When scales are uniform IK is a breeze because the lengths of your bones will never change, but when a circle is sheared it becomes an ellipse. This causes lots of issues because you can no longer perform IK the "traditional" way (algebraically using trigonometric functions), it requires a more geometric approach to solve; the algebra then becomes the grunt work, because the solution is held back by that initial realisation.
Oh I thought it was something more complicated than that, so now if a parent bone has irregular scaling the child bones dont inherit the skew?
 

Nux

GameMaker Staff
GameMaker Dev.
child bones dont inherit the skew?
No, the child bones will always inherit the skew, that's why the solution isn't obvious (since the child bones joint length isn't a constant value).

I think this might help paint a better picture:


The goal was the produce an IK solution where the child bone does this:


This is the desired solution for said 2 bone system (I'm using DragonBones, because it's my preferred software, but the same works in Spine):


As you can see the length of the child squashes and stretches because of the skew from the parent's scales.
 
Last edited:
G

Giovalian

Guest
Very good my developer friend. I'm interested in knowing how to run an animation from the beginning. because when I execute an animation of an attack it does it from the last place where I am and sometimes it starts from the beginning. This is a percistent problem in me. Very good code of yours. Yeah!
 
M

mazimadu

Guest
Hmm, my mind wonders.
The problem is that I already have Spine and use it frequently.
The problem with spine is that it does not support physics.
I wonder?
 

Nux

GameMaker Staff
GameMaker Dev.
Very good my developer friend. I'm interested in knowing how to run an animation from the beginning. because when I execute an animation of an attack it does it from the last place where I am and sometimes it starts from the beginning. This is a percistent problem in me. Very good code of yours. Yeah!
Hey! Sorry for the delay, I've been busy with university.

I believe there was a pretty major bug with animationStates which I've actually fixed in an updated version. If you don't use Spriter, check this out: https://github.com/NuxiiGit/2DSKAnimation.

I plan on removing the old version, supporting Spriter in the new version, and adding/cleaning some features which have been bugging me forever. I just haven't had the time, and gamemaker recently released a crippling update which I'm not ready to deal with.

Call me when the GML improvements drop.
 

Joe Ellis

Member
Hey! Sorry for the delay, I've been busy with university.

I believe there was a pretty major bug with animationStates which I've actually fixed in an updated version. If you don't use Spriter, check this out: https://github.com/NuxiiGit/2DSKAnimation.

I plan on removing the old version, supporting Spriter in the new version, and adding/cleaning some features which have been bugging me forever. I just haven't had the time, and gamemaker recently released a crippling update which I'm not ready to deal with.

Call me when the GML improvements drop.
Was gonna say I haven't heard from you in a while, that gml update is gold, you could re-write the whole thing and it will be 300 times better than before, well in speed terms
but yeah, its gonna take a while to get used to it, sure is with me
 
  • Like
Reactions: Nux
E

ElViejoSanta

Guest
I don't know why but I can't open it. This is the error messagge:


___________________________________________
############################################################################################
FATAL ERROR in
action number 1
of Create Event
for object obj_armature:

REAL argument is undefined
at gml_Script_sk_atlas_create_dragonbones_context (line 28) - var sk_tex_dxframe = real(sk_db_subtex_record[? "frameX"]);
############################################################################################
--------------------------------------------------------------------------------------------
stack frame is
gml_Script_sk_atlas_create_dragonbones_context (line 28)
called from - gml_Script_sk_atlas_create_dragonbones (line 6) - return sk_atlas_create_dragonbones_context(__sk_file_read_all(argument0),argument1,argument2,argument3);
called from - gml_Object_obj_armature_Create_0 (line 3) - atlas = sk_atlas_create_dragonbones("Santa_tex.json",spr_santa,0,1);


Can any of you guys help me out?
Thank you!
 

Nux

GameMaker Staff
GameMaker Dev.
Can any of you guys help me out?
Thank you!
This has been broken for a while, now. All because YYG thought it would be smart to make the real function throw a run-time error when it can't parse a string. There's nothing I can do about this right now.

I actually plan of fixing this project once the new GML updates release, because they will have exception handling. So you will have to wait a couple of weeks. Sorry about this!


Alternatively, you can add this script called real_real to your game to get a temporary, hacky fix:
Code:
#macro real real_real
/// @desc The real real function.
/// @param str {String} The string to parse.
var json = json_decode("\"value\":" + string(argument0) + "}");
if (json == -1) then return 0; // default
var value = json[? "value"];
ds_map_destroy(json);
return is_real(value) ? value : 0;
 
Last edited:

duran can

Member
isn't work, no errors but just black room.

This has been broken for a while, now. All because YYG thought it would be smart to make the real function throw a run-time error when it can't parse a string. There's nothing I can do about this right now.

I actually plan of fixing this project once the new GML updates release, because they will have exception handling. So you will have to wait a couple of weeks. Sorry about this!


Alternatively, you can add this script called real_real to your game to get a temporary, hacky fix:
Code:
#macro real real_real
/// @desc The real real function.
/// @param str {String} The string to parse.
var json = json_decode("\"value\":" + string(argument0) + "}");
if (json == -1) then return 0; // default
var value = json[? "value"];
ds_map_destroy(json);
return is_real(value) ? value : 0;
 
Top