This commit is contained in:
badlogic 2022-04-13 14:20:01 +02:00
commit 898743739d
25 changed files with 255 additions and 92 deletions

View File

@ -455,25 +455,25 @@ Skin *SkeletonBinary::readSkin(DataInput *input, bool defaultSkin, SkeletonData
skin = new (__FILE__, __LINE__) Skin(readStringRef(input, skeletonData)); skin = new (__FILE__, __LINE__) Skin(readStringRef(input, skeletonData));
for (int i = 0, n = readVarint(input, true); i < n; i++) { for (int i = 0, n = readVarint(input, true); i < n; i++) {
int boneIndex = readVarint(input, true); int boneIndex = readVarint(input, true);
if (boneIndex >= skeletonData->_bones.size()) return NULL; if (boneIndex >= (int)skeletonData->_bones.size()) return NULL;
skin->getBones().add(skeletonData->_bones[boneIndex]); skin->getBones().add(skeletonData->_bones[boneIndex]);
} }
for (int i = 0, n = readVarint(input, true); i < n; i++) { for (int i = 0, n = readVarint(input, true); i < n; i++) {
int ikIndex = readVarint(input, true); int ikIndex = readVarint(input, true);
if (ikIndex >= skeletonData->_ikConstraints.size()) return NULL; if (ikIndex >= (int)skeletonData->_ikConstraints.size()) return NULL;
skin->getConstraints().add(skeletonData->_ikConstraints[ikIndex]); skin->getConstraints().add(skeletonData->_ikConstraints[ikIndex]);
} }
for (int i = 0, n = readVarint(input, true); i < n; i++) { for (int i = 0, n = readVarint(input, true); i < n; i++) {
int transformIndex = readVarint(input, true); int transformIndex = readVarint(input, true);
if (transformIndex >= skeletonData->_transformConstraints.size()) return NULL; if (transformIndex >= (int)skeletonData->_transformConstraints.size()) return NULL;
skin->getConstraints().add(skeletonData->_transformConstraints[transformIndex]); skin->getConstraints().add(skeletonData->_transformConstraints[transformIndex]);
} }
for (int i = 0, n = readVarint(input, true); i < n; i++) { for (int i = 0, n = readVarint(input, true); i < n; i++) {
int pathIndex = readVarint(input, true); int pathIndex = readVarint(input, true);
if (pathIndex >= skeletonData->_pathConstraints.size()) return NULL; if (pathIndex >= (int)skeletonData->_pathConstraints.size()) return NULL;
skin->getConstraints().add(skeletonData->_pathConstraints[pathIndex]); skin->getConstraints().add(skeletonData->_pathConstraints[pathIndex]);
} }
slotCount = readVarint(input, true); slotCount = readVarint(input, true);

View File

@ -11,4 +11,4 @@ dest_files=[ "res://.import/mix-and-match.atlas-3d349b543ecdcc01fb29033adaef0841
[params] [params]
normal_texture_prefix="n" normal_map_prefix="n"

View File

@ -11,4 +11,4 @@ dest_files=[ "res://.import/raptor.atlas-66da4b831eebf404341993162ba3ddb8.spatla
[params] [params]
normal_texture_prefix="n" normal_map_prefix="n"

View File

@ -1,10 +1,22 @@
[gd_resource type="SpineSkeletonDataResource" load_steps=3 format=2] [gd_resource type="SpineSkeletonDataResource" load_steps=5 format=2]
[ext_resource path="res://assets/spineboy/spineboy.atlas" type="SpineAtlasResource" id=1] [ext_resource path="res://assets/spineboy/spineboy.atlas" type="SpineAtlasResource" id=1]
[ext_resource path="res://assets/spineboy/spineboy-pro.json" type="SpineSkeletonFileResource" id=2] [ext_resource path="res://assets/spineboy/spineboy-pro.json" type="SpineSkeletonFileResource" id=2]
[sub_resource type="SpineAnimationMix" id=1]
from = "run"
to = "idle"
mix = 1.0
[sub_resource type="SpineAnimationMix" id=2]
from = "idle"
to = "run"
mix = 1.0
[resource] [resource]
atlas_res = ExtResource( 1 ) atlas_res = ExtResource( 1 )
skeleton_file_res = ExtResource( 2 ) skeleton_file_res = ExtResource( 2 )
default_mix = 0.2
animation_mixes = [ SubResource( 1 ), SubResource( 2 ), null, null ]
animations = null animations = null
skins = null skins = null

View File

@ -11,4 +11,4 @@ dest_files=[ "res://.import/spineboy.atlas-54c12b5ff1cdaaa1b4e452a7d0d868c9.spat
[params] [params]
normal_texture_prefix="n" normal_map_prefix="n"

View File

@ -1,34 +1,12 @@
[gd_scene load_steps=7 format=2] [gd_scene load_steps=3 format=2]
[ext_resource path="res://examples/helloworld/spineboy-helloworld.gd" type="Script" id=1] [ext_resource path="res://examples/helloworld/spineboy-helloworld.gd" type="Script" id=1]
[ext_resource path="res://examples/mix-and-match/mix-and-match.gd" type="Script" id=2]
[ext_resource path="res://assets/spineboy/spinebody-data-res.tres" type="SpineSkeletonDataResource" id=3] [ext_resource path="res://assets/spineboy/spinebody-data-res.tres" type="SpineSkeletonDataResource" id=3]
[ext_resource path="res://assets/mix-and-match/mix-and-match-data.tres" type="SpineSkeletonDataResource" id=4]
[ext_resource path="res://assets/raptor/raprot-data.tres" type="SpineSkeletonDataResource" id=5]
[sub_resource type="GDScript" id=1]
script/source = "extends SpineSprite
func _ready():
get_animation_state().set_animation(\"walk\", true)
"
[node name="Node2D" type="Node2D"] [node name="Node2D" type="Node2D"]
[node name="Spineboy" type="SpineSprite" parent="."] [node name="Spineboy" type="SpineSprite" parent="."]
position = Vector2( 137.107, 540.132 ) position = Vector2( 496.207, 477.185 )
scale = Vector2( 0.466832, 0.466832 ) scale = Vector2( 0.466832, 0.466832 )
skeleton_data_res = ExtResource( 3 ) skeleton_data_res = ExtResource( 3 )
script = ExtResource( 1 ) script = ExtResource( 1 )
[node name="MixAndMatch" type="SpineSprite" parent="."]
position = Vector2( 402.469, 534.677 )
scale = Vector2( 0.366163, 0.366163 )
skeleton_data_res = ExtResource( 4 )
script = ExtResource( 2 )
[node name="Raptor" type="SpineSprite" parent="."]
position = Vector2( 793.667, 527.026 )
scale = Vector2( 0.343143, 0.343143 )
skeleton_data_res = ExtResource( 5 )
script = SubResource( 1 )

View File

@ -1,4 +1,4 @@
extends SpineSprite extends SpineSprite
func _ready(): func _ready():
get_animation_state().set_animation("walk", true, 0) get_animation_state().set_animation("walk", true, 0)

View File

@ -0,0 +1,12 @@
[gd_scene load_steps=3 format=2]
[ext_resource path="res://assets/spineboy/spinebody-data-res.tres" type="SpineSkeletonDataResource" id=1]
[ext_resource path="res://examples/simple-input/spineboy-simple-input.gd" type="Script" id=2]
[node name="Node2D" type="Node2D"]
[node name="Spineboy" type="SpineSprite" parent="."]
position = Vector2( 501.503, 472.035 )
scale = Vector2( 0.518624, 0.518624 )
skeleton_data_res = ExtResource( 1 )
script = ExtResource( 2 )

View File

@ -0,0 +1,19 @@
extends SpineSprite
func _ready():
get_animation_state().set_animation("idle", true, 0)
func _process(delta):
if Input.is_action_just_pressed("ui_left"):
get_animation_state().set_animation("run", true, 0)
get_skeleton().set_scale_x(-1)
if Input.is_action_just_released("ui_left"):
get_animation_state().set_animation("idle", true, 0)
if (Input.is_action_just_pressed("ui_right")):
get_animation_state().set_animation("run", true, 0)
get_skeleton().set_scale_x(1)
if Input.is_action_just_released("ui_right"):
get_animation_state().set_animation("idle", true, 0)

View File

@ -11,7 +11,7 @@ config_version=4
[application] [application]
config/name="spine-godot-examples" config/name="spine-godot-examples"
run/main_scene="res://tests/batch-test.tscn" run/main_scene="res://examples/simple-input/simple-input.tscn"
run/low_processor_mode=true run/low_processor_mode=true
config/icon="res://icon.png" config/icon="res://icon.png"

View File

@ -6,6 +6,5 @@ cp -r .idea godot
cp custom.py godot cp custom.py godot
cp -r ../spine-cpp/spine-cpp spine_godot cp -r ../spine-cpp/spine-cpp spine_godot
pushd godot pushd godot
scons -Q compiledb custom_modules="../spine_godot" scons compiledb=yes custom_modules="../spine_godot" -j16
scons target=debug custom_modules="../spine_godot" --jobs=8
popd popd

View File

@ -32,7 +32,7 @@
#include "SpineConstant.h" #include "SpineConstant.h"
#include "core/reference.h" #include "core/reference.h"
#include <spine/spine.h> #include <spine/Animation.h>
class SpineEvent; class SpineEvent;
class SpineSkeleton; class SpineSkeleton;

View File

@ -70,8 +70,8 @@ public:
if (error != OK) { if (error != OK) {
ERR_PRINT(vformat("Can't load texture: \"%s\"", String(path.buffer()))); ERR_PRINT(vformat("Can't load texture: \"%s\"", String(path.buffer())));
auto renderer_object = memnew(SpineRendererObject); auto renderer_object = memnew(SpineRendererObject);
renderer_object->texture = nullptr; renderer_object->texture = Ref<Texture>(nullptr);
renderer_object->normal_map = nullptr; renderer_object->normal_map = Ref<Texture>(nullptr);
page.setRendererObject((void *) renderer_object); page.setRendererObject((void *) renderer_object);
return; return;
} }
@ -79,7 +79,7 @@ public:
textures->append(texture); textures->append(texture);
auto renderer_object = memnew(SpineRendererObject); auto renderer_object = memnew(SpineRendererObject);
renderer_object->texture = texture; renderer_object->texture = texture;
renderer_object->normal_map = nullptr; renderer_object->normal_map = Ref<Texture>(nullptr);
String temp_path = fixed_path; String temp_path = fixed_path;
String new_path = vformat("%s/%s_%s", temp_path.get_base_dir(), normal_map_prefix, temp_path.get_file()); String new_path = vformat("%s/%s_%s", temp_path.get_base_dir(), normal_map_prefix, temp_path.get_file());

View File

@ -30,14 +30,11 @@
#ifndef GODOT_SPINEATLASRESOURCE_H #ifndef GODOT_SPINEATLASRESOURCE_H
#define GODOT_SPINEATLASRESOURCE_H #define GODOT_SPINEATLASRESOURCE_H
#include <spine/Atlas.h>
#include "core/io/resource_loader.h" #include "core/io/resource_loader.h"
#include "core/io/resource_saver.h" #include "core/io/resource_saver.h"
#include "core/io/image_loader.h" #include "core/io/image_loader.h"
#include <spine/Atlas.h>
class spine::Atlas;
class GodotSpineTextureLoader; class GodotSpineTextureLoader;
class SpineAtlasResource : public Resource { class SpineAtlasResource : public Resource {

View File

@ -76,13 +76,40 @@ SpineEditorPlugin::SpineEditorPlugin(EditorNode *node) {
add_import_plugin(memnew(SpineAtlasResourceImportPlugin)); add_import_plugin(memnew(SpineAtlasResourceImportPlugin));
add_import_plugin(memnew(SpineJsonResourceImportPlugin)); add_import_plugin(memnew(SpineJsonResourceImportPlugin));
add_import_plugin(memnew(SpineBinaryResourceImportPlugin)); add_import_plugin(memnew(SpineBinaryResourceImportPlugin));
add_inspector_plugin(memnew(SpineAnimationMixesInspectorPlugin));
} }
SpineEditorPlugin::~SpineEditorPlugin() { SpineEditorPlugin::~SpineEditorPlugin() {
} }
bool SpineEditorPlugin::handles(Object *object) const { bool SpineEditorPlugin::handles(Object *object) const {
return object->is_class("SpineSprite"); return object->is_class("SpineSprite") || object->is_class("SpineSkeletonDataResource");
}
SpineAnimationMixesInspectorPlugin::SpineAnimationMixesInspectorPlugin(): add_mix_button(nullptr) {
add_mix_button = memnew(Button);
add_mix_button->set_text("Add mix");
}
SpineAnimationMixesInspectorPlugin::~SpineAnimationMixesInspectorPlugin() {
}
bool SpineAnimationMixesInspectorPlugin::can_handle(Object *object) {
return object->is_class("SpineSkeletonDataResource");
}
void SpineAnimationMixesInspectorPlugin::parse_begin(Object *object) {
sprite = object->cast_to<SpineSprite>(object);
}
bool SpineAnimationMixesInspectorPlugin::parse_property(Object *object, Variant::Type type, const String &path,
PropertyHint hint, const String &hint_text, int usage) {
if (path == "animation_mixes") {
add_custom_control(add_mix_button);
return true;
}
return false;
} }
#endif #endif

View File

@ -32,29 +32,31 @@
#ifdef TOOLS_ENABLED #ifdef TOOLS_ENABLED
#include "editor/editor_node.h" #include "editor/editor_node.h"
#include "SpineSprite.h"
#include "editor/editor_properties.h"
class SpineAtlasResourceImportPlugin : public EditorImportPlugin { class SpineAtlasResourceImportPlugin : public EditorImportPlugin {
GDCLASS(SpineAtlasResourceImportPlugin, EditorImportPlugin) GDCLASS(SpineAtlasResourceImportPlugin, EditorImportPlugin)
public: public:
String get_importer_name() const override { return "spine.atlas"; } String get_importer_name() const override { return "spine.atlas"; }
String get_visible_name() const override { return "Spine Runtime Atlas"; } String get_visible_name() const override { return "Spine Runtime Atlas"; }
void get_recognized_extensions(List<String> *extensions) const override { extensions->push_back("atlas"); } void get_recognized_extensions(List<String> *extensions) const override { extensions->push_back("atlas"); }
String get_preset_name(int idx) const override { return idx == 0 ? "Default" : "Unknown"; } String get_preset_name(int idx) const override { return idx == 0 ? "Default" : "Unknown"; }
int get_preset_count() const override { return 1; } int get_preset_count() const override { return 1; }
String get_save_extension() const override { return "spatlas"; } String get_save_extension() const override { return "spatlas"; }
String get_resource_type() const override { return "SpineAtlasResource"; } String get_resource_type() const override { return "SpineAtlasResource"; }
void get_import_options(List<ImportOption> *options, int preset) const override; void get_import_options(List<ImportOption> *options, int preset) const override;
bool get_option_visibility(const String &option, const Map<StringName, Variant> &options) const override { return true; } bool get_option_visibility(const String &option, const Map<StringName, Variant> &options) const override { return true; }
Error import(const String &source_file, const String &save_path, const Map<StringName, Variant> &options, List<String> *platform_variants, List<String> *gen_files, Variant *metadata) override; Error import(const String &source_file, const String &save_path, const Map<StringName, Variant> &options, List<String> *platform_variants, List<String> *gen_files, Variant *metadata) override;
}; };
@ -63,23 +65,23 @@ class SpineJsonResourceImportPlugin : public EditorImportPlugin {
public: public:
String get_importer_name() const override { return "spine.json"; } String get_importer_name() const override { return "spine.json"; }
String get_visible_name() const override { return "Spine Skeleton Json"; } String get_visible_name() const override { return "Spine Skeleton Json"; }
void get_recognized_extensions(List<String> *extensions) const override { extensions->push_back("json"); } void get_recognized_extensions(List<String> *extensions) const override { extensions->push_back("json"); }
String get_preset_name(int idx) const override { return idx == 0 ? "Default" : "Unknown"; } String get_preset_name(int idx) const override { return idx == 0 ? "Default" : "Unknown"; }
int get_preset_count() const override { return 1; } int get_preset_count() const override { return 1; }
String get_save_extension() const override { return "spjson"; } String get_save_extension() const override { return "spjson"; }
String get_resource_type() const override { return "SpineSkeletonFileResource"; } String get_resource_type() const override { return "SpineSkeletonFileResource"; }
void get_import_options(List<ImportOption> *options, int preset) const override {} void get_import_options(List<ImportOption> *options, int preset) const override {}
bool get_option_visibility(const String &option, const Map<StringName, Variant> &options) const override { return true; } bool get_option_visibility(const String &option, const Map<StringName, Variant> &options) const override { return true; }
Error import(const String &source_file, const String &save_path, const Map<StringName, Variant> &options, List<String> *platform_variants, List<String> *gen_files, Variant *metadata) override; Error import(const String &source_file, const String &save_path, const Map<StringName, Variant> &options, List<String> *platform_variants, List<String> *gen_files, Variant *metadata) override;
}; };
@ -116,11 +118,46 @@ public:
~SpineEditorPlugin(); ~SpineEditorPlugin();
String get_name() const override { return "SpineEditorPlugin"; } String get_name() const override { return "SpineEditorPlugin"; }
bool has_main_screen() const { return false; } bool has_main_screen() const { return false; }
bool handles(Object *object) const override; bool handles(Object *object) const override;
}; };
class SpineAnimationMixesInspectorPlugin: public EditorInspectorPlugin {
GDCLASS(SpineAnimationMixesInspectorPlugin, EditorInspectorPlugin)
SpineSprite *sprite;
Button *add_mix_button;
Vector<Button *> delete_mix;
public:
SpineAnimationMixesInspectorPlugin();
~SpineAnimationMixesInspectorPlugin() override;
bool can_handle(Object *object) override;
void parse_begin(Object *object) override;
bool parse_property(Object *object, Variant::Type type, const String &path, PropertyHint hint, const String &hint_text, int usage) override;
};
class SpineAnimationMixesProperty: public EditorProperty {
GDCLASS(SpineAnimationMixesProperty, EditorProperty)
public:
SpineAnimationMixesProperty();
~SpineAnimationMixesProperty();
};
class SpineEditorPropertyMix: public EditorProperty {
GDCLASS(SpineEditorPropertyMix, EditorProperty)
EditorPropertyText *from_property;
EditorPropertyText *to_property;
EditorPropertyFloat *mix_property;
public:
};
#endif #endif
#endif//GODOT_SPINEEDITORPLUGIN_H #endif//GODOT_SPINEEDITORPLUGIN_H

View File

@ -31,6 +31,8 @@
#define GODOT_SPINEEVENT_H #define GODOT_SPINEEVENT_H
#include "SpineEventData.h" #include "SpineEventData.h"
#include "core/reference.h"
#include <spine/Event.h>
class SpineEvent : public Reference { class SpineEvent : public Reference {
GDCLASS(SpineEvent, Reference) GDCLASS(SpineEvent, Reference)

View File

@ -31,6 +31,7 @@
#define GODOT_SPINEIKCONSTRAINT_H #define GODOT_SPINEIKCONSTRAINT_H
#include "SpineIkConstraintData.h" #include "SpineIkConstraintData.h"
#include <spine/IkConstraint.h>
class SpineBone; class SpineBone;

View File

@ -29,10 +29,48 @@
#include "SpineSkeletonDataResource.h" #include "SpineSkeletonDataResource.h"
#ifdef TOOLS_ENABLED void SpineAnimationMix::_bind_methods() {
#include "editor/editor_node.h" ClassDB::bind_method(D_METHOD("set_from", "from"), &SpineAnimationMix::set_from);
#include "editor/editor_inspector.h" ClassDB::bind_method(D_METHOD("get_from"), &SpineAnimationMix::get_from);
#endif ClassDB::bind_method(D_METHOD("set_to", "to"), &SpineAnimationMix::set_to);
ClassDB::bind_method(D_METHOD("get_to"), &SpineAnimationMix::get_to);
ClassDB::bind_method(D_METHOD("set_mix", "mix"), &SpineAnimationMix::set_mix);
ClassDB::bind_method(D_METHOD("get_mix"), &SpineAnimationMix::get_mix);
ADD_PROPERTY(PropertyInfo(Variant::STRING, "from"), "set_from", "get_from");
ADD_PROPERTY(PropertyInfo(Variant::STRING, "to"), "set_to", "get_to");
ADD_PROPERTY(PropertyInfo(Variant::REAL, "mix"), "set_mix", "get_mix");
}
SpineAnimationMix::SpineAnimationMix() {
}
SpineAnimationMix::~SpineAnimationMix() {
}
void SpineAnimationMix::set_from(const StringName &from) {
this->from = from;
}
String SpineAnimationMix::get_from() {
return from;
}
void SpineAnimationMix::set_to(const StringName &to) {
this->to = to;
}
String SpineAnimationMix::get_to() {
return to;
}
void SpineAnimationMix::set_mix(float mix) {
this->mix = mix;
}
float SpineAnimationMix::get_mix() {
return mix;
}
void SpineSkeletonDataResource::_bind_methods() { void SpineSkeletonDataResource::_bind_methods() {
ClassDB::bind_method(D_METHOD("is_skeleton_data_loaded"), &SpineSkeletonDataResource::is_skeleton_data_loaded); ClassDB::bind_method(D_METHOD("is_skeleton_data_loaded"), &SpineSkeletonDataResource::is_skeleton_data_loaded);
@ -40,6 +78,10 @@ void SpineSkeletonDataResource::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_atlas_res"), &SpineSkeletonDataResource::get_atlas_res); ClassDB::bind_method(D_METHOD("get_atlas_res"), &SpineSkeletonDataResource::get_atlas_res);
ClassDB::bind_method(D_METHOD("set_skeleton_file_res", "skeleton_file_res"), &SpineSkeletonDataResource::set_skeleton_file_res); ClassDB::bind_method(D_METHOD("set_skeleton_file_res", "skeleton_file_res"), &SpineSkeletonDataResource::set_skeleton_file_res);
ClassDB::bind_method(D_METHOD("get_skeleton_file_res"), &SpineSkeletonDataResource::get_skeleton_file_res); ClassDB::bind_method(D_METHOD("get_skeleton_file_res"), &SpineSkeletonDataResource::get_skeleton_file_res);
ClassDB::bind_method(D_METHOD("set_default_mix", "default_mix"), &SpineSkeletonDataResource::set_default_mix);
ClassDB::bind_method(D_METHOD("get_default_mix"), &SpineSkeletonDataResource::get_default_mix);
ClassDB::bind_method(D_METHOD("set_animation_mixes", "mixes"), &SpineSkeletonDataResource::set_animation_mixes);
ClassDB::bind_method(D_METHOD("get_animation_mixes"), &SpineSkeletonDataResource::get_animation_mixes);
// Spine API // Spine API
ClassDB::bind_method(D_METHOD("find_bone", "bone_name"), &SpineSkeletonDataResource::find_bone); ClassDB::bind_method(D_METHOD("find_bone", "bone_name"), &SpineSkeletonDataResource::find_bone);
@ -75,9 +117,12 @@ void SpineSkeletonDataResource::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "atlas_res", PropertyHint::PROPERTY_HINT_RESOURCE_TYPE, "SpineAtlasResource"), "set_atlas_res", "get_atlas_res"); ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "atlas_res", PropertyHint::PROPERTY_HINT_RESOURCE_TYPE, "SpineAtlasResource"), "set_atlas_res", "get_atlas_res");
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "skeleton_file_res", PropertyHint::PROPERTY_HINT_RESOURCE_TYPE, "SpineSkeletonFileResource"), "set_skeleton_file_res", "get_skeleton_file_res"); ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "skeleton_file_res", PropertyHint::PROPERTY_HINT_RESOURCE_TYPE, "SpineSkeletonFileResource"), "set_skeleton_file_res", "get_skeleton_file_res");
ADD_PROPERTY(PropertyInfo(Variant::REAL, "default_mix"), "set_default_mix", "get_default_mix");
ADD_GROUP("Animation mixes", "");
ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "animation_mixes"), "set_animation_mixes", "get_animation_mixes");
} }
SpineSkeletonDataResource::SpineSkeletonDataResource() : skeleton_data(nullptr), animation_state_data(nullptr) { SpineSkeletonDataResource::SpineSkeletonDataResource() : skeleton_data(nullptr), animation_state_data(nullptr), default_mix(0) {
} }
SpineSkeletonDataResource::~SpineSkeletonDataResource() { SpineSkeletonDataResource::~SpineSkeletonDataResource() {
@ -137,6 +182,7 @@ void SpineSkeletonDataResource::set_atlas_res(const Ref<SpineAtlasResource> &atl
atlas_res = atlas; atlas_res = atlas;
update_skeleton_data(); update_skeleton_data();
} }
Ref<SpineAtlasResource> SpineSkeletonDataResource::get_atlas_res() { Ref<SpineAtlasResource> SpineSkeletonDataResource::get_atlas_res() {
return atlas_res; return atlas_res;
} }
@ -145,6 +191,7 @@ void SpineSkeletonDataResource::set_skeleton_file_res(const Ref<SpineSkeletonFil
skeleton_file_res = skeleton_file; skeleton_file_res = skeleton_file;
update_skeleton_data(); update_skeleton_data();
} }
Ref<SpineSkeletonFileResource> SpineSkeletonDataResource::get_skeleton_file_res() { Ref<SpineSkeletonFileResource> SpineSkeletonDataResource::get_skeleton_file_res() {
return skeleton_file_res; return skeleton_file_res;
} }
@ -169,23 +216,21 @@ void SpineSkeletonDataResource::get_skin_names(Vector<String> &skin_names) const
} }
} }
void SpineSkeletonDataResource::_get_property_list(List<PropertyInfo> *p_list) const { void SpineSkeletonDataResource::set_default_mix(float default_mix) {
PropertyInfo property; this->default_mix = default_mix;
Vector<String> animation_names; if (animation_state_data) animation_state_data->setDefaultMix(default_mix);
}
property.name = "animations"; float SpineSkeletonDataResource::get_default_mix() {
property.type = Variant::STRING; return default_mix;
get_animation_names(animation_names); }
property.hint_string = String(",").join(animation_names);
property.hint = PROPERTY_HINT_ENUM;
p_list->push_back(property);
property.name = "skins"; void SpineSkeletonDataResource::set_animation_mixes(Array animation_mixes) {
property.type = Variant::STRING; this->animation_mixes = animation_mixes;
get_skin_names(animation_names); }
property.hint_string = String(",").join(animation_names);
property.hint = PROPERTY_HINT_ENUM; Array SpineSkeletonDataResource::get_animation_mixes() {
p_list->push_back(property); return animation_mixes;
} }
#define CHECK(x) \ #define CHECK(x) \

View File

@ -12,8 +12,34 @@
#include "SpinePathConstraintData.h" #include "SpinePathConstraintData.h"
#include "SpineEventData.h" #include "SpineEventData.h"
class SpineAnimationMix : public Resource {
GDCLASS(SpineAnimationMix, Resource)
protected:
static void _bind_methods();
String from;
String to;
float mix;
public:
SpineAnimationMix();
~SpineAnimationMix();
void set_from(const StringName &from);
String get_from();
void set_to(const StringName &to);
String get_to();
void set_mix(float mix);
float get_mix();
};
class SpineSkeletonDataResource : public Resource { class SpineSkeletonDataResource : public Resource {
GDCLASS(SpineSkeletonDataResource, Resource); GDCLASS(SpineSkeletonDataResource, Resource)
protected: protected:
static void _bind_methods(); static void _bind_methods();
@ -21,6 +47,8 @@ protected:
private: private:
Ref<SpineAtlasResource> atlas_res; Ref<SpineAtlasResource> atlas_res;
Ref<SpineSkeletonFileResource> skeleton_file_res; Ref<SpineSkeletonFileResource> skeleton_file_res;
float default_mix;
Array animation_mixes;
spine::SkeletonData *skeleton_data; spine::SkeletonData *skeleton_data;
spine::AnimationStateData *animation_state_data; spine::AnimationStateData *animation_state_data;
@ -49,7 +77,13 @@ public:
void get_skin_names(Vector<String> &l) const; void get_skin_names(Vector<String> &l) const;
void _get_property_list(List<PropertyInfo> *p_list) const; void set_default_mix(float default_mix);
float get_default_mix();
void set_animation_mixes(Array animation_mixes);
Array get_animation_mixes();
// Spine API // Spine API
Ref<SpineBoneData> find_bone(const String &bone_name) const; Ref<SpineBoneData> find_bone(const String &bone_name) const;

View File

@ -0,0 +1 @@
<svg height="16" viewBox="0 0 16 16" width="16" xmlns="http://www.w3.org/2000/svg"><g fill="#ff4000"><path d="m5.21 2.36c0 1.15.84 1.79 2.43 2 1.35.21 2.57.11 3-1.05.75-2.22-1.09-1.66-2.64-1.91s-2.85-.9-2.79.96z"/><path d="m5.69 7.1c.15.86.95 1.36 2.18 1.32s2.13-.51 2.28-1.42c.23-1.74-1.15-1.08-2.36-1s-2.39-.59-2.1 1.1z"/><path d="m7.29 11.05c.24.64.91.91 1.82.72s1.53-.49 1.48-1.23c-.09-1.35-1-.93-1.89-.73s-1.89-.03-1.41 1.24z"/><path d="m8.07 14.06c.07.54.54.86 1.27.86s1.3-.3 1.39-.88c.18-1.08-.64-.68-1.38-.67s-1.42-.37-1.28.69z"/></g></svg>

After

Width:  |  Height:  |  Size: 548 B

View File

@ -0,0 +1 @@
<svg height="16" viewBox="0 0 16 16" width="16" xmlns="http://www.w3.org/2000/svg"><g fill="#ff4000"><path d="m5.21 2.36c0 1.15.84 1.79 2.43 2 1.35.21 2.57.11 3-1.05.75-2.22-1.09-1.66-2.64-1.91s-2.85-.9-2.79.96z"/><path d="m5.69 7.1c.15.86.95 1.36 2.18 1.32s2.13-.51 2.28-1.42c.23-1.74-1.15-1.08-2.36-1s-2.39-.59-2.1 1.1z"/><path d="m7.29 11.05c.24.64.91.91 1.82.72s1.53-.49 1.48-1.23c-.09-1.35-1-.93-1.89-.73s-1.89-.03-1.41 1.24z"/><path d="m8.07 14.06c.07.54.54.86 1.27.86s1.3-.3 1.39-.88c.18-1.08-.64-.68-1.38-.67s-1.42-.37-1.28.69z"/></g></svg>

After

Width:  |  Height:  |  Size: 548 B

View File

@ -0,0 +1 @@
<svg height="16" viewBox="0 0 16 16" width="16" xmlns="http://www.w3.org/2000/svg"><g fill="#ff4000"><path d="m5.21 2.36c0 1.15.84 1.79 2.43 2 1.35.21 2.57.11 3-1.05.75-2.22-1.09-1.66-2.64-1.91s-2.85-.9-2.79.96z"/><path d="m5.69 7.1c.15.86.95 1.36 2.18 1.32s2.13-.51 2.28-1.42c.23-1.74-1.15-1.08-2.36-1s-2.39-.59-2.1 1.1z"/><path d="m7.29 11.05c.24.64.91.91 1.82.72s1.53-.49 1.48-1.23c-.09-1.35-1-.93-1.89-.73s-1.89-.03-1.41 1.24z"/><path d="m8.07 14.06c.07.54.54.86 1.27.86s1.3-.3 1.39-.88c.18-1.08-.64-.68-1.38-.67s-1.42-.37-1.28.69z"/></g></svg>

After

Width:  |  Height:  |  Size: 548 B

View File

@ -0,0 +1 @@
<svg height="16" viewBox="0 0 16 16" width="16" xmlns="http://www.w3.org/2000/svg"><g fill="#ff4000"><path d="m5.21 2.36c0 1.15.84 1.79 2.43 2 1.35.21 2.57.11 3-1.05.75-2.22-1.09-1.66-2.64-1.91s-2.85-.9-2.79.96z"/><path d="m5.69 7.1c.15.86.95 1.36 2.18 1.32s2.13-.51 2.28-1.42c.23-1.74-1.15-1.08-2.36-1s-2.39-.59-2.1 1.1z"/><path d="m7.29 11.05c.24.64.91.91 1.82.72s1.53-.49 1.48-1.23c-.09-1.35-1-.93-1.89-.73s-1.89-.03-1.41 1.24z"/><path d="m8.07 14.06c.07.54.54.86 1.27.86s1.3-.3 1.39-.88c.18-1.08-.64-.68-1.38-.67s-1.42-.37-1.28.69z"/></g></svg>

After

Width:  |  Height:  |  Size: 548 B

View File

@ -73,14 +73,11 @@ void register_spine_godot_types() {
#ifdef TOOLS_ENABLED #ifdef TOOLS_ENABLED
EditorNode::add_init_callback(editor_init_callback); EditorNode::add_init_callback(editor_init_callback);
#endif #endif
ClassDB::register_class<SpineAtlasResource>(); ClassDB::register_class<SpineAtlasResource>();
ClassDB::register_class<SpineSkeletonFileResource>(); ClassDB::register_class<SpineSkeletonFileResource>();
ClassDB::register_class<SpineSkeletonDataResource>(); ClassDB::register_class<SpineSkeletonDataResource>();
ClassDB::register_class<SpineSkeletonDataResource>(); ClassDB::register_class<SpineAnimationMix>();
ClassDB::register_class<SpineSprite>(); ClassDB::register_class<SpineSprite>();
ClassDB::register_class<SpineSprite>();
ClassDB::register_class<SpineSkeleton>();
ClassDB::register_class<SpineSkeleton>(); ClassDB::register_class<SpineSkeleton>();
ClassDB::register_class<SpineAnimationState>(); ClassDB::register_class<SpineAnimationState>();
ClassDB::register_class<SpineAnimation>(); ClassDB::register_class<SpineAnimation>();
@ -98,7 +95,6 @@ void register_spine_godot_types() {
ClassDB::register_class<SpineTransformConstraintData>(); ClassDB::register_class<SpineTransformConstraintData>();
ClassDB::register_class<SpinePathConstraintData>(); ClassDB::register_class<SpinePathConstraintData>();
ClassDB::register_class<SpineBone>(); ClassDB::register_class<SpineBone>();
ClassDB::register_class<SpineBone>();
ClassDB::register_class<SpineSlot>(); ClassDB::register_class<SpineSlot>();
ClassDB::register_class<SpineIkConstraint>(); ClassDB::register_class<SpineIkConstraint>();
ClassDB::register_class<SpinePathConstraint>(); ClassDB::register_class<SpinePathConstraint>();