From 7f4ee229f59d077030fef85dc7c2b5ae5152eb54 Mon Sep 17 00:00:00 2001 From: Mario Zechner Date: Mon, 4 Apr 2022 12:22:47 +0200 Subject: [PATCH] [godot] Fix git ignore. --- .../spine_godot/GodotSpineExtension.cpp | 73 ++ spine-godot/spine_godot/GodotSpineExtension.h | 54 + ...ourceFormatLoaderSpineSkeletonJsonData.cpp | 56 + ...esourceFormatLoaderSpineSkeletonJsonData.h | 45 + ...sourceFormatSaverSpineSkeletonJsonData.cpp | 48 + ...ResourceFormatSaverSpineSkeletonJsonData.h | 45 + spine-godot/spine_godot/SCsub | 9 + spine-godot/spine_godot/SpineAnimation.cpp | 96 ++ spine-godot/spine_godot/SpineAnimation.h | 74 ++ .../spine_godot/SpineAnimationState.cpp | 191 ++++ spine-godot/spine_godot/SpineAnimationState.h | 94 ++ .../SpineAnimationStateDataResource.cpp | 163 +++ .../SpineAnimationStateDataResource.h | 76 ++ .../spine_godot/SpineAtlasResource.cpp | 239 +++++ spine-godot/spine_godot/SpineAtlasResource.h | 100 ++ spine-godot/spine_godot/SpineAttachment.cpp | 55 + spine-godot/spine_godot/SpineAttachment.h | 64 ++ spine-godot/spine_godot/SpineBone.cpp | 536 ++++++++++ spine-godot/spine_godot/SpineBone.h | 175 ++++ spine-godot/spine_godot/SpineBoneData.cpp | 163 +++ spine-godot/spine_godot/SpineBoneData.h | 103 ++ .../spine_godot/SpineCollisionShapeProxy.cpp | 196 ++++ .../spine_godot/SpineCollisionShapeProxy.h | 80 ++ spine-godot/spine_godot/SpineConstant.cpp | 60 ++ spine-godot/spine_godot/SpineConstant.h | 81 ++ .../spine_godot/SpineConstraintData.cpp | 59 ++ spine-godot/spine_godot/SpineConstraintData.h | 66 ++ spine-godot/spine_godot/SpineEvent.cpp | 110 ++ spine-godot/spine_godot/SpineEvent.h | 91 ++ spine-godot/spine_godot/SpineEventData.cpp | 36 + spine-godot/spine_godot/SpineEventData.h | 58 ++ spine-godot/spine_godot/SpineIkConstraint.cpp | 146 +++ spine-godot/spine_godot/SpineIkConstraint.h | 94 ++ .../spine_godot/SpineIkConstraintData.cpp | 123 +++ .../spine_godot/SpineIkConstraintData.h | 78 ++ .../spine_godot/SpinePathConstraint.cpp | 145 +++ spine-godot/spine_godot/SpinePathConstraint.h | 94 ++ .../spine_godot/SpinePathConstraintData.cpp | 168 +++ .../spine_godot/SpinePathConstraintData.h | 108 ++ spine-godot/spine_godot/SpineRendererObject.h | 41 + .../spine_godot/SpineRuntimeEditorPlugin.cpp | 99 ++ .../spine_godot/SpineRuntimeEditorPlugin.h | 98 ++ spine-godot/spine_godot/SpineSkeleton.cpp | 413 ++++++++ spine-godot/spine_godot/SpineSkeleton.h | 129 +++ .../spine_godot/SpineSkeletonDataResource.cpp | 455 +++++++++ .../spine_godot/SpineSkeletonDataResource.h | 140 +++ .../SpineSkeletonJsonDataResource.cpp | 55 + .../SpineSkeletonJsonDataResource.h | 50 + spine-godot/spine_godot/SpineSkin.cpp | 161 +++ spine-godot/spine_godot/SpineSkin.h | 85 ++ .../SpineSkinAttachmentMapEntries.cpp | 93 ++ .../SpineSkinAttachmentMapEntries.h | 93 ++ spine-godot/spine_godot/SpineSlot.cpp | 141 +++ spine-godot/spine_godot/SpineSlot.h | 90 ++ spine-godot/spine_godot/SpineSlotData.cpp | 114 +++ spine-godot/spine_godot/SpineSlotData.h | 88 ++ spine-godot/spine_godot/SpineSprite.cpp | 966 ++++++++++++++++++ spine-godot/spine_godot/SpineSprite.h | 154 +++ .../spine_godot/SpineSpriteAnimateDialog.cpp | 351 +++++++ .../spine_godot/SpineSpriteAnimateDialog.h | 87 ++ .../spine_godot/SpineSpriteMeshInstance2D.cpp | 48 + .../spine_godot/SpineSpriteMeshInstance2D.h | 57 ++ spine-godot/spine_godot/SpineTimeline.cpp | 99 ++ spine-godot/spine_godot/SpineTimeline.h | 75 ++ spine-godot/spine_godot/SpineTrackEntry.cpp | 265 +++++ spine-godot/spine_godot/SpineTrackEntry.h | 131 +++ .../spine_godot/SpineTransformConstraint.cpp | 148 +++ .../spine_godot/SpineTransformConstraint.h | 93 ++ .../SpineTransformConstraintData.cpp | 118 +++ .../SpineTransformConstraintData.h | 74 ++ spine-godot/spine_godot/config.py | 5 + spine-godot/spine_godot/register_types.cpp | 144 +++ spine-godot/spine_godot/register_types.h | 31 + 73 files changed, 9443 insertions(+) create mode 100644 spine-godot/spine_godot/GodotSpineExtension.cpp create mode 100644 spine-godot/spine_godot/GodotSpineExtension.h create mode 100644 spine-godot/spine_godot/ResourceFormatLoaderSpineSkeletonJsonData.cpp create mode 100644 spine-godot/spine_godot/ResourceFormatLoaderSpineSkeletonJsonData.h create mode 100644 spine-godot/spine_godot/ResourceFormatSaverSpineSkeletonJsonData.cpp create mode 100644 spine-godot/spine_godot/ResourceFormatSaverSpineSkeletonJsonData.h create mode 100644 spine-godot/spine_godot/SCsub create mode 100644 spine-godot/spine_godot/SpineAnimation.cpp create mode 100644 spine-godot/spine_godot/SpineAnimation.h create mode 100644 spine-godot/spine_godot/SpineAnimationState.cpp create mode 100644 spine-godot/spine_godot/SpineAnimationState.h create mode 100644 spine-godot/spine_godot/SpineAnimationStateDataResource.cpp create mode 100644 spine-godot/spine_godot/SpineAnimationStateDataResource.h create mode 100644 spine-godot/spine_godot/SpineAtlasResource.cpp create mode 100644 spine-godot/spine_godot/SpineAtlasResource.h create mode 100644 spine-godot/spine_godot/SpineAttachment.cpp create mode 100644 spine-godot/spine_godot/SpineAttachment.h create mode 100644 spine-godot/spine_godot/SpineBone.cpp create mode 100644 spine-godot/spine_godot/SpineBone.h create mode 100644 spine-godot/spine_godot/SpineBoneData.cpp create mode 100644 spine-godot/spine_godot/SpineBoneData.h create mode 100644 spine-godot/spine_godot/SpineCollisionShapeProxy.cpp create mode 100644 spine-godot/spine_godot/SpineCollisionShapeProxy.h create mode 100644 spine-godot/spine_godot/SpineConstant.cpp create mode 100644 spine-godot/spine_godot/SpineConstant.h create mode 100644 spine-godot/spine_godot/SpineConstraintData.cpp create mode 100644 spine-godot/spine_godot/SpineConstraintData.h create mode 100644 spine-godot/spine_godot/SpineEvent.cpp create mode 100644 spine-godot/spine_godot/SpineEvent.h create mode 100644 spine-godot/spine_godot/SpineEventData.cpp create mode 100644 spine-godot/spine_godot/SpineEventData.h create mode 100644 spine-godot/spine_godot/SpineIkConstraint.cpp create mode 100644 spine-godot/spine_godot/SpineIkConstraint.h create mode 100644 spine-godot/spine_godot/SpineIkConstraintData.cpp create mode 100644 spine-godot/spine_godot/SpineIkConstraintData.h create mode 100644 spine-godot/spine_godot/SpinePathConstraint.cpp create mode 100644 spine-godot/spine_godot/SpinePathConstraint.h create mode 100644 spine-godot/spine_godot/SpinePathConstraintData.cpp create mode 100644 spine-godot/spine_godot/SpinePathConstraintData.h create mode 100644 spine-godot/spine_godot/SpineRendererObject.h create mode 100644 spine-godot/spine_godot/SpineRuntimeEditorPlugin.cpp create mode 100644 spine-godot/spine_godot/SpineRuntimeEditorPlugin.h create mode 100644 spine-godot/spine_godot/SpineSkeleton.cpp create mode 100644 spine-godot/spine_godot/SpineSkeleton.h create mode 100644 spine-godot/spine_godot/SpineSkeletonDataResource.cpp create mode 100644 spine-godot/spine_godot/SpineSkeletonDataResource.h create mode 100644 spine-godot/spine_godot/SpineSkeletonJsonDataResource.cpp create mode 100644 spine-godot/spine_godot/SpineSkeletonJsonDataResource.h create mode 100644 spine-godot/spine_godot/SpineSkin.cpp create mode 100644 spine-godot/spine_godot/SpineSkin.h create mode 100644 spine-godot/spine_godot/SpineSkinAttachmentMapEntries.cpp create mode 100644 spine-godot/spine_godot/SpineSkinAttachmentMapEntries.h create mode 100644 spine-godot/spine_godot/SpineSlot.cpp create mode 100644 spine-godot/spine_godot/SpineSlot.h create mode 100644 spine-godot/spine_godot/SpineSlotData.cpp create mode 100644 spine-godot/spine_godot/SpineSlotData.h create mode 100644 spine-godot/spine_godot/SpineSprite.cpp create mode 100644 spine-godot/spine_godot/SpineSprite.h create mode 100644 spine-godot/spine_godot/SpineSpriteAnimateDialog.cpp create mode 100644 spine-godot/spine_godot/SpineSpriteAnimateDialog.h create mode 100644 spine-godot/spine_godot/SpineSpriteMeshInstance2D.cpp create mode 100644 spine-godot/spine_godot/SpineSpriteMeshInstance2D.h create mode 100644 spine-godot/spine_godot/SpineTimeline.cpp create mode 100644 spine-godot/spine_godot/SpineTimeline.h create mode 100644 spine-godot/spine_godot/SpineTrackEntry.cpp create mode 100644 spine-godot/spine_godot/SpineTrackEntry.h create mode 100644 spine-godot/spine_godot/SpineTransformConstraint.cpp create mode 100644 spine-godot/spine_godot/SpineTransformConstraint.h create mode 100644 spine-godot/spine_godot/SpineTransformConstraintData.cpp create mode 100644 spine-godot/spine_godot/SpineTransformConstraintData.h create mode 100644 spine-godot/spine_godot/config.py create mode 100644 spine-godot/spine_godot/register_types.cpp create mode 100644 spine-godot/spine_godot/register_types.h diff --git a/spine-godot/spine_godot/GodotSpineExtension.cpp b/spine-godot/spine_godot/GodotSpineExtension.cpp new file mode 100644 index 000000000..cace4e354 --- /dev/null +++ b/spine-godot/spine_godot/GodotSpineExtension.cpp @@ -0,0 +1,73 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "GodotSpineExtension.h" + +#include "core/variant_parser.h" +#include + +#include + +spine::SpineExtension *spine::getDefaultExtension() { + return new GodotSpineExtension(); +} + +GodotSpineExtension::GodotSpineExtension() {} +GodotSpineExtension::~GodotSpineExtension() {} + +void *GodotSpineExtension::_alloc(size_t size, const char *file, int line) { + return memalloc(size); +} + +void *GodotSpineExtension::_calloc(size_t size, const char *file, int line) { + auto p = memalloc(size); + memset(p, 0, size); + return p; +} + +void *GodotSpineExtension::_realloc(void *ptr, size_t size, const char *file, int line) { + return memrealloc(ptr, size); +} + +void GodotSpineExtension::_free(void *mem, const char *file, int line) { + memfree(mem); +} + +char *GodotSpineExtension::_readFile(const spine::String &path, int *length) { + Error error; + auto res = FileAccess::get_file_as_array(String(path.buffer()), &error); + if (error != OK) { + if (length) *length = 0; + return NULL; + } + auto r = alloc(res.size(), __FILE__, __LINE__); + memcpy(r, res.ptr(), res.size()); + if (length) *length = res.size(); + return r; +} \ No newline at end of file diff --git a/spine-godot/spine_godot/GodotSpineExtension.h b/spine-godot/spine_godot/GodotSpineExtension.h new file mode 100644 index 000000000..e00726051 --- /dev/null +++ b/spine-godot/spine_godot/GodotSpineExtension.h @@ -0,0 +1,54 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEEXTENSION_H +#define GODOT_SPINEEXTENSION_H + + +#include +class GodotSpineExtension : public spine::SpineExtension { +public: + GodotSpineExtension(); + + virtual ~GodotSpineExtension(); + +protected: + virtual void *_alloc(size_t size, const char *file, int line); + + virtual void *_calloc(size_t size, const char *file, int line); + + virtual void *_realloc(void *ptr, size_t size, const char *file, int line); + + virtual void _free(void *mem, const char *file, int line); + + virtual char *_readFile(const spine::String &path, int *length); +}; + + +#endif//GODOT_SPINEEXTENSION_H diff --git a/spine-godot/spine_godot/ResourceFormatLoaderSpineSkeletonJsonData.cpp b/spine-godot/spine_godot/ResourceFormatLoaderSpineSkeletonJsonData.cpp new file mode 100644 index 000000000..9c1cc80e5 --- /dev/null +++ b/spine-godot/spine_godot/ResourceFormatLoaderSpineSkeletonJsonData.cpp @@ -0,0 +1,56 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "ResourceFormatLoaderSpineSkeletonJsonData.h" +#include "SpineSkeletonJsonDataResource.h" + +RES ResourceFormatLoaderSpineSkeletonJsonData::load(const String &p_path, const String &p_original_path, Error *r_error) { + Ref skeleton = memnew(SpineSkeletonJsonDataResource); + skeleton->load_from_file(p_path); + + if (r_error) { + *r_error = OK; + } + return skeleton; +} + +void ResourceFormatLoaderSpineSkeletonJsonData::get_recognized_extensions(List *r_extensions) const { + const char json_ext[] = "spjson"; + if (!r_extensions->find(json_ext)) { + r_extensions->push_back(json_ext); + } +} + +String ResourceFormatLoaderSpineSkeletonJsonData::get_resource_type(const String &p_path) const { + return "SpineSkeletonJsonDataResource"; +} + +bool ResourceFormatLoaderSpineSkeletonJsonData::handles_type(const String &p_type) const { + return p_type == "SpineSkeletonJsonDataResource" || ClassDB::is_parent_class(p_type, "SpineSkeletonJsonDataResource"); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/ResourceFormatLoaderSpineSkeletonJsonData.h b/spine-godot/spine_godot/ResourceFormatLoaderSpineSkeletonJsonData.h new file mode 100644 index 000000000..9736655f6 --- /dev/null +++ b/spine-godot/spine_godot/ResourceFormatLoaderSpineSkeletonJsonData.h @@ -0,0 +1,45 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_RESOURCEFORMATLOADERSPINESKELETONJSONDATA_H +#define GODOT_RESOURCEFORMATLOADERSPINESKELETONJSONDATA_H + +#include "core/io/resource_loader.h" + +class ResourceFormatLoaderSpineSkeletonJsonData : public ResourceFormatLoader { + GDCLASS(ResourceFormatLoaderSpineSkeletonJsonData, ResourceFormatLoader); + +public: + virtual RES load(const String &p_path, const String &p_original_path, Error *r_error = NULL); + virtual void get_recognized_extensions(List *r_extensions) const; + virtual bool handles_type(const String &p_type) const; + virtual String get_resource_type(const String &p_path) const; +}; + +#endif//GODOT_RESOURCEFORMATLOADERSPINESKELETONJSONDATA_H diff --git a/spine-godot/spine_godot/ResourceFormatSaverSpineSkeletonJsonData.cpp b/spine-godot/spine_godot/ResourceFormatSaverSpineSkeletonJsonData.cpp new file mode 100644 index 000000000..5fa669c04 --- /dev/null +++ b/spine-godot/spine_godot/ResourceFormatSaverSpineSkeletonJsonData.cpp @@ -0,0 +1,48 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "ResourceFormatSaverSpineSkeletonJsonData.h" + +#include "SpineSkeletonJsonDataResource.h" + +Error ResourceFormatSaverSpineSkeletonJsonData::save(const String &p_path, const RES &p_resource, uint32_t p_flags) { + Ref res = p_resource.get_ref_ptr(); + Error error = res->save_to_file(p_path); + return error; +} + +void ResourceFormatSaverSpineSkeletonJsonData::get_recognized_extensions(const RES &p_resource, List *p_extensions) const { + if (Object::cast_to(*p_resource)) { + p_extensions->push_back("spjson"); + } +} + +bool ResourceFormatSaverSpineSkeletonJsonData::recognize(const RES &p_resource) const { + return Object::cast_to(*p_resource) != nullptr; +} diff --git a/spine-godot/spine_godot/ResourceFormatSaverSpineSkeletonJsonData.h b/spine-godot/spine_godot/ResourceFormatSaverSpineSkeletonJsonData.h new file mode 100644 index 000000000..2c42ee5d0 --- /dev/null +++ b/spine-godot/spine_godot/ResourceFormatSaverSpineSkeletonJsonData.h @@ -0,0 +1,45 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_RESOURCEFORMATSAVERSPINESKELETONJSONDATA_H +#define GODOT_RESOURCEFORMATSAVERSPINESKELETONJSONDATA_H + +#include "core/io/resource_saver.h" + +class ResourceFormatSaverSpineSkeletonJsonData : public ResourceFormatSaver { + GDCLASS(ResourceFormatSaverSpineSkeletonJsonData, ResourceFormatSaver); + +public: + Error save(const String &p_path, const RES &p_resource, uint32_t p_flags = 0) override; + void get_recognized_extensions(const RES &p_resource, List *p_extensions) const override; + bool recognize(const RES &p_resource) const override; +}; + + +#endif//GODOT_RESOURCEFORMATSAVERSPINESKELETONJSONDATA_H diff --git a/spine-godot/spine_godot/SCsub b/spine-godot/spine_godot/SCsub new file mode 100644 index 000000000..f7d88af0b --- /dev/null +++ b/spine-godot/spine_godot/SCsub @@ -0,0 +1,9 @@ +Import('env') + +env_spine_runtime = env.Clone() + +env_spine_runtime.Prepend(CPPPATH=["spine-cpp/include"]) +env_spine_runtime.Append(CCFLAGS=['-O2']) + +env_spine_runtime.add_source_files(env.modules_sources, "spine-cpp/src/spine/*.cpp") +env_spine_runtime.add_source_files(env.modules_sources, "*.cpp") diff --git a/spine-godot/spine_godot/SpineAnimation.cpp b/spine-godot/spine_godot/SpineAnimation.cpp new file mode 100644 index 000000000..7f0772f24 --- /dev/null +++ b/spine-godot/spine_godot/SpineAnimation.cpp @@ -0,0 +1,96 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineAnimation.h" + +#include "SpineSkeleton.h" +#include "SpineEvent.h" +#include "SpineTimeline.h" + +// enable more than 5 arguments of a method bind function +#include "core/method_bind_ext.gen.inc" + +void SpineAnimation::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_anim_name"), &SpineAnimation::get_anim_name); + ClassDB::bind_method(D_METHOD("get_duration"), &SpineAnimation::get_duration); + ClassDB::bind_method(D_METHOD("set_duration", "v"), &SpineAnimation::set_duration); + + ClassDB::bind_method(D_METHOD("apply", "skeleton", "last_time", "time", "loop", "events", "alpha", "blend", "direction"), &SpineAnimation::apply); + ClassDB::bind_method(D_METHOD("get_timelines"), &SpineAnimation::get_timelines); + ClassDB::bind_method(D_METHOD("has_timeline", "ids"), &SpineAnimation::has_timeline); +} + +SpineAnimation::SpineAnimation() : animation(NULL) {} +SpineAnimation::~SpineAnimation() {} + +String SpineAnimation::get_anim_name() { + return animation->getName().buffer(); +} + +float SpineAnimation::get_duration() { + return animation->getDuration(); +} +void SpineAnimation::set_duration(float v) { + animation->setDuration(v); +} + +void SpineAnimation::apply(Ref skeleton, float lastTime, float time, bool loop, + Array pEvents, float alpha, SpineConstant::MixBlend blend, + SpineConstant::MixDirection direction) { + spine::Vector events; + events.setSize(pEvents.size(), nullptr); + for (size_t i = 0; i < events.size(); ++i) { + events[i] = ((Ref) (pEvents[i]))->get_spine_object(); + } + animation->apply(*(skeleton->get_spine_object()), lastTime, time, loop, &events, alpha, (spine::MixBlend) blend, (spine::MixDirection) direction); +} + +Array SpineAnimation::get_timelines() { + auto &timelines = animation->getTimelines(); + Array res; + res.resize(timelines.size()); + + for (size_t i = 0; i < res.size(); ++i) { + auto a = Ref(memnew(SpineTimeline)); + a->set_spine_object(timelines[i]); + res.set(i, a); + } + + return res; +} + +bool SpineAnimation::has_timeline(Array ids) { + spine::Vector list; + list.setSize(ids.size(), 0); + + for (size_t i = 0; i < list.size(); ++i) { + list[i] = (int64_t) ids[i]; + } + return animation->hasTimeline(list); +} diff --git a/spine-godot/spine_godot/SpineAnimation.h b/spine-godot/spine_godot/SpineAnimation.h new file mode 100644 index 000000000..98dbed587 --- /dev/null +++ b/spine-godot/spine_godot/SpineAnimation.h @@ -0,0 +1,74 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEANIMATION_H +#define GODOT_SPINEANIMATION_H + +#include "core/variant_parser.h" + +#include "SpineConstant.h" + +#include + +class SpineEvent; +class SpineSkeleton; +class SpineTimeline; + +class SpineAnimation : public Reference { + GDCLASS(SpineAnimation, Reference); + +private: + spine::Animation *animation; + +protected: + static void _bind_methods(); + +public: + SpineAnimation(); + ~SpineAnimation(); + + inline void set_spine_object(spine::Animation *a) { + animation = a; + } + inline spine::Animation *get_spine_object() { + return animation; + } + + // Vector> pEvents + void apply(Ref skeleton, float lastTime, float time, bool loop, Array pEvents, float alpha, SpineConstant::MixBlend blend, SpineConstant::MixDirection direction); + + Array get_timelines(); // Vector> + bool has_timeline(Array ids);// Vector + + String get_anim_name(); + float get_duration(); + void set_duration(float v); +}; + +#endif//GODOT_SPINEANIMATION_H diff --git a/spine-godot/spine_godot/SpineAnimationState.cpp b/spine-godot/spine_godot/SpineAnimationState.cpp new file mode 100644 index 000000000..155a1d6d3 --- /dev/null +++ b/spine-godot/spine_godot/SpineAnimationState.cpp @@ -0,0 +1,191 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineAnimationState.h" + +void SpineAnimationState::_bind_methods() { + ClassDB::bind_method(D_METHOD("set_animation", "anim_name", "loop", "track_id"), &SpineAnimationState::set_animation, DEFVAL(true), DEFVAL(0)); + ClassDB::bind_method(D_METHOD("update", "delta"), &SpineAnimationState::update, DEFVAL(0)); + ClassDB::bind_method(D_METHOD("apply", "skeleton"), &SpineAnimationState::apply); + ClassDB::bind_method(D_METHOD("clear_tracks"), &SpineAnimationState::clear_tracks); + ClassDB::bind_method(D_METHOD("clear_track"), &SpineAnimationState::clear_track); + ClassDB::bind_method(D_METHOD("add_animation", "anim_name", "delay", "loop", "track_id"), &SpineAnimationState::add_animation, DEFVAL(0), DEFVAL(true), DEFVAL(0)); + ClassDB::bind_method(D_METHOD("set_empty_animation", "track_id", "mix_duration"), &SpineAnimationState::set_empty_animation); + ClassDB::bind_method(D_METHOD("add_empty_animation", "track_id", "mix_duration", "delay"), &SpineAnimationState::add_empty_animation); + ClassDB::bind_method(D_METHOD("set_empty_animations", "mix_duration"), &SpineAnimationState::set_empty_animations); + ClassDB::bind_method(D_METHOD("get_data"), &SpineAnimationState::get_data); + ClassDB::bind_method(D_METHOD("get_time_scale"), &SpineAnimationState::get_time_scale); + ClassDB::bind_method(D_METHOD("set_time_scale", "time_scale"), &SpineAnimationState::set_time_scale); + ClassDB::bind_method(D_METHOD("disable_queue"), &SpineAnimationState::disable_queue); + ClassDB::bind_method(D_METHOD("enable_queue"), &SpineAnimationState::enable_queue); + // ClassDB::bind_method(D_METHOD("reload"), &SpineAnimationState::reload_animation_state); + ClassDB::bind_method(D_METHOD("get_current", "track_id"), &SpineAnimationState::get_current); +} + +SpineAnimationState::SpineAnimationState() : animation_state(NULL) { +} + +SpineAnimationState::~SpineAnimationState() { + if (animation_state) { + delete animation_state; + animation_state = NULL; + } +} + +void SpineAnimationState::load_animation_state(Ref ad) { + if (animation_state) { + delete animation_state; + animation_state = NULL; + } + animation_state = new spine::AnimationState(ad->get_animation_state_data()); + anim_state_data_res = ad; +} + +void SpineAnimationState::reload_animation_state() { + if (!anim_state_data_res.is_valid()) { + ERR_PRINT(" Reload animation state fail, because anim_state_data_res not set!"); + return; + } + if (animation_state) { + delete animation_state; + animation_state = NULL; + } + animation_state = new spine::AnimationState(anim_state_data_res->get_animation_state_data()); +} + +#define CHECK_V \ + if (!animation_state) { \ + ERR_PRINT("The animation state is not loaded yet!"); \ + return; \ + } +#define CHECK_X(x) \ + if (!animation_state) { \ + ERR_PRINT("The animation state is not loaded yet!"); \ + return x; \ + } +#define S_T(x) (spine::String(x.utf8())) +Ref SpineAnimationState::set_animation(const String &anim_name, bool loop, uint64_t track) { + CHECK_X(NULL); + auto skeleton_data = anim_state_data_res->get_skeleton(); + auto anim = skeleton_data->find_animation(anim_name); + if (!anim.is_valid() || anim->get_spine_object() == NULL) { + ERR_PRINT(String("Can not find animation: ") + anim_name); + return NULL; + } + auto entry = animation_state->setAnimation(track, anim->get_spine_object(), loop); + Ref gd_entry(memnew(SpineTrackEntry)); + gd_entry->set_spine_object(entry); + return gd_entry; +} +Ref SpineAnimationState::add_animation(const String &anim_name, float delay, bool loop, uint64_t track) { + CHECK_X(NULL); + auto skeleton_data = anim_state_data_res->get_skeleton(); + auto anim = skeleton_data->find_animation(anim_name); + if (!anim.is_valid() || anim->get_spine_object() == NULL) { + ERR_PRINT(String("Can not find animation: ") + anim_name); + return NULL; + } + auto entry = animation_state->addAnimation(track, anim->get_spine_object(), loop, delay); + Ref gd_entry(memnew(SpineTrackEntry)); + gd_entry->set_spine_object(entry); + return gd_entry; +} + +Ref SpineAnimationState::set_empty_animation(uint64_t track_id, float mix_duration) { + CHECK_X(NULL); + auto entry = animation_state->setEmptyAnimation(track_id, mix_duration); + Ref gd_entry(memnew(SpineTrackEntry)); + gd_entry->set_spine_object(entry); + return gd_entry; +} +Ref SpineAnimationState::add_empty_animation(uint64_t track_id, float mix_duration, float delay) { + CHECK_X(NULL); + auto entry = animation_state->addEmptyAnimation(track_id, mix_duration, delay); + Ref gd_entry(memnew(SpineTrackEntry)); + gd_entry->set_spine_object(entry); + return gd_entry; +} +void SpineAnimationState::set_empty_animations(float mix_duration) { + CHECK_V; + animation_state->setEmptyAnimations(mix_duration); +} + +void SpineAnimationState::update(float delta) { + CHECK_V; + animation_state->update(delta); +} +bool SpineAnimationState::apply(Ref skeleton) { + CHECK_X(false); + return animation_state->apply(*(skeleton->get_spine_object())); +} + + +void SpineAnimationState::clear_tracks() { + CHECK_V; + animation_state->clearTracks(); +} +void SpineAnimationState::clear_track(uint64_t track_id) { + CHECK_V; + animation_state->clearTrack(track_id); +} + +Ref SpineAnimationState::get_data() { + CHECK_X(NULL); + return anim_state_data_res; +} + +float SpineAnimationState::get_time_scale() { + CHECK_X(0); + return animation_state->getTimeScale(); +} +void SpineAnimationState::set_time_scale(float v) { + CHECK_V; + animation_state->setTimeScale(v); +} + +void SpineAnimationState::disable_queue() { + CHECK_V; + animation_state->disableQueue(); +} +void SpineAnimationState::enable_queue() { + CHECK_V; + animation_state->enableQueue(); +} + +Ref SpineAnimationState::get_current(uint64_t track_index) { + CHECK_X(NULL); + Ref gd_entry(memnew(SpineTrackEntry)); + auto entry = animation_state->getCurrent(track_index); + if (entry == NULL) return NULL; + gd_entry->set_spine_object(entry); + return gd_entry; +} + +#undef CHECK_V +#undef CHECK_X diff --git a/spine-godot/spine_godot/SpineAnimationState.h b/spine-godot/spine_godot/SpineAnimationState.h new file mode 100644 index 000000000..097be72ac --- /dev/null +++ b/spine-godot/spine_godot/SpineAnimationState.h @@ -0,0 +1,94 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEANIMATIONSTATE_H +#define GODOT_SPINEANIMATIONSTATE_H + +#include "core/variant_parser.h" + +#include "SpineAnimationStateDataResource.h" +#include "SpineSkeleton.h" +#include "SpineTrackEntry.h" + +class SpineAnimationState : public Reference { + GDCLASS(SpineAnimationState, Reference); + +protected: + static void _bind_methods(); + +private: + spine::AnimationState *animation_state; + + Ref anim_state_data_res; + +public: + void load_animation_state(Ref ad); + + inline void set_animation_state(spine::AnimationState *a) { + animation_state = a; + } + inline spine::AnimationState *get_animation_state() { + return animation_state; + } + + void reload_animation_state(); + + Ref set_animation(const String &anim_name, bool loop, uint64_t track_id); + inline void set_animation_by_ref(Ref anim, bool loop, uint64_t track_id) { + if (anim.is_valid()) { + animation_state->setAnimation(track_id, anim->get_spine_object(), loop); + } + } + Ref add_animation(const String &anim_name, float delay, bool loop, uint64_t track_id); + + Ref set_empty_animation(uint64_t track_id, float mix_duration); + Ref add_empty_animation(uint64_t track_id, float mix_duration, float delay); + void set_empty_animations(float mix_duration); + + Ref get_data(); + + float get_time_scale(); + void set_time_scale(float v); + + void disable_queue(); + void enable_queue(); + + void update(float delta); + bool apply(Ref skeleton); + + void clear_tracks(); + void clear_track(uint64_t track_id); + + Ref get_current(uint64_t track_index); + + SpineAnimationState(); + ~SpineAnimationState(); +}; + +#endif//GODOT_SPINEANIMATIONSTATE_H diff --git a/spine-godot/spine_godot/SpineAnimationStateDataResource.cpp b/spine-godot/spine_godot/SpineAnimationStateDataResource.cpp new file mode 100644 index 000000000..de4041ec2 --- /dev/null +++ b/spine-godot/spine_godot/SpineAnimationStateDataResource.cpp @@ -0,0 +1,163 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineAnimationStateDataResource.h" + +SpineAnimationStateDataResource::SpineAnimationStateDataResource() : animation_state_data(NULL), animation_state_data_created(false), default_mix(0.5f) { +} +SpineAnimationStateDataResource::~SpineAnimationStateDataResource() { + if (animation_state_data) { + delete animation_state_data; + animation_state_data = NULL; + } +} + +void SpineAnimationStateDataResource::_bind_methods() { + ClassDB::bind_method(D_METHOD("set_skeleton", "skeleton"), &SpineAnimationStateDataResource::set_skeleton); + ClassDB::bind_method(D_METHOD("get_spine_object"), &SpineAnimationStateDataResource::get_skeleton); + ClassDB::bind_method(D_METHOD("_on_skeleton_data_loaded"), &SpineAnimationStateDataResource::_on_skeleton_data_loaded); + ClassDB::bind_method(D_METHOD("is_animation_state_data_created"), &SpineAnimationStateDataResource::is_animation_state_data_created); + ClassDB::bind_method(D_METHOD("_on_skeleton_data_changed"), &SpineAnimationStateDataResource::_on_skeleton_data_changed); + ClassDB::bind_method(D_METHOD("set_default_mix", "mix"), &SpineAnimationStateDataResource::set_default_mix); + ClassDB::bind_method(D_METHOD("get_default_mix"), &SpineAnimationStateDataResource::get_default_mix); + ClassDB::bind_method(D_METHOD("get_mix", "from", "to"), &SpineAnimationStateDataResource::get_mix); + ClassDB::bind_method(D_METHOD("set_mix", "from", "to", "mix"), &SpineAnimationStateDataResource::set_mix); + + ADD_SIGNAL(MethodInfo("animation_state_data_created")); + ADD_SIGNAL(MethodInfo("skeleton_data_res_changed")); + ADD_SIGNAL(MethodInfo("animation_state_data_changed")); + + ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "skeleton", PropertyHint::PROPERTY_HINT_RESOURCE_TYPE, "SpineSkeletonDataResource"), "set_skeleton", "get_spine_object"); + ADD_PROPERTY(PropertyInfo(Variant::REAL, "default_mix", PropertyHint::PROPERTY_HINT_EXP_RANGE, "0,1,0.01"), "set_default_mix", "get_default_mix"); +} + +void SpineAnimationStateDataResource::set_skeleton(const Ref &s) { + skeleton = s; + + _on_skeleton_data_changed(); + if (skeleton.is_valid()) { + skeleton->connect("skeleton_data_loaded", this, "_on_skeleton_data_loaded"); + skeleton->connect("atlas_res_changed", this, "_on_skeleton_data_changed"); + skeleton->connect("skeleton_json_res_changed", this, "_on_skeleton_data_changed"); + + if (skeleton->is_skeleton_data_loaded()) { + _on_skeleton_data_loaded(); + } + } else { + if (animation_state_data) { + delete animation_state_data; + animation_state_data = NULL; + animation_state_data_created = false; + // print_line("Animation state data deleted."); + } + } +} +Ref SpineAnimationStateDataResource::get_skeleton() { + return skeleton; +} + +void SpineAnimationStateDataResource::set_default_mix(float m) { + default_mix = m; + if (!is_animation_state_data_created()) { + // ERR_PRINT("'set_default_mix' fail. Animation state data is not created!"); + return; + } + animation_state_data->setDefaultMix(((m >= 0 && m <= 1) ? m : m <= 0 ? 0 + : 1)); + // emit_signal("animation_state_data_changed"); +} +float SpineAnimationStateDataResource::get_default_mix() { + if (!is_animation_state_data_created()) { + // ERR_PRINT("'get_default_mix' fail. Animation state data is not created!"); + return default_mix; + } + default_mix = animation_state_data->getDefaultMix(); + return default_mix; +} + +void SpineAnimationStateDataResource::set_mix(const String &from, const String &to, float mix_duration) { + if (!is_animation_state_data_created()) { + ERR_PRINT("'set_mix' fail. Animation state data is not created!"); + return; + } + auto anim_from = get_skeleton()->find_animation(from); + auto anim_to = get_skeleton()->find_animation(to); + if (!anim_from.is_valid()) { + ERR_PRINT("'set_mix' fail. From animation animation not found!"); + return; + } + if (!anim_to.is_valid()) { + ERR_PRINT("'set_mix' fail. To animation animation not found!"); + return; + } + animation_state_data->setMix(anim_from->get_spine_object(), anim_to->get_spine_object(), mix_duration); +} +float SpineAnimationStateDataResource::get_mix(const String &from, const String &to) { + if (!is_animation_state_data_created()) { + ERR_PRINT("'set_mix' fail. Animation state data is not created!"); + return 0; + } + auto anim_from = get_skeleton()->find_animation(from); + auto anim_to = get_skeleton()->find_animation(to); + if (!anim_from.is_valid()) { + ERR_PRINT("'set_mix' fail. From animation animation not found!"); + return 0; + } + if (!anim_to.is_valid()) { + ERR_PRINT("'set_mix' fail. To animation animation not found!"); + return 0; + } + return animation_state_data->getMix(anim_from->get_spine_object(), anim_to->get_spine_object()); +} + +void SpineAnimationStateDataResource::_on_skeleton_data_loaded() { + animation_state_data = new spine::AnimationStateData(skeleton->get_skeleton_data()); + // print_line("Animation state data created."); + + + emit_signal("animation_state_data_created"); + animation_state_data->setDefaultMix(default_mix); + animation_state_data_created = true; +} + +void SpineAnimationStateDataResource::_on_skeleton_data_changed() { + animation_state_data_created = false; + if (animation_state_data) { + delete animation_state_data; + animation_state_data = NULL; + // print_line("Animation state data deleted."); + } + + // print_line("skeleton_data_res_changed emitted"); + emit_signal("skeleton_data_res_changed"); +} + +bool SpineAnimationStateDataResource::is_animation_state_data_created() { + return animation_state_data_created; +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineAnimationStateDataResource.h b/spine-godot/spine_godot/SpineAnimationStateDataResource.h new file mode 100644 index 000000000..58f0cd536 --- /dev/null +++ b/spine-godot/spine_godot/SpineAnimationStateDataResource.h @@ -0,0 +1,76 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEANIMATIONSTATEDATARESOURCE_H +#define GODOT_SPINEANIMATIONSTATEDATARESOURCE_H + +#include "core/variant_parser.h" + +#include "SpineSkeletonDataResource.h" + +class SpineAnimationStateDataResource : public Resource { + GDCLASS(SpineAnimationStateDataResource, Resource); + +protected: + static void _bind_methods(); + +private: + Ref skeleton; + + spine::AnimationStateData *animation_state_data; + + bool animation_state_data_created; + + float default_mix; + +public: + void set_skeleton(const Ref &s); + Ref get_skeleton(); + + inline spine::AnimationStateData *get_animation_state_data() { + return animation_state_data; + } + + void set_default_mix(float m); + float get_default_mix(); + + void set_mix(const String &from, const String &to, float mix_duration); + float get_mix(const String &from, const String &to); + + + void _on_skeleton_data_loaded(); + void _on_skeleton_data_changed(); + + bool is_animation_state_data_created(); + + SpineAnimationStateDataResource(); + ~SpineAnimationStateDataResource(); +}; + +#endif//GODOT_SPINEANIMATIONSTATEDATARESOURCE_H diff --git a/spine-godot/spine_godot/SpineAtlasResource.cpp b/spine-godot/spine_godot/SpineAtlasResource.cpp new file mode 100644 index 000000000..088426621 --- /dev/null +++ b/spine-godot/spine_godot/SpineAtlasResource.cpp @@ -0,0 +1,239 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineAtlasResource.h" +#include "core/io/json.h" + +#include + +class GodotSpineTextureLoader : public spine::TextureLoader { +private: + Array *textures, *normal_maps; + String normal_map_prefix; + +public: + GodotSpineTextureLoader(Array *t, Array *nt, const String &p) : textures(t), normal_maps(nt), normal_map_prefix(p) { + if (textures) textures->clear(); + if (normal_maps) normal_maps->clear(); + } + + String fix_path(const String &path) { + if (path.size() > 5 && path[4] == '/' && path[5] == '/') return path; + const String prefix = "res:/"; + auto i = path.find(prefix); + auto sub_str_pos = i + prefix.size() - 1; + if (sub_str_pos < 0) return path; + auto res = path.substr(sub_str_pos); + + if (res.size() > 0) { + if (res[0] != '/') { + return prefix + "/" + res; + } else { + return prefix + res; + } + } + return path; + } + + virtual void load(spine::AtlasPage &page, const spine::String &path) { + Error err = OK; + auto fixed_path = fix_path(String(path.buffer())); + + Ref texture = ResourceLoader::load(fixed_path, "", false, &err); + if (err != OK) { + print_error(vformat("Can't load texture: \"%s\"", String(path.buffer()))); + page.setRendererObject((void *) memnew(SpineRendererObject{nullptr})); + return; + } + + if (textures) textures->append(texture); + auto spine_renderer_object = memnew(SpineRendererObject); + spine_renderer_object->texture = texture; + + String temp_path = fixed_path; + String new_path = vformat("%s/%s_%s", temp_path.get_base_dir(), normal_map_prefix, temp_path.get_file()); + if (ResourceLoader::exists(new_path)) { + Ref normal_map = ResourceLoader::load(new_path); + if (normal_maps) normal_maps->append(normal_map); + spine_renderer_object->normal_map = normal_map; + } + + page.setRendererObject((void *) spine_renderer_object); + + page.width = texture->get_width(); + page.height = texture->get_height(); + } + + virtual void unload(void *p) { + auto spine_renderer_object = (SpineRendererObject *) p; + Ref &texture = spine_renderer_object->texture; + if (texture.is_valid()) texture.unref(); + Ref &normal_map = spine_renderer_object->normal_map; + if (normal_map.is_valid()) normal_map.unref(); + memdelete(spine_renderer_object); + } +}; + +SpineAtlasResource::SpineAtlasResource() : atlas(nullptr), normal_texture_prefix("n") {} + +SpineAtlasResource::~SpineAtlasResource() { + if (atlas) delete atlas; +} + +void SpineAtlasResource::_bind_methods() { + ClassDB::bind_method(D_METHOD("load_from_atlas_file", "path"), &SpineAtlasResource::load_from_atlas_file); + + ClassDB::bind_method(D_METHOD("get_source_path"), &SpineAtlasResource::get_source_path); + + ClassDB::bind_method(D_METHOD("get_textures"), &SpineAtlasResource::get_textures); + ClassDB::bind_method(D_METHOD("get_normal_maps"), &SpineAtlasResource::get_normal_maps); + + ADD_PROPERTY(PropertyInfo(Variant::STRING, "source_path"), "", "get_source_path"); + ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "textures"), "", "get_textures"); + ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "normal_maps"), "", "get_normal_maps"); +} + + +Array SpineAtlasResource::get_textures() { + return textures; +} + +Array SpineAtlasResource::get_normal_maps() { + return normal_maps; +} + +String SpineAtlasResource::get_source_path() { + return source_path; +} + +Error SpineAtlasResource::load_from_atlas_file(const String &p_path) { + source_path = p_path; + Error err; + + atlas_data = FileAccess::get_file_as_string(p_path, &err); + if (err != OK) return err; + + if (atlas) delete atlas; + textures.clear(); + normal_maps.clear(); + atlas = new spine::Atlas(atlas_data.utf8(), atlas_data.size(), source_path.get_base_dir().utf8(), new GodotSpineTextureLoader(&textures, &normal_maps, normal_texture_prefix)); + if (atlas) return OK; + + textures.clear(); + normal_maps.clear(); + return ERR_FILE_UNRECOGNIZED; +} + +Error SpineAtlasResource::load_from_file(const String &p_path) { + Error err; + String json_string = FileAccess::get_file_as_string(p_path, &err); + if (err != OK) return err; + + String error_string; + int error_line; + JSON json; + Variant result; + err = json.parse(json_string, result, error_string, error_line); + if (err != OK) return err; + + Dictionary content = Dictionary(result); + source_path = content["source_path"]; + atlas_data = content["atlas_data"]; + normal_texture_prefix = content["normal_texture_prefix"]; + + if (atlas) delete atlas; + textures.clear(); + normal_maps.clear(); + atlas = new spine::Atlas(atlas_data.utf8(), atlas_data.size(), source_path.get_base_dir().utf8(), new GodotSpineTextureLoader(&textures, &normal_maps, normal_texture_prefix)); + if (atlas) return OK; + + textures.clear(); + normal_maps.clear(); + return ERR_FILE_UNRECOGNIZED; +} + +Error SpineAtlasResource::save_to_file(const String &p_path) { + Error err; + FileAccess *file = FileAccess::open(p_path, FileAccess::WRITE, &err); + if (err != OK) { + if (file) file->close(); + return err; + } + + Dictionary content; + content["source_path"] = source_path; + content["atlas_data"] = atlas_data; + content["normal_texture_prefix"] = normal_texture_prefix; + + file->store_string(JSON::print(content)); + file->close(); + + return OK; +} + +RES SpineAtlasResourceFormatLoader::load(const String &p_path, const String &p_original_path, Error *r_error) { + Ref atlas = memnew(SpineAtlasResource); + atlas->load_from_file(p_path); + + if (r_error) { + *r_error = OK; + } + return atlas; +} + +void SpineAtlasResourceFormatLoader::get_recognized_extensions(List *r_extensions) const { + const char atlas_ext[] = "spatlas"; + if (!r_extensions->find(atlas_ext)) { + r_extensions->push_back(atlas_ext); + } +} + +String SpineAtlasResourceFormatLoader::get_resource_type(const String &p_path) const { + return "SpineAtlasResource"; +} + +bool SpineAtlasResourceFormatLoader::handles_type(const String &p_type) const { + return p_type == "SpineAtlasResource" || ClassDB::is_parent_class(p_type, "SpineAtlasResource"); +} + +Error SpineAtlasResourceFormatSaver::save(const String &p_path, const RES &p_resource, uint32_t p_flags) { + Ref res = p_resource.get_ref_ptr(); + Error error = res->save_to_file(p_path); + return error; +} + +void SpineAtlasResourceFormatSaver::get_recognized_extensions(const RES &p_resource, List *p_extensions) const { + if (Object::cast_to(*p_resource)) { + p_extensions->push_back("spatlas"); + } +} + +bool SpineAtlasResourceFormatSaver::recognize(const RES &p_resource) const { + return Object::cast_to(*p_resource) != nullptr; +} diff --git a/spine-godot/spine_godot/SpineAtlasResource.h b/spine-godot/spine_godot/SpineAtlasResource.h new file mode 100644 index 000000000..84c7cc9ca --- /dev/null +++ b/spine-godot/spine_godot/SpineAtlasResource.h @@ -0,0 +1,100 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEATLASRESOURCE_H +#define GODOT_SPINEATLASRESOURCE_H + + +#include "core/variant_parser.h" +#include "core/io/resource_loader.h" +#include "core/io/resource_saver.h" +#include "core/io/image_loader.h" +#include "scene/resources/texture.h" + +#include +#include +#include +#include "SpineRendererObject.h" + +class SpineAtlasResource : public Resource { + GDCLASS(SpineAtlasResource, Resource); + +protected: + static void _bind_methods(); + + spine::Atlas *atlas; + + String source_path; + String atlas_data; + String normal_texture_prefix; + + Array textures; + Array normal_maps; + +public: + inline String &get_atlas_data() { return atlas_data; } + + inline spine::Atlas *get_spine_atlas() { return atlas; } + + inline void set_normal_texture_prefix(const String &p) { normal_texture_prefix = p; } + + Error load_from_atlas_file(const String &p_path);// .atlas + + Error load_from_file(const String &p_path);// .spatlas + Error save_to_file(const String &p_path); // .spatlas + + String get_source_path(); + Array get_textures(); + Array get_normal_maps(); + + SpineAtlasResource(); + virtual ~SpineAtlasResource(); +}; + +class SpineAtlasResourceFormatLoader : public ResourceFormatLoader { +GDCLASS(SpineAtlasResourceFormatLoader, ResourceFormatLoader); + +public: + virtual RES load(const String &p_path, const String &p_original_path, Error *r_error = NULL); + virtual void get_recognized_extensions(List *r_extensions) const; + virtual bool handles_type(const String &p_type) const; + virtual String get_resource_type(const String &p_path) const; +}; + +class SpineAtlasResourceFormatSaver : public ResourceFormatSaver { +GDCLASS(SpineAtlasResourceFormatSaver, ResourceFormatSaver); + +public: + Error save(const String &p_path, const RES &p_resource, uint32_t p_flags = 0) override; + void get_recognized_extensions(const RES &p_resource, List *p_extensions) const override; + bool recognize(const RES &p_resource) const override; +}; + + +#endif//GODOT_SPINEATLASRESOURCE_H diff --git a/spine-godot/spine_godot/SpineAttachment.cpp b/spine-godot/spine_godot/SpineAttachment.cpp new file mode 100644 index 000000000..e25f54c5e --- /dev/null +++ b/spine-godot/spine_godot/SpineAttachment.cpp @@ -0,0 +1,55 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineAttachment.h" + +void SpineAttachment::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_attachment_name"), &SpineAttachment::get_attachment_name); + ClassDB::bind_method(D_METHOD("copy"), &SpineAttachment::copy); +} + +SpineAttachment::SpineAttachment() : attachment(NULL) {} +SpineAttachment::~SpineAttachment() { + if (attachment) { + attachment->dereference(); + attachment = NULL; + } +} + +String SpineAttachment::get_attachment_name() { + return attachment->getName().buffer(); +} + +Ref SpineAttachment::copy() { + auto a = attachment->copy(); + if (a == NULL) return NULL; + Ref gd_attachment(memnew(SpineAttachment)); + gd_attachment->set_spine_object(a); + return gd_attachment; +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineAttachment.h b/spine-godot/spine_godot/SpineAttachment.h new file mode 100644 index 000000000..81ec52c9d --- /dev/null +++ b/spine-godot/spine_godot/SpineAttachment.h @@ -0,0 +1,64 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEATTACHMENT_H +#define GODOT_SPINEATTACHMENT_H + +#include "core/variant_parser.h" + +#include + +class SpineAttachment : public Reference { + GDCLASS(SpineAttachment, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Attachment *attachment; + +public: + SpineAttachment(); + ~SpineAttachment(); + + inline void set_spine_object(spine::Attachment *a) { + attachment = a; + if (attachment) + attachment->reference(); + } + inline spine::Attachment *get_spine_object() { + return attachment; + } + + String get_attachment_name(); + + Ref copy(); +}; + +#endif//GODOT_SPINEATTACHMENT_H diff --git a/spine-godot/spine_godot/SpineBone.cpp b/spine-godot/spine_godot/SpineBone.cpp new file mode 100644 index 000000000..afde7a781 --- /dev/null +++ b/spine-godot/spine_godot/SpineBone.cpp @@ -0,0 +1,536 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineBone.h" + +#include "SpineSprite.h" +#include "SpineSkeleton.h" + +void SpineBone::_bind_methods() { + ClassDB::bind_method(D_METHOD("update_world_transform"), &SpineBone::update_world_transform); + // void set_to_setup_pose(); + // + // Vector2 world_to_local(Vector2 world_position); + // + // Vector2 local_to_world(Vector2 local_position); + // + // float world_to_local_rotation(float world_rotation); + // + // float local_to_world_rotation(float local_rotation); + // + // void rotate_world(float degrees); + ClassDB::bind_method(D_METHOD("set_to_setup_pose"), &SpineBone::set_to_setup_pose); + ClassDB::bind_method(D_METHOD("world_to_local", "world_position"), &SpineBone::world_to_local); + ClassDB::bind_method(D_METHOD("local_to_world", "local_position"), &SpineBone::local_to_world); + ClassDB::bind_method(D_METHOD("world_to_local_rotation", "world_rotation"), &SpineBone::world_to_local_rotation); + ClassDB::bind_method(D_METHOD("local_to_world_rotation", "local_rotation"), &SpineBone::local_to_world_rotation); + ClassDB::bind_method(D_METHOD("rotate_world"), &SpineBone::rotate_world); + // + // float get_world_to_local_rotation_x(); + // float get_world_to_local_rotation_y(); + // + // Ref get_data(); + // + // Ref get_skeleton(); + // + // Ref get_parent(); + // + // Array get_children(); + ClassDB::bind_method(D_METHOD("get_world_to_local_rotation_x"), &SpineBone::get_world_to_local_rotation_x); + ClassDB::bind_method(D_METHOD("get_world_to_local_rotation_y"), &SpineBone::get_world_to_local_rotation_y); + ClassDB::bind_method(D_METHOD("get_data"), &SpineBone::get_data); + ClassDB::bind_method(D_METHOD("get_skeleton"), &SpineBone::get_skeleton); + ClassDB::bind_method(D_METHOD("get_parent"), &SpineBone::get_parent); + ClassDB::bind_method(D_METHOD("get_children"), &SpineBone::get_children); + // + // float get_x(); + // void set_x(float v); + // + // float get_y(); + // void set_y(float v); + // + // float get_rotation(); + // void set_rotation(float v); + // + // float get_scale_x(); + // void set_scale_x(float v); + ClassDB::bind_method(D_METHOD("get_x"), &SpineBone::get_x); + ClassDB::bind_method(D_METHOD("set_x", "v"), &SpineBone::set_x); + ClassDB::bind_method(D_METHOD("get_y"), &SpineBone::get_y); + ClassDB::bind_method(D_METHOD("set_y", "v"), &SpineBone::set_y); + ClassDB::bind_method(D_METHOD("get_rotation"), &SpineBone::get_rotation); + ClassDB::bind_method(D_METHOD("set_rotation", "v"), &SpineBone::set_rotation); + ClassDB::bind_method(D_METHOD("get_scale_x"), &SpineBone::get_scale_x); + ClassDB::bind_method(D_METHOD("set_scale_x", "v"), &SpineBone::set_scale_x); + // + // float get_scale_y(); + // void set_scale_y(float v); + // + // float get_shear_x(); + // void set_shear_x(float v); + // + // float get_shear_y(); + // void set_shear_y(float v); + // + // float get_applied_rotation(); + // void set_applied_rotation(float v); + ClassDB::bind_method(D_METHOD("get_scale_y"), &SpineBone::get_scale_y); + ClassDB::bind_method(D_METHOD("set_scale_y", "v"), &SpineBone::set_scale_y); + ClassDB::bind_method(D_METHOD("get_shear_x"), &SpineBone::get_shear_x); + ClassDB::bind_method(D_METHOD("set_shear_x", "v"), &SpineBone::set_shear_x); + ClassDB::bind_method(D_METHOD("get_shear_y"), &SpineBone::get_shear_y); + ClassDB::bind_method(D_METHOD("set_shear_y", "v"), &SpineBone::set_shear_y); + ClassDB::bind_method(D_METHOD("get_applied_rotation"), &SpineBone::get_applied_rotation); + ClassDB::bind_method(D_METHOD("set_applied_rotation", "v"), &SpineBone::set_applied_rotation); + // + // float get_a_x(); + // void set_a_x(float v); + // + // float get_a_y(); + // void set_a_y(float v); + // + // float get_a_scale_x(); + // void set_a_scale_x(float v); + // + // float get_a_scale_y(); + // void set_a_scale_y(float v); + ClassDB::bind_method(D_METHOD("get_a_x"), &SpineBone::get_a_x); + ClassDB::bind_method(D_METHOD("set_a_x", "v"), &SpineBone::set_a_x); + ClassDB::bind_method(D_METHOD("get_a_y"), &SpineBone::get_a_y); + ClassDB::bind_method(D_METHOD("set_a_y", "v"), &SpineBone::set_a_y); + ClassDB::bind_method(D_METHOD("get_a_scale_x"), &SpineBone::get_a_scale_x); + ClassDB::bind_method(D_METHOD("set_a_scale_x", "v"), &SpineBone::set_a_scale_x); + ClassDB::bind_method(D_METHOD("get_a_scale_y"), &SpineBone::get_a_scale_y); + ClassDB::bind_method(D_METHOD("set_a_scale_y", "v"), &SpineBone::set_a_scale_y); + // + // float get_a_shear_x(); + // void set_a_shear_x(float v); + // + // float get_a_shear_y(); + // void set_a_shear_y(float v); + // + // float get_a(); + // void set_a(float v); + // + // float get_b(); + // void set_b(float v); + ClassDB::bind_method(D_METHOD("get_a_shear_x"), &SpineBone::get_a_shear_x); + ClassDB::bind_method(D_METHOD("set_a_shear_x", "v"), &SpineBone::set_a_shear_x); + ClassDB::bind_method(D_METHOD("get_a_shear_y"), &SpineBone::get_a_shear_y); + ClassDB::bind_method(D_METHOD("set_a_shear_y", "v"), &SpineBone::set_a_shear_y); + ClassDB::bind_method(D_METHOD("get_a"), &SpineBone::get_a); + ClassDB::bind_method(D_METHOD("set_a", "v"), &SpineBone::set_a); + ClassDB::bind_method(D_METHOD("get_b"), &SpineBone::get_b); + ClassDB::bind_method(D_METHOD("set_b", "v"), &SpineBone::set_b); + // + // float get_c(); + // void set_c(float v); + // + // float get_d(); + // void set_d(float v); + // + // float get_world_x(); + // void set_world_x(float v); + // + // float get_world_y(); + // void set_world_y(float v); + ClassDB::bind_method(D_METHOD("get_c"), &SpineBone::get_c); + ClassDB::bind_method(D_METHOD("set_c", "v"), &SpineBone::set_c); + ClassDB::bind_method(D_METHOD("get_d"), &SpineBone::get_d); + ClassDB::bind_method(D_METHOD("set_d", "v"), &SpineBone::set_d); + ClassDB::bind_method(D_METHOD("get_world_x"), &SpineBone::get_world_x); + ClassDB::bind_method(D_METHOD("set_world_x", "v"), &SpineBone::set_world_x); + ClassDB::bind_method(D_METHOD("get_world_y"), &SpineBone::get_world_y); + ClassDB::bind_method(D_METHOD("set_world_y", "v"), &SpineBone::set_world_y); + // + // float get_world_rotation_x(); + // float get_world_rotation_y(); + // + // float get_world_scale_x(); + // float get_world_scale_y(); + // + // bool is_applied_valid(); + // void set_applied_valid(bool v); + // + // bool is_active(); + // void set_active(bool v); + ClassDB::bind_method(D_METHOD("get_world_rotation_x"), &SpineBone::get_world_rotation_x); + ClassDB::bind_method(D_METHOD("get_world_rotation_y"), &SpineBone::get_world_rotation_y); + ClassDB::bind_method(D_METHOD("get_world_scale_x"), &SpineBone::get_world_scale_x); + ClassDB::bind_method(D_METHOD("get_world_scale_y"), &SpineBone::get_world_scale_y); + ClassDB::bind_method(D_METHOD("is_active"), &SpineBone::is_active); + ClassDB::bind_method(D_METHOD("set_active", "v"), &SpineBone::set_active); + + ClassDB::bind_method(D_METHOD("get_godot_transform"), &SpineBone::get_godot_transform); + ClassDB::bind_method(D_METHOD("set_godot_transform", "local_transform"), &SpineBone::set_godot_transform); + ClassDB::bind_method(D_METHOD("get_godot_global_transform"), &SpineBone::get_godot_global_transform); + ClassDB::bind_method(D_METHOD("set_godot_global_transform", "global_transform"), &SpineBone::set_godot_global_transform); + + ClassDB::bind_method(D_METHOD("apply_world_transform_2d", "node2d"), &SpineBone::apply_world_transform_2d); +} + +SpineBone::SpineBone() : bone(NULL), the_sprite(nullptr) {} +SpineBone::~SpineBone() {} + +void SpineBone::update_world_transform() { + bone->updateWorldTransform(); +} + +void SpineBone::set_to_setup_pose() { + bone->setToSetupPose(); +} + +Vector2 SpineBone::world_to_local(Vector2 world_position) { + float x, y; + bone->worldToLocal(world_position.x, world_position.y, x, y); + return Vector2(x, y); +} + +Vector2 SpineBone::local_to_world(Vector2 local_position) { + float x, y; + bone->localToWorld(local_position.x, local_position.y, x, y); + return Vector2(x, y); +} + +float SpineBone::world_to_local_rotation(float world_rotation) { + return bone->worldToLocalRotation(world_rotation); +} + +float SpineBone::local_to_world_rotation(float local_rotation) { + return bone->localToWorldRotation(local_rotation); +} + +void SpineBone::rotate_world(float degrees) { + bone->rotateWorld(degrees); +} + +float SpineBone::get_world_to_local_rotation_x() { + return bone->getWorldToLocalRotationX(); +} +float SpineBone::get_world_to_local_rotation_y() { + return bone->getWorldToLocalRotationY(); +} + +Ref SpineBone::get_data() { + auto &bd = bone->getData(); + Ref gd_bd(memnew(SpineBoneData)); + gd_bd->set_spine_object(&bd); + return gd_bd; +} + +Ref SpineBone::get_skeleton() { + auto &s = bone->getSkeleton(); + Ref gd_s(memnew(SpineSkeleton)); + gd_s->set_spine_object(&s); + gd_s->set_spine_sprite(the_sprite); + return gd_s; +} + +Ref SpineBone::get_parent() { + auto b = bone->getParent(); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + gd_b->set_spine_sprite(the_sprite); + return gd_b; +} + +Array SpineBone::get_children() { + auto bs = bone->getChildren(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + auto b = bs[i]; + if (b == NULL) gd_bs[i] = Ref(NULL); + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + gd_b->set_spine_sprite(the_sprite); + gd_bs[i] = gd_b; + } + return gd_bs; +} + +float SpineBone::get_x() { + return bone->getX(); +} +void SpineBone::set_x(float v) { + bone->setX(v); +} + +float SpineBone::get_y() { + return bone->getY(); +} +void SpineBone::set_y(float v) { + bone->setY(v); +} + +float SpineBone::get_rotation() { + return bone->getRotation(); +} +void SpineBone::set_rotation(float v) { + bone->setRotation(v); +} + +float SpineBone::get_scale_x() { + return bone->getScaleX(); +} +void SpineBone::set_scale_x(float v) { + bone->setScaleX(v); +} + +float SpineBone::get_scale_y() { + return bone->getScaleY(); +} +void SpineBone::set_scale_y(float v) { + bone->setScaleY(v); +} + +float SpineBone::get_shear_x() { + return bone->getShearX(); +} +void SpineBone::set_shear_x(float v) { + bone->setShearX(v); +} + +float SpineBone::get_shear_y() { + return bone->getShearY(); +} +void SpineBone::set_shear_y(float v) { + bone->setShearY(v); +} + +float SpineBone::get_applied_rotation() { + return bone->getAppliedRotation(); +} +void SpineBone::set_applied_rotation(float v) { + bone->setAppliedRotation(v); +} + +float SpineBone::get_a_x() { + return bone->getAX(); +} +void SpineBone::set_a_x(float v) { + bone->setAX(v); +} + +float SpineBone::get_a_y() { + return bone->getAY(); +} +void SpineBone::set_a_y(float v) { + bone->setAY(v); +} + +float SpineBone::get_a_scale_x() { + return bone->getAScaleX(); +} +void SpineBone::set_a_scale_x(float v) { + bone->setAScaleX(v); +} + +float SpineBone::get_a_scale_y() { + return bone->getAScaleY(); +} +void SpineBone::set_a_scale_y(float v) { + bone->setAScaleY(v); +} + +float SpineBone::get_a_shear_x() { + return bone->getAShearX(); +} +void SpineBone::set_a_shear_x(float v) { + bone->setAShearX(v); +} + +float SpineBone::get_a_shear_y() { + return bone->getAShearY(); +} +void SpineBone::set_a_shear_y(float v) { + bone->setAShearY(v); +} + +float SpineBone::get_a() { + return bone->getA(); +} +void SpineBone::set_a(float v) { + bone->setA(v); +} + +float SpineBone::get_b() { + return bone->getB(); +} +void SpineBone::set_b(float v) { + bone->setB(v); +} + +float SpineBone::get_c() { + return bone->getC(); +} +void SpineBone::set_c(float v) { + bone->setC(v); +} + +float SpineBone::get_d() { + return bone->getD(); +} +void SpineBone::set_d(float v) { + bone->setD(v); +} + +float SpineBone::get_world_x() { + return bone->getWorldX(); +} +void SpineBone::set_world_x(float v) { + bone->setWorldX(v); +} + +float SpineBone::get_world_y() { + return bone->getWorldY(); +} +void SpineBone::set_world_y(float v) { + bone->setWorldY(v); +} + +float SpineBone::get_world_rotation_x() { + return bone->getWorldRotationX(); +} +float SpineBone::get_world_rotation_y() { + return bone->getWorldRotationY(); +} + +float SpineBone::get_world_scale_x() { + return bone->getWorldScaleX(); +} +float SpineBone::get_world_scale_y() { + return bone->getWorldScaleY(); +} + +bool SpineBone::is_active() { + return bone->isActive(); +} +void SpineBone::set_active(bool v) { + bone->setActive(v); +} + +// External feature functions +void SpineBone::apply_world_transform_2d(Variant o) { + if (o.get_type() == Variant::OBJECT) { + auto node = (Node *) o; + if (node->is_class("Node2D")) { + auto node2d = (Node2D *) node; + // In godot the y-axis is nag to spine + node2d->set_transform(Transform2D( + get_a(), get_c(), + get_b(), get_d(), + get_world_x(), -get_world_y())); + // Fix the rotation + auto pos = node2d->get_position(); + node2d->translate(-pos); + node2d->set_rotation(-node2d->get_rotation()); + node2d->translate(pos); + } + } +} + +Transform2D SpineBone::get_godot_transform() { + if (get_spine_object() == nullptr) + return Transform2D(); + Transform2D trans; + trans.translate(get_x(), -get_y()); + // It seems that spine uses degree for rotation + trans.rotate(Math::deg2rad(-get_rotation())); + trans.scale(Size2(get_scale_x(), get_scale_y())); + return trans; +} + +void SpineBone::set_godot_transform(Transform2D trans) { + if (get_spine_object() == nullptr) + return; + Vector2 position = trans.get_origin(); + position.y *= -1; + real_t rotation = trans.get_rotation(); + rotation = Math::rad2deg(-rotation); + Vector2 scale = trans.get_scale(); + + set_x(position.x); + set_y(position.y); + set_rotation(rotation); + set_scale_x(scale.x); + set_scale_y(scale.y); +} + +Transform2D SpineBone::get_godot_global_transform() { + if (get_spine_object() == nullptr) + return Transform2D(); + if (the_sprite == nullptr) + return get_godot_transform(); + Transform2D res = the_sprite->get_transform(); + res.translate(get_world_x(), -get_world_y()); + res.rotate(Math::deg2rad(-get_world_rotation_x())); + res.scale(Vector2(get_world_scale_x(), get_world_scale_y())); + auto p = the_sprite->get_parent() ? Object::cast_to(the_sprite->get_parent()) : nullptr; + if (p) { + return p->get_global_transform() * res; + } + return res; +} + +void SpineBone::set_godot_global_transform(Transform2D transform) { + if (get_spine_object() == nullptr) + return; + if (the_sprite == nullptr) + set_godot_transform(transform); + transform = the_sprite->get_global_transform().affine_inverse() * transform; + Vector2 position = transform.get_origin(); + real_t rotation = transform.get_rotation(); + Vector2 scale = transform.get_scale(); + position.y *= -1; + auto parent = get_parent(); + if (parent.is_valid()) { + position = parent->world_to_local(position); + if (parent->get_world_scale_x() != 0) + scale.x /= parent->get_world_scale_x(); + else + print_error("The parent scale.x is zero."); + if (parent->get_world_scale_y() != 0) + scale.y /= parent->get_world_scale_y(); + else + print_error("The parent scale.y is zero."); + } + rotation = world_to_local_rotation(Math::rad2deg(-rotation)); + + set_x(position.x); + set_y(position.y); + set_rotation(rotation); + set_scale_x(scale.x); + set_scale_y(scale.y); +} + +void SpineBone::set_spine_sprite(SpineSprite *s) { + the_sprite = s; +} diff --git a/spine-godot/spine_godot/SpineBone.h b/spine-godot/spine_godot/SpineBone.h new file mode 100644 index 000000000..b7efd1381 --- /dev/null +++ b/spine-godot/spine_godot/SpineBone.h @@ -0,0 +1,175 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEBONE_H +#define GODOT_SPINEBONE_H + +#include "core/variant_parser.h" +#include + +#include +#include + +#include "SpineBoneData.h" +#include "SpineIkConstraint.h" +#include "SpinePathConstraint.h" +#include "SpineTransformConstraint.h" + +class SpineSkeleton; +class SpineSprite; + +class SpineBone : public Reference { + GDCLASS(SpineBone, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Bone *bone; + + SpineSprite *the_sprite; + +public: + SpineBone(); + ~SpineBone(); + + inline void set_spine_object(spine::Bone *b) { + bone = b; + } + inline spine::Bone *get_spine_object() { + return bone; + } + + void set_spine_sprite(SpineSprite *s); + + void update_world_transform(); + + void set_to_setup_pose(); + + Vector2 world_to_local(Vector2 world_position); + + Vector2 local_to_world(Vector2 local_position); + + float world_to_local_rotation(float world_rotation); + + float local_to_world_rotation(float local_rotation); + + void rotate_world(float degrees); + + float get_world_to_local_rotation_x(); + float get_world_to_local_rotation_y(); + + Ref get_data(); + + Ref get_skeleton(); + + Ref get_parent(); + + Array get_children(); + + float get_x(); + void set_x(float v); + + float get_y(); + void set_y(float v); + + float get_rotation(); + void set_rotation(float v); + + float get_scale_x(); + void set_scale_x(float v); + + float get_scale_y(); + void set_scale_y(float v); + + float get_shear_x(); + void set_shear_x(float v); + + float get_shear_y(); + void set_shear_y(float v); + + float get_applied_rotation(); + void set_applied_rotation(float v); + + float get_a_x(); + void set_a_x(float v); + + float get_a_y(); + void set_a_y(float v); + + float get_a_scale_x(); + void set_a_scale_x(float v); + + float get_a_scale_y(); + void set_a_scale_y(float v); + + float get_a_shear_x(); + void set_a_shear_x(float v); + + float get_a_shear_y(); + void set_a_shear_y(float v); + + float get_a(); + void set_a(float v); + + float get_b(); + void set_b(float v); + + float get_c(); + void set_c(float v); + + float get_d(); + void set_d(float v); + + float get_world_x(); + void set_world_x(float v); + + float get_world_y(); + void set_world_y(float v); + + float get_world_rotation_x(); + float get_world_rotation_y(); + + float get_world_scale_x(); + float get_world_scale_y(); + + bool is_active(); + void set_active(bool v); + + // External feature functions + void apply_world_transform_2d(Variant o); + + Transform2D get_godot_transform(); + void set_godot_transform(Transform2D trans); + + Transform2D get_godot_global_transform(); + void set_godot_global_transform(Transform2D trans); +}; + +#endif//GODOT_SPINEBONE_H diff --git a/spine-godot/spine_godot/SpineBoneData.cpp b/spine-godot/spine_godot/SpineBoneData.cpp new file mode 100644 index 000000000..b870527dc --- /dev/null +++ b/spine-godot/spine_godot/SpineBoneData.cpp @@ -0,0 +1,163 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineBoneData.h" + +void SpineBoneData::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_index"), &SpineBoneData::get_index); + ClassDB::bind_method(D_METHOD("get_bone_name"), &SpineBoneData::get_bone_name); + ClassDB::bind_method(D_METHOD("get_parent"), &SpineBoneData::get_parent); + + ClassDB::bind_method(D_METHOD("get_length"), &SpineBoneData::get_length); + ClassDB::bind_method(D_METHOD("set_length", "v"), &SpineBoneData::set_length); + + ClassDB::bind_method(D_METHOD("get_x"), &SpineBoneData::get_x); + ClassDB::bind_method(D_METHOD("set_x", "v"), &SpineBoneData::set_x); + + ClassDB::bind_method(D_METHOD("get_y"), &SpineBoneData::get_y); + ClassDB::bind_method(D_METHOD("set_y", "v"), &SpineBoneData::set_y); + + ClassDB::bind_method(D_METHOD("get_rotation"), &SpineBoneData::get_rotation); + ClassDB::bind_method(D_METHOD("set_rotation", "v"), &SpineBoneData::set_rotation); + + ClassDB::bind_method(D_METHOD("get_scale_x"), &SpineBoneData::get_scale_x); + ClassDB::bind_method(D_METHOD("set_scale_x", "v"), &SpineBoneData::set_scale_x); + + ClassDB::bind_method(D_METHOD("get_scale_y"), &SpineBoneData::get_scale_y); + ClassDB::bind_method(D_METHOD("set_scale_y", "v"), &SpineBoneData::set_scale_y); + + ClassDB::bind_method(D_METHOD("get_shear_x"), &SpineBoneData::get_shear_x); + ClassDB::bind_method(D_METHOD("set_shear_x", "v"), &SpineBoneData::set_shear_x); + + ClassDB::bind_method(D_METHOD("get_shear_y"), &SpineBoneData::get_shear_y); + ClassDB::bind_method(D_METHOD("set_shear_y", "v"), &SpineBoneData::set_shear_y); + + ClassDB::bind_method(D_METHOD("get_transform_mode"), &SpineBoneData::get_transform_mode); + ClassDB::bind_method(D_METHOD("set_transform_mode", "v"), &SpineBoneData::set_transform_mode); + + ClassDB::bind_method(D_METHOD("is_skin_required"), &SpineBoneData::is_skin_required); + ClassDB::bind_method(D_METHOD("set_skin_required", "v"), &SpineBoneData::set_skin_required); + + BIND_ENUM_CONSTANT(TRANSFORMMODE_NORMAL); + BIND_ENUM_CONSTANT(TRANSFORMMODE_ONLYTRANSLATION); + BIND_ENUM_CONSTANT(TRANSFORMMODE_NOROTATIONORREFLECTION); + BIND_ENUM_CONSTANT(TRANSFORMMODE_NOSCALE); + BIND_ENUM_CONSTANT(TRANSFORMMODE_NOSCALEORREFLECTION); +} + +SpineBoneData::SpineBoneData() : bone_data(NULL) {} +SpineBoneData::~SpineBoneData() {} + +int SpineBoneData::get_index() { + return bone_data->getIndex(); +} + +String SpineBoneData::get_bone_name() { + return bone_data->getName().buffer(); +} + +Ref SpineBoneData::get_parent() { + auto p = bone_data->getParent(); + if (p == NULL) return NULL; + Ref gd_bone_data(memnew(SpineBoneData)); + gd_bone_data->set_spine_object(p); + return gd_bone_data; +} + +float SpineBoneData::get_length() { + return bone_data->getLength(); +} +void SpineBoneData::set_length(float v) { + bone_data->setLength(v); +} + +float SpineBoneData::get_x() { + return bone_data->getX(); +} +void SpineBoneData::set_x(float v) { + bone_data->setX(v); +} + +float SpineBoneData::get_y() { + return bone_data->getY(); +} +void SpineBoneData::set_y(float v) { + bone_data->setY(v); +} + +float SpineBoneData::get_rotation() { + return bone_data->getRotation(); +} +void SpineBoneData::set_rotation(float v) { + bone_data->setRotation(v); +} + +float SpineBoneData::get_scale_x() { + return bone_data->getScaleX(); +} +void SpineBoneData::set_scale_x(float v) { + bone_data->setScaleX(v); +} + +float SpineBoneData::get_scale_y() { + return bone_data->getScaleY(); +} +void SpineBoneData::set_scale_y(float v) { + bone_data->setScaleY(v); +} + +float SpineBoneData::get_shear_x() { + return bone_data->getShearX(); +} +void SpineBoneData::set_shear_x(float v) { + bone_data->setShearX(v); +} + +float SpineBoneData::get_shear_y() { + return bone_data->getShearY(); +} +void SpineBoneData::set_shear_y(float v) { + bone_data->setShearY(v); +} + +SpineBoneData::TransformMode SpineBoneData::get_transform_mode() { + auto tm = (int) bone_data->getTransformMode(); + return (TransformMode) tm; +} +void SpineBoneData::set_transform_mode(TransformMode v) { + auto tm = (int) v; + bone_data->setTransformMode((spine::TransformMode) tm); +} + +bool SpineBoneData::is_skin_required() { + return bone_data->isSkinRequired(); +} +void SpineBoneData::set_skin_required(bool v) { + bone_data->setSkinRequired(v); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineBoneData.h b/spine-godot/spine_godot/SpineBoneData.h new file mode 100644 index 000000000..dc3e3feb6 --- /dev/null +++ b/spine-godot/spine_godot/SpineBoneData.h @@ -0,0 +1,103 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEBONEDATA_H +#define GODOT_SPINEBONEDATA_H + +#include "core/variant_parser.h" + +#include + +class SpineBoneData : public Reference { + GDCLASS(SpineBoneData, Reference); + +protected: + static void _bind_methods(); + +private: + spine::BoneData *bone_data; + +public: + SpineBoneData(); + ~SpineBoneData(); + + inline void set_spine_object(spine::BoneData *b) { + bone_data = b; + } + inline spine::BoneData *get_spine_object() { + return bone_data; + } + + enum TransformMode { + TRANSFORMMODE_NORMAL = 0, + TRANSFORMMODE_ONLYTRANSLATION, + TRANSFORMMODE_NOROTATIONORREFLECTION, + TRANSFORMMODE_NOSCALE, + TRANSFORMMODE_NOSCALEORREFLECTION + }; + + int get_index(); + + String get_bone_name(); + + Ref get_parent(); + + float get_length(); + void set_length(float v); + + float get_x(); + void set_x(float v); + + float get_y(); + void set_y(float v); + + float get_rotation(); + void set_rotation(float v); + + float get_scale_x(); + void set_scale_x(float v); + + float get_scale_y(); + void set_scale_y(float v); + + float get_shear_x(); + void set_shear_x(float v); + + float get_shear_y(); + void set_shear_y(float v); + + TransformMode get_transform_mode(); + void set_transform_mode(TransformMode v); + + bool is_skin_required(); + void set_skin_required(bool v); +}; + +VARIANT_ENUM_CAST(SpineBoneData::TransformMode); +#endif//GODOT_SPINEBONEDATA_H diff --git a/spine-godot/spine_godot/SpineCollisionShapeProxy.cpp b/spine-godot/spine_godot/SpineCollisionShapeProxy.cpp new file mode 100644 index 000000000..9015db60d --- /dev/null +++ b/spine-godot/spine_godot/SpineCollisionShapeProxy.cpp @@ -0,0 +1,196 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineCollisionShapeProxy.h" + +#include "SpineSprite.h" + +void SpineCollisionShapeProxy::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_spine_sprite_path"), &SpineCollisionShapeProxy::get_spine_sprite_path); + ClassDB::bind_method(D_METHOD("set_spine_sprite_path", "v"), &SpineCollisionShapeProxy::set_spine_sprite_path); + + ClassDB::bind_method(D_METHOD("get_slot"), &SpineCollisionShapeProxy::get_slot); + ClassDB::bind_method(D_METHOD("set_slot", "v"), &SpineCollisionShapeProxy::set_slot); + + ClassDB::bind_method(D_METHOD("get_sync_transform"), &SpineCollisionShapeProxy::get_sync_transform); + ClassDB::bind_method(D_METHOD("set_sync_transform", "v"), &SpineCollisionShapeProxy::set_sync_transform); + + ADD_PROPERTY(PropertyInfo(Variant::NODE_PATH, "spine_sprite_path"), "set_spine_sprite_path", "get_spine_sprite_path"); + ADD_PROPERTY(PropertyInfo(Variant::BOOL, "sync_transform"), "set_sync_transform", "get_sync_transform"); +} + +SpineCollisionShapeProxy::SpineCollisionShapeProxy() : sync_transform(true) { +} + +SpineCollisionShapeProxy::~SpineCollisionShapeProxy() { +} + +void SpineCollisionShapeProxy::_notification(int p_what) { + switch (p_what) { + case NOTIFICATION_READY: { + set_process_internal(true); + } break; + case NOTIFICATION_INTERNAL_PROCESS: { + if (!disabled) { + if (sync_transform) _sync_transform(get_spine_sprite()); + _update_polygon_from_spine_sprite(get_spine_sprite()); + if (is_visible()) update(); + } + } break; + } +} + +SpineSprite *SpineCollisionShapeProxy::get_spine_sprite() const { + return (SpineSprite *) get_node_or_null(spine_sprite_path); +} + +NodePath SpineCollisionShapeProxy::get_spine_sprite_path() { + return spine_sprite_path; +} + +void SpineCollisionShapeProxy::set_spine_sprite_path(NodePath v) { + spine_sprite_path = v; + + _update_polygon_from_spine_sprite(get_spine_sprite()); +} + +String SpineCollisionShapeProxy::get_slot() const { + return slot; +} + +void SpineCollisionShapeProxy::set_slot(const String &v) { + slot = v; + _update_polygon_from_spine_sprite(get_spine_sprite()); +} + +void SpineCollisionShapeProxy::_update_polygon_from_spine_sprite(SpineSprite *sprite) { + _clear_polygon(); + if (sprite == nullptr || slot.empty()) { + return; + } + + if (!sprite->get_skeleton().is_valid()) { + return; + } + + auto sk = sprite->get_skeleton()->get_spine_object(); + + spine::Vector vertices; + + spine::Slot *s = sk->findSlot(spine::String(slot.utf8())); + if (!s) { + return; + } + spine::Attachment *attachment = s->getAttachment(); + if (!attachment) { + return; + } + + if (attachment->getRTTI().isExactly(spine::BoundingBoxAttachment::rtti)) { + auto *box = (spine::BoundingBoxAttachment *) attachment; + + vertices.setSize(box->getWorldVerticesLength(), 0); + box->computeWorldVertices(*s, vertices); + } else { + return; + } + + polygon.resize(vertices.size() / 2); + for (size_t j = 0; j < vertices.size(); j += 2) { + polygon.set(j / 2, Vector2(vertices[j], -vertices[j + 1])); + } + + set_polygon(polygon); +} + +void SpineCollisionShapeProxy::_clear_polygon() { + polygon.clear(); + set_polygon(polygon); +} + +void SpineCollisionShapeProxy::_sync_transform(SpineSprite *sprite) { + if (sprite == nullptr) return; + set_global_transform(sprite->get_global_transform()); +} + +bool SpineCollisionShapeProxy::get_sync_transform() { + return sync_transform; +} + +void SpineCollisionShapeProxy::set_sync_transform(bool v) { + sync_transform = v; +} + +void SpineCollisionShapeProxy::_get_property_list(List *p_list) const { + PropertyInfo p; + Vector res; + + p.name = "slot"; + p.type = Variant::STRING; + _get_slot_list(res); + if (res.empty()) res.push_back("No Slot"); + p.hint_string = String(",").join(res); + p.hint = PROPERTY_HINT_ENUM; + p_list->push_back(p); +} + +bool SpineCollisionShapeProxy::_get(const StringName &p_property, Variant &r_value) const { + if (p_property == "slot") { + r_value = get_slot(); + return true; + } + return false; +} + +bool SpineCollisionShapeProxy::_set(const StringName &p_property, const Variant &p_value) { + if (p_property == "slot") { + set_slot(p_value); + return true; + } + return false; +} + +void SpineCollisionShapeProxy::_get_slot_list(Vector &res) const { + if (get_spine_sprite() == nullptr) { + return; + } + + auto sprite = get_spine_sprite(); + if (!sprite->get_skeleton().is_valid()) { + return; + } + + auto slots = sprite->get_skeleton()->get_slots(); + res.resize(slots.size()); + for (size_t i = 0; i < res.size(); ++i) { + auto slot = (Ref) slots[i]; + if (slot.is_valid()) + res.set(i, slot->get_data()->get_slot_name()); + } +} diff --git a/spine-godot/spine_godot/SpineCollisionShapeProxy.h b/spine-godot/spine_godot/SpineCollisionShapeProxy.h new file mode 100644 index 000000000..c29eaa591 --- /dev/null +++ b/spine-godot/spine_godot/SpineCollisionShapeProxy.h @@ -0,0 +1,80 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINECOLLISIONSHAPEPROXY_H +#define GODOT_SPINECOLLISIONSHAPEPROXY_H + +#include "scene/2d/collision_polygon_2d.h" + +class SpineSprite; +class SpineAnimationState; +class SpineSkeleton; + +class SpineCollisionShapeProxy : public CollisionPolygon2D { + GDCLASS(SpineCollisionShapeProxy, CollisionPolygon2D) +protected: + static void _bind_methods(); + + NodePath spine_sprite_path; + + String slot; + + bool sync_transform; + +protected: + void _notification(int p_what); + void _get_property_list(List *p_list) const; + bool _get(const StringName &p_property, Variant &r_value) const; + bool _set(const StringName &p_property, const Variant &p_value); + + + SpineSprite *get_spine_sprite() const; + + void _update_polygon_from_spine_sprite(SpineSprite *sprite); + void _clear_polygon(); + void _sync_transform(SpineSprite *sprite); + + void _get_slot_list(Vector &res) const; + +public: + SpineCollisionShapeProxy(); + ~SpineCollisionShapeProxy(); + + NodePath get_spine_sprite_path(); + void set_spine_sprite_path(NodePath v); + + String get_slot() const; + void set_slot(const String &v); + + bool get_sync_transform(); + void set_sync_transform(bool v); +}; + + +#endif//GODOT_SPINECOLLISIONSHAPEPROXY_H diff --git a/spine-godot/spine_godot/SpineConstant.cpp b/spine-godot/spine_godot/SpineConstant.cpp new file mode 100644 index 000000000..760ff668a --- /dev/null +++ b/spine-godot/spine_godot/SpineConstant.cpp @@ -0,0 +1,60 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineConstant.h" + +void SpineConstant::_bind_methods() { + BIND_ENUM_CONSTANT(MixBlend_Setup); + BIND_ENUM_CONSTANT(MixBlend_First); + BIND_ENUM_CONSTANT(MixBlend_Replace); + BIND_ENUM_CONSTANT(MixBlend_Add); + + BIND_ENUM_CONSTANT(MixDirection_In); + BIND_ENUM_CONSTANT(MixDirection_Out); + + BIND_ENUM_CONSTANT(Property_Rotate); + BIND_ENUM_CONSTANT(Property_X); + BIND_ENUM_CONSTANT(Property_Y); + BIND_ENUM_CONSTANT(Property_ScaleX); + BIND_ENUM_CONSTANT(Property_ScaleY); + BIND_ENUM_CONSTANT(Property_ShearX); + BIND_ENUM_CONSTANT(Property_ShearY); + BIND_ENUM_CONSTANT(Property_Rgb); + BIND_ENUM_CONSTANT(Property_Alpha); + BIND_ENUM_CONSTANT(Property_Rgb2); + BIND_ENUM_CONSTANT(Property_Attachment); + BIND_ENUM_CONSTANT(Property_Deform); + BIND_ENUM_CONSTANT(Property_Event); + BIND_ENUM_CONSTANT(Property_DrawOrder); + BIND_ENUM_CONSTANT(Property_IkConstraint); + BIND_ENUM_CONSTANT(Property_TransformConstraint); + BIND_ENUM_CONSTANT(Property_PathConstraintPosition); + BIND_ENUM_CONSTANT(Property_PathConstraintSpacing); + BIND_ENUM_CONSTANT(Property_PathConstraintMix); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineConstant.h b/spine-godot/spine_godot/SpineConstant.h new file mode 100644 index 000000000..c7f86d8b9 --- /dev/null +++ b/spine-godot/spine_godot/SpineConstant.h @@ -0,0 +1,81 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINECONSTANT_H +#define GODOT_SPINECONSTANT_H + +#include "core/variant_parser.h" + +class SpineConstant : public Object { + GDCLASS(SpineConstant, Object); + +protected: + static void _bind_methods(); + +public: + enum MixBlend { + MixBlend_Setup = 0, + MixBlend_First, + MixBlend_Replace, + MixBlend_Add + }; + + enum MixDirection { + MixDirection_In = 0, + MixDirection_Out + }; + + enum PropertyId { + Property_Rotate = 1 << 0, + Property_X = 1 << 1, + Property_Y = 1 << 2, + Property_ScaleX = 1 << 3, + Property_ScaleY = 1 << 4, + Property_ShearX = 1 << 5, + Property_ShearY = 1 << 6, + Property_Rgb = 1 << 7, + Property_Alpha = 1 << 8, + Property_Rgb2 = 1 << 9, + Property_Attachment = 1 << 10, + Property_Deform = 1 << 11, + Property_Event = 1 << 12, + Property_DrawOrder = 1 << 13, + Property_IkConstraint = 1 << 14, + Property_TransformConstraint = 1 << 15, + Property_PathConstraintPosition = 1 << 16, + Property_PathConstraintSpacing = 1 << 17, + Property_PathConstraintMix = 1 << 18 + }; +}; + +VARIANT_ENUM_CAST(SpineConstant::MixBlend); +VARIANT_ENUM_CAST(SpineConstant::MixDirection); +VARIANT_ENUM_CAST(SpineConstant::PropertyId); + +#endif//GODOT_SPINECONSTANT_H diff --git a/spine-godot/spine_godot/SpineConstraintData.cpp b/spine-godot/spine_godot/SpineConstraintData.cpp new file mode 100644 index 000000000..16bbac435 --- /dev/null +++ b/spine-godot/spine_godot/SpineConstraintData.cpp @@ -0,0 +1,59 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineConstraintData.h" + +void SpineConstraintData::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_constraint_data_name"), &SpineConstraintData::get_constraint_data_name); + ClassDB::bind_method(D_METHOD("get_order"), &SpineConstraintData::get_order); + ClassDB::bind_method(D_METHOD("set_order", "v"), &SpineConstraintData::set_order); + ClassDB::bind_method(D_METHOD("is_skin_required"), &SpineConstraintData::is_skin_required); + ClassDB::bind_method(D_METHOD("set_skin_required", "v"), &SpineConstraintData::set_skin_required); +} + +SpineConstraintData::SpineConstraintData() : constraint_data(NULL) {} +SpineConstraintData::~SpineConstraintData() {} + +String SpineConstraintData::get_constraint_data_name() { + return constraint_data->getName().buffer(); +} + +uint64_t SpineConstraintData::get_order() { + return constraint_data->getOrder(); +} +void SpineConstraintData::set_order(uint64_t v) { + constraint_data->setOrder(v); +} + +bool SpineConstraintData::is_skin_required() { + return constraint_data->isSkinRequired(); +} +void SpineConstraintData::set_skin_required(bool v) { + constraint_data->setSkinRequired(v); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineConstraintData.h b/spine-godot/spine_godot/SpineConstraintData.h new file mode 100644 index 000000000..35b9dd52a --- /dev/null +++ b/spine-godot/spine_godot/SpineConstraintData.h @@ -0,0 +1,66 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINECONSTRAINTDATA_H +#define GODOT_SPINECONSTRAINTDATA_H + +#include "core/variant_parser.h" + +#include + +class SpineConstraintData : public Reference { + GDCLASS(SpineConstraintData, Reference); + +protected: + static void _bind_methods(); + +private: + spine::ConstraintData *constraint_data; + +public: + SpineConstraintData(); + ~SpineConstraintData(); + + inline void set_spine_object(spine::ConstraintData *c) { + constraint_data = c; + } + virtual inline spine::ConstraintData *get_spine_object() { + return constraint_data; + } + + String get_constraint_data_name(); + + uint64_t get_order(); + void set_order(uint64_t v); + + bool is_skin_required(); + void set_skin_required(bool v); +}; + +#endif//GODOT_SPINECONSTRAINTDATA_H diff --git a/spine-godot/spine_godot/SpineEvent.cpp b/spine-godot/spine_godot/SpineEvent.cpp new file mode 100644 index 000000000..9d753db33 --- /dev/null +++ b/spine-godot/spine_godot/SpineEvent.cpp @@ -0,0 +1,110 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineEvent.h" + +void SpineEvent::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_data"), &SpineEvent::get_data); + ClassDB::bind_method(D_METHOD("get_event_name"), &SpineEvent::get_event_name); + ClassDB::bind_method(D_METHOD("get_time"), &SpineEvent::get_time); + ClassDB::bind_method(D_METHOD("get_int_value"), &SpineEvent::get_int_value); + ClassDB::bind_method(D_METHOD("set_int_value", "v"), &SpineEvent::set_int_value); + ClassDB::bind_method(D_METHOD("get_float_value"), &SpineEvent::get_float_value); + ClassDB::bind_method(D_METHOD("set_float_value", "v"), &SpineEvent::set_float_value); + ClassDB::bind_method(D_METHOD("get_string_value"), &SpineEvent::get_string_value); + ClassDB::bind_method(D_METHOD("set_string_value", "v"), &SpineEvent::set_string_value); + ClassDB::bind_method(D_METHOD("get_volume"), &SpineEvent::get_volume); + ClassDB::bind_method(D_METHOD("set_volume", "v"), &SpineEvent::set_volume); + ClassDB::bind_method(D_METHOD("get_balance"), &SpineEvent::get_balance); + ClassDB::bind_method(D_METHOD("set_balance", "v"), &SpineEvent::set_balance); + // + // BIND_ENUM_CONSTANT(EVENTTYPE_START); + // BIND_ENUM_CONSTANT(EVENTTYPE_INTERRUPT); + // BIND_ENUM_CONSTANT(EVENTTYPE_END); + // BIND_ENUM_CONSTANT(EVENTTYPE_COMPLETE); + // BIND_ENUM_CONSTANT(EVENTTYPE_DISPOSE); + // BIND_ENUM_CONSTANT(EVENTTYPE_EVENT); +} + +SpineEvent::SpineEvent() : event(NULL) {} +SpineEvent::~SpineEvent() {} + +Ref SpineEvent::get_data() { + Ref event_data(memnew(SpineEventData)); + event_data->set_spine_object(&(event->getData())); + return event_data; +} + +String SpineEvent::get_event_name() { + return event->getData().getName().buffer(); +} + +float SpineEvent::get_time() { + return event->getTime(); +} + +int SpineEvent::get_int_value() { + return event->getIntValue(); +} + +void SpineEvent::set_int_value(int v) { + event->setIntValue(v); +} + +float SpineEvent::get_float_value() { + return event->getFloatValue(); +} + +void SpineEvent::set_float_value(float v) { + event->setFloatValue(v); +} + +String SpineEvent::get_string_value() { + return event->getStringValue().buffer(); +} + +void SpineEvent::set_string_value(const String &v) { + event->setStringValue(spine::String(v.utf8())); +} + +float SpineEvent::get_volume() { + return event->getVolume(); +} + +void SpineEvent::set_volume(float v) { + event->setVolume(v); +} + +float SpineEvent::get_balance() { + return event->getBalance(); +} + +void SpineEvent::set_balance(float v) { + event->setBalance(v); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineEvent.h b/spine-godot/spine_godot/SpineEvent.h new file mode 100644 index 000000000..bbbf0b986 --- /dev/null +++ b/spine-godot/spine_godot/SpineEvent.h @@ -0,0 +1,91 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEEVENT_H +#define GODOT_SPINEEVENT_H + +#include "core/variant_parser.h" + +#include + +#include "SpineEventData.h" + +class SpineEvent : public Reference { + GDCLASS(SpineEvent, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Event *event; + +public: + SpineEvent(); + ~SpineEvent(); + + inline void set_spine_object(spine::Event *e) { + event = e; + } + inline spine::Event *get_spine_object() const { + return event; + } + + enum EventType { + EVENTTYPE_START = spine::EventType_Start, + EVENTTYPE_INTERRUPT = spine::EventType_Interrupt, + EVENTTYPE_END = spine::EventType_End, + EVENTTYPE_COMPLETE = spine::EventType_Complete, + EVENTTYPE_DISPOSE = spine::EventType_Dispose, + EVENTTYPE_EVENT = spine::EventType_Event + }; + + + Ref get_data(); + + String get_event_name(); + + float get_time(); + + int get_int_value(); + void set_int_value(int inValue); + + float get_float_value(); + void set_float_value(float inValue); + + String get_string_value(); + void set_string_value(const String &inValue); + + float get_volume(); + void set_volume(float inValue); + + float get_balance(); + void set_balance(float inValue); +}; + +#endif//GODOT_SPINEEVENT_H diff --git a/spine-godot/spine_godot/SpineEventData.cpp b/spine-godot/spine_godot/SpineEventData.cpp new file mode 100644 index 000000000..bca195e79 --- /dev/null +++ b/spine-godot/spine_godot/SpineEventData.cpp @@ -0,0 +1,36 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineEventData.h" + +void SpineEventData::_bind_methods() { +} + +SpineEventData::SpineEventData() : event_data(NULL) {} +SpineEventData::~SpineEventData() {} diff --git a/spine-godot/spine_godot/SpineEventData.h b/spine-godot/spine_godot/SpineEventData.h new file mode 100644 index 000000000..1cf669f26 --- /dev/null +++ b/spine-godot/spine_godot/SpineEventData.h @@ -0,0 +1,58 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEEVENTDATA_H +#define GODOT_SPINEEVENTDATA_H + +#include "core/variant_parser.h" + +#include + +class SpineEventData : public Reference { + GDCLASS(SpineEventData, Reference); + +protected: + static void _bind_methods(); + +private: + const spine::EventData *event_data; + +public: + SpineEventData(); + ~SpineEventData(); + + inline void set_spine_object(const spine::EventData *e) { + event_data = e; + } + inline const spine::EventData *get_spine_object() { + return event_data; + } +}; + +#endif//GODOT_SPINEEVENTDATA_H diff --git a/spine-godot/spine_godot/SpineIkConstraint.cpp b/spine-godot/spine_godot/SpineIkConstraint.cpp new file mode 100644 index 000000000..d88492b48 --- /dev/null +++ b/spine-godot/spine_godot/SpineIkConstraint.cpp @@ -0,0 +1,146 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineIkConstraint.h" +#include "SpineBone.h" + +void SpineIkConstraint::_bind_methods() { + // ClassDB::bind_method(D_METHOD("apply"), &SpineIkConstraint::apply); + ClassDB::bind_method(D_METHOD("update"), &SpineIkConstraint::update); + ClassDB::bind_method(D_METHOD("get_order"), &SpineIkConstraint::get_order); + ClassDB::bind_method(D_METHOD("get_data"), &SpineIkConstraint::get_data); + ClassDB::bind_method(D_METHOD("get_bones"), &SpineIkConstraint::get_bones); + ClassDB::bind_method(D_METHOD("get_target"), &SpineIkConstraint::get_target); + ClassDB::bind_method(D_METHOD("set_target", "v"), &SpineIkConstraint::set_target); + ClassDB::bind_method(D_METHOD("get_bend_direction"), &SpineIkConstraint::get_bend_direction); + ClassDB::bind_method(D_METHOD("set_bend_direction", "v"), &SpineIkConstraint::set_bend_direction); + ClassDB::bind_method(D_METHOD("get_compress"), &SpineIkConstraint::get_compress); + ClassDB::bind_method(D_METHOD("set_compress", "v"), &SpineIkConstraint::set_compress); + ClassDB::bind_method(D_METHOD("get_stretch"), &SpineIkConstraint::get_stretch); + ClassDB::bind_method(D_METHOD("set_stretch", "v"), &SpineIkConstraint::set_stretch); + ClassDB::bind_method(D_METHOD("get_mix"), &SpineIkConstraint::get_mix); + ClassDB::bind_method(D_METHOD("set_mix", "v"), &SpineIkConstraint::set_mix); + ClassDB::bind_method(D_METHOD("get_softness"), &SpineIkConstraint::get_softness); + ClassDB::bind_method(D_METHOD("set_softness", "v"), &SpineIkConstraint::set_softness); + ClassDB::bind_method(D_METHOD("is_active"), &SpineIkConstraint::is_active); + ClassDB::bind_method(D_METHOD("set_active", "v"), &SpineIkConstraint::set_active); +} + +SpineIkConstraint::SpineIkConstraint() : ik_constraint(NULL) {} +SpineIkConstraint::~SpineIkConstraint() {} + +// void SpineIkConstraint::apply(){ +// ik_constraint->apply(); +// } + +void SpineIkConstraint::update() { + ik_constraint->update(); +} + +int SpineIkConstraint::get_order() { + return ik_constraint->getOrder(); +} + +Ref SpineIkConstraint::get_data() { + auto &ikc = ik_constraint->getData(); + Ref gd_ikc(memnew(SpineIkConstraintData)); + gd_ikc->set_spine_object(&ikc); + return gd_ikc; +} + +Array SpineIkConstraint::get_bones() { + auto &bs = ik_constraint->getBones(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + auto b = bs[i]; + if (b == NULL) gd_bs[i] = Ref(NULL); + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + gd_bs[i] = gd_b; + } + return gd_bs; +} + +Ref SpineIkConstraint::get_target() { + auto b = ik_constraint->getTarget(); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + return gd_b; +} +void SpineIkConstraint::set_target(Ref v) { + if (v.is_valid()) { + ik_constraint->setTarget(v->get_spine_object()); + } else { + ik_constraint->setTarget(NULL); + } +} + +int SpineIkConstraint::get_bend_direction() { + return ik_constraint->getBendDirection(); +} +void SpineIkConstraint::set_bend_direction(int v) { + ik_constraint->setBendDirection(v); +} + +bool SpineIkConstraint::get_compress() { + return ik_constraint->getCompress(); +} +void SpineIkConstraint::set_compress(bool v) { + ik_constraint->setCompress(v); +} + +bool SpineIkConstraint::get_stretch() { + return ik_constraint->getStretch(); +} +void SpineIkConstraint::set_stretch(bool v) { + ik_constraint->setStretch(v); +} + +float SpineIkConstraint::get_mix() { + return ik_constraint->getMix(); +} +void SpineIkConstraint::set_mix(float v) { + ik_constraint->setMix(v); +} + +float SpineIkConstraint::get_softness() { + return ik_constraint->getSoftness(); +} +void SpineIkConstraint::set_softness(float v) { + ik_constraint->setSoftness(v); +} + +bool SpineIkConstraint::is_active() { + return ik_constraint->isActive(); +} +void SpineIkConstraint::set_active(bool v) { + ik_constraint->setActive(v); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineIkConstraint.h b/spine-godot/spine_godot/SpineIkConstraint.h new file mode 100644 index 000000000..c7c4aeefe --- /dev/null +++ b/spine-godot/spine_godot/SpineIkConstraint.h @@ -0,0 +1,94 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEIKCONSTRAINT_H +#define GODOT_SPINEIKCONSTRAINT_H + +#include "core/variant_parser.h" + +#include + +#include "SpineIkConstraintData.h" + +class SpineBone; + +class SpineIkConstraint : public Reference { + GDCLASS(SpineIkConstraint, Reference); + +protected: + static void _bind_methods(); + +private: + spine::IkConstraint *ik_constraint; + +public: + SpineIkConstraint(); + ~SpineIkConstraint(); + + inline void set_spine_object(spine::IkConstraint *ic) { + ik_constraint = ic; + } + inline spine::IkConstraint *get_spine_object() { + return ik_constraint; + } + + // The spine-runtime-cpp 4.0 seems to not have a apply function implementation. + // void apply(); + + void update(); + + int get_order(); + + Ref get_data(); + + Array get_bones(); + + Ref get_target(); + void set_target(Ref v); + + int get_bend_direction(); + void set_bend_direction(int v); + + bool get_compress(); + void set_compress(bool v); + + bool get_stretch(); + void set_stretch(bool v); + + float get_mix(); + void set_mix(float v); + + float get_softness(); + void set_softness(float v); + + bool is_active(); + void set_active(bool v); +}; + +#endif//GODOT_SPINEIKCONSTRAINT_H diff --git a/spine-godot/spine_godot/SpineIkConstraintData.cpp b/spine-godot/spine_godot/SpineIkConstraintData.cpp new file mode 100644 index 000000000..62731aecf --- /dev/null +++ b/spine-godot/spine_godot/SpineIkConstraintData.cpp @@ -0,0 +1,123 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineIkConstraintData.h" + +void SpineIkConstraintData::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_all_bone_data"), &SpineIkConstraintData::get_bones); + ClassDB::bind_method(D_METHOD("get_target"), &SpineIkConstraintData::get_target); + ClassDB::bind_method(D_METHOD("set_target", "v"), &SpineIkConstraintData::set_target); + ClassDB::bind_method(D_METHOD("get_bend_direction"), &SpineIkConstraintData::get_bend_direction); + ClassDB::bind_method(D_METHOD("set_bend_direction", "v"), &SpineIkConstraintData::set_bend_direction); + ClassDB::bind_method(D_METHOD("get_compress"), &SpineIkConstraintData::get_compress); + ClassDB::bind_method(D_METHOD("set_compress", "v"), &SpineIkConstraintData::set_compress); + ClassDB::bind_method(D_METHOD("get_stretch"), &SpineIkConstraintData::get_stretch); + ClassDB::bind_method(D_METHOD("set_stretch", "v"), &SpineIkConstraintData::set_stretch); + ClassDB::bind_method(D_METHOD("get_uniform"), &SpineIkConstraintData::get_uniform); + ClassDB::bind_method(D_METHOD("set_uniform", "v"), &SpineIkConstraintData::set_uniform); + ClassDB::bind_method(D_METHOD("get_mix"), &SpineIkConstraintData::get_mix); + ClassDB::bind_method(D_METHOD("set_mix", "v"), &SpineIkConstraintData::set_mix); + ClassDB::bind_method(D_METHOD("get_softness"), &SpineIkConstraintData::get_softness); + ClassDB::bind_method(D_METHOD("set_softness", "v"), &SpineIkConstraintData::set_softness); +} + +SpineIkConstraintData::SpineIkConstraintData() {} +SpineIkConstraintData::~SpineIkConstraintData() {} + +Array SpineIkConstraintData::get_bones() { + auto bs = get_spine_data()->getBones(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineBoneData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} + +Ref SpineIkConstraintData::get_target() { + auto b = get_spine_data()->getTarget(); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineBoneData)); + gd_b->set_spine_object(b); + return gd_b; +} +void SpineIkConstraintData::set_target(Ref v) { + if (v.is_valid()) { + get_spine_data()->setTarget(v->get_spine_object()); + } else { + get_spine_data()->setTarget(NULL); + } +} + +int SpineIkConstraintData::get_bend_direction() { + return get_spine_data()->getBendDirection(); +} +void SpineIkConstraintData::set_bend_direction(int v) { + get_spine_data()->setBendDirection(v); +} + +bool SpineIkConstraintData::get_compress() { + return get_spine_data()->getCompress(); +} +void SpineIkConstraintData::set_compress(bool v) { + get_spine_data()->setCompress(v); +} + +bool SpineIkConstraintData::get_stretch() { + return get_spine_data()->getStretch(); +} +void SpineIkConstraintData::set_stretch(bool v) { + get_spine_data()->setStretch(v); +} + +bool SpineIkConstraintData::get_uniform() { + return get_spine_data()->getUniform(); +} +void SpineIkConstraintData::set_uniform(bool v) { + get_spine_data()->setUniform(v); +} + +float SpineIkConstraintData::get_mix() { + return get_spine_data()->getMix(); +} +void SpineIkConstraintData::set_mix(float v) { + get_spine_data()->setMix(v); +} + +float SpineIkConstraintData::get_softness() { + return get_spine_data()->getSoftness(); +} +void SpineIkConstraintData::set_softness(float v) { + get_spine_data()->setSoftness(v); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineIkConstraintData.h b/spine-godot/spine_godot/SpineIkConstraintData.h new file mode 100644 index 000000000..da0434d0b --- /dev/null +++ b/spine-godot/spine_godot/SpineIkConstraintData.h @@ -0,0 +1,78 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEIKCONSTRAINTDATA_H +#define GODOT_SPINEIKCONSTRAINTDATA_H + +#include "core/variant_parser.h" + +#include + +#include "SpineConstraintData.h" +#include "SpineBoneData.h" + +class SpineIkConstraintData : public SpineConstraintData { + GDCLASS(SpineIkConstraintData, SpineConstraintData); + +protected: + static void _bind_methods(); + +public: + SpineIkConstraintData(); + ~SpineIkConstraintData(); + + virtual inline spine::IkConstraintData *get_spine_data() { + return (spine::IkConstraintData *) SpineConstraintData::get_spine_object(); + } + + Array get_bones(); + + Ref get_target(); + void set_target(Ref v); + + int get_bend_direction(); + void set_bend_direction(int v); + + bool get_compress(); + void set_compress(bool v); + + bool get_stretch(); + void set_stretch(bool v); + + bool get_uniform(); + void set_uniform(bool v); + + float get_mix(); + void set_mix(float v); + + float get_softness(); + void set_softness(float v); +}; + +#endif//GODOT_SPINEIKCONSTRAINTDATA_H diff --git a/spine-godot/spine_godot/SpinePathConstraint.cpp b/spine-godot/spine_godot/SpinePathConstraint.cpp new file mode 100644 index 000000000..3df032a22 --- /dev/null +++ b/spine-godot/spine_godot/SpinePathConstraint.cpp @@ -0,0 +1,145 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpinePathConstraint.h" + +void SpinePathConstraint::_bind_methods() { + // ClassDB::bind_method(D_METHOD("apply"), &SpinePathConstraint::apply); + ClassDB::bind_method(D_METHOD("update"), &SpinePathConstraint::update); + ClassDB::bind_method(D_METHOD("get_order"), &SpinePathConstraint::get_order); + ClassDB::bind_method(D_METHOD("get_position"), &SpinePathConstraint::get_position); + ClassDB::bind_method(D_METHOD("set_position", "v"), &SpinePathConstraint::set_position); + ClassDB::bind_method(D_METHOD("get_spacing"), &SpinePathConstraint::get_spacing); + ClassDB::bind_method(D_METHOD("set_spacing", "v"), &SpinePathConstraint::set_spacing); + ClassDB::bind_method(D_METHOD("get_mix_rotate"), &SpinePathConstraint::get_mix_rotate); + ClassDB::bind_method(D_METHOD("set_mix_rotate", "v"), &SpinePathConstraint::set_mix_rotate); + ClassDB::bind_method(D_METHOD("get_mix_x"), &SpinePathConstraint::get_mix_x); + ClassDB::bind_method(D_METHOD("set_mix_x", "v"), &SpinePathConstraint::set_mix_x); + ClassDB::bind_method(D_METHOD("get_mix_y"), &SpinePathConstraint::get_mix_y); + ClassDB::bind_method(D_METHOD("set_mix_y", "v"), &SpinePathConstraint::set_mix_y); + ClassDB::bind_method(D_METHOD("get_bones"), &SpinePathConstraint::get_bones); + ClassDB::bind_method(D_METHOD("get_target"), &SpinePathConstraint::get_target); + ClassDB::bind_method(D_METHOD("set_target", "v"), &SpinePathConstraint::set_target); + ClassDB::bind_method(D_METHOD("get_data"), &SpinePathConstraint::get_data); + ClassDB::bind_method(D_METHOD("is_active"), &SpinePathConstraint::is_active); + ClassDB::bind_method(D_METHOD("set_active", "v"), &SpinePathConstraint::set_active); +} + +SpinePathConstraint::SpinePathConstraint() : path_constraint(NULL) {} +SpinePathConstraint::~SpinePathConstraint() {} + +// void SpinePathConstraint::apply(){ +// path_constraint->apply(); +// } + +void SpinePathConstraint::update() { + path_constraint->update(); +} + +int SpinePathConstraint::get_order() { + return path_constraint->getOrder(); +} + +float SpinePathConstraint::get_position() { + return path_constraint->getPosition(); +} +void SpinePathConstraint::set_position(float v) { + path_constraint->setPosition(v); +} + +float SpinePathConstraint::get_spacing() { + return path_constraint->getSpacing(); +} +void SpinePathConstraint::set_spacing(float v) { + path_constraint->setSpacing(v); +} + +float SpinePathConstraint::get_mix_rotate() { + return path_constraint->getMixRotate(); +} +void SpinePathConstraint::set_mix_rotate(float v) { + path_constraint->setMixRotate(v); +} + +float SpinePathConstraint::get_mix_x() { + return path_constraint->getMixX(); +} +void SpinePathConstraint::set_mix_x(float v) { + path_constraint->setMixX(v); +} + +float SpinePathConstraint::get_mix_y() { + return path_constraint->getMixY(); +} +void SpinePathConstraint::set_mix_y(float v) { + path_constraint->setMixY(v); +} + +Array SpinePathConstraint::get_bones() { + auto &bs = path_constraint->getBones(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + auto b = bs[i]; + if (b == NULL) gd_bs[i] = Ref(NULL); + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + gd_bs[i] = gd_b; + } + return gd_bs; +} + +Ref SpinePathConstraint::get_target() { + auto s = path_constraint->getTarget(); + if (s == NULL) return NULL; + Ref gd_s(memnew(SpineSlot)); + gd_s->set_spine_object(s); + return gd_s; +} +void SpinePathConstraint::set_target(Ref v) { + if (v.is_valid()) { + path_constraint->setTarget(v->get_spine_object()); + } else { + path_constraint->setTarget(NULL); + } +} + +Ref SpinePathConstraint::get_data() { + auto &sd = path_constraint->getData(); + Ref gd_sd(memnew(SpinePathConstraintData)); + gd_sd->set_spine_object(&sd); + return gd_sd; +} + +bool SpinePathConstraint::is_active() { + return path_constraint->isActive(); +} +void SpinePathConstraint::set_active(bool v) { + path_constraint->setActive(v); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpinePathConstraint.h b/spine-godot/spine_godot/SpinePathConstraint.h new file mode 100644 index 000000000..dcd41d09e --- /dev/null +++ b/spine-godot/spine_godot/SpinePathConstraint.h @@ -0,0 +1,94 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEPATHCONSTRAINT_H +#define GODOT_SPINEPATHCONSTRAINT_H + +#include "core/variant_parser.h" + +#include + +#include "SpineBone.h" +#include "SpineSlot.h" +#include "SpinePathConstraintData.h" + +class SpinePathConstraint : public Reference { + GDCLASS(SpinePathConstraint, Reference); + +protected: + static void _bind_methods(); + +private: + spine::PathConstraint *path_constraint; + +public: + SpinePathConstraint(); + ~SpinePathConstraint(); + + inline void set_spine_object(spine::PathConstraint *pc) { + path_constraint = pc; + } + inline spine::PathConstraint *get_spine_object() { + return path_constraint; + } + + // The spine-runtime-cpp 4.0 seems to not have a apply function implementation. + // void apply(); + + void update(); + + int get_order(); + + float get_position(); + void set_position(float v); + + float get_spacing(); + void set_spacing(float v); + + float get_mix_rotate(); + void set_mix_rotate(float v); + + float get_mix_x(); + void set_mix_x(float v); + + float get_mix_y(); + void set_mix_y(float v); + + Array get_bones(); + + Ref get_target(); + void set_target(Ref v); + + Ref get_data(); + + bool is_active(); + void set_active(bool v); +}; + +#endif//GODOT_SPINEPATHCONSTRAINT_H diff --git a/spine-godot/spine_godot/SpinePathConstraintData.cpp b/spine-godot/spine_godot/SpinePathConstraintData.cpp new file mode 100644 index 000000000..5d0f34b64 --- /dev/null +++ b/spine-godot/spine_godot/SpinePathConstraintData.cpp @@ -0,0 +1,168 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpinePathConstraintData.h" + + +void SpinePathConstraintData::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_all_bone_data"), &SpinePathConstraintData::get_bones); + ClassDB::bind_method(D_METHOD("get_target"), &SpinePathConstraintData::get_target); + ClassDB::bind_method(D_METHOD("set_target", "V"), &SpinePathConstraintData::set_target); + ClassDB::bind_method(D_METHOD("get_position_mode"), &SpinePathConstraintData::get_position_mode); + ClassDB::bind_method(D_METHOD("set_position_mode", "V"), &SpinePathConstraintData::set_position_mode); + ClassDB::bind_method(D_METHOD("get_spacing_mode"), &SpinePathConstraintData::get_spacing_mode); + ClassDB::bind_method(D_METHOD("set_spacing_mode", "V"), &SpinePathConstraintData::set_spacing_mode); + ClassDB::bind_method(D_METHOD("get_rotate_mode"), &SpinePathConstraintData::get_rotate_mode); + ClassDB::bind_method(D_METHOD("set_rotate_mode", "V"), &SpinePathConstraintData::set_rotate_mode); + ClassDB::bind_method(D_METHOD("get_offset_rotation"), &SpinePathConstraintData::get_offset_rotation); + ClassDB::bind_method(D_METHOD("set_offset_rotation", "V"), &SpinePathConstraintData::set_offset_rotation); + ClassDB::bind_method(D_METHOD("get_position"), &SpinePathConstraintData::get_position); + ClassDB::bind_method(D_METHOD("set_position", "V"), &SpinePathConstraintData::set_position); + ClassDB::bind_method(D_METHOD("get_spacing"), &SpinePathConstraintData::get_spacing); + ClassDB::bind_method(D_METHOD("set_spacing", "V"), &SpinePathConstraintData::set_spacing); + ClassDB::bind_method(D_METHOD("get_mix_rotate"), &SpinePathConstraintData::get_mix_rotate); + ClassDB::bind_method(D_METHOD("set_mix_rotate", "V"), &SpinePathConstraintData::set_mix_rotate); + ClassDB::bind_method(D_METHOD("get_mix_x"), &SpinePathConstraintData::get_mix_x); + ClassDB::bind_method(D_METHOD("set_mix_x", "V"), &SpinePathConstraintData::set_mix_x); + ClassDB::bind_method(D_METHOD("get_mix_y"), &SpinePathConstraintData::get_mix_y); + ClassDB::bind_method(D_METHOD("set_mix_y", "V"), &SpinePathConstraintData::set_mix_y); + + BIND_ENUM_CONSTANT(POSITIONMODE_FIXED); + BIND_ENUM_CONSTANT(POSITIONMODE_PERCENT); + + BIND_ENUM_CONSTANT(SPACINGMODE_LENGTH); + BIND_ENUM_CONSTANT(SPACINGMODE_FIXED); + BIND_ENUM_CONSTANT(SPACINGMODE_PERCENT); + + BIND_ENUM_CONSTANT(ROTATEMODE_TANGENT); + BIND_ENUM_CONSTANT(ROTATEMODE_CHAIN); + BIND_ENUM_CONSTANT(ROTATEMODE_CHAINSCALE); +} + +SpinePathConstraintData::SpinePathConstraintData() {} +SpinePathConstraintData::~SpinePathConstraintData() {} + +Array SpinePathConstraintData::get_bones() { + auto bs = get_spine_data()->getBones(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineBoneData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} + +Ref SpinePathConstraintData::get_target() { + auto s = get_spine_data()->getTarget(); + if (s == NULL) return NULL; + Ref gd_s(memnew(SpineSlotData)); + gd_s->set_spine_object(s); + return gd_s; +} +void SpinePathConstraintData::set_target(Ref v) { + if (v.is_valid()) { + get_spine_data()->setTarget(v->get_spine_object()); + } else { + get_spine_data()->setTarget(NULL); + } +} + +SpinePathConstraintData::PositionMode SpinePathConstraintData::get_position_mode() { + auto m = (int) get_spine_data()->getPositionMode(); + return (PositionMode) m; +} +void SpinePathConstraintData::set_position_mode(PositionMode v) { + auto m = (int) v; + get_spine_data()->setPositionMode((spine::PositionMode) m); +} + +SpinePathConstraintData::SpacingMode SpinePathConstraintData::get_spacing_mode() { + auto m = (int) get_spine_data()->getSpacingMode(); + return (SpacingMode) m; +} +void SpinePathConstraintData::set_spacing_mode(SpacingMode v) { + auto m = (int) v; + get_spine_data()->setSpacingMode((spine::SpacingMode) m); +} + +SpinePathConstraintData::RotateMode SpinePathConstraintData::get_rotate_mode() { + auto m = (int) get_spine_data()->getRotateMode(); + return (RotateMode) m; +} +void SpinePathConstraintData::set_rotate_mode(RotateMode v) { + auto m = (int) v; + get_spine_data()->setRotateMode((spine::RotateMode) m); +} + +float SpinePathConstraintData::get_offset_rotation() { + return get_spine_data()->getOffsetRotation(); +} +void SpinePathConstraintData::set_offset_rotation(float v) { + get_spine_data()->setOffsetRotation(v); +} + +float SpinePathConstraintData::get_position() { + return get_spine_data()->getPosition(); +} +void SpinePathConstraintData::set_position(float v) { + get_spine_data()->setPosition(v); +} + +float SpinePathConstraintData::get_spacing() { + return get_spine_data()->getSpacing(); +} +void SpinePathConstraintData::set_spacing(float v) { + get_spine_data()->setSpacing(v); +} + +float SpinePathConstraintData::get_mix_rotate() { + return get_spine_data()->getMixRotate(); +} +void SpinePathConstraintData::set_mix_rotate(float v) { + get_spine_data()->setMixRotate(v); +} + +float SpinePathConstraintData::get_mix_x() { + return get_spine_data()->getMixX(); +} +void SpinePathConstraintData::set_mix_x(float v) { + get_spine_data()->setMixX(v); +} + +float SpinePathConstraintData::get_mix_y() { + return get_spine_data()->getMixY(); +} +void SpinePathConstraintData::set_mix_y(float v) { + get_spine_data()->setMixY(v); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpinePathConstraintData.h b/spine-godot/spine_godot/SpinePathConstraintData.h new file mode 100644 index 000000000..068a68ec0 --- /dev/null +++ b/spine-godot/spine_godot/SpinePathConstraintData.h @@ -0,0 +1,108 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINEPATHCONSTRAINTDATA_H +#define GODOT_SPINEPATHCONSTRAINTDATA_H + +#include "core/variant_parser.h" + +#include + +#include "SpineConstraintData.h" +#include "SpineBoneData.h" +#include "SpineSlotData.h" + +class SpinePathConstraintData : public SpineConstraintData { + GDCLASS(SpinePathConstraintData, SpineConstraintData); + +protected: + static void _bind_methods(); + +public: + SpinePathConstraintData(); + ~SpinePathConstraintData(); + + virtual inline spine::PathConstraintData *get_spine_data() { + return (spine::PathConstraintData *) SpineConstraintData::get_spine_object(); + } + + enum PositionMode { + POSITIONMODE_FIXED = 0, + POSITIONMODE_PERCENT + }; + + enum SpacingMode { + SPACINGMODE_LENGTH = 0, + SPACINGMODE_FIXED, + SPACINGMODE_PERCENT + }; + + enum RotateMode { + ROTATEMODE_TANGENT = 0, + ROTATEMODE_CHAIN, + ROTATEMODE_CHAINSCALE + }; + + Array get_bones(); + + Ref get_target(); + void set_target(Ref v); + + PositionMode get_position_mode(); + void set_position_mode(PositionMode v); + + SpacingMode get_spacing_mode(); + void set_spacing_mode(SpacingMode v); + + RotateMode get_rotate_mode(); + void set_rotate_mode(RotateMode v); + + float get_offset_rotation(); + void set_offset_rotation(float v); + + float get_position(); + void set_position(float v); + + float get_spacing(); + void set_spacing(float v); + + float get_mix_rotate(); + void set_mix_rotate(float v); + + float get_mix_x(); + void set_mix_x(float v); + + float get_mix_y(); + void set_mix_y(float v); +}; + +VARIANT_ENUM_CAST(SpinePathConstraintData::PositionMode); +VARIANT_ENUM_CAST(SpinePathConstraintData::SpacingMode); +VARIANT_ENUM_CAST(SpinePathConstraintData::RotateMode); +#endif//GODOT_SPINEPATHCONSTRAINTDATA_H diff --git a/spine-godot/spine_godot/SpineRendererObject.h b/spine-godot/spine_godot/SpineRendererObject.h new file mode 100644 index 000000000..11b9370a9 --- /dev/null +++ b/spine-godot/spine_godot/SpineRendererObject.h @@ -0,0 +1,41 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINERENDEREROBJECT_H +#define GODOT_SPINERENDEREROBJECT_H + +#include + +struct SpineRendererObject { + Ref texture; + Ref normal_map; +}; + + +#endif diff --git a/spine-godot/spine_godot/SpineRuntimeEditorPlugin.cpp b/spine-godot/spine_godot/SpineRuntimeEditorPlugin.cpp new file mode 100644 index 000000000..80de73af7 --- /dev/null +++ b/spine-godot/spine_godot/SpineRuntimeEditorPlugin.cpp @@ -0,0 +1,99 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifdef TOOLS_ENABLED +#include "SpineRuntimeEditorPlugin.h" + +#include "SpineAtlasResource.h" +#include "SpineSkeletonJsonDataResource.h" +#include "SpineSpriteAnimateDialog.h" + +#include "SpineSprite.h" + +Error SpineAtlasResourceImportPlugin::import(const String &p_source_file, const String &p_save_path, const Map &p_options, List *r_platform_variants, List *r_gen_files, Variant *r_metadata) { + Ref res(memnew(SpineAtlasResource)); + res->set_normal_texture_prefix(p_options["normal_texture_prefix"]); + res->load_from_atlas_file(p_source_file); + + String file_name = vformat("%s.%s", p_save_path, get_save_extension()); + auto err = ResourceSaver::save(file_name, res); + return err; +} + +void SpineAtlasResourceImportPlugin::get_import_options(List *r_options, int p_preset) const { + if (p_preset == 0) { + ImportOption op; + op.option.name = "normal_texture_prefix"; + op.option.type = Variant::STRING; + op.option.hint_string = "String"; + op.default_value = String("n"); + r_options->push_back(op); + } +} + +Error SpineJsonResourceImportPlugin::import(const String &p_source_file, const String &p_save_path, const Map &p_options, List *r_platform_variants, List *r_gen_files, Variant *r_metadata) { + Ref res(memnew(SpineSkeletonJsonDataResource)); + res->load_from_file(p_source_file); + + String file_name = vformat("%s.%s", p_save_path, get_save_extension()); + auto err = ResourceSaver::save(file_name, res); + return err; +} + +//=======================| SpineRuntimeEditorPlugin |============================ +SpineRuntimeEditorPlugin::SpineRuntimeEditorPlugin(EditorNode *p_node) { + add_import_plugin(memnew(SpineAtlasResourceImportPlugin)); + add_import_plugin(memnew(SpineJsonResourceImportPlugin)); + + auto animate_button = memnew(ToolButton); + animate_button->set_text("Animate"); + add_control_to_container(CONTAINER_CANVAS_EDITOR_MENU, animate_button); + + animate_dialog = memnew(SpineSpriteAnimateDialog); + get_editor_interface()->get_base_control()->add_child(animate_dialog); + animate_dialog->set_animate_button(animate_button); + animate_dialog->set_plugin(this); +} + +SpineRuntimeEditorPlugin::~SpineRuntimeEditorPlugin() { +} + +bool SpineRuntimeEditorPlugin::handles(Object *p_object) const { + return p_object->is_class("SpineSprite"); +} + +void SpineRuntimeEditorPlugin::make_visible(bool p_visible) { + if (get_editor_interface()->get_selection()->get_selected_node_list().size() != 1) { + p_visible = false; + } + animate_dialog->get_animate_button()->set_visible(p_visible); +} + + +#endif \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineRuntimeEditorPlugin.h b/spine-godot/spine_godot/SpineRuntimeEditorPlugin.h new file mode 100644 index 000000000..cf95ec696 --- /dev/null +++ b/spine-godot/spine_godot/SpineRuntimeEditorPlugin.h @@ -0,0 +1,98 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINERUNTIMEEDITORPLUGIN_H +#define GODOT_SPINERUNTIMEEDITORPLUGIN_H + +#ifdef TOOLS_ENABLED +#include "editor/editor_node.h" + +class SpineAtlasResourceImportPlugin : public EditorImportPlugin { + GDCLASS(SpineAtlasResourceImportPlugin, EditorImportPlugin); + +public: + String get_importer_name() const override { return "spine.atlas"; } + String get_visible_name() const override { return "Spine Runtime Atlas"; } + void get_recognized_extensions(List *p_extensions) const override { p_extensions->push_back("atlas"); } + String get_preset_name(int p_idx) const override { + if (p_idx == 0) return "Default"; + else + return "Unknown"; + } + int get_preset_count() const override { return 1; } + String get_save_extension() const override { return "spatlas"; } + String get_resource_type() const override { return "SpineAtlasResource"; } + void get_import_options(List *r_options, int p_preset) const override; + bool get_option_visibility(const String &p_option, const Map &p_options) const override { return true; } + Error import(const String &p_source_file, const String &p_save_path, const Map &p_options, List *r_platform_variants, List *r_gen_files, Variant *r_metadata) override; +}; + +class SpineJsonResourceImportPlugin : public EditorImportPlugin { + GDCLASS(SpineJsonResourceImportPlugin, EditorImportPlugin); + +public: + String get_importer_name() const override { return "spine.json"; } + String get_visible_name() const override { return "Spine Runtime Json"; } + void get_recognized_extensions(List *p_extensions) const override { p_extensions->push_back("json"); } + String get_preset_name(int p_idx) const override { + if (p_idx == 0) return "Default"; + else + return "Unknown"; + } + int get_preset_count() const override { return 1; } + String get_save_extension() const override { return "spjson"; } + String get_resource_type() const override { return "SpineSkeletonJsonDataResource"; } + void get_import_options(List *r_options, int p_preset) const override {} + bool get_option_visibility(const String &p_option, const Map &p_options) const override { return true; } + Error import(const String &p_source_file, const String &p_save_path, const Map &p_options, List *r_platform_variants, List *r_gen_files, Variant *r_metadata) override; +}; + +class SpineSpriteAnimateDialog; + +class SpineRuntimeEditorPlugin : public EditorPlugin { + GDCLASS(SpineRuntimeEditorPlugin, EditorPlugin); + +protected: + SpineSpriteAnimateDialog *animate_dialog; + +public: + SpineRuntimeEditorPlugin(EditorNode *p_node); + ~SpineRuntimeEditorPlugin(); + + String get_name() const override { return "SpineRuntimeEditorPlugin"; } + bool has_main_screen() const { return false; } + + bool handles(Object *p_object) const override; + void make_visible(bool p_visible) override; + + void _on_animate_button_pressed(); +}; +#endif + +#endif//GODOT_SPINERUNTIMEEDITORPLUGIN_H diff --git a/spine-godot/spine_godot/SpineSkeleton.cpp b/spine-godot/spine_godot/SpineSkeleton.cpp new file mode 100644 index 000000000..2f3d1fd2b --- /dev/null +++ b/spine-godot/spine_godot/SpineSkeleton.cpp @@ -0,0 +1,413 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSkeleton.h" + +void SpineSkeleton::_bind_methods() { + //void update_world_transform(); + // + // void set_to_setup_pose(); + // + // void set_bones_to_setup_pose(); + // + // void set_slots_to_setup_pose(); + ClassDB::bind_method(D_METHOD("update_world_transform"), &SpineSkeleton::update_world_transform); + ClassDB::bind_method(D_METHOD("set_to_setup_pose"), &SpineSkeleton::set_to_setup_pose); + ClassDB::bind_method(D_METHOD("set_bones_to_setup_pose"), &SpineSkeleton::set_bones_to_setup_pose); + ClassDB::bind_method(D_METHOD("set_slots_to_setup_pose"), &SpineSkeleton::set_slots_to_setup_pose); + // + // Ref find_bone(const String &name); + // int find_bone_index(const String &name); + // + // Ref find_slot(const String &name); + // int find_slot_index(const String &name); + // + // void set_skin_by_name(const String &skin_name); + // void set_skin(Ref new_skin); + // + // Ref get_attachment_by_slot_name(const String &slot_name, const String &attachment_name); + // Ref get_attachment_by_slot_index(int slot_index, const String &attachment_name); + ClassDB::bind_method(D_METHOD("find_bone", "bone_name"), &SpineSkeleton::find_bone); + ClassDB::bind_method(D_METHOD("find_slot", "slot_name"), &SpineSkeleton::find_slot); + ClassDB::bind_method(D_METHOD("set_skin_by_name", "skin_name"), &SpineSkeleton::set_skin_by_name); + ClassDB::bind_method(D_METHOD("set_skin", "new_skin"), &SpineSkeleton::set_skin); + ClassDB::bind_method(D_METHOD("get_attachment_by_slot_name", "slot_name", "attachment_name"), &SpineSkeleton::get_attachment_by_slot_name); + ClassDB::bind_method(D_METHOD("get_attachment_by_slot_index", "slot_index", "attachment_name"), &SpineSkeleton::get_attachment_by_slot_index); + // + // void set_attachment(const String &slot_name, const String &attachment_name); + // + // Ref find_ik_constraint(const String &constraint_name); + // Ref find_transform_constraint(const String &constraint_name); + // Ref find_path_constraint(const String &constraint_name); + // + // void update(float delta); + // + // Dictionary get_bounds(); + // + // Ref get_root_bone(); + // + // Ref get_data(); + ClassDB::bind_method(D_METHOD("set_attachment", "slot_name", "attachment_name"), &SpineSkeleton::set_attachment); + ClassDB::bind_method(D_METHOD("find_ik_constraint", "constraint_name"), &SpineSkeleton::find_ik_constraint); + ClassDB::bind_method(D_METHOD("find_transform_constraint", "constraint_name"), &SpineSkeleton::find_transform_constraint); + ClassDB::bind_method(D_METHOD("find_path_constraint", "constraint_name"), &SpineSkeleton::find_path_constraint); + ClassDB::bind_method(D_METHOD("get_bounds"), &SpineSkeleton::get_bounds); + ClassDB::bind_method(D_METHOD("get_root_bone"), &SpineSkeleton::get_root_bone); + ClassDB::bind_method(D_METHOD("get_data"), &SpineSkeleton::get_data); + // + // Array get_bones(); + // Array get_slots(); + // Array get_draw_orders(); + // Array get_ik_constraints(); + // Array get_path_constraints(); + // Array get_transform_constraints(); + // + // Ref get_skin(); + ClassDB::bind_method(D_METHOD("get_bones"), &SpineSkeleton::get_bones); + ClassDB::bind_method(D_METHOD("get_slots"), &SpineSkeleton::get_slots); + ClassDB::bind_method(D_METHOD("get_draw_orders"), &SpineSkeleton::get_draw_orders); + ClassDB::bind_method(D_METHOD("get_ik_constraints"), &SpineSkeleton::get_ik_constraints); + ClassDB::bind_method(D_METHOD("get_path_constraints"), &SpineSkeleton::get_path_constraints); + ClassDB::bind_method(D_METHOD("get_transform_constraints"), &SpineSkeleton::get_transform_constraints); + ClassDB::bind_method(D_METHOD("get_skin"), &SpineSkeleton::get_skin); + // + // Color get_color(); + // void set_color(Color v); + // + // float get_time(); + // void set_time(float v); + // + // void set_position(Vector2 pos); + ClassDB::bind_method(D_METHOD("get_color"), &SpineSkeleton::get_color); + ClassDB::bind_method(D_METHOD("set_color", "v"), &SpineSkeleton::set_color); + ClassDB::bind_method(D_METHOD("set_position", "pos"), &SpineSkeleton::set_position); + // + // float get_x(); + // void set_x(float v); + // + // float get_y(); + // void set_y(float v); + // + // float get_scale_x(); + // void set_scale_x(float v); + // + // float get_scale_y(); + // void set_scale_y(float v); + ClassDB::bind_method(D_METHOD("get_x"), &SpineSkeleton::get_x); + ClassDB::bind_method(D_METHOD("set_x", "v"), &SpineSkeleton::set_x); + ClassDB::bind_method(D_METHOD("get_y"), &SpineSkeleton::get_y); + ClassDB::bind_method(D_METHOD("set_y", "v"), &SpineSkeleton::set_y); + ClassDB::bind_method(D_METHOD("get_scale_x"), &SpineSkeleton::get_scale_x); + ClassDB::bind_method(D_METHOD("set_scale_x", "v"), &SpineSkeleton::set_scale_x); + ClassDB::bind_method(D_METHOD("get_scale_y"), &SpineSkeleton::get_scale_y); + ClassDB::bind_method(D_METHOD("set_scale_y", "v"), &SpineSkeleton::set_scale_y); +} + +SpineSkeleton::SpineSkeleton() : skeleton(NULL), spine_object(false), the_sprite(nullptr) { +} + +SpineSkeleton::~SpineSkeleton() { + if (skeleton && !spine_object) { + delete skeleton; + skeleton = NULL; + } +} + +void SpineSkeleton::load_skeleton(Ref sd) { + if (skeleton && !spine_object) { + delete skeleton; + skeleton = NULL; + } + skeleton = new spine::Skeleton(sd->get_skeleton_data()); + spine_object = false; +} + +#define S_T(x) (spine::String(x.utf8())) +void SpineSkeleton::update_world_transform() { + skeleton->updateWorldTransform(); +} + +void SpineSkeleton::set_to_setup_pose() { + skeleton->setToSetupPose(); +} + +void SpineSkeleton::set_bones_to_setup_pose() { + skeleton->setBonesToSetupPose(); +} + +void SpineSkeleton::set_slots_to_setup_pose() { + skeleton->setSlotsToSetupPose(); +} + +Ref SpineSkeleton::find_bone(const String &name) { + if (name.empty()) return NULL; + auto b = skeleton->findBone(S_T(name)); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + gd_b->set_spine_sprite(the_sprite); + return gd_b; +} + +Ref SpineSkeleton::find_slot(const String &name) { + if (name.empty()) return NULL; + auto s = skeleton->findSlot(S_T(name)); + if (s == NULL) return NULL; + Ref gd_s(memnew(SpineSlot)); + gd_s->set_spine_object(s); + return gd_s; +} + +void SpineSkeleton::set_skin_by_name(const String &skin_name) { + skeleton->setSkin(S_T(skin_name)); +} +void SpineSkeleton::set_skin(Ref new_skin) { + if (new_skin.is_valid()) { + skeleton->setSkin(new_skin->get_spine_object()); + } else { + skeleton->setSkin(NULL); + } +} + +Ref SpineSkeleton::get_attachment_by_slot_name(const String &slot_name, const String &attachment_name) { + auto a = skeleton->getAttachment(S_T(slot_name), S_T(attachment_name)); + if (a == NULL) return NULL; + Ref gd_a(memnew(SpineAttachment)); + gd_a->set_spine_object(a); + return gd_a; +} +Ref SpineSkeleton::get_attachment_by_slot_index(int slot_index, const String &attachment_name) { + auto a = skeleton->getAttachment(slot_index, S_T(attachment_name)); + if (a == NULL) return NULL; + Ref gd_a(memnew(SpineAttachment)); + gd_a->set_spine_object(a); + return gd_a; +} + +void SpineSkeleton::set_attachment(const String &slot_name, const String &attachment_name) { + ERR_FAIL_COND(slot_name.empty()); + ERR_FAIL_COND(get_attachment_by_slot_name(slot_name, attachment_name) == NULL); + skeleton->setAttachment(S_T(slot_name), S_T(attachment_name)); +} + +Ref SpineSkeleton::find_ik_constraint(const String &constraint_name) { + if (constraint_name.empty()) return NULL; + auto c = skeleton->findIkConstraint(S_T(constraint_name)); + if (c == NULL) return NULL; + Ref gd_c(memnew(SpineIkConstraint)); + gd_c->set_spine_object(c); + return gd_c; +} +Ref SpineSkeleton::find_transform_constraint(const String &constraint_name) { + if (constraint_name.empty()) return NULL; + auto c = skeleton->findTransformConstraint(S_T(constraint_name)); + if (c == NULL) return NULL; + Ref gd_c(memnew(SpineTransformConstraint)); + gd_c->set_spine_object(c); + return gd_c; +} +Ref SpineSkeleton::find_path_constraint(const String &constraint_name) { + if (constraint_name.empty()) return NULL; + auto c = skeleton->findPathConstraint(S_T(constraint_name)); + if (c == NULL) return NULL; + Ref gd_c(memnew(SpinePathConstraint)); + gd_c->set_spine_object(c); + return gd_c; +} + +Dictionary SpineSkeleton::get_bounds() { + float x, y, w, h; + spine::Vector vertex_buffer; + skeleton->getBounds(x, y, w, h, vertex_buffer); + + Dictionary res; + res["x"] = x; + res["y"] = y; + res["w"] = w; + res["h"] = h; + + Array gd_a; + gd_a.resize(vertex_buffer.size()); + for (size_t i = 0; i < gd_a.size(); ++i) { + gd_a[i] = vertex_buffer[i]; + } + res["vertex_buffer"] = gd_a; + + return res; +} + +Ref SpineSkeleton::get_root_bone() { + auto b = skeleton->getRootBone(); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + gd_b->set_spine_sprite(the_sprite); + return gd_b; +} + +Ref SpineSkeleton::get_data() const { + auto sd = skeleton->getData(); + if (sd == NULL) return NULL; + Ref gd_sd(memnew(SpineSkeletonDataResource)); + gd_sd->set_spine_object(sd); + return gd_sd; +} + +Array SpineSkeleton::get_bones() { + auto &as = skeleton->getBones(); + Array gd_as; + gd_as.resize(as.size()); + for (size_t i = 0; i < gd_as.size(); ++i) { + auto b = as[i]; + if (b == NULL) gd_as[i] = Ref(NULL); + Ref gd_a(memnew(SpineBone)); + gd_a->set_spine_object(b); + gd_a->set_spine_sprite(the_sprite); + gd_as[i] = gd_a; + } + return gd_as; +} +Array SpineSkeleton::get_slots() { + auto &as = skeleton->getSlots(); + Array gd_as; + gd_as.resize(as.size()); + for (size_t i = 0; i < gd_as.size(); ++i) { + auto b = as[i]; + if (b == NULL) gd_as[i] = Ref(NULL); + Ref gd_a(memnew(SpineSlot)); + gd_a->set_spine_object(b); + gd_as[i] = gd_a; + } + return gd_as; +} +Array SpineSkeleton::get_draw_orders() { + auto &as = skeleton->getDrawOrder(); + Array gd_as; + gd_as.resize(as.size()); + for (size_t i = 0; i < gd_as.size(); ++i) { + auto b = as[i]; + if (b == NULL) gd_as[i] = Ref(NULL); + Ref gd_a(memnew(SpineSlot)); + gd_a->set_spine_object(b); + gd_as[i] = gd_a; + } + return gd_as; +} +Array SpineSkeleton::get_ik_constraints() { + auto &as = skeleton->getIkConstraints(); + Array gd_as; + gd_as.resize(as.size()); + for (size_t i = 0; i < gd_as.size(); ++i) { + auto b = as[i]; + if (b == NULL) gd_as[i] = Ref(NULL); + Ref gd_a(memnew(SpineIkConstraint)); + gd_a->set_spine_object(b); + gd_as[i] = gd_a; + } + return gd_as; +} +Array SpineSkeleton::get_path_constraints() { + auto &as = skeleton->getPathConstraints(); + Array gd_as; + gd_as.resize(as.size()); + for (size_t i = 0; i < gd_as.size(); ++i) { + auto b = as[i]; + if (b == NULL) gd_as[i] = Ref(NULL); + Ref gd_a(memnew(SpinePathConstraint)); + gd_a->set_spine_object(b); + gd_as[i] = gd_a; + } + return gd_as; +} +Array SpineSkeleton::get_transform_constraints() { + auto &as = skeleton->getTransformConstraints(); + Array gd_as; + gd_as.resize(as.size()); + for (size_t i = 0; i < gd_as.size(); ++i) { + auto b = as[i]; + if (b == NULL) gd_as[i] = Ref(NULL); + Ref gd_a(memnew(SpineTransformConstraint)); + gd_a->set_spine_object(b); + gd_as[i] = gd_a; + } + return gd_as; +} + +Ref SpineSkeleton::get_skin() { + auto s = skeleton->getSkin(); + if (s == NULL) return NULL; + Ref gd_s(memnew(SpineSkin)); + gd_s->set_spine_object(s); + return gd_s; +} + +Color SpineSkeleton::get_color() { + auto &c = skeleton->getColor(); + return Color(c.r, c.g, c.b, c.a); +} +void SpineSkeleton::set_color(Color v) { + auto &c = skeleton->getColor(); + c.set(v.r, v.g, v.b, v.a); +} + +void SpineSkeleton::set_position(Vector2 pos) { + skeleton->setPosition(pos.x, pos.y); +} + +float SpineSkeleton::get_x() { + return skeleton->getX(); +} +void SpineSkeleton::set_x(float v) { + skeleton->setX(v); +} + +float SpineSkeleton::get_y() { + return skeleton->getY(); +} +void SpineSkeleton::set_y(float v) { + skeleton->setY(v); +} + +float SpineSkeleton::get_scale_x() { + return skeleton->getScaleX(); +} +void SpineSkeleton::set_scale_x(float v) { + skeleton->setScaleX(v); +} + +float SpineSkeleton::get_scale_y() { + return skeleton->getScaleY(); +} +void SpineSkeleton::set_scale_y(float v) { + skeleton->setScaleY(v); +} + +void SpineSkeleton::set_spine_sprite(SpineSprite *s) { + the_sprite = s; +} diff --git a/spine-godot/spine_godot/SpineSkeleton.h b/spine-godot/spine_godot/SpineSkeleton.h new file mode 100644 index 000000000..942665c6a --- /dev/null +++ b/spine-godot/spine_godot/SpineSkeleton.h @@ -0,0 +1,129 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESKELETON_H +#define GODOT_SPINESKELETON_H + +#include "core/variant_parser.h" + +#include + +#include "SpineSkeletonDataResource.h" +#include "SpineBone.h" +#include "SpineSlot.h" + +class SpineSprite; + +class SpineSkeleton : public Reference { + GDCLASS(SpineSkeleton, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Skeleton *skeleton; + bool spine_object; + + SpineSprite *the_sprite; + +public: + SpineSkeleton(); + ~SpineSkeleton(); + + void load_skeleton(Ref sd); + + inline void set_spine_object(spine::Skeleton *s) { + skeleton = s; + spine_object = true; + } + inline spine::Skeleton *get_spine_object() { + return skeleton; + } + + void set_spine_sprite(SpineSprite *s); + + + void update_world_transform(); + + void set_to_setup_pose(); + + void set_bones_to_setup_pose(); + + void set_slots_to_setup_pose(); + + Ref find_bone(const String &name); + + Ref find_slot(const String &name); + + void set_skin_by_name(const String &skin_name); + void set_skin(Ref new_skin); + + Ref get_attachment_by_slot_name(const String &slot_name, const String &attachment_name); + Ref get_attachment_by_slot_index(int slot_index, const String &attachment_name); + + void set_attachment(const String &slot_name, const String &attachment_name); + + Ref find_ik_constraint(const String &constraint_name); + Ref find_transform_constraint(const String &constraint_name); + Ref find_path_constraint(const String &constraint_name); + + Dictionary get_bounds(); + + Ref get_root_bone(); + + Ref get_data() const; + + Array get_bones(); + Array get_slots(); + Array get_draw_orders(); + Array get_ik_constraints(); + Array get_path_constraints(); + Array get_transform_constraints(); + + Ref get_skin(); + + Color get_color(); + void set_color(Color v); + + void set_position(Vector2 pos); + + float get_x(); + void set_x(float v); + + float get_y(); + void set_y(float v); + + float get_scale_x(); + void set_scale_x(float v); + + float get_scale_y(); + void set_scale_y(float v); +}; + +#endif//GODOT_SPINESKELETON_H diff --git a/spine-godot/spine_godot/SpineSkeletonDataResource.cpp b/spine-godot/spine_godot/SpineSkeletonDataResource.cpp new file mode 100644 index 000000000..977913c61 --- /dev/null +++ b/spine-godot/spine_godot/SpineSkeletonDataResource.cpp @@ -0,0 +1,455 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSkeletonDataResource.h" + +void SpineSkeletonDataResource::_bind_methods() { + ClassDB::bind_method(D_METHOD("set_atlas_res", "atlas_res"), &SpineSkeletonDataResource::set_atlas_res); + ClassDB::bind_method(D_METHOD("get_atlas_res"), &SpineSkeletonDataResource::get_atlas_res); + ClassDB::bind_method(D_METHOD("set_skeleton_json_res", "skeleton_json_res"), &SpineSkeletonDataResource::set_skeleton_json_res); + ClassDB::bind_method(D_METHOD("get_skeleton_json_res"), &SpineSkeletonDataResource::get_skeleton_json_res); + ClassDB::bind_method(D_METHOD("is_skeleton_data_loaded"), &SpineSkeletonDataResource::is_skeleton_data_loaded); + ClassDB::bind_method(D_METHOD("find_animation", "animation_name"), &SpineSkeletonDataResource::find_animation); + ClassDB::bind_method(D_METHOD("get_sk_name"), &SpineSkeletonDataResource::get_sk_name); + ClassDB::bind_method(D_METHOD("set_sk_name", "sk_name"), &SpineSkeletonDataResource::set_sk_name); + ClassDB::bind_method(D_METHOD("get_x"), &SpineSkeletonDataResource::get_x); + ClassDB::bind_method(D_METHOD("set_x", "v"), &SpineSkeletonDataResource::set_x); + ClassDB::bind_method(D_METHOD("get_y"), &SpineSkeletonDataResource::get_y); + ClassDB::bind_method(D_METHOD("set_y", "v"), &SpineSkeletonDataResource::set_y); + ClassDB::bind_method(D_METHOD("get_width"), &SpineSkeletonDataResource::get_width); + ClassDB::bind_method(D_METHOD("get_height"), &SpineSkeletonDataResource::get_height); + ClassDB::bind_method(D_METHOD("get_version"), &SpineSkeletonDataResource::get_version); + ClassDB::bind_method(D_METHOD("get_fps"), &SpineSkeletonDataResource::get_fps); + ClassDB::bind_method(D_METHOD("set_fps", "v"), &SpineSkeletonDataResource::set_fps); + + ClassDB::bind_method(D_METHOD("find_bone", "bone_name"), &SpineSkeletonDataResource::find_bone); + ClassDB::bind_method(D_METHOD("find_slot", "slot_name"), &SpineSkeletonDataResource::find_slot); + ClassDB::bind_method(D_METHOD("find_skin", "skin_name"), &SpineSkeletonDataResource::find_skin); + ClassDB::bind_method(D_METHOD("find_event", "event_data_name"), &SpineSkeletonDataResource::find_event); + ClassDB::bind_method(D_METHOD("find_ik_constraint_data", "constraint_name"), &SpineSkeletonDataResource::find_ik_constraint); + ClassDB::bind_method(D_METHOD("find_transform_constraint_data", "constraint_name"), &SpineSkeletonDataResource::find_transform_constraint); + ClassDB::bind_method(D_METHOD("find_path_constraint_data", "constraint_name"), &SpineSkeletonDataResource::find_path_constraint); + ClassDB::bind_method(D_METHOD("get_all_bone_data"), &SpineSkeletonDataResource::get_bones); + ClassDB::bind_method(D_METHOD("get_all_slot_data"), &SpineSkeletonDataResource::get_slots); + ClassDB::bind_method(D_METHOD("get_skins"), &SpineSkeletonDataResource::get_skins); + ClassDB::bind_method(D_METHOD("get_default_skin"), &SpineSkeletonDataResource::get_default_skin); + ClassDB::bind_method(D_METHOD("set_default_skin", "v"), &SpineSkeletonDataResource::set_default_skin); + ClassDB::bind_method(D_METHOD("get_all_event_data"), &SpineSkeletonDataResource::get_events); + ClassDB::bind_method(D_METHOD("get_animations"), &SpineSkeletonDataResource::get_animations); + ClassDB::bind_method(D_METHOD("get_all_ik_constraint_data"), &SpineSkeletonDataResource::get_ik_constraints); + ClassDB::bind_method(D_METHOD("get_all_transform_constraint_data"), &SpineSkeletonDataResource::get_transform_constraints); + ClassDB::bind_method(D_METHOD("get_all_path_constraint_data"), &SpineSkeletonDataResource::get_path_constraints); + + ADD_SIGNAL(MethodInfo("skeleton_data_loaded")); + ADD_SIGNAL(MethodInfo("atlas_res_changed")); + ADD_SIGNAL(MethodInfo("skeleton_json_res_changed")); + + 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_json_res", PropertyHint::PROPERTY_HINT_RESOURCE_TYPE, "SpineSkeletonJsonDataResource"), "set_skeleton_json_res", "get_skeleton_json_res"); +} + +SpineSkeletonDataResource::SpineSkeletonDataResource() : valid(false), spine_object(false), skeleton_data(NULL) { +} +SpineSkeletonDataResource::~SpineSkeletonDataResource() { + if (skeleton_data && !spine_object) { + delete skeleton_data; + skeleton_data = NULL; + } +} + +bool SpineSkeletonDataResource::is_skeleton_data_loaded() const { + return valid || spine_object; +} + +void SpineSkeletonDataResource::load_res(spine::Atlas *a, const String &json_string) { + if (json_string.empty()) return; + auto path = get_path(); + spine::SkeletonJson json(a); + auto temp_skeleton_data = json.readSkeletonData(json_string.utf8()); + if (!temp_skeleton_data) { + print_error(String("Error happened while loading skeleton json data: ") + path); + print_error(String("Error msg: ") + json.getError().buffer()); + return; + } + if (skeleton_data) { + delete skeleton_data; + skeleton_data = NULL; + } + skeleton_data = temp_skeleton_data; + + valid = true; + // print_line("Skeleton json data loaded!"); +} + +void SpineSkeletonDataResource::update_skeleton_data() { + if (atlas_res.is_valid() && skeleton_json_res.is_valid()) { + load_res(atlas_res->get_spine_atlas(), skeleton_json_res->get_json_string()); + if (valid) { + emit_signal("skeleton_data_loaded"); + } + } +} + +void SpineSkeletonDataResource::set_atlas_res(const Ref &a) { + atlas_res = a; + valid = false; + emit_signal("atlas_res_changed"); + update_skeleton_data(); +} +Ref SpineSkeletonDataResource::get_atlas_res() { + if (spine_object) { + print_line("Getting atlas res from a spine_object skeleton! The result may be NULL!"); + } + return atlas_res; +} + +void SpineSkeletonDataResource::set_skeleton_json_res(const Ref &s) { + skeleton_json_res = s; + valid = false; + // print_line("skeleton_json_res_changed emitted"); + emit_signal("skeleton_json_res_changed"); + update_skeleton_data(); +} +Ref SpineSkeletonDataResource::get_skeleton_json_res() { + if (spine_object) { + print_line("Getting atlas res from a spine_object skeleton! The result may be NULL!"); + } + return skeleton_json_res; +} + +#define CHECK_V \ + if (!is_skeleton_data_loaded()) { \ + ERR_PRINT("skeleton data has not loaded yet!"); \ + return; \ + } +#define CHECK_X(x) \ + if (!is_skeleton_data_loaded()) { \ + ERR_PRINT("skeleton data has not loaded yet!"); \ + return x; \ + } +#define S_T(x) (spine::String(x.utf8())) +Ref SpineSkeletonDataResource::find_animation(const String &animation_name) { + CHECK_X(NULL); + if (animation_name.empty()) { + return NULL; + } + auto a = skeleton_data->findAnimation(S_T(animation_name)); + if (!a) return NULL; + Ref sa(memnew(SpineAnimation)); + sa->set_spine_object(a); + return sa; +} +String SpineSkeletonDataResource::get_sk_name() { + CHECK_X("error"); + return skeleton_data->getName().buffer(); +} +void SpineSkeletonDataResource::set_sk_name(const String &v) { + CHECK_V; + skeleton_data->setName(S_T(v)); +} +float SpineSkeletonDataResource::get_x() { + CHECK_X(0); + return skeleton_data->getX(); +} +void SpineSkeletonDataResource::set_x(float v) { + CHECK_V; + skeleton_data->setX(v); +} +float SpineSkeletonDataResource::get_y() { + CHECK_X(0); + return skeleton_data->getY(); +} +void SpineSkeletonDataResource::set_y(float v) { + CHECK_V; + skeleton_data->setY(v); +} +float SpineSkeletonDataResource::get_width() { + CHECK_X(0); + return skeleton_data->getWidth(); +} +float SpineSkeletonDataResource::get_height() { + CHECK_X(0); + return skeleton_data->getHeight(); +} +String SpineSkeletonDataResource::get_version() { + CHECK_X("error"); + return skeleton_data->getVersion().buffer(); +} +float SpineSkeletonDataResource::get_fps() { + CHECK_X(0); + return skeleton_data->getFps(); +} +void SpineSkeletonDataResource::set_fps(float v) { + CHECK_V; + skeleton_data->setFps(v); +} + +Ref SpineSkeletonDataResource::find_bone(const String &bone_name) { + if (bone_name.empty()) return NULL; + auto b = skeleton_data->findBone(S_T(bone_name)); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineBoneData)); + gd_b->set_spine_object(b); + return gd_b; +} + +Ref SpineSkeletonDataResource::find_slot(const String &slot_name) { + if (slot_name.empty()) return NULL; + auto b = skeleton_data->findSlot(S_T(slot_name)); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineSlotData)); + gd_b->set_spine_object(b); + return gd_b; +} + +Ref SpineSkeletonDataResource::find_skin(const String &skin_name) { + if (skin_name.empty()) return NULL; + auto b = skeleton_data->findSkin(S_T(skin_name)); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineSkin)); + gd_b->set_spine_object(b); + return gd_b; +} + +Ref SpineSkeletonDataResource::find_event(const String &event_data_name) { + if (event_data_name.empty()) return NULL; + auto b = skeleton_data->findEvent(S_T(event_data_name)); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineEventData)); + gd_b->set_spine_object(b); + return gd_b; +} + +Ref SpineSkeletonDataResource::find_ik_constraint(const String &constraint_name) { + if (constraint_name.empty()) return NULL; + auto b = skeleton_data->findIkConstraint(S_T(constraint_name)); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineIkConstraintData)); + gd_b->set_spine_object(b); + return gd_b; +} +Ref SpineSkeletonDataResource::find_transform_constraint(const String &constraint_name) { + if (constraint_name.empty()) return NULL; + auto b = skeleton_data->findTransformConstraint(S_T(constraint_name)); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineTransformConstraintData)); + gd_b->set_spine_object(b); + return gd_b; +} +Ref SpineSkeletonDataResource::find_path_constraint(const String &constraint_name) { + if (constraint_name.empty()) return NULL; + auto b = skeleton_data->findPathConstraint(S_T(constraint_name)); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpinePathConstraintData)); + gd_b->set_spine_object(b); + return gd_b; +} + +Array SpineSkeletonDataResource::get_bones() { + auto bs = skeleton_data->getBones(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineBoneData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} +Array SpineSkeletonDataResource::get_slots() { + auto bs = skeleton_data->getSlots(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineSlotData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} +Array SpineSkeletonDataResource::get_skins() const { + auto bs = skeleton_data->getSkins(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineSkin)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} + +Ref SpineSkeletonDataResource::get_default_skin() { + auto b = skeleton_data->getDefaultSkin(); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineSkin)); + gd_b->set_spine_object(b); + return gd_b; +} +void SpineSkeletonDataResource::set_default_skin(Ref v) { + if (v.is_valid()) { + skeleton_data->setDefaultSkin(v->get_spine_object()); + } else + skeleton_data->setDefaultSkin(NULL); +} + +Array SpineSkeletonDataResource::get_events() { + auto bs = skeleton_data->getEvents(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineEventData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} +Array SpineSkeletonDataResource::get_animations() { + auto bs = skeleton_data->getAnimations(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineAnimation)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} +Array SpineSkeletonDataResource::get_ik_constraints() { + auto bs = skeleton_data->getIkConstraints(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineIkConstraintData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} +Array SpineSkeletonDataResource::get_transform_constraints() { + auto bs = skeleton_data->getTransformConstraints(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineTransformConstraintData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} +Array SpineSkeletonDataResource::get_path_constraints() { + auto bs = skeleton_data->getPathConstraints(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpinePathConstraintData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} +#undef S_T +#undef CHECK_V +#undef CHECK_X + +//External feature functions +void SpineSkeletonDataResource::get_animation_names(Vector &res) const { + res.clear(); + if (!is_skeleton_data_loaded()) { + return; + } + auto as = skeleton_data->getAnimations(); + for (size_t i = 0; i < as.size(); ++i) { + auto a = as[i]; + if (a) { + res.push_back(a->getName().buffer()); + } else { + res.push_back(""); + } + } +} +void SpineSkeletonDataResource::get_skin_names(Vector &res) const { + res.clear(); + if (!is_skeleton_data_loaded()) { + return; + } + auto as = get_skins(); + res.resize(as.size()); + for (size_t i = 0; i < as.size(); ++i) { + auto a = Ref(as[i]); + if (a.is_valid()) { + res.push_back(a->get_skin_name()); + } else { + res.push_back(""); + } + } +} + +void SpineSkeletonDataResource::_get_property_list(List *p_list) const { + PropertyInfo p; + Vector res; + + p.name = "animations"; + p.type = Variant::STRING; + get_animation_names(res); + p.hint_string = String(",").join(res); + p.hint = PROPERTY_HINT_ENUM; + p_list->push_back(p); + + p.name = "skins"; + p.type = Variant::STRING; + get_skin_names(res); + p.hint_string = String(",").join(res); + p.hint = PROPERTY_HINT_ENUM; + p_list->push_back(p); +} diff --git a/spine-godot/spine_godot/SpineSkeletonDataResource.h b/spine-godot/spine_godot/SpineSkeletonDataResource.h new file mode 100644 index 000000000..eaabaa11c --- /dev/null +++ b/spine-godot/spine_godot/SpineSkeletonDataResource.h @@ -0,0 +1,140 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESKELETONDATARESOURCE_H +#define GODOT_SPINESKELETONDATARESOURCE_H + +#include "core/variant_parser.h" + +#include + +#include "SpineAtlasResource.h" +#include "SpineSkeletonJsonDataResource.h" +#include "SpineAnimation.h" +#include "SpineBoneData.h" +#include "SpineSlotData.h" +#include "SpineSkin.h" +#include "SpineIkConstraintData.h" +#include "SpineTransformConstraintData.h" +#include "SpinePathConstraintData.h" +#include "SpineEventData.h" + +class SpineSkeletonDataResource : public Resource { + GDCLASS(SpineSkeletonDataResource, Resource); + +protected: + static void _bind_methods(); + +private: + Ref atlas_res; + Ref skeleton_json_res; + bool valid; + bool spine_object; + + spine::SkeletonData *skeleton_data; + + void update_skeleton_data(); + +public: + inline void set_spine_object(spine::SkeletonData *s) { + skeleton_data = s; + if (s) + spine_object = true; + } + inline spine::SkeletonData *get_spine_object() { + return skeleton_data; + } + + void load_res(spine::Atlas *a, const String &json_path); + + SpineSkeletonDataResource(); + virtual ~SpineSkeletonDataResource(); + + void _get_property_list(List *p_list) const; + + void set_atlas_res(const Ref &a); + Ref get_atlas_res(); + + void set_skeleton_json_res(const Ref &s); + Ref get_skeleton_json_res(); + + inline spine::SkeletonData *get_skeleton_data() { return skeleton_data; } + + bool is_skeleton_data_loaded() const; + + void get_animation_names(Vector &l) const; + void get_skin_names(Vector &l) const; + + // spine api + Ref find_bone(const String &bone_name); + + Ref find_slot(const String &slot_name); + + Ref find_skin(const String &skin_name); + + Ref find_event(const String &event_data_name); + + Ref find_animation(const String &animation_name); + + Ref find_ik_constraint(const String &constraint_name); + Ref find_transform_constraint(const String &constraint_name); + Ref find_path_constraint(const String &constraint_name); + + Array get_bones(); + Array get_slots(); + Array get_skins() const; + + Ref get_default_skin(); + void set_default_skin(Ref v); + + Array get_events(); + Array get_animations(); + Array get_ik_constraints(); + Array get_transform_constraints(); + Array get_path_constraints(); + + String get_sk_name(); + void set_sk_name(const String &v); + + float get_x(); + void set_x(float v); + + float get_y(); + void set_y(float v); + + float get_width(); + float get_height(); + + String get_version(); + + float get_fps(); + void set_fps(float v); +}; + +#endif//GODOT_SPINESKELETONDATARESOURCE_H diff --git a/spine-godot/spine_godot/SpineSkeletonJsonDataResource.cpp b/spine-godot/spine_godot/SpineSkeletonJsonDataResource.cpp new file mode 100644 index 000000000..d332a791a --- /dev/null +++ b/spine-godot/spine_godot/SpineSkeletonJsonDataResource.cpp @@ -0,0 +1,55 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSkeletonJsonDataResource.h" + + +void SpineSkeletonJsonDataResource::_bind_methods() { +} + +Error SpineSkeletonJsonDataResource::load_from_file(const String &p_path) { + Error err; + + json_string = FileAccess::get_file_as_string(p_path, &err); + return err; +} + +Error SpineSkeletonJsonDataResource::save_to_file(const String &p_path) { + Error err; + FileAccess *file = FileAccess::open(p_path, FileAccess::WRITE, &err); + if (err != OK) { + if (file) file->close(); + return err; + } + + file->store_string(json_string); + file->close(); + + return OK; +} diff --git a/spine-godot/spine_godot/SpineSkeletonJsonDataResource.h b/spine-godot/spine_godot/SpineSkeletonJsonDataResource.h new file mode 100644 index 000000000..8b6045bf6 --- /dev/null +++ b/spine-godot/spine_godot/SpineSkeletonJsonDataResource.h @@ -0,0 +1,50 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESKELETONJSONDATARESOURCE_H +#define GODOT_SPINESKELETONJSONDATARESOURCE_H + +#include "core/variant_parser.h" + +class SpineSkeletonJsonDataResource : public Resource { + GDCLASS(SpineSkeletonJsonDataResource, Resource); + +protected: + static void _bind_methods(); + + String json_string; + +public: + inline const String &get_json_string() { return json_string; } + + Error load_from_file(const String &p_path); + Error save_to_file(const String &p_path); +}; + +#endif//GODOT_SPINESKELETONJSONDATARESOURCE_H diff --git a/spine-godot/spine_godot/SpineSkin.cpp b/spine-godot/spine_godot/SpineSkin.cpp new file mode 100644 index 000000000..b30f01ae5 --- /dev/null +++ b/spine-godot/spine_godot/SpineSkin.cpp @@ -0,0 +1,161 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSkin.h" + +#include "SpineBoneData.h" +#include "SpineConstraintData.h" + +void SpineSkin::_bind_methods() { + ClassDB::bind_method(D_METHOD("init", "name"), &SpineSkin::init); + ClassDB::bind_method(D_METHOD("set_attachment", "slot_index", "name", "attachment"), &SpineSkin::set_attachment); + ClassDB::bind_method(D_METHOD("get_attachment", "slot_index", "name"), &SpineSkin::get_attachment); + ClassDB::bind_method(D_METHOD("remove_attachment", "slot_index", "name"), &SpineSkin::remove_attachment); + ClassDB::bind_method(D_METHOD("find_names_for_slot", "slot_index"), &SpineSkin::find_names_for_slot); + ClassDB::bind_method(D_METHOD("find_attachments_for_slot", "slot_index"), &SpineSkin::find_attachments_for_slot); + ClassDB::bind_method(D_METHOD("get_skin_name"), &SpineSkin::get_skin_name); + ClassDB::bind_method(D_METHOD("add_skin", "other"), &SpineSkin::add_skin); + ClassDB::bind_method(D_METHOD("copy_skin", "other"), &SpineSkin::copy_skin); + ClassDB::bind_method(D_METHOD("get_attachments"), &SpineSkin::get_attachments); + ClassDB::bind_method(D_METHOD("get_all_bone_data"), &SpineSkin::get_bones); + ClassDB::bind_method(D_METHOD("get_all_constraint_data"), &SpineSkin::get_constraint); +} + +SpineSkin::SpineSkin() : skin(NULL) {} +SpineSkin::~SpineSkin() {} + +#define S_T(x) (spine::String(x.utf8())) +Ref SpineSkin::init(const String &name) { + skin = new spine::Skin(S_T(name)); + return this; +} + +void SpineSkin::set_attachment(uint64_t slot_index, const String &name, Ref attachment) { + if (!attachment.is_valid()) { + ERR_PRINT("attachment is invalid!"); + return; + } + skin->setAttachment(slot_index, S_T(name), attachment->get_spine_object()); +} + +Ref SpineSkin::get_attachment(uint64_t slot_index, const String &name) { + auto a = skin->getAttachment(slot_index, S_T(name)); + if (a == NULL) return NULL; + Ref gd_attachment(memnew(SpineAttachment)); + gd_attachment->set_spine_object(a); + return gd_attachment; +} + +void SpineSkin::remove_attachment(uint64_t slot_index, const String &name) { + skin->removeAttachment(slot_index, S_T(name)); +} + +Array SpineSkin::find_names_for_slot(uint64_t slot_index) { + spine::Vector names; + skin->findNamesForSlot(slot_index, names); + Array gd_names; + gd_names.resize(names.size()); + for (size_t i = 0; i < names.size(); ++i) { + gd_names[i] = names[i].buffer(); + } + return gd_names; +} + +Array SpineSkin::find_attachments_for_slot(uint64_t slot_index) { + spine::Vector as; + skin->findAttachmentsForSlot(slot_index, as); + Array gd_as; + gd_as.resize(as.size()); + for (size_t i = 0; i < as.size(); ++i) { + if (as[i] == NULL) gd_as[i] = Ref(NULL); + else { + Ref gd_a(memnew(SpineAttachment)); + gd_a->set_spine_object(as[i]); + gd_as[i] = gd_a; + } + } + return gd_as; +} + +String SpineSkin::get_skin_name() { + return skin->getName().buffer(); +} + +void SpineSkin::add_skin(Ref other) { + if (other.is_valid() && other->get_spine_object()) { + skin->addSkin(other->get_spine_object()); + } else { + ERR_PRINT("other is NULL!"); + } +} + +void SpineSkin::copy_skin(Ref other) { + if (other.is_valid() && other->get_spine_object()) { + skin->copySkin(other->get_spine_object()); + } else { + ERR_PRINT("other is NULL!"); + } +} + +Ref SpineSkin::get_attachments() { + auto *es = new spine::Skin::AttachmentMap::Entries(skin->getAttachments()); + Ref gd_es(memnew(SpineSkinAttachmentMapEntries)); + gd_es->set_spine_object(es); + return gd_es; +} + +Array SpineSkin::get_bones() { + auto bs = skin->getBones(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineBoneData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} + +Array SpineSkin::get_constraint() { + auto cs = skin->getConstraints(); + Array gd_cs; + gd_cs.resize(cs.size()); + for (size_t i = 0; i < cs.size(); ++i) { + if (cs[i] == NULL) gd_cs[i] = Ref(NULL); + else { + Ref gd_c(memnew(SpineConstraintData)); + gd_c->set_spine_object(cs[i]); + gd_cs[i] = gd_c; + } + } + return gd_cs; +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineSkin.h b/spine-godot/spine_godot/SpineSkin.h new file mode 100644 index 000000000..3e1780f2a --- /dev/null +++ b/spine-godot/spine_godot/SpineSkin.h @@ -0,0 +1,85 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESKIN_H +#define GODOT_SPINESKIN_H + +#include "core/variant_parser.h" + +#include + +#include "SpineAttachment.h" +#include "SpineSkinAttachmentMapEntries.h" + +class SpineSkin : public Reference { + GDCLASS(SpineSkin, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Skin *skin; + +public: + SpineSkin(); + ~SpineSkin(); + + inline void set_spine_object(spine::Skin *s) { + skin = s; + } + spine::Skin *get_spine_object() { + return skin; + } + + Ref init(const String &name); + + void set_attachment(uint64_t slot_index, const String &name, Ref attachment); + + Ref get_attachment(uint64_t slot_index, const String &name); + + void remove_attachment(uint64_t slot_index, const String &name); + + Array find_names_for_slot(uint64_t slot_index); + + Array find_attachments_for_slot(uint64_t slot_index); + + String get_skin_name(); + + void add_skin(Ref other); + + void copy_skin(Ref other); + + Ref get_attachments(); + + Array get_bones(); + + Array get_constraint(); +}; + +#endif//GODOT_SPINESKIN_H diff --git a/spine-godot/spine_godot/SpineSkinAttachmentMapEntries.cpp b/spine-godot/spine_godot/SpineSkinAttachmentMapEntries.cpp new file mode 100644 index 000000000..67089b011 --- /dev/null +++ b/spine-godot/spine_godot/SpineSkinAttachmentMapEntries.cpp @@ -0,0 +1,93 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSkinAttachmentMapEntries.h" + +void SpineSkinAttachmentMapEntry::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_slot_index"), &SpineSkinAttachmentMapEntry::get_slot_index); + ClassDB::bind_method(D_METHOD("set_slot_index", "v"), &SpineSkinAttachmentMapEntry::set_slot_index); + ClassDB::bind_method(D_METHOD("get_entry_name"), &SpineSkinAttachmentMapEntry::get_entry_name); + ClassDB::bind_method(D_METHOD("set_entry_name", "v"), &SpineSkinAttachmentMapEntry::set_entry_name); + ClassDB::bind_method(D_METHOD("get_attachment"), &SpineSkinAttachmentMapEntry::get_attachment); + ClassDB::bind_method(D_METHOD("set_attachment", "v"), &SpineSkinAttachmentMapEntry::set_attachment); +} + +SpineSkinAttachmentMapEntry::SpineSkinAttachmentMapEntry() : entry(NULL) {} +SpineSkinAttachmentMapEntry::~SpineSkinAttachmentMapEntry() {} + +uint64_t SpineSkinAttachmentMapEntry::get_slot_index() { + return entry->_slotIndex; +} +void SpineSkinAttachmentMapEntry::set_slot_index(uint64_t v) { + entry->_slotIndex = v; +} + +String SpineSkinAttachmentMapEntry::get_entry_name() { + return entry->_name.buffer(); +} +void SpineSkinAttachmentMapEntry::set_entry_name(const String &v) { + entry->_name = spine::String(v.utf8()); +} + +Ref SpineSkinAttachmentMapEntry::get_attachment() { + if (entry->_attachment == NULL) return NULL; + Ref gd_attachment(memnew(SpineAttachment)); + gd_attachment->set_spine_object(entry->_attachment); + return gd_attachment; +} +void SpineSkinAttachmentMapEntry::set_attachment(Ref v) { + if (v.is_valid()) { + entry->_attachment = v->get_spine_object(); + } else { + entry->_attachment = NULL; + } +} + +void SpineSkinAttachmentMapEntries::_bind_methods() { + ClassDB::bind_method(D_METHOD("has_next"), &SpineSkinAttachmentMapEntries::has_next); + ClassDB::bind_method(D_METHOD("next"), &SpineSkinAttachmentMapEntries::next); +} + +SpineSkinAttachmentMapEntries::SpineSkinAttachmentMapEntries() : entries(NULL) {} +SpineSkinAttachmentMapEntries::~SpineSkinAttachmentMapEntries() { + if (entries) { + delete entries; + return; + } +} + +bool SpineSkinAttachmentMapEntries::has_next() { + return entries->hasNext(); +} +Ref SpineSkinAttachmentMapEntries::next() { + auto &e = entries->next(); + Ref gd_entry(memnew(SpineSkinAttachmentMapEntry)); + gd_entry->set_spine_object(&e); + return gd_entry; +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineSkinAttachmentMapEntries.h b/spine-godot/spine_godot/SpineSkinAttachmentMapEntries.h new file mode 100644 index 000000000..b0f3922ef --- /dev/null +++ b/spine-godot/spine_godot/SpineSkinAttachmentMapEntries.h @@ -0,0 +1,93 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESKINATTACHMENTMAPENTRIES_H +#define GODOT_SPINESKINATTACHMENTMAPENTRIES_H + +#include "core/variant_parser.h" + +#include + +#include "SpineAttachment.h" + +class SpineSkinAttachmentMapEntry : public Reference { + GDCLASS(SpineSkinAttachmentMapEntry, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Skin::AttachmentMap::Entry *entry; + +public: + SpineSkinAttachmentMapEntry(); + ~SpineSkinAttachmentMapEntry(); + + inline void set_spine_object(spine::Skin::AttachmentMap::Entry *e) { + entry = e; + } + inline spine::Skin::AttachmentMap::Entry *get_spine_object() { + return entry; + } + + uint64_t get_slot_index(); + void set_slot_index(uint64_t v); + + String get_entry_name(); + void set_entry_name(const String &v); + + Ref get_attachment(); + void set_attachment(Ref v); +}; + +class SpineSkinAttachmentMapEntries : public Reference { + GDCLASS(SpineSkinAttachmentMapEntries, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Skin::AttachmentMap::Entries *entries; + +public: + SpineSkinAttachmentMapEntries(); + ~SpineSkinAttachmentMapEntries(); + + inline void set_spine_object(spine::Skin::AttachmentMap::Entries *e) { + entries = e; + } + inline spine::Skin::AttachmentMap::Entries *get_spine_object() { + return entries; + } + + bool has_next(); + Ref next(); +}; + +#endif//GODOT_SPINESKINATTACHMENTMAPENTRIES_H diff --git a/spine-godot/spine_godot/SpineSlot.cpp b/spine-godot/spine_godot/SpineSlot.cpp new file mode 100644 index 000000000..14149b9e1 --- /dev/null +++ b/spine-godot/spine_godot/SpineSlot.cpp @@ -0,0 +1,141 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSlot.h" + +#include "SpineBone.h" +#include "SpineSkeleton.h" + + +void SpineSlot::_bind_methods() { + ClassDB::bind_method(D_METHOD("set_to_setup_pos"), &SpineSlot::set_to_setup_pos); + ClassDB::bind_method(D_METHOD("get_data"), &SpineSlot::get_data); + ClassDB::bind_method(D_METHOD("get_bone"), &SpineSlot::get_bone); + ClassDB::bind_method(D_METHOD("get_skeleton"), &SpineSlot::get_skeleton); + ClassDB::bind_method(D_METHOD("get_color"), &SpineSlot::get_color); + ClassDB::bind_method(D_METHOD("set_color"), &SpineSlot::set_color); + ClassDB::bind_method(D_METHOD("get_dark_color"), &SpineSlot::get_dark_color); + ClassDB::bind_method(D_METHOD("set_dark_color", "v"), &SpineSlot::set_dark_color); + ClassDB::bind_method(D_METHOD("has_dark_color"), &SpineSlot::has_dark_color); + ClassDB::bind_method(D_METHOD("get_attachment"), &SpineSlot::get_attachment); + ClassDB::bind_method(D_METHOD("set_attachment", "v"), &SpineSlot::set_attachment); + ClassDB::bind_method(D_METHOD("get_attachment_state"), &SpineSlot::get_attachment_state); + ClassDB::bind_method(D_METHOD("set_attachment_state", "v"), &SpineSlot::set_attachment_state); + ClassDB::bind_method(D_METHOD("get_deform"), &SpineSlot::get_deform); + ClassDB::bind_method(D_METHOD("set_deform", "v"), &SpineSlot::set_deform); +} + +SpineSlot::SpineSlot() : slot(NULL) {} +SpineSlot::~SpineSlot() {} + +void SpineSlot::set_to_setup_pos() { + slot->setToSetupPose(); +} + +Ref SpineSlot::get_data() { + auto &sd = slot->getData(); + Ref gd_sd(memnew(SpineSlotData)); + gd_sd->set_spine_object(&sd); + return gd_sd; +} + +Ref SpineSlot::get_bone() { + auto &b = slot->getBone(); + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(&b); + return gd_b; +} + +Ref SpineSlot::get_skeleton() { + auto &s = slot->getSkeleton(); + Ref gd_s(memnew(SpineSkeleton)); + gd_s->set_spine_object(&s); + return gd_s; +} + +Color SpineSlot::get_color() { + auto &c = slot->getColor(); + return Color(c.r, c.g, c.b, c.a); +} +void SpineSlot::set_color(Color v) { + auto &c = slot->getColor(); + c.set(v.r, v.g, v.b, v.a); +} + +Color SpineSlot::get_dark_color() { + auto &c = slot->getDarkColor(); + return Color(c.r, c.g, c.b, c.a); +} +void SpineSlot::set_dark_color(Color v) { + auto &c = slot->getDarkColor(); + c.set(v.r, v.g, v.b, v.a); +} + +bool SpineSlot::has_dark_color() { + return slot->hasDarkColor(); +} + +Ref SpineSlot::get_attachment() { + auto a = slot->getAttachment(); + if (a == NULL) return NULL; + Ref gd_a(memnew(SpineAttachment)); + gd_a->set_spine_object(a); + return gd_a; +} +void SpineSlot::set_attachment(Ref v) { + if (v.is_valid()) { + slot->setAttachment(v->get_spine_object()); + } else { + slot->setAttachment(NULL); + } +} + +int SpineSlot::get_attachment_state() { + return slot->getAttachmentState(); +} +void SpineSlot::set_attachment_state(int v) { + slot->setAttachmentState(v); +} + +Array SpineSlot::get_deform() { + auto &ds = slot->getDeform(); + Array gd_ds; + gd_ds.resize(ds.size()); + for (size_t i = 0; i < ds.size(); ++i) { + gd_ds[i] = ds[i]; + } + return gd_ds; +} +void SpineSlot::set_deform(Array gd_ds) { + auto &ds = slot->getDeform(); + ds.setSize(gd_ds.size(), 0); + for (size_t i = 0; i < gd_ds.size(); ++i) { + ds[i] = gd_ds[i]; + } +} diff --git a/spine-godot/spine_godot/SpineSlot.h b/spine-godot/spine_godot/SpineSlot.h new file mode 100644 index 000000000..afca412af --- /dev/null +++ b/spine-godot/spine_godot/SpineSlot.h @@ -0,0 +1,90 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESLOT_H +#define GODOT_SPINESLOT_H + +#include "core/variant_parser.h" + +#include + +#include "SpineSlotData.h" +#include "SpineAttachment.h" + +class SpineSkeleton; + +class SpineBone; + +class SpineSlot : public Reference { + GDCLASS(SpineSlot, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Slot *slot; + +public: + SpineSlot(); + ~SpineSlot(); + + inline void set_spine_object(spine::Slot *s) { + slot = s; + } + inline spine::Slot *get_spine_object() { + return slot; + } + + void set_to_setup_pos(); + + Ref get_data(); + + Ref get_bone(); + + Ref get_skeleton(); + + Color get_color(); + void set_color(Color v); + + Color get_dark_color(); + void set_dark_color(Color v); + + bool has_dark_color(); + + Ref get_attachment(); + void set_attachment(Ref v); + + int get_attachment_state(); + void set_attachment_state(int v); + + Array get_deform(); + void set_deform(Array v); +}; + +#endif//GODOT_SPINESLOT_H diff --git a/spine-godot/spine_godot/SpineSlotData.cpp b/spine-godot/spine_godot/SpineSlotData.cpp new file mode 100644 index 000000000..bf3c48f20 --- /dev/null +++ b/spine-godot/spine_godot/SpineSlotData.cpp @@ -0,0 +1,114 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSlotData.h" + +void SpineSlotData::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_index"), &SpineSlotData::get_index); + ClassDB::bind_method(D_METHOD("get_slot_name"), &SpineSlotData::get_slot_name); + ClassDB::bind_method(D_METHOD("get_bone_data"), &SpineSlotData::get_bone_data); + ClassDB::bind_method(D_METHOD("get_color"), &SpineSlotData::get_color); + ClassDB::bind_method(D_METHOD("get_dark_color"), &SpineSlotData::get_dark_color); + ClassDB::bind_method(D_METHOD("has_dark_color"), &SpineSlotData::has_dark_color); + ClassDB::bind_method(D_METHOD("set_has_dark_color", "v"), &SpineSlotData::set_has_dark_color); + ClassDB::bind_method(D_METHOD("get_attachment_name"), &SpineSlotData::get_attachment_name); + ClassDB::bind_method(D_METHOD("set_attachment_name", "v"), &SpineSlotData::set_attachment_name); + ClassDB::bind_method(D_METHOD("get_blend_mode"), &SpineSlotData::get_blend_mode); + ClassDB::bind_method(D_METHOD("set_blend_mode", "v"), &SpineSlotData::set_blend_mode); + + ClassDB::bind_method(D_METHOD("set_color", "v"), &SpineSlotData::set_color); + ClassDB::bind_method(D_METHOD("set_dark_color", "v"), &SpineSlotData::set_dark_color); + + BIND_ENUM_CONSTANT(BLENDMODE_NORMAL); + BIND_ENUM_CONSTANT(BLENDMODE_ADDITIVE); + BIND_ENUM_CONSTANT(BLENDMODE_MULTIPLY); + BIND_ENUM_CONSTANT(BLENDMODE_SCREEN); +} + +SpineSlotData::SpineSlotData() : slot_data(NULL) {} +SpineSlotData::~SpineSlotData() {} + +#define S_T(x) (spine::String(x.utf8())) +int SpineSlotData::get_index() { + return slot_data->getIndex(); +} + +String SpineSlotData::get_slot_name() { + return slot_data->getName().buffer(); +} + +Ref SpineSlotData::get_bone_data() { + auto &bd = slot_data->getBoneData(); + Ref gd_bone_data(memnew(SpineBoneData)); + gd_bone_data->set_spine_object(&bd); + return gd_bone_data; +} + +Color SpineSlotData::get_color() { + auto &c = slot_data->getColor(); + return Color(c.r, c.g, c.b, c.a); +} +void SpineSlotData::set_color(Color v) { + auto &c = slot_data->getColor(); + c.set(v.r, v.g, v.b, v.a); +} + +Color SpineSlotData::get_dark_color() { + auto &c = slot_data->getDarkColor(); + return Color(c.r, c.g, c.b, c.a); +} +void SpineSlotData::set_dark_color(Color v) { + auto &c = slot_data->getDarkColor(); + c.set(v.r, v.g, v.b, v.a); +} + +bool SpineSlotData::has_dark_color() { + return slot_data->hasDarkColor(); +} +void SpineSlotData::set_has_dark_color(bool v) { + slot_data->setHasDarkColor(v); +} + +String SpineSlotData::get_attachment_name() { + return slot_data->getAttachmentName().buffer(); +} +void SpineSlotData::set_attachment_name(const String &v) { + slot_data->setAttachmentName(S_T(v)); +} + +SpineSlotData::BlendMode SpineSlotData::get_blend_mode() { + auto bm = (int) slot_data->getBlendMode(); + return (BlendMode) bm; +} +void SpineSlotData::set_blend_mode(BlendMode v) { + auto bm = (int) v; + slot_data->setBlendMode((spine::BlendMode) bm); +} + +#undef S_T \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineSlotData.h b/spine-godot/spine_godot/SpineSlotData.h new file mode 100644 index 000000000..1778bba55 --- /dev/null +++ b/spine-godot/spine_godot/SpineSlotData.h @@ -0,0 +1,88 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESLOTDATA_H +#define GODOT_SPINESLOTDATA_H +#include "core/variant_parser.h" + +#include + +#include "SpineBoneData.h" + +class SpineSlotData : public Reference { + GDCLASS(SpineSlotData, Reference); + +protected: + static void _bind_methods(); + +private: + spine::SlotData *slot_data; + +public: + SpineSlotData(); + ~SpineSlotData(); + + inline void set_spine_object(spine::SlotData *s) { + slot_data = s; + } + inline spine::SlotData *get_spine_object() { + return slot_data; + } + + enum BlendMode { + BLENDMODE_NORMAL = 0, + BLENDMODE_ADDITIVE, + BLENDMODE_MULTIPLY, + BLENDMODE_SCREEN + }; + + int get_index(); + + String get_slot_name(); + + Ref get_bone_data(); + + Color get_color(); + void set_color(Color c); + + Color get_dark_color(); + void set_dark_color(Color c); + + bool has_dark_color(); + void set_has_dark_color(bool v); + + String get_attachment_name(); + void set_attachment_name(const String &v); + + BlendMode get_blend_mode(); + void set_blend_mode(BlendMode v); +}; + +VARIANT_ENUM_CAST(SpineSlotData::BlendMode); +#endif//GODOT_SPINESLOTDATA_H diff --git a/spine-godot/spine_godot/SpineSprite.cpp b/spine-godot/spine_godot/SpineSprite.cpp new file mode 100644 index 000000000..dedb91940 --- /dev/null +++ b/spine-godot/spine_godot/SpineSprite.cpp @@ -0,0 +1,966 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSprite.h" + +#include "SpineEvent.h" +#include "SpineTrackEntry.h" + +void SpineSprite::_bind_methods() { + ClassDB::bind_method(D_METHOD("set_animation_state_data_res", "animation_state_data_res"), &SpineSprite::set_animation_state_data_res); + ClassDB::bind_method(D_METHOD("get_animation_state_data_res"), &SpineSprite::get_animation_state_data_res); + ClassDB::bind_method(D_METHOD("_on_animation_data_created"), &SpineSprite::_on_animation_data_created); + ClassDB::bind_method(D_METHOD("get_skeleton"), &SpineSprite::get_skeleton); + ClassDB::bind_method(D_METHOD("get_animation_state"), &SpineSprite::get_animation_state); + ClassDB::bind_method(D_METHOD("_on_animation_data_changed"), &SpineSprite::_on_animation_data_changed); + + ClassDB::bind_method(D_METHOD("get_current_animations"), &SpineSprite::get_current_animations); + ClassDB::bind_method(D_METHOD("set_current_animations", "current_animations"), &SpineSprite::set_current_animations); + + ClassDB::bind_method(D_METHOD("get_select_track_id"), &SpineSprite::get_select_track_id); + ClassDB::bind_method(D_METHOD("set_select_track_id", "track_id"), &SpineSprite::set_select_track_id); + ClassDB::bind_method(D_METHOD("get_clear_track"), &SpineSprite::get_clear_track); + ClassDB::bind_method(D_METHOD("set_clear_track", "v"), &SpineSprite::set_clear_track); + ClassDB::bind_method(D_METHOD("get_clear_tracks"), &SpineSprite::get_clear_tracks); + ClassDB::bind_method(D_METHOD("set_clear_tracks", "v"), &SpineSprite::set_clear_tracks); + + ClassDB::bind_method(D_METHOD("get_empty_animation_duration"), &SpineSprite::get_empty_animation_duration); + ClassDB::bind_method(D_METHOD("set_empty_animation_duration", "track_id"), &SpineSprite::set_empty_animation_duration); + ClassDB::bind_method(D_METHOD("get_set_empty_animation"), &SpineSprite::get_set_empty_animation); + ClassDB::bind_method(D_METHOD("set_set_empty_animation", "v"), &SpineSprite::set_set_empty_animation); + ClassDB::bind_method(D_METHOD("get_set_empty_animations"), &SpineSprite::get_set_empty_animations); + ClassDB::bind_method(D_METHOD("set_set_empty_animations", "v"), &SpineSprite::set_set_empty_animations); + + ClassDB::bind_method(D_METHOD("get_bind_slot_nodes"), &SpineSprite::get_bind_slot_nodes); + ClassDB::bind_method(D_METHOD("set_bind_slot_nodes", "v"), &SpineSprite::set_bind_slot_nodes); + ClassDB::bind_method(D_METHOD("get_overlap"), &SpineSprite::get_overlap); + ClassDB::bind_method(D_METHOD("set_overlap", "v"), &SpineSprite::set_overlap); + + ClassDB::bind_method(D_METHOD("bone_get_global_transform", "bone_name"), &SpineSprite::bone_get_global_transform); + ClassDB::bind_method(D_METHOD("bone_set_global_transform", "bone_name", "global_transform"), &SpineSprite::bone_set_global_transform); + + ClassDB::bind_method(D_METHOD("set_process_mode", "v"), &SpineSprite::set_process_mode); + ClassDB::bind_method(D_METHOD("get_process_mode"), &SpineSprite::get_process_mode); + + ClassDB::bind_method(D_METHOD("manual_update", "delta"), &SpineSprite::_update_all); + + ADD_SIGNAL(MethodInfo("animation_state_ready", PropertyInfo(Variant::OBJECT, "animation_state", PROPERTY_HINT_TYPE_STRING, "SpineAnimationState"), PropertyInfo(Variant::OBJECT, "skeleton", PROPERTY_HINT_TYPE_STRING, "SpineSkeleton"))); + ADD_SIGNAL(MethodInfo("animation_start", PropertyInfo(Variant::OBJECT, "animation_state", PROPERTY_HINT_TYPE_STRING, "SpineAnimationState"), PropertyInfo(Variant::OBJECT, "track_entry", PROPERTY_HINT_TYPE_STRING, "SpineTrackEntry"), PropertyInfo(Variant::OBJECT, "event", PROPERTY_HINT_TYPE_STRING, "SpineEvent"))); + ADD_SIGNAL(MethodInfo("animation_interrupt", PropertyInfo(Variant::OBJECT, "animation_state", PROPERTY_HINT_TYPE_STRING, "SpineAnimationState"), PropertyInfo(Variant::OBJECT, "track_entry", PROPERTY_HINT_TYPE_STRING, "SpineTrackEntry"), PropertyInfo(Variant::OBJECT, "event", PROPERTY_HINT_TYPE_STRING, "SpineEvent"))); + ADD_SIGNAL(MethodInfo("animation_end", PropertyInfo(Variant::OBJECT, "animation_state", PROPERTY_HINT_TYPE_STRING, "SpineAnimationState"), PropertyInfo(Variant::OBJECT, "track_entry", PROPERTY_HINT_TYPE_STRING, "SpineTrackEntry"), PropertyInfo(Variant::OBJECT, "event", PROPERTY_HINT_TYPE_STRING, "SpineEvent"))); + ADD_SIGNAL(MethodInfo("animation_complete", PropertyInfo(Variant::OBJECT, "animation_state", PROPERTY_HINT_TYPE_STRING, "SpineAnimationState"), PropertyInfo(Variant::OBJECT, "track_entry", PROPERTY_HINT_TYPE_STRING, "SpineTrackEntry"), PropertyInfo(Variant::OBJECT, "event", PROPERTY_HINT_TYPE_STRING, "SpineEvent"))); + ADD_SIGNAL(MethodInfo("animation_dispose", PropertyInfo(Variant::OBJECT, "animation_state", PROPERTY_HINT_TYPE_STRING, "SpineAnimationState"), PropertyInfo(Variant::OBJECT, "track_entry", PROPERTY_HINT_TYPE_STRING, "SpineTrackEntry"), PropertyInfo(Variant::OBJECT, "event", PROPERTY_HINT_TYPE_STRING, "SpineEvent"))); + ADD_SIGNAL(MethodInfo("animation_event", PropertyInfo(Variant::OBJECT, "animation_state", PROPERTY_HINT_TYPE_STRING, "SpineAnimationState"), PropertyInfo(Variant::OBJECT, "track_entry", PROPERTY_HINT_TYPE_STRING, "SpineTrackEntry"), PropertyInfo(Variant::OBJECT, "event", PROPERTY_HINT_TYPE_STRING, "SpineEvent"))); + + ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "animation_state_data_res", PropertyHint::PROPERTY_HINT_RESOURCE_TYPE, "SpineAnimationStateDataResource"), "set_animation_state_data_res", "get_animation_state_data_res"); + + ADD_PROPERTY(PropertyInfo(Variant::BOOL, "overlap"), "set_overlap", "get_overlap"); + ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "bind_slot_nodes"), "set_bind_slot_nodes", "get_bind_slot_nodes"); + ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "custom_skin_resource", PropertyHint::PROPERTY_HINT_RESOURCE_TYPE, "SpineCustomSkinResource"), "set_skin", "get_skin"); + + ADD_GROUP("animation", ""); + ADD_PROPERTY(PropertyInfo(Variant::INT, "process_mode", PROPERTY_HINT_ENUM, "Process,Physics,Manually"), "set_process_mode", "get_process_mode"); + + ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "current_animations"), "set_current_animations", "get_current_animations"); + + BIND_ENUM_CONSTANT(ProcessMode::ProcessMode_Process); + BIND_ENUM_CONSTANT(ProcessMode::ProcessMode_Physics); + BIND_ENUM_CONSTANT(ProcessMode::ProcessMode_Manual); +} + +SpineSprite::SpineSprite() : select_track_id(0), empty_animation_duration(0.2f), skeleton_clipper(NULL), + overlap(false), + process_mode(ProcessMode_Process) { + skeleton_clipper = new spine::SkeletonClipping(); +} +SpineSprite::~SpineSprite() { + delete skeleton_clipper; +} + +void SpineSprite::_notification(int p_what) { + switch (p_what) { + case NOTIFICATION_READY: { + set_process_internal(process_mode == ProcessMode_Process); + set_physics_process_internal(process_mode == ProcessMode_Physics); + remove_redundant_mesh_instances(); + } break; + case NOTIFICATION_INTERNAL_PROCESS: { + if (process_mode == ProcessMode_Process) + _update_all(get_process_delta_time()); + } break; + case NOTIFICATION_INTERNAL_PHYSICS_PROCESS: { + if (process_mode == ProcessMode_Physics) + _update_all(get_physics_process_delta_time()); + } break; + } +} + +void SpineSprite::_update_all(float delta) { + if (!(skeleton.is_valid() && animation_state.is_valid()) || mesh_instances.empty()) + return; + + animation_state->update(delta); + if (!is_visible_in_tree()) + return; + + animation_state->apply(skeleton); + + skeleton->update_world_transform(); + + update_mesh_from_skeleton(skeleton); + + update(); + + update_bind_slot_nodes(); +} + +void SpineSprite::update_bind_slot_nodes() { + if (animation_state.is_valid() && skeleton.is_valid()) { + for (size_t i = 0, n = bind_slot_nodes.size(); i < n; ++i) { + auto a = bind_slot_nodes[i]; + if (a.get_type() == Variant::DICTIONARY) { + auto d = (Dictionary) a; + if (d.has("slot_name") && d.has("node_path")) { + NodePath node_path = d["node_path"]; + Node *node = get_node_or_null(node_path); + if (node && node->is_class("Node2D")) { + Node2D *node2d = (Node2D *) node; + + String slot_name = d["slot_name"]; + auto slot = skeleton->find_slot(slot_name); + if (slot.is_valid()) { + auto bone = slot->get_bone(); + if (bone.is_valid()) { + update_bind_slot_node_transform(bone, node2d); + update_bind_slot_node_draw_order(slot_name, node2d); + } + } + } + } + } else if (a.get_type() == Variant::ARRAY) { + auto as = (Array) a;// 0: slot_name, 1: node_path + if (as.size() >= 2 && as[0].get_type() == Variant::STRING && as[1].get_type() == Variant::NODE_PATH) { + NodePath node_path = as[1]; + Node *node = get_node_or_null(node_path); + if (node && node->is_class("Node2D")) { + Node2D *node2d = (Node2D *) node; + + String slot_name = as[0]; + auto slot = skeleton->find_slot(slot_name); + if (slot.is_valid()) { + auto bone = slot->get_bone(); + if (bone.is_valid()) { + update_bind_slot_node_transform(bone, node2d); + update_bind_slot_node_draw_order(slot_name, node2d); + } + } + } + } + } + } + } +} +void SpineSprite::update_bind_slot_node_transform(Ref bone, Node2D *node2d) { + bone->apply_world_transform_2d(node2d); +} +void SpineSprite::update_bind_slot_node_draw_order(const String &slot_name, Node2D *node2d) { + auto mesh_ins = find_node(slot_name); + if (mesh_ins) { + auto pos = mesh_ins->get_index(); + + // get child + auto node = find_child_node_by_node(node2d); + if (node && node->get_index() != pos + 1) { + move_child(node, pos + 1); + } + } +} +Node *SpineSprite::find_child_node_by_node(Node *node) { + if (node == NULL) return NULL; + while (node && node->get_parent() != this) node = node->get_parent(); + return node; +} + +void SpineSprite::set_animation_state_data_res(const Ref &s) { + animation_state_data_res = s; + + // update run time skeleton and meshes + _on_animation_data_changed(); +} +Ref SpineSprite::get_animation_state_data_res() { + return animation_state_data_res; +} + +void SpineSprite::_on_animation_data_created() { + // print_line("_on_animation_data_created"); + skeleton = Ref(memnew(SpineSkeleton)); + skeleton->load_skeleton(animation_state_data_res->get_skeleton()); + skeleton->set_spine_sprite(this); + // print_line("Run time skeleton created."); + + animation_state = Ref(memnew(SpineAnimationState)); + animation_state->load_animation_state(animation_state_data_res); + animation_state->get_animation_state()->setListener(this); + // print_line("Run time animation state created."); + + // add mesh instances related by current skeleton + animation_state->update(0); + animation_state->apply(skeleton); + skeleton->update_world_transform(); + gen_mesh_from_skeleton(skeleton); + + if (process_mode == ProcessMode_Process) { + _notification(NOTIFICATION_INTERNAL_PROCESS); + } else if (process_mode == ProcessMode_Physics) { + _notification(NOTIFICATION_INTERNAL_PHYSICS_PROCESS); + } + + emit_signal("animation_state_ready", animation_state, skeleton); +} +void SpineSprite::_on_animation_data_changed() { + // print_line("_on_animation_data_changed"); + remove_mesh_instances(); + skeleton.unref(); + animation_state.unref(); + if (!animation_state_data_res.is_null()) { + if (!animation_state_data_res->is_connected("animation_state_data_created", this, "_on_animation_data_created")) + animation_state_data_res->connect("animation_state_data_created", this, "_on_animation_data_created"); + if (!animation_state_data_res->is_connected("skeleton_data_res_changed", this, "_on_animation_data_changed")) + animation_state_data_res->connect("skeleton_data_res_changed", this, "_on_animation_data_changed"); + if (!animation_state_data_res->is_connected("animation_state_data_changed", this, "_on_animation_data_changed")) + animation_state_data_res->connect("animation_state_data_changed", this, "_on_animation_data_changed"); + + if (animation_state_data_res->is_animation_state_data_created()) { + _on_animation_data_created(); + } + } +} + +Ref SpineSprite::get_skeleton() { + return skeleton; +} +Ref SpineSprite::get_animation_state() { + return animation_state; +} + +void SpineSprite::gen_mesh_from_skeleton(Ref s) { + auto sk = s->get_spine_object(); + for (size_t i = 0, n = sk->getSlots().size(); i < n; ++i) { + // creat a mesh instance 2d for every slot + auto mesh_ins = memnew(SpineSpriteMeshInstance2D); + add_child(mesh_ins); + mesh_ins->set_position(Vector2(0, 0)); + mesh_ins->set_owner(this); + mesh_instances.push_back(mesh_ins); + + spine::Slot *slot = sk->getDrawOrder()[i]; + mesh_ins->set_name(slot->getData().getName().buffer()); + Ref gd_slot(memnew(SpineSlot)); + gd_slot->set_spine_object(slot); + mesh_ins->set_slot(gd_slot); + + // creat a material + Ref mat(memnew(CanvasItemMaterial)); + CanvasItemMaterial::BlendMode blend_mode; + switch (slot->getData().getBlendMode()) { + case spine::BlendMode_Normal: + blend_mode = CanvasItemMaterial::BLEND_MODE_MIX; + break; + case spine::BlendMode_Additive: + blend_mode = CanvasItemMaterial::BLEND_MODE_ADD; + break; + case spine::BlendMode_Multiply: + blend_mode = CanvasItemMaterial::BLEND_MODE_MUL; + break; + case spine::BlendMode_Screen: + blend_mode = CanvasItemMaterial::BLEND_MODE_MIX; + break; + default: + blend_mode = CanvasItemMaterial::BLEND_MODE_MIX; + } + mat->set_blend_mode(blend_mode); + mesh_ins->set_material(mat); + } +} + +void SpineSprite::remove_mesh_instances() { + for (size_t i = 0; i < mesh_instances.size(); ++i) { + remove_child(mesh_instances[i]); + memdelete(mesh_instances[i]); + } + mesh_instances.clear(); +} + +void SpineSprite::remove_redundant_mesh_instances() { + Vector ms; + // remove the redundant mesh instances that added by duplicating + // print_line("start clearing"); + for (size_t i = 0, n = get_child_count(); i < n; ++i) { + auto node = get_child(i); + // print_line(String("get a node: ") + node->get_name()); + if (node && node->is_class("SpineSpriteMeshInstance2D")) { + if (mesh_instances.find((SpineSpriteMeshInstance2D *) node) == -1) { + // print_line("marked clear"); + ms.push_back(node); + } + } + } + for (size_t i = 0, n = ms.size(); i < n; ++i) { + remove_child(ms[i]); + memdelete(ms[i]); + } + ms.clear(); + // print_line("end clearing"); +} + +#define TEMP_COPY(t, get_res) \ + do { \ + auto &temp_uvs = get_res; \ + t.setSize(temp_uvs.size(), 0); \ + for (size_t j = 0; j < t.size(); ++j) { \ + t[j] = temp_uvs[j]; \ + } \ + } while (false); +void SpineSprite::update_mesh_from_skeleton(Ref s) { + static const unsigned short VERTEX_STRIDE = 2; + static const unsigned short UV_STRIDE = 2; + static unsigned short quad_indices[] = {0, 1, 2, 2, 3, 0}; + + auto sk = s->get_spine_object(); + for (size_t i = 0, n = sk->getSlots().size(); i < n; ++i) { + spine::Vector vertices; + spine::Vector uvs; + spine::Vector indices; + + spine::Slot *slot = sk->getDrawOrder()[i]; + + spine::Attachment *attachment = slot->getAttachment(); + if (!attachment) { + // set invisible to mesh instance + mesh_instances[i]->set_visible(false); + + skeleton_clipper->clipEnd(*slot); + continue; + } + mesh_instances[i]->set_visible(true); + + spine::Color skeleton_color = sk->getColor(); + spine::Color slot_color = slot->getColor(); + spine::Color tint(skeleton_color.r * slot_color.r, skeleton_color.g * slot_color.g, skeleton_color.b * slot_color.b, skeleton_color.a * slot_color.a); + + Ref tex; + Ref normal_tex; + size_t v_num = 0; + + if (attachment->getRTTI().isExactly(spine::RegionAttachment::rtti)) { + spine::RegionAttachment *region_attachment = (spine::RegionAttachment *) attachment; + + auto p_spine_renderer_object = (SpineRendererObject *) ((spine::AtlasRegion *) region_attachment->getRendererObject())->page->getRendererObject(); + tex = p_spine_renderer_object->texture; + normal_tex = p_spine_renderer_object->normal_map; + + v_num = 4; + vertices.setSize(v_num * VERTEX_STRIDE, 0); + + region_attachment->computeWorldVertices(*slot, vertices, 0); + + TEMP_COPY(uvs, region_attachment->getUVs()); + + indices.setSize(sizeof(quad_indices) / sizeof(unsigned short), 0); + for (size_t j = 0, qn = indices.size(); j < qn; ++j) { + indices[j] = quad_indices[j]; + } + + auto attachment_color = region_attachment->getColor(); + tint.r *= attachment_color.r; + tint.g *= attachment_color.g; + tint.b *= attachment_color.b; + tint.a *= attachment_color.a; + } else if (attachment->getRTTI().isExactly(spine::MeshAttachment::rtti)) { + spine::MeshAttachment *mesh = (spine::MeshAttachment *) attachment; + + auto p_spine_renderer_object = (SpineRendererObject *) ((spine::AtlasRegion *) mesh->getRendererObject())->page->getRendererObject(); + tex = p_spine_renderer_object->texture; + normal_tex = p_spine_renderer_object->normal_map; + + v_num = mesh->getWorldVerticesLength() / VERTEX_STRIDE; + vertices.setSize(mesh->getWorldVerticesLength(), 0); + + mesh->computeWorldVertices(*slot, 0, mesh->getWorldVerticesLength(), vertices, 0); + + // uvs = mesh->getUVs(); + // indices = mesh->getTriangles(); + TEMP_COPY(uvs, mesh->getUVs()); + TEMP_COPY(indices, mesh->getTriangles()); + + auto attachment_color = mesh->getColor(); + tint.r *= attachment_color.r; + tint.g *= attachment_color.g; + tint.b *= attachment_color.b; + tint.a *= attachment_color.a; + } else if (attachment->getRTTI().isExactly(spine::ClippingAttachment::rtti)) { + auto clip = (spine::ClippingAttachment *) attachment; + skeleton_clipper->clipStart(*slot, clip); + continue; + } else { + skeleton_clipper->clipEnd(*slot); + continue; + } + + auto mesh_ins = mesh_instances[i]; + VisualServer::get_singleton()->canvas_item_clear(mesh_ins->get_canvas_item()); + + if (skeleton_clipper->isClipping()) { + skeleton_clipper->clipTriangles(vertices, indices, uvs, VERTEX_STRIDE); + + if (skeleton_clipper->getClippedTriangles().size() == 0) { + skeleton_clipper->clipEnd(*slot); + continue; + } + + auto &clipped_vertices = skeleton_clipper->getClippedVertices(); + v_num = clipped_vertices.size() / VERTEX_STRIDE; + auto &clipped_uvs = skeleton_clipper->getClippedUVs(); + auto &clipped_indices = skeleton_clipper->getClippedTriangles(); + + if (indices.size() > 0) { + Vector p_points, p_uvs; + Vector p_colors; + Vector p_indices; + p_points.resize(v_num); + p_uvs.resize(v_num); + p_colors.resize(v_num); + for (size_t j = 0; j < v_num; j++) { + p_points.set(j, Vector2(clipped_vertices[j * VERTEX_STRIDE], -clipped_vertices[j * VERTEX_STRIDE + 1])); + p_uvs.set(j, Vector2(clipped_uvs[j * VERTEX_STRIDE], clipped_uvs[j * VERTEX_STRIDE + 1])); + p_colors.set(j, Color(tint.r, tint.g, tint.b, tint.a)); + } + p_indices.resize(clipped_indices.size()); + for (size_t j = 0; j < clipped_indices.size(); ++j) { + p_indices.set(j, clipped_indices[j]); + } + + VisualServer::get_singleton()->canvas_item_add_triangle_array(mesh_ins->get_canvas_item(), + p_indices, + p_points, + p_colors, + p_uvs, + Vector(), + Vector(), + tex.is_null() ? RID() : tex->get_rid(), + -1, + normal_tex.is_null() ? RID() : normal_tex->get_rid()); + } + } else { + if (indices.size() > 0) { + Vector p_points, p_uvs; + Vector p_colors; + Vector p_indices; + p_points.resize(v_num); + p_uvs.resize(v_num); + p_colors.resize(v_num); + for (size_t j = 0; j < v_num; j++) { + p_points.set(j, Vector2(vertices[j * VERTEX_STRIDE], -vertices[j * VERTEX_STRIDE + 1])); + p_uvs.set(j, Vector2(uvs[j * VERTEX_STRIDE], uvs[j * VERTEX_STRIDE + 1])); + p_colors.set(j, Color(tint.r, tint.g, tint.b, tint.a)); + } + p_indices.resize(indices.size()); + for (size_t j = 0; j < indices.size(); ++j) { + p_indices.set(j, indices[j]); + } + + VisualServer::get_singleton()->canvas_item_add_triangle_array(mesh_ins->get_canvas_item(), + p_indices, + p_points, + p_colors, + p_uvs, + Vector(), + Vector(), + tex.is_null() ? RID() : tex->get_rid(), + -1, + normal_tex.is_null() ? RID() : normal_tex->get_rid()); + } + } + skeleton_clipper->clipEnd(*slot); + + if (mesh_ins->get_material()->is_class("CanvasItemMaterial")) { + Ref mat = mesh_ins->get_material(); + CanvasItemMaterial::BlendMode blend_mode; + switch (slot->getData().getBlendMode()) { + case spine::BlendMode_Normal: + blend_mode = CanvasItemMaterial::BLEND_MODE_MIX; + break; + case spine::BlendMode_Additive: + blend_mode = CanvasItemMaterial::BLEND_MODE_ADD; + break; + case spine::BlendMode_Multiply: + blend_mode = CanvasItemMaterial::BLEND_MODE_MUL; + break; + case spine::BlendMode_Screen: + blend_mode = CanvasItemMaterial::BLEND_MODE_MIX; + break; + default: + blend_mode = CanvasItemMaterial::BLEND_MODE_MIX; + } + mat->set_blend_mode(blend_mode); + } + } + skeleton_clipper->clipEnd(); +} + +void SpineSprite::callback(spine::AnimationState *state, spine::EventType type, spine::TrackEntry *entry, spine::Event *event) { + Ref gd_entry(NULL); + Ref gd_event(NULL); + + if (entry) { + gd_entry = Ref(memnew(SpineTrackEntry)); + gd_entry->set_spine_object(entry); + } + if (event) { + gd_event = Ref(memnew(SpineEvent)); + gd_event->set_spine_object(event); + } + + switch (type) { + case spine::EventType_Start: { + emit_signal("animation_start", animation_state, gd_entry, gd_event); + } break; + case spine::EventType_Interrupt: { + emit_signal("animation_interrupt", animation_state, gd_entry, gd_event); + } break; + case spine::EventType_End: { + emit_signal("animation_end", animation_state, gd_entry, gd_event); + } break; + case spine::EventType_Complete: { + emit_signal("animation_complete", animation_state, gd_entry, gd_event); + } break; + case spine::EventType_Dispose: { + emit_signal("animation_dispose", animation_state, gd_entry, gd_event); + } break; + case spine::EventType_Event: { + emit_signal("animation_event", animation_state, gd_entry, gd_event); + } break; + } +} + +// External feature functions +Array SpineSprite::get_current_animations() { + return current_animations.duplicate(true); +} +void SpineSprite::set_current_animations(Array as) { + current_animations = as.duplicate(true); + + // validate it then play the animations + _validate_and_play_current_animations(); +} + +int SpineSprite::get_select_track_id() { + return select_track_id; +} +void SpineSprite::set_select_track_id(int v) { + select_track_id = v; + + if (select_track_id < 0) select_track_id = 0; +} + +bool SpineSprite::get_clear_track() { + return false; +} +void SpineSprite::set_clear_track(bool v) { + if (v && animation_state.is_valid() && skeleton.is_valid()) + animation_state->clear_track(select_track_id); +} + +bool SpineSprite::get_clear_tracks() { + return false; +} +void SpineSprite::set_clear_tracks(bool v) { + if (v && animation_state.is_valid() && skeleton.is_valid()) + animation_state->clear_tracks(); +} + +float SpineSprite::get_empty_animation_duration() { + return empty_animation_duration; +} +void SpineSprite::set_empty_animation_duration(float v) { + empty_animation_duration = v; +} + +bool SpineSprite::get_set_empty_animation() { + return false; +} +void SpineSprite::set_set_empty_animation(bool v) { + if (v && animation_state.is_valid() && skeleton.is_valid()) + animation_state->set_empty_animation(select_track_id, empty_animation_duration); +} + +bool SpineSprite::get_set_empty_animations() { + return false; +} +void SpineSprite::set_set_empty_animations(bool v) { + if (v && animation_state.is_valid() && skeleton.is_valid()) + animation_state->set_empty_animations(empty_animation_duration); +} + +Array SpineSprite::get_bind_slot_nodes() { + return bind_slot_nodes; +} + +void SpineSprite::set_bind_slot_nodes(Array v) { + bind_slot_nodes = v; +} + +bool SpineSprite::get_overlap() { + return overlap; +} + +void SpineSprite::set_overlap(bool v) { + overlap = v; +} + +void SpineSprite::bind_slot_with_node_2d(const String &slot_name, Node2D *n) { + auto node_path = n->get_path_to(this); + + // check if has the same binding + for (size_t i = 0, size = bind_slot_nodes.size(); i < size; ++i) { + auto a = bind_slot_nodes[i]; + if (a.get_type() == Variant::DICTIONARY) { + auto d = (Dictionary) a; + if (d.has("slot_name") && d.has("node_path")) { + if (slot_name == d["slot_name"] && node_path == d["node_path"]) { + return; + } + } + } else if (a.get_type() == Variant::ARRAY) { + auto as = (Array) a; + if (as.size() >= 2 && as[0].get_type() == Variant::STRING && as[1].get_type() == Variant::NODE_PATH) { + if (slot_name == as[0] && node_path == as[1]) { + return; + } + } + } + } + + Array bound; + bound.resize(2); + bound[0] = slot_name; + bound[1] = node_path; + + bind_slot_nodes.append(bound); +} +void SpineSprite::unbind_slot_with_node_2d(const String &slot_name, Node2D *n) { + auto node_path = n->get_path_to(this); + + for (size_t i = 0, size = bind_slot_nodes.size(); i < size; ++i) { + auto a = bind_slot_nodes[i]; + if (a.get_type() == Variant::DICTIONARY) { + auto d = (Dictionary) a; + if (d.has("slot_name") && d.has("node_path")) { + if (slot_name == d["slot_name"] && node_path == d["node_path"]) { + bind_slot_nodes.remove(i); + return; + } + } + } else if (a.get_type() == Variant::ARRAY) { + auto as = (Array) a; + if (as.size() >= 2 && as[0].get_type() == Variant::STRING && as[1].get_type() == Variant::NODE_PATH) { + if (slot_name == as[0] && node_path == as[1]) { + bind_slot_nodes.remove(i); + return; + } + } + } + } +} + +Transform2D SpineSprite::bone_get_global_transform(const String &bone_name) { + if (!animation_state.is_valid() && !skeleton.is_valid()) { + return get_global_transform(); + } + auto bone = skeleton->find_bone(bone_name); + if (!bone.is_valid()) { + print_error(vformat("Bone: '%s' not found.", bone_name)); + return get_global_transform(); + } + return bone->get_godot_global_transform(); +} + +void SpineSprite::bone_set_global_transform(const String &bone_name, Transform2D transform) { + if (!animation_state.is_valid() && !skeleton.is_valid()) { + return; + } + auto bone = skeleton->find_bone(bone_name); + if (!bone.is_valid()) { + return; + } + bone->set_godot_global_transform(transform); +} + +SpineSprite::ProcessMode SpineSprite::get_process_mode() { + return process_mode; +} + +void SpineSprite::set_process_mode(SpineSprite::ProcessMode v) { + process_mode = v; + set_process_internal(process_mode == ProcessMode_Process); + set_physics_process_internal(process_mode == ProcessMode_Physics); +} + +void SpineSprite::_get_property_list(List *p_list) const { + p_list->push_back(PropertyInfo(Variant::NIL, "Current Animation Editor", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_CATEGORY)); + p_list->push_back(PropertyInfo(Variant::BOOL, "setup_pose_trigger", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + p_list->push_back(PropertyInfo(Variant::BOOL, "clear_tracks_trigger", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + p_list->push_back(PropertyInfo(Variant::BOOL, "set_empty_animations_trigger", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + p_list->push_back(PropertyInfo(Variant::REAL, "empty_animation_duration")); + p_list->push_back(PropertyInfo(Variant::INT, "track_count", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + + for (size_t i = 0; i < current_animations.size(); ++i) { + String prefix = vformat("ca/%d/", (unsigned int) i); + p_list->push_back(PropertyInfo(Variant::NIL, vformat("ID %d", (unsigned int) i), PROPERTY_HINT_NONE, prefix, PROPERTY_USAGE_GROUP)); + p_list->push_back(PropertyInfo(Variant::INT, vformat("%strack_id", prefix), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + + Vector anim_list; + if (skeleton.is_valid() && skeleton->get_data().is_valid()) { + skeleton->get_data()->get_animation_names(anim_list); + } + if (anim_list.empty()) anim_list.push_back("No Animation"); + p_list->push_back(PropertyInfo(Variant::STRING, vformat("%sanimation", prefix), PROPERTY_HINT_ENUM, String(",").join(anim_list), PROPERTY_USAGE_EDITOR)); + + p_list->push_back(PropertyInfo(Variant::REAL, vformat("%sdelay", prefix), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + + p_list->push_back(PropertyInfo(Variant::BOOL, vformat("%sloop", prefix), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + + p_list->push_back(PropertyInfo(Variant::BOOL, vformat("%sempty", prefix), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + p_list->push_back(PropertyInfo(Variant::REAL, vformat("%sempty_animation_duration", prefix), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + + p_list->push_back(PropertyInfo(Variant::BOOL, vformat("%sclear", prefix), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR)); + } +} + +bool SpineSprite::_get(const StringName &p_property, Variant &r_value) const { + if (p_property == "setup_pose_trigger" || p_property == "clear_tracks_trigger" || p_property == "set_empty_animations_trigger") { + r_value = false; + return true; + } + if (p_property == "empty_animation_duration") { + r_value = empty_animation_duration; + return true; + } + if (p_property == "track_count") { + r_value = get_current_animation_count(); + return true; + } + String p = p_property; + if (p.size() > 2 && p[0] == 'c' && p[1] == 'a' && p[2] == '/') { + Vector sp = p.split("/"); + if (sp.size() > 2) { + int64_t id = sp[1].to_int64(); + if (id >= 0 && id < current_animations.size()) { + auto &key = sp[2]; + if (current_animations[id].get_type() == Variant::DICTIONARY) { + Dictionary dic = current_animations.get(id); + if (dic.has(key)) { + r_value = dic[key]; + } else { + if (key == "track_id") r_value = 0; + else if (key == "animation") + r_value = ""; + else if (key == "loop") + r_value = true; + else if (key == "empty") + r_value = false; + else if (key == "empty_animation_duration") + r_value = 0.3; + else if (key == "clear") + r_value = false; + else if (key == "delay") + r_value = 0; + else + return false; + } + return true; + } + } + } + } + return false; +} + +bool SpineSprite::_set(const StringName &p_property, const Variant &p_value) { + if (p_property == "setup_pose_trigger") { + if (p_value) { + if (skeleton.is_valid()) { + skeleton->set_bones_to_setup_pose(); + skeleton->set_slots_to_setup_pose(); + } + } + return true; + } + if (p_property == "clear_tracks_trigger") { + if (p_value) { + if (animation_state.is_valid() && skeleton.is_valid()) { + animation_state->clear_tracks(); + } + } + return true; + } + if (p_property == "set_empty_animations_trigger") { + if (p_value) { + if (animation_state.is_valid() && skeleton.is_valid()) { + animation_state->set_empty_animations(empty_animation_duration); + } + } + return true; + } + if (p_property == "empty_animation_duration") { + empty_animation_duration = p_value; + return true; + } + if (p_property == "track_count") { + set_current_animation_count(p_value); + return true; + } + String p = p_property; + if (p.size() > 2 && p[0] == 'c' && p[1] == 'a' && p[2] == '/') { + Vector sp = p.split("/"); + if (sp.size() > 2) { + int64_t id = sp[1].to_int64(); + if (id >= 0 && id < current_animations.size()) { + auto &key = sp[2]; + if (current_animations[id].get_type() != Variant::DICTIONARY) { + current_animations.set(id, Dictionary()); + } + + Dictionary dic = current_animations.get(id); + dic[key] = p_value; + + _validate_and_play_current_animations(); + return true; + } + } + } + return false; +} + +int64_t SpineSprite::get_current_animation_count() const { + return current_animations.size(); +} + +void SpineSprite::set_current_animation_count(int64_t v) { + if (v < 0) v = 0; + while (current_animations.size() < v) { + Dictionary d; + d["track_id"] = current_animations.size(); + d["animation"] = ""; + d["delay"] = 0; + d["loop"] = true; + d["empty"] = false; + d["empty_animation_duration"] = 0.3; + d["clear"] = false; + current_animations.push_back(d); + } + while (current_animations.size() > v) { + if (animation_state.is_valid() && skeleton.is_valid()) { + if (current_animations.back().get_type() == Variant::DICTIONARY) { + Dictionary back = current_animations.back(); + if (back.has("track_id")) { + int64_t track_id = back["track_id"]; + int track_cnt = 0; + for (size_t i = 0; i < current_animations.size(); ++i) { + if (current_animations[i].get_type() == Variant::DICTIONARY) { + Dictionary d = current_animations[i]; + if (d.has("track_id") && track_id == (int64_t) d["track_id"]) { + track_cnt += 1; + } + } + } + if (track_cnt == 0) + animation_state->clear_track(track_id); + } + } + } + current_animations.pop_back(); + } + property_list_changed_notify(); +} + +void SpineSprite::_validate_and_play_current_animations() { + if (animation_state.is_valid() && skeleton.is_valid()) { + int64_t track_cnt = 0; + HashMap has_track; + for (size_t i = 0; i < current_animations.size(); ++i) { + auto a = current_animations[i]; + if (a.get_type() == Variant::DICTIONARY) { + Dictionary d = a; + + int64_t track_id = 0; + String animation = ""; + float delay = 0; + bool loop = true; + bool empty = false; + float empty_animation_duration = 0.3; + bool clear = false; + + if (d.has("track_id")) track_id = d["track_id"]; + if (d.has("animation")) animation = d["animation"]; + if (d.has("delay")) delay = d["delay"]; + if (d.has("loop")) loop = d["loop"]; + if (d.has("empty")) empty = d["empty"]; + if (d.has("empty_animation_duration")) empty_animation_duration = d["empty_animation_duration"]; + if (d.has("clear")) clear = d["clear"]; + + if (track_id < 0) { + print_line(vformat("track_id at 'ID %d' can not be less than 0!", (unsigned int) i)); + continue; + } + + track_cnt += 1; + + + if (empty) { + if (has_track.has(track_id)) + animation_state->add_empty_animation(track_id, empty_animation_duration, delay); + else + animation_state->set_empty_animation(track_id, empty_animation_duration); + has_track[track_id] = true; + } else if (clear) { + animation_state->clear_track(track_id); + } else if (skeleton->get_data()->find_animation(animation).is_valid()) { + if (has_track.has(track_id)) + animation_state->add_animation(animation, delay, loop, track_id); + else + animation_state->set_animation(animation, loop, track_id); + has_track[track_id] = true; + } + } + } + + if (track_cnt == 0) animation_state->clear_tracks(); + } +} diff --git a/spine-godot/spine_godot/SpineSprite.h b/spine-godot/spine_godot/SpineSprite.h new file mode 100644 index 000000000..fc7276091 --- /dev/null +++ b/spine-godot/spine_godot/SpineSprite.h @@ -0,0 +1,154 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESPRITE_H +#define GODOT_SPINESPRITE_H + +#include +#include + +#include "SpineAnimationState.h" +#include "SpineAnimationStateDataResource.h" +#include "SpineSkeleton.h" +#include "SpineSpriteMeshInstance2D.h" + +class SpineSprite : public Node2D, public spine::AnimationStateListenerObject { + GDCLASS(SpineSprite, Node2D); + +protected: + static void _bind_methods(); + + void _notification(int p_what); + + void _get_property_list(List *p_list) const; + bool _get(const StringName &p_property, Variant &r_value) const; + bool _set(const StringName &p_property, const Variant &p_value); + + void _validate_and_play_current_animations(); + +public: + enum ProcessMode { + ProcessMode_Process, + ProcessMode_Physics, + ProcessMode_Manual + }; + +private: + Ref animation_state_data_res; + + Ref skeleton; + Ref animation_state; + + Vector mesh_instances; + + Array current_animations; + int select_track_id; + float empty_animation_duration; + + Array bind_slot_nodes; + bool overlap; + + ProcessMode process_mode; + + spine::SkeletonClipping *skeleton_clipper; + +public: + SpineSprite(); + ~SpineSprite(); + + void set_animation_state_data_res(const Ref &a); + Ref get_animation_state_data_res(); + + Ref get_skeleton(); + Ref get_animation_state(); + + void gen_mesh_from_skeleton(Ref s); + void remove_mesh_instances(); + void remove_redundant_mesh_instances(); + + void update_mesh_from_skeleton(Ref s); + + void update_bind_slot_nodes(); + void update_bind_slot_node_transform(Ref bone, Node2D *node2d); + void update_bind_slot_node_draw_order(const String &slot_name, Node2D *node2d); + Node *find_child_node_by_node(Node *node); + + virtual void callback(spine::AnimationState *state, spine::EventType type, spine::TrackEntry *entry, spine::Event *event); + + void _on_animation_data_created(); + void _on_animation_data_changed(); + + void _update_all(float delta); + + // External feature functions + Array get_current_animations(); + void set_current_animations(Array as); + + int get_select_track_id(); + void set_select_track_id(int v); + + bool get_clear_track(); + void set_clear_track(bool v); + + bool get_clear_tracks(); + void set_clear_tracks(bool v); + + float get_empty_animation_duration(); + void set_empty_animation_duration(float v); + + bool get_set_empty_animation(); + void set_set_empty_animation(bool v); + + bool get_set_empty_animations(); + void set_set_empty_animations(bool v); + + Array get_bind_slot_nodes(); + void set_bind_slot_nodes(Array v); + + void bind_slot_with_node_2d(const String &slot_name, Node2D *n); + void unbind_slot_with_node_2d(const String &slot_name, Node2D *n); + + // bone manipulations + Transform2D bone_get_global_transform(const String &bone_name); + void bone_set_global_transform(const String &bone_name, Transform2D transform); + + //allow z-manipulation + bool get_overlap(); + void set_overlap(bool v); + + // current animation count + int64_t get_current_animation_count() const; + void set_current_animation_count(int64_t v); + + ProcessMode get_process_mode(); + void set_process_mode(ProcessMode v); +}; + +VARIANT_ENUM_CAST(SpineSprite::ProcessMode); +#endif//GODOT_SPINESPRITE_H diff --git a/spine-godot/spine_godot/SpineSpriteAnimateDialog.cpp b/spine-godot/spine_godot/SpineSpriteAnimateDialog.cpp new file mode 100644 index 000000000..33bebdd66 --- /dev/null +++ b/spine-godot/spine_godot/SpineSpriteAnimateDialog.cpp @@ -0,0 +1,351 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSpriteAnimateDialog.h" + +#ifdef TOOLS_ENABLED + +#include "SpineSprite.h" + +void SpineSpriteAnimateDialog::_bind_methods() { + ClassDB::bind_method(D_METHOD("_on_animate_button_pressed"), &SpineSpriteAnimateDialog::_on_animate_button_pressed); + ClassDB::bind_method(D_METHOD("_on_scene_tree_selected"), &SpineSpriteAnimateDialog::_on_scene_tree_selected); + ClassDB::bind_method(D_METHOD("_on_scene_tree_hide"), &SpineSpriteAnimateDialog::_on_scene_tree_hide); + ClassDB::bind_method(D_METHOD("_on_animate_dialog_action"), &SpineSpriteAnimateDialog::_on_animate_dialog_action); +} + +SpineSpriteAnimateDialog::SpineSpriteAnimateDialog() { + animate_dialog = memnew(ConfirmationDialog); + add_child(animate_dialog); + animate_dialog->get_ok()->set_text("Generate"); + animate_dialog_override_button = animate_dialog->add_button("Override", false, "override"); + animate_dialog_override_button->set_visible(false); + animate_dialog->set_title("Animations Generator"); + animate_dialog->set_resizable(true); + animate_dialog->set_custom_minimum_size(Vector2(550, 400)); + animate_dialog->set_hide_on_ok(false); + animate_dialog->connect("custom_action", this, "_on_animate_dialog_action"); + Vector al; + al.push_back("confirmed"); + animate_dialog->connect("confirmed", this, "_on_animate_dialog_action", al); + + auto vb = memnew(VBoxContainer); + animate_dialog->add_child(vb); + + auto scroll = memnew(ScrollContainer); + scroll->set_h_size_flags(SIZE_EXPAND_FILL); + scroll->set_v_size_flags(SIZE_EXPAND_FILL); + // vb->add_margin_child("Animations", scroll); + vb->add_child(scroll); + + animate_dialog_tree = memnew(Tree); + animate_dialog_tree->set_h_size_flags(SIZE_EXPAND_FILL); + animate_dialog_tree->set_v_size_flags(SIZE_EXPAND_FILL); + scroll->add_child(animate_dialog_tree); + + animate_dialog_tree->set_columns(3); + animate_dialog_tree->set_column_titles_visible(true); + animate_dialog_tree->set_hide_folding(true); + animate_dialog_tree->set_hide_root(true); + + animate_dialog_tree->set_column_title(0, TTR("Animation")); + animate_dialog_tree->set_column_title(1, TTR("Loop")); + animate_dialog_tree->set_column_title(2, TTR("Track ID")); + + animate_dialog_tree->create_item(); + add_row("test1"); + add_row("test12"); + add_row("test13"); + + auto l = memnew(Label); + l->set_text("W.I.P"); + vb->add_child(l); + + scene_tree_dialog = memnew(SceneTreeDialog); + scene_tree_dialog->set_title("Choose a AnimationPlayer to override, or choose none to create a new one."); + Vector valid_types; + valid_types.push_back("AnimationPlayer"); + scene_tree_dialog->get_scene_tree()->set_valid_types(valid_types); + scene_tree_dialog->get_scene_tree()->set_show_enabled_subscene(true); + scene_tree_dialog->get_ok()->hide(); + add_child(scene_tree_dialog); + scene_tree_dialog->connect("selected", this, "_on_scene_tree_selected"); + scene_tree_dialog->connect("popup_hide", this, "_on_scene_tree_hide"); + + error_dialog = memnew(AcceptDialog); + add_child(error_dialog); +} + +SpineSpriteAnimateDialog::~SpineSpriteAnimateDialog() { +} + +void SpineSpriteAnimateDialog::set_animate_button(ToolButton *b) { + animate_button = b; + animate_button->connect("pressed", this, "_on_animate_button_pressed"); +} + +void SpineSpriteAnimateDialog::add_row(const String &animation, bool loop, int64_t track_id) { + auto item = animate_dialog_tree->create_item(); + item->set_text(0, animation); + + item->set_cell_mode(1, TreeItem::CELL_MODE_CHECK); + item->set_checked(1, loop); + item->set_editable(1, true); + + item->set_cell_mode(2, TreeItem::CELL_MODE_RANGE); + item->set_range(2, track_id); + item->set_editable(2, true); +} + +void SpineSpriteAnimateDialog::clear_tree() { + animate_dialog_tree->clear(); + animate_dialog_tree->create_item(); +} + +void SpineSpriteAnimateDialog::error(const String &text, const String &title) { + error_dialog->set_text(text); + error_dialog->set_title(title); + error_dialog->popup_centered(); +} + +#define ERROR_MSG(x) \ + do { \ + error(x); \ + err = true; \ + return; \ + } while (false) +void SpineSpriteAnimateDialog::load_data_from_sprite(SpineSprite *sprite, bool &err) { + if (sprite == nullptr) { + ERROR_MSG("The sprite is null."); + } + if (!sprite->get_animation_state().is_valid() || !sprite->get_skeleton().is_valid()) { + ERROR_MSG("The sprite is not loaded."); + } + clear_tree(); + + Vector animations; + sprite->get_skeleton()->get_data()->get_animation_names(animations); + + for (size_t i = 0; i < animations.size(); ++i) { + add_row(animations[i]); + } + + err = false; +} + +#define MIN_TRACK_LENGTH 0.15 + +void SpineSpriteAnimateDialog::gen_new_animation_player(SpineSprite *sprite, bool &err) { + if (sprite == nullptr) { + ERROR_MSG("The sprite player is null."); + } + if (!sprite->get_animation_state().is_valid() || !sprite->get_skeleton().is_valid()) { + ERROR_MSG("The sprite is not loaded."); + } + auto p = sprite->get_parent(); + if (p == nullptr) { + p = sprite; + } + + auto anim_player = memnew(AnimationPlayer); + anim_player->set_name("AnimationPlayer"); + p->add_child(anim_player); + anim_player->set_owner(sprite->get_owner()); + anim_player->set_root(anim_player->get_path_to(p)); + + gen_animations(sprite, anim_player, get_data_from_tree(), MIN_TRACK_LENGTH, err); +} + +Dictionary SpineSpriteAnimateDialog::get_data_from_tree() { + Dictionary res; + if (animate_dialog_tree->get_root() == nullptr) return res; + + auto item = animate_dialog_tree->get_root()->get_children(); + while (item) { + Dictionary row; + row["loop"] = item->is_checked(1); + row["track_id"] = item->get_range(2); + + res[item->get_text(0)] = row; + item = item->get_next(); + } + return res; +} + +void SpineSpriteAnimateDialog::gen_animations(SpineSprite *sprite, AnimationPlayer *anim_player, const Dictionary &config, float min_duration, bool &err) { + if (sprite == nullptr || anim_player == nullptr) { + ERROR_MSG("The sprite or animation player is null."); + } + if (!sprite->get_animation_state().is_valid() || !sprite->get_skeleton().is_valid()) { + ERROR_MSG("The sprite is not loaded."); + } + if (anim_player->get_node_or_null(anim_player->get_root()) == nullptr) { + ERROR_MSG("The root node of animation player is null."); + } + + auto path_to_sprite = anim_player->get_node(anim_player->get_root())->get_path_to(sprite); + + Array animations = sprite->get_skeleton()->get_data()->get_animations(); + for (size_t i = 0; i < animations.size(); ++i) { + auto spine_anim = (Ref) animations[i]; + + Dictionary ca; + if (config.has(spine_anim->get_anim_name())) { + ca = config[spine_anim->get_anim_name()]; + } + + if (!ca.has("loop")) ca["loop"] = true; + if (!ca.has("track_id")) ca["track_id"] = 0; + + Array key_frame_value; + key_frame_value.push_back(gen_current_animation_data(spine_anim->get_anim_name(), ca["track_id"], ca["loop"], false, false, 0.3, 0)); + + auto anim = Ref(memnew(Animation)); + auto track_index = anim->add_track(Animation::TYPE_VALUE); + anim->set_length(min_duration > spine_anim->get_duration() ? min_duration : spine_anim->get_duration()); + anim->track_set_path(track_index, NodePath(vformat("%s:current_animations", path_to_sprite))); + anim->track_insert_key(track_index, 0.0, key_frame_value); + anim->value_track_set_update_mode(track_index, Animation::UPDATE_DISCRETE); + + if (anim_player->has_animation(spine_anim->get_anim_name())) + anim_player->remove_animation(spine_anim->get_anim_name()); + anim_player->add_animation(spine_anim->get_anim_name(), anim); + } + + err = false; +} + +Dictionary SpineSpriteAnimateDialog::gen_current_animation_data(const String &animation, int64_t track_id, bool loop, bool clear, bool empty, bool empty_duration, float delay) { + Dictionary res; + res["animation"] = animation; + res["track_id"] = track_id; + res["loop"] = loop; + res["clear"] = clear; + res["empty"] = empty; + res["empty_animation_duration"] = empty_duration; + res["delay"] = delay; + return res; +} + + +void SpineSpriteAnimateDialog::load_data_from_anim_player(AnimationPlayer *anim_player, bool &err) { + if (anim_player == nullptr) { + ERROR_MSG("The animation player is null."); + } + auto root = anim_player->get_node_or_null(anim_player->get_root()); + if (root == nullptr) return; + + auto sprite = get_node_or_null(spine_sprite_path); + if (sprite == nullptr) return; + + auto item = animate_dialog_tree->get_root()->get_children(); + while (item) { + String animation = item->get_text(0); + + auto anim = anim_player->get_animation(animation); + if (anim.is_valid() && anim->get_track_count() > 0) { + if (anim->track_get_type(0) == Animation::TYPE_VALUE) { + auto track_path = anim->track_get_path(0); + if (root->get_node_or_null(track_path) == sprite) { + if (anim->track_get_key_count(0) > 0) { + Array key_frame_value = anim->track_get_key_value(0, 0); + if (!key_frame_value.empty()) { + Dictionary _ca = key_frame_value.front(); + if (_ca.has("loop")) item->set_checked(1, _ca["loop"]); + if (_ca.has("track_id")) item->set_range(2, _ca["track_id"]); + } + } + } + } + } + + item = item->get_next(); + } + + err = false; +} + +//----- Signals ----- +void SpineSpriteAnimateDialog::_on_scene_tree_selected(NodePath path) { + // print_line(vformat("anime: %s", path)); + auto node = get_node_or_null(path); + if (node == nullptr) { + error("The node you chose is null."); + return; + } + if (!node->is_class("AnimationPlayer")) { + error("The node you chose is not AnimationPlayer."); + return; + } + anim_player_path = path; +} + +void SpineSpriteAnimateDialog::_on_animate_button_pressed() { + anim_player_path = String(""); + auto node = (Node *) the_plugin->get_editor_interface()->get_selection()->get_selected_nodes().back(); + spine_sprite_path = node->get_path(); + + // print_line(vformat("sp: %s", spine_sprite_path)); + + animate_dialog_override_button->set_visible(false); + scene_tree_dialog->popup_centered_ratio(); +} + +void SpineSpriteAnimateDialog::_on_scene_tree_hide() { + animate_dialog->popup_centered(); + + bool err = false; + load_data_from_sprite((SpineSprite *) get_node_or_null(spine_sprite_path), err); + + if (err) animate_dialog->hide(); + + err = false; + auto node = get_node_or_null(anim_player_path); + if (node != nullptr) { + load_data_from_anim_player((AnimationPlayer *) node, err); + animate_dialog_override_button->set_visible(!err); + } else { + animate_dialog_override_button->set_visible(false); + } +} + +void SpineSpriteAnimateDialog::_on_animate_dialog_action(const String &act) { + bool err = false; + if (act == "confirmed") { + gen_new_animation_player((SpineSprite *) get_node_or_null(spine_sprite_path), err); + } else if (act == "override") { + gen_animations((SpineSprite *) get_node_or_null(spine_sprite_path), (AnimationPlayer *) get_node_or_null(anim_player_path), get_data_from_tree(), MIN_TRACK_LENGTH, err); + } + if (!err) { + animate_dialog->hide(); + } +} + + +#endif \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineSpriteAnimateDialog.h b/spine-godot/spine_godot/SpineSpriteAnimateDialog.h new file mode 100644 index 000000000..04f26d619 --- /dev/null +++ b/spine-godot/spine_godot/SpineSpriteAnimateDialog.h @@ -0,0 +1,87 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESPRITEANIMATEDIALOG_H +#define GODOT_SPINESPRITEANIMATEDIALOG_H + +#ifdef TOOLS_ENABLED +#include "editor/editor_node.h" + +class SpineSprite; + +class SpineSpriteAnimateDialog : public Control { + GDCLASS(SpineSpriteAnimateDialog, Control); + +protected: + static void _bind_methods(); + + AcceptDialog *error_dialog; + + ToolButton *animate_button; + EditorPlugin *the_plugin; + + ConfirmationDialog *animate_dialog; + Button *animate_dialog_override_button; + Tree *animate_dialog_tree; + SceneTreeDialog *scene_tree_dialog; + + NodePath spine_sprite_path; + NodePath anim_player_path; + + void add_row(const String &animation, bool loop = true, int64_t track_id = 0); + void clear_tree(); + + void error(const String &text, const String &title = "Error"); + + void load_data_from_sprite(SpineSprite *sprite, bool &err); + void load_data_from_anim_player(AnimationPlayer *anim_player, bool &err); + + Dictionary get_data_from_tree(); + + void gen_new_animation_player(SpineSprite *sprite, bool &err); + void gen_animations(SpineSprite *sprite, AnimationPlayer *anim_player, const Dictionary &config, float min_duration, bool &err); + Dictionary gen_current_animation_data(const String &animation, int64_t track_id, bool loop, bool clear, bool empty, bool empty_duration, float delay); + +public: + SpineSpriteAnimateDialog(); + ~SpineSpriteAnimateDialog(); + + void set_animate_button(ToolButton *b); + inline ToolButton *get_animate_button() { return animate_button; } + + inline void set_plugin(EditorPlugin *p) { the_plugin = p; } + + void _on_animate_button_pressed(); + void _on_scene_tree_selected(NodePath path); + void _on_scene_tree_hide(); + void _on_animate_dialog_action(const String &act); +}; +#endif + +#endif//GODOT_SPINESPRITEANIMATEDIALOG_H diff --git a/spine-godot/spine_godot/SpineSpriteMeshInstance2D.cpp b/spine-godot/spine_godot/SpineSpriteMeshInstance2D.cpp new file mode 100644 index 000000000..aba2064f0 --- /dev/null +++ b/spine-godot/spine_godot/SpineSpriteMeshInstance2D.cpp @@ -0,0 +1,48 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineSpriteMeshInstance2D.h" + +#include "SpineBone.h" + +void SpineSpriteMeshInstance2D::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_slot"), &SpineSpriteMeshInstance2D::get_slot); + ClassDB::bind_method(D_METHOD("apply_transform_2d", "node2d"), &SpineSpriteMeshInstance2D::apply_transform_2d); +} + +SpineSpriteMeshInstance2D::SpineSpriteMeshInstance2D() {} +SpineSpriteMeshInstance2D::~SpineSpriteMeshInstance2D() {} + +Ref SpineSpriteMeshInstance2D::get_slot() { + return slot; +} + +void SpineSpriteMeshInstance2D::apply_transform_2d(Variant o) { + slot->get_bone()->apply_world_transform_2d(o); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineSpriteMeshInstance2D.h b/spine-godot/spine_godot/SpineSpriteMeshInstance2D.h new file mode 100644 index 000000000..c748b21cb --- /dev/null +++ b/spine-godot/spine_godot/SpineSpriteMeshInstance2D.h @@ -0,0 +1,57 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINESPRITEMESHINSTANCE2D_H +#define GODOT_SPINESPRITEMESHINSTANCE2D_H + +#include + +#include "SpineSlot.h" + +class SpineSpriteMeshInstance2D : public MeshInstance2D { + GDCLASS(SpineSpriteMeshInstance2D, MeshInstance2D); + +protected: + static void _bind_methods(); + + Ref slot; + +public: + SpineSpriteMeshInstance2D(); + ~SpineSpriteMeshInstance2D(); + + inline void set_slot(Ref s) { + slot = s; + } + Ref get_slot(); + + void apply_transform_2d(Variant o); +}; + +#endif//GODOT_SPINESPRITEMESHINSTANCE2D_H diff --git a/spine-godot/spine_godot/SpineTimeline.cpp b/spine-godot/spine_godot/SpineTimeline.cpp new file mode 100644 index 000000000..29561c595 --- /dev/null +++ b/spine-godot/spine_godot/SpineTimeline.cpp @@ -0,0 +1,99 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineTimeline.h" + +#include "SpineSkeleton.h" +#include "SpineEvent.h" + +// enable more than 5 arguments of a method bind function +#include "core/method_bind_ext.gen.inc" + +void SpineTimeline::_bind_methods() { + ClassDB::bind_method(D_METHOD("apply", "skeleton", "lastTime", "time", "pEvents", "alpha", "blend", "direction"), &SpineTimeline::apply); + ClassDB::bind_method(D_METHOD("get_frame_entries"), &SpineTimeline::get_frame_entries); + ClassDB::bind_method(D_METHOD("get_frame_count"), &SpineTimeline::get_frame_count); + ClassDB::bind_method(D_METHOD("get_frames"), &SpineTimeline::get_frames); + ClassDB::bind_method(D_METHOD("get_duration"), &SpineTimeline::get_duration); + ClassDB::bind_method(D_METHOD("getPropertyIds"), &SpineTimeline::getPropertyIds); +} + + +SpineTimeline::SpineTimeline() : timeline(nullptr) { +} + +SpineTimeline::~SpineTimeline() { +} + +void SpineTimeline::apply(Ref skeleton, float lastTime, float time, Array pEvents, float alpha, + SpineConstant::MixBlend blend, SpineConstant::MixDirection direction) { + spine::Vector events; + events.setSize(pEvents.size(), nullptr); + for (size_t i = 0; i < events.size(); ++i) { + events[i] = ((Ref) pEvents[i])->get_spine_object(); + } + + timeline->apply(*(skeleton->get_spine_object()), lastTime, time, &events, alpha, (spine::MixBlend) blend, (spine::MixDirection) direction); +} + +int64_t SpineTimeline::get_frame_entries() { + return timeline->getFrameEntries(); +} + +int64_t SpineTimeline::get_frame_count() { + return timeline->getFrameCount(); +} + +Array SpineTimeline::get_frames() { + auto &frames = timeline->getFrames(); + Array res; + res.resize(frames.size()); + + for (size_t i = 0; i < res.size(); ++i) { + res[i] = frames[i]; + } + + return res; +} + +float SpineTimeline::get_duration() { + return timeline->getDuration(); +} + +Array SpineTimeline::getPropertyIds() { + auto &ids = timeline->getPropertyIds(); + Array res; + res.resize(ids.size()); + + for (size_t i = 0; i < res.size(); ++i) { + res[i] = (int64_t) ids[i]; + } + + return res; +} diff --git a/spine-godot/spine_godot/SpineTimeline.h b/spine-godot/spine_godot/SpineTimeline.h new file mode 100644 index 000000000..404d7dd26 --- /dev/null +++ b/spine-godot/spine_godot/SpineTimeline.h @@ -0,0 +1,75 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINETIMELINE_H +#define GODOT_SPINETIMELINE_H + +#include "core/variant_parser.h" + +#include "spine/Timeline.h" + +#include "SpineConstant.h" + +class SpineSkeleton; +class SpineEvent; + +class SpineTimeline : public Reference { + GDCLASS(SpineTimeline, Reference); + +protected: + static void _bind_methods(); + +private: + spine::Timeline *timeline; + +public: + SpineTimeline(); + ~SpineTimeline(); + + inline void set_spine_object(spine::Timeline *v) { timeline = v; } + inline spine::Timeline *get_spine_object() { return timeline; } + + // Vector + void apply(Ref skeleton, float lastTime, float time, Array pEvents, float alpha, SpineConstant::MixBlend blend, SpineConstant::MixDirection direction); + + int64_t get_frame_entries(); + + int64_t get_frame_count(); + + // Vector + Array get_frames(); + + float get_duration(); + + // Vector + Array getPropertyIds(); +}; + + +#endif//GODOT_SPINETIMELINE_H diff --git a/spine-godot/spine_godot/SpineTrackEntry.cpp b/spine-godot/spine_godot/SpineTrackEntry.cpp new file mode 100644 index 000000000..fe6979af9 --- /dev/null +++ b/spine-godot/spine_godot/SpineTrackEntry.cpp @@ -0,0 +1,265 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineTrackEntry.h" + +void SpineTrackEntry::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_track_index"), &SpineTrackEntry::get_track_index); + + ClassDB::bind_method(D_METHOD("get_animation"), &SpineTrackEntry::get_animation); + + ClassDB::bind_method(D_METHOD("get_loop"), &SpineTrackEntry::get_loop); + ClassDB::bind_method(D_METHOD("set_loop", "v"), &SpineTrackEntry::set_loop); + + ClassDB::bind_method(D_METHOD("get_hold_previous"), &SpineTrackEntry::get_hold_previous); + ClassDB::bind_method(D_METHOD("set_hold_previous", "v"), &SpineTrackEntry::set_hold_previous); + + ClassDB::bind_method(D_METHOD("get_reverse"), &SpineTrackEntry::get_reverse); + ClassDB::bind_method(D_METHOD("set_reverse", "v"), &SpineTrackEntry::set_reverse); + + ClassDB::bind_method(D_METHOD("get_delay"), &SpineTrackEntry::get_delay); + ClassDB::bind_method(D_METHOD("set_delay", "v"), &SpineTrackEntry::set_delay); + + ClassDB::bind_method(D_METHOD("get_track_time"), &SpineTrackEntry::get_track_time); + ClassDB::bind_method(D_METHOD("set_track_time", "v"), &SpineTrackEntry::set_track_time); + + ClassDB::bind_method(D_METHOD("get_track_end"), &SpineTrackEntry::get_track_end); + ClassDB::bind_method(D_METHOD("set_track_end", "v"), &SpineTrackEntry::set_track_end); + + ClassDB::bind_method(D_METHOD("get_animation_start"), &SpineTrackEntry::get_animation_start); + ClassDB::bind_method(D_METHOD("set_animation_start", "v"), &SpineTrackEntry::set_animation_start); + + ClassDB::bind_method(D_METHOD("get_animation_last"), &SpineTrackEntry::get_animation_last); + ClassDB::bind_method(D_METHOD("set_animation_last", "v"), &SpineTrackEntry::set_animation_last); + + ClassDB::bind_method(D_METHOD("get_animation_time"), &SpineTrackEntry::get_animation_time); + + ClassDB::bind_method(D_METHOD("get_time_scale"), &SpineTrackEntry::get_time_scale); + ClassDB::bind_method(D_METHOD("set_time_scale", "v"), &SpineTrackEntry::set_time_scale); + + ClassDB::bind_method(D_METHOD("get_alpha"), &SpineTrackEntry::get_alpha); + ClassDB::bind_method(D_METHOD("set_alpha", "v"), &SpineTrackEntry::set_alpha); + + ClassDB::bind_method(D_METHOD("get_event_threshold"), &SpineTrackEntry::get_event_threshold); + ClassDB::bind_method(D_METHOD("set_event_threshold", "v"), &SpineTrackEntry::set_event_threshold); + + ClassDB::bind_method(D_METHOD("get_attachment_threshold"), &SpineTrackEntry::get_attachment_threshold); + ClassDB::bind_method(D_METHOD("set_attachment_threshold", "v"), &SpineTrackEntry::set_attachment_threshold); + + ClassDB::bind_method(D_METHOD("get_draw_order_threshold"), &SpineTrackEntry::get_draw_order_threshold); + ClassDB::bind_method(D_METHOD("set_draw_order_threshold", "v"), &SpineTrackEntry::set_draw_order_threshold); + + ClassDB::bind_method(D_METHOD("get_next"), &SpineTrackEntry::get_next); + + ClassDB::bind_method(D_METHOD("is_complete"), &SpineTrackEntry::is_complete); + + ClassDB::bind_method(D_METHOD("get_mix_time"), &SpineTrackEntry::get_mix_time); + ClassDB::bind_method(D_METHOD("set_mix_time", "v"), &SpineTrackEntry::set_mix_time); + + ClassDB::bind_method(D_METHOD("get_mix_duration"), &SpineTrackEntry::get_mix_duration); + ClassDB::bind_method(D_METHOD("set_mix_duration", "v"), &SpineTrackEntry::set_mix_duration); + + ClassDB::bind_method(D_METHOD("get_mix_blend"), &SpineTrackEntry::get_mix_blend); + ClassDB::bind_method(D_METHOD("set_mix_blend", "v"), &SpineTrackEntry::set_mix_blend); + + ClassDB::bind_method(D_METHOD("get_mixing_from"), &SpineTrackEntry::get_mixing_from); + ClassDB::bind_method(D_METHOD("get_mixing_to"), &SpineTrackEntry::get_mixing_to); + + ClassDB::bind_method(D_METHOD("reset_rotation_directions"), &SpineTrackEntry::reset_rotation_directions); + + BIND_ENUM_CONSTANT(MIXBLEND_SETUP); + BIND_ENUM_CONSTANT(MIXBLEND_FIRST); + BIND_ENUM_CONSTANT(MIXBLEND_REPLACE); + BIND_ENUM_CONSTANT(MIXBLEND_ADD); +} + +SpineTrackEntry::SpineTrackEntry() : track_entry(NULL) {} +SpineTrackEntry::~SpineTrackEntry() {} + +int SpineTrackEntry::get_track_index() { + return track_entry->getTrackIndex(); +} + +Ref SpineTrackEntry::get_animation() { + Ref gd_anim(memnew(SpineAnimation)); + auto anim = track_entry->getAnimation(); + if (anim == NULL) return NULL; + gd_anim->set_spine_object(anim); + return gd_anim; +} + +bool SpineTrackEntry::get_loop() { + return track_entry->getLoop(); +} +void SpineTrackEntry::set_loop(bool v) { + track_entry->setLoop(v); +} + +bool SpineTrackEntry::get_hold_previous() { + return track_entry->getHoldPrevious(); +} +void SpineTrackEntry::set_hold_previous(bool v) { + track_entry->setHoldPrevious(v); +} + +float SpineTrackEntry::get_delay() { + return track_entry->getDelay(); +} +void SpineTrackEntry::set_delay(float v) { + track_entry->setDelay(v); +} + +float SpineTrackEntry::get_track_time() { + return track_entry->getTrackTime(); +} +void SpineTrackEntry::set_track_time(float v) { + track_entry->setTrackTime(v); +} + +float SpineTrackEntry::get_track_end() { + return track_entry->getTrackEnd(); +} +void SpineTrackEntry::set_track_end(float v) { + track_entry->setTrackEnd(v); +} + +float SpineTrackEntry::get_animation_start() { + return track_entry->getAnimationStart(); +} +void SpineTrackEntry::set_animation_start(float v) { + track_entry->setAnimationStart(v); +} + +float SpineTrackEntry::get_animation_last() { + return track_entry->getAnimationLast(); +} +void SpineTrackEntry::set_animation_last(float v) { + track_entry->setAnimationLast(v); +} + +float SpineTrackEntry::get_animation_time() { + return track_entry->getAnimationTime(); +} + +float SpineTrackEntry::get_time_scale() { + return track_entry->getTimeScale(); +} +void SpineTrackEntry::set_time_scale(float v) { + track_entry->setTimeScale(v); +} + +float SpineTrackEntry::get_alpha() { + return track_entry->getAlpha(); +} +void SpineTrackEntry::set_alpha(float v) { + track_entry->setAlpha(v); +} + +float SpineTrackEntry::get_event_threshold() { + return track_entry->getEventThreshold(); +} +void SpineTrackEntry::set_event_threshold(float v) { + track_entry->setEventThreshold(v); +} + +float SpineTrackEntry::get_attachment_threshold() { + return track_entry->getAttachmentThreshold(); +} +void SpineTrackEntry::set_attachment_threshold(float v) { + track_entry->setAttachmentThreshold(v); +} + +float SpineTrackEntry::get_draw_order_threshold() { + return track_entry->getDrawOrderThreshold(); +} +void SpineTrackEntry::set_draw_order_threshold(float v) { + track_entry->setDrawOrderThreshold(v); +} + +Ref SpineTrackEntry::get_next() { + Ref gd_entry(memnew(SpineTrackEntry)); + auto entry = track_entry->getNext(); + if (entry == NULL) return NULL; + gd_entry->set_spine_object(entry); + return gd_entry; +} + +bool SpineTrackEntry::is_complete() { + return track_entry->isComplete(); +} + +float SpineTrackEntry::get_mix_time() { + return track_entry->getMixTime(); +} +void SpineTrackEntry::set_mix_time(float v) { + track_entry->setMixTime(v); +} + +float SpineTrackEntry::get_mix_duration() { + return track_entry->getMixDuration(); +} +void SpineTrackEntry::set_mix_duration(float v) { + track_entry->setMixDuration(v); +} + +SpineTrackEntry::MixBlend SpineTrackEntry::get_mix_blend() { + int mb = track_entry->getMixBlend(); + return (MixBlend) mb; +} +void SpineTrackEntry::set_mix_blend(SpineTrackEntry::MixBlend v) { + int mb = (int) v; + track_entry->setMixBlend((spine::MixBlend) mb); +} + +Ref SpineTrackEntry::get_mixing_from() { + Ref gd_entry(memnew(SpineTrackEntry)); + auto entry = track_entry->getMixingFrom(); + if (entry == NULL) return NULL; + gd_entry->set_spine_object(entry); + return gd_entry; +} +Ref SpineTrackEntry::get_mixing_to() { + Ref gd_entry(memnew(SpineTrackEntry)); + auto entry = track_entry->getMixingTo(); + if (entry == NULL) return NULL; + gd_entry->set_spine_object(entry); + return gd_entry; +} + +void SpineTrackEntry::reset_rotation_directions() { + track_entry->resetRotationDirections(); +} + +bool SpineTrackEntry::get_reverse() { + return track_entry->getReverse(); +} + +void SpineTrackEntry::set_reverse(bool v) { + track_entry->setReverse(v); +} diff --git a/spine-godot/spine_godot/SpineTrackEntry.h b/spine-godot/spine_godot/SpineTrackEntry.h new file mode 100644 index 000000000..25c4b785f --- /dev/null +++ b/spine-godot/spine_godot/SpineTrackEntry.h @@ -0,0 +1,131 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINETRACKENTRY_H +#define GODOT_SPINETRACKENTRY_H + +#include "core/variant_parser.h" + +#include + +#include "SpineAnimation.h" + +class SpineTrackEntry : public Reference { + GDCLASS(SpineTrackEntry, Reference); + +protected: + static void _bind_methods(); + +private: + spine::TrackEntry *track_entry; + +public: + SpineTrackEntry(); + ~SpineTrackEntry(); + + inline void set_spine_object(spine::TrackEntry *t) { + track_entry = t; + } + inline spine::TrackEntry *get_spine_object() { + return track_entry; + } + + enum MixBlend { + MIXBLEND_SETUP = 0, + MIXBLEND_FIRST, + MIXBLEND_REPLACE, + MIXBLEND_ADD + }; + + int get_track_index(); + + Ref get_animation(); + + bool get_loop(); + void set_loop(bool v); + + bool get_hold_previous(); + void set_hold_previous(bool v); + + bool get_reverse(); + void set_reverse(bool v); + + float get_delay(); + void set_delay(float v); + + float get_track_time(); + void set_track_time(float v); + + float get_track_end(); + void set_track_end(float v); + + float get_animation_start(); + void set_animation_start(float v); + + float get_animation_last(); + void set_animation_last(float v); + + float get_animation_time(); + + float get_time_scale(); + void set_time_scale(float v); + + float get_alpha(); + void set_alpha(float v); + + float get_event_threshold(); + void set_event_threshold(float v); + + float get_attachment_threshold(); + void set_attachment_threshold(float v); + + float get_draw_order_threshold(); + void set_draw_order_threshold(float v); + + Ref get_next(); + + bool is_complete(); + + float get_mix_time(); + void set_mix_time(float v); + + float get_mix_duration(); + void set_mix_duration(float v); + + MixBlend get_mix_blend(); + void set_mix_blend(MixBlend v); + + Ref get_mixing_from(); + Ref get_mixing_to(); + + void reset_rotation_directions(); +}; + +VARIANT_ENUM_CAST(SpineTrackEntry::MixBlend); +#endif//GODOT_SPINETRACKENTRY_H diff --git a/spine-godot/spine_godot/SpineTransformConstraint.cpp b/spine-godot/spine_godot/SpineTransformConstraint.cpp new file mode 100644 index 000000000..2166a5917 --- /dev/null +++ b/spine-godot/spine_godot/SpineTransformConstraint.cpp @@ -0,0 +1,148 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineTransformConstraint.h" + +void SpineTransformConstraint::_bind_methods() { + ClassDB::bind_method(D_METHOD("update"), &SpineTransformConstraint::update); + ClassDB::bind_method(D_METHOD("get_data"), &SpineTransformConstraint::get_data); + ClassDB::bind_method(D_METHOD("get_bones"), &SpineTransformConstraint::get_bones); + ClassDB::bind_method(D_METHOD("get_target"), &SpineTransformConstraint::get_target); + ClassDB::bind_method(D_METHOD("set_target", "v"), &SpineTransformConstraint::set_target); + ClassDB::bind_method(D_METHOD("get_mix_rotate"), &SpineTransformConstraint::get_mix_rotate); + ClassDB::bind_method(D_METHOD("set_mix_rotate", "v"), &SpineTransformConstraint::set_mix_rotate); + ClassDB::bind_method(D_METHOD("get_mix_x"), &SpineTransformConstraint::get_mix_x); + ClassDB::bind_method(D_METHOD("set_mix_x", "v"), &SpineTransformConstraint::set_mix_x); + ClassDB::bind_method(D_METHOD("get_mix_y"), &SpineTransformConstraint::get_mix_y); + ClassDB::bind_method(D_METHOD("set_mix_y", "v"), &SpineTransformConstraint::set_mix_y); + ClassDB::bind_method(D_METHOD("get_mix_scale_x"), &SpineTransformConstraint::get_mix_scale_x); + ClassDB::bind_method(D_METHOD("set_mix_scale_x", "v"), &SpineTransformConstraint::set_mix_scale_x); + ClassDB::bind_method(D_METHOD("get_mix_scale_y"), &SpineTransformConstraint::get_mix_scale_y); + ClassDB::bind_method(D_METHOD("set_mix_scale_y", "v"), &SpineTransformConstraint::set_mix_scale_y); + ClassDB::bind_method(D_METHOD("get_mix_shear_y"), &SpineTransformConstraint::get_mix_shear_y); + ClassDB::bind_method(D_METHOD("set_mix_shear_y", "v"), &SpineTransformConstraint::set_mix_shear_y); + ClassDB::bind_method(D_METHOD("is_active"), &SpineTransformConstraint::is_active); + ClassDB::bind_method(D_METHOD("set_active", "v"), &SpineTransformConstraint::set_active); +} + +SpineTransformConstraint::SpineTransformConstraint() : transform_constraint(NULL) {} +SpineTransformConstraint::~SpineTransformConstraint() {} + +void SpineTransformConstraint::update() { + transform_constraint->update(); +} + +int SpineTransformConstraint::get_order() { + return transform_constraint->getOrder(); +} + +Ref SpineTransformConstraint::get_data() { + auto &d = transform_constraint->getData(); + Ref gd_d(memnew(SpineTransformConstraintData)); + gd_d->set_spine_object(&d); + return gd_d; +} + +Array SpineTransformConstraint::get_bones() { + auto &bs = transform_constraint->getBones(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + auto b = bs[i]; + if (b == NULL) gd_bs[i] = Ref(NULL); + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + gd_bs[i] = gd_b; + } + return gd_bs; +} + +Ref SpineTransformConstraint::get_target() { + auto b = transform_constraint->getTarget(); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineBone)); + gd_b->set_spine_object(b); + return gd_b; +} +void SpineTransformConstraint::set_target(Ref v) { + if (v.is_valid()) { + transform_constraint->setTarget(v->get_spine_object()); + } else { + transform_constraint->setTarget(NULL); + } +} + +float SpineTransformConstraint::get_mix_rotate() { + return transform_constraint->getMixRotate(); +} +void SpineTransformConstraint::set_mix_rotate(float v) { + transform_constraint->setMixRotate(v); +} + +float SpineTransformConstraint::get_mix_x() { + return transform_constraint->getMixX(); +} +void SpineTransformConstraint::set_mix_x(float v) { + transform_constraint->setMixX(v); +} + +float SpineTransformConstraint::get_mix_y() { + return transform_constraint->getMixY(); +} +void SpineTransformConstraint::set_mix_y(float v) { + transform_constraint->setMixY(v); +} + +float SpineTransformConstraint::get_mix_scale_x() { + return transform_constraint->getMixScaleX(); +} +void SpineTransformConstraint::set_mix_scale_x(float v) { + transform_constraint->setMixScaleX(v); +} + +float SpineTransformConstraint::get_mix_scale_y() { + return transform_constraint->getMixScaleY(); +} +void SpineTransformConstraint::set_mix_scale_y(float v) { + transform_constraint->setMixScaleY(v); +} + +float SpineTransformConstraint::get_mix_shear_y() { + return transform_constraint->getMixShearY(); +} +void SpineTransformConstraint::set_mix_shear_y(float v) { + transform_constraint->setMixShearY(v); +} + +bool SpineTransformConstraint::is_active() { + return transform_constraint->isActive(); +} +void SpineTransformConstraint::set_active(bool v) { + transform_constraint->setActive(v); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineTransformConstraint.h b/spine-godot/spine_godot/SpineTransformConstraint.h new file mode 100644 index 000000000..6430f05fb --- /dev/null +++ b/spine-godot/spine_godot/SpineTransformConstraint.h @@ -0,0 +1,93 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINETRANSFORMCONSTRAINT_H +#define GODOT_SPINETRANSFORMCONSTRAINT_H + +#include "core/variant_parser.h" + +#include + +#include "SpineTransformConstraintData.h" +#include "SpineBone.h" + +class SpineTransformConstraint : public Reference { + GDCLASS(SpineTransformConstraint, Reference); + +protected: + static void _bind_methods(); + +private: + spine::TransformConstraint *transform_constraint; + +public: + SpineTransformConstraint(); + ~SpineTransformConstraint(); + + inline void set_spine_object(spine::TransformConstraint *tc) { + transform_constraint = tc; + } + inline spine::TransformConstraint *get_spine_object() { + return transform_constraint; + } + + void update(); + + int get_order(); + + Ref get_data(); + + Array get_bones(); + + Ref get_target(); + void set_target(Ref v); + + float get_mix_rotate(); + void set_mix_rotate(float v); + + float get_mix_x(); + void set_mix_x(float v); + + float get_mix_y(); + void set_mix_y(float v); + + float get_mix_scale_x(); + void set_mix_scale_x(float v); + + float get_mix_scale_y(); + void set_mix_scale_y(float v); + + float get_mix_shear_y(); + void set_mix_shear_y(float v); + + bool is_active(); + void set_active(bool v); +}; + +#endif//GODOT_SPINETRANSFORMCONSTRAINT_H diff --git a/spine-godot/spine_godot/SpineTransformConstraintData.cpp b/spine-godot/spine_godot/SpineTransformConstraintData.cpp new file mode 100644 index 000000000..c7534cafb --- /dev/null +++ b/spine-godot/spine_godot/SpineTransformConstraintData.cpp @@ -0,0 +1,118 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "SpineTransformConstraintData.h" + +void SpineTransformConstraintData::_bind_methods() { + ClassDB::bind_method(D_METHOD("get_all_bone_data"), &SpineTransformConstraintData::get_bones); + ClassDB::bind_method(D_METHOD("get_target"), &SpineTransformConstraintData::get_target); + ClassDB::bind_method(D_METHOD("get_mix_rotate"), &SpineTransformConstraintData::get_mix_rotate); + ClassDB::bind_method(D_METHOD("get_mix_x"), &SpineTransformConstraintData::get_mix_x); + ClassDB::bind_method(D_METHOD("get_mix_y"), &SpineTransformConstraintData::get_mix_y); + ClassDB::bind_method(D_METHOD("get_mix_scale_x"), &SpineTransformConstraintData::get_mix_scale_x); + ClassDB::bind_method(D_METHOD("get_mix_scale_y"), &SpineTransformConstraintData::get_mix_scale_y); + ClassDB::bind_method(D_METHOD("get_mix_shear_y"), &SpineTransformConstraintData::get_mix_shear_y); + ClassDB::bind_method(D_METHOD("get_offset_rotation"), &SpineTransformConstraintData::get_offset_rotation); + ClassDB::bind_method(D_METHOD("get_offset_x"), &SpineTransformConstraintData::get_offset_x); + ClassDB::bind_method(D_METHOD("get_offset_y"), &SpineTransformConstraintData::get_offset_y); + ClassDB::bind_method(D_METHOD("get_offset_scale_x"), &SpineTransformConstraintData::get_offset_scale_x); + ClassDB::bind_method(D_METHOD("get_offset_scale_y"), &SpineTransformConstraintData::get_offset_scale_y); + ClassDB::bind_method(D_METHOD("get_offset_shear_y"), &SpineTransformConstraintData::get_offset_shear_y); + ClassDB::bind_method(D_METHOD("is_relative"), &SpineTransformConstraintData::is_relative); + ClassDB::bind_method(D_METHOD("is_local"), &SpineTransformConstraintData::is_local); +} + +SpineTransformConstraintData::SpineTransformConstraintData() {} +SpineTransformConstraintData::~SpineTransformConstraintData() {} + +Array SpineTransformConstraintData::get_bones() { + auto bs = get_spine_data()->getBones(); + Array gd_bs; + gd_bs.resize(bs.size()); + for (size_t i = 0; i < bs.size(); ++i) { + if (bs[i] == NULL) gd_bs[i] = Ref(NULL); + else { + Ref gd_b(memnew(SpineBoneData)); + gd_b->set_spine_object(bs[i]); + gd_bs[i] = gd_b; + } + } + return gd_bs; +} +Ref SpineTransformConstraintData::get_target() { + auto b = get_spine_data()->getTarget(); + if (b == NULL) return NULL; + Ref gd_b(memnew(SpineBoneData)); + gd_b->set_spine_object(b); + return gd_b; +} +float SpineTransformConstraintData::get_mix_rotate() { + return get_spine_data()->getMixRotate(); +} +float SpineTransformConstraintData::get_mix_x() { + return get_spine_data()->getMixX(); +} +float SpineTransformConstraintData::get_mix_y() { + return get_spine_data()->getMixY(); +} +float SpineTransformConstraintData::get_mix_scale_x() { + return get_spine_data()->getMixScaleX(); +} +float SpineTransformConstraintData::get_mix_scale_y() { + return get_spine_data()->getMixScaleY(); +} +float SpineTransformConstraintData::get_mix_shear_y() { + return get_spine_data()->getMixShearY(); +} + +float SpineTransformConstraintData::get_offset_rotation() { + return get_spine_data()->getOffsetRotation(); +} +float SpineTransformConstraintData::get_offset_x() { + return get_spine_data()->getOffsetX(); +} +float SpineTransformConstraintData::get_offset_y() { + return get_spine_data()->getOffsetY(); +} +float SpineTransformConstraintData::get_offset_scale_x() { + return get_spine_data()->getOffsetScaleX(); +} +float SpineTransformConstraintData::get_offset_scale_y() { + return get_spine_data()->getOffsetScaleY(); +} +float SpineTransformConstraintData::get_offset_shear_y() { + return get_spine_data()->getOffsetShearY(); +} + +bool SpineTransformConstraintData::is_relative() { + return get_spine_data()->isRelative(); +} +bool SpineTransformConstraintData::is_local() { + return get_spine_data()->isLocal(); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/SpineTransformConstraintData.h b/spine-godot/spine_godot/SpineTransformConstraintData.h new file mode 100644 index 000000000..6c1b21569 --- /dev/null +++ b/spine-godot/spine_godot/SpineTransformConstraintData.h @@ -0,0 +1,74 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#ifndef GODOT_SPINETRANSFORMCONSTRAINTDATA_H +#define GODOT_SPINETRANSFORMCONSTRAINTDATA_H + +#include "core/variant_parser.h" + +#include + +#include "SpineConstraintData.h" +#include "SpineBoneData.h" + +class SpineTransformConstraintData : public SpineConstraintData { + GDCLASS(SpineTransformConstraintData, SpineConstraintData); + +protected: + static void _bind_methods(); + +public: + SpineTransformConstraintData(); + ~SpineTransformConstraintData(); + + virtual inline spine::TransformConstraintData *get_spine_data() { + return (spine::TransformConstraintData *) SpineConstraintData::get_spine_object(); + } + + Array get_bones(); + Ref get_target(); + float get_mix_rotate(); + float get_mix_x(); + float get_mix_y(); + float get_mix_scale_x(); + float get_mix_scale_y(); + float get_mix_shear_y(); + + float get_offset_rotation(); + float get_offset_x(); + float get_offset_y(); + float get_offset_scale_x(); + float get_offset_scale_y(); + float get_offset_shear_y(); + + bool is_relative(); + bool is_local(); +}; + +#endif//GODOT_SPINETRANSFORMCONSTRAINTDATA_H diff --git a/spine-godot/spine_godot/config.py b/spine-godot/spine_godot/config.py new file mode 100644 index 000000000..827e2c435 --- /dev/null +++ b/spine-godot/spine_godot/config.py @@ -0,0 +1,5 @@ +def can_build(env, platform): + return True + +def configure(env): + pass \ No newline at end of file diff --git a/spine-godot/spine_godot/register_types.cpp b/spine-godot/spine_godot/register_types.cpp new file mode 100644 index 000000000..1fd9ad626 --- /dev/null +++ b/spine-godot/spine_godot/register_types.cpp @@ -0,0 +1,144 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +#include "register_types.h" + +#include "core/class_db.h" + +#include "SpineAtlasResource.h" +#include "SpineSkeletonDataResource.h" +#include "ResourceFormatLoaderSpineSkeletonJsonData.h" +#include "ResourceFormatSaverSpineSkeletonJsonData.h" +#include "SpineSprite.h" +#include "SpineAnimationStateDataResource.h" +#include "SpineSkeleton.h" +#include "SpineAnimationState.h" +#include "SpineEventData.h" +#include "SpineEvent.h" +#include "SpineTrackEntry.h" +#include "SpineBoneData.h" +#include "SpineSlotData.h" +#include "SpineAttachment.h" +#include "SpineSkinAttachmentMapEntries.h" +#include "SpineConstraintData.h" +#include "SpineSkin.h" +#include "SpineIkConstraintData.h" +#include "SpineTransformConstraintData.h" +#include "SpinePathConstraintData.h" +#include "SpineSpriteMeshInstance2D.h" +#include "SpineTimeline.h" +#include "SpineConstant.h" +#include "SpineCollisionShapeProxy.h" +#include "SpineSpriteAnimateDialog.h" + + +static Ref atlas_loader; +static Ref atlas_saver; +static Ref json_skeleton_loader; +static Ref json_skeleton_saver; + +// editor plugin +#ifdef TOOLS_ENABLED +#include "editor/editor_export.h" +#include "editor/editor_node.h" + +#include "SpineRuntimeEditorPlugin.h" + +static void editor_init_callback() { + EditorNode::get_singleton()->add_editor_plugin(memnew(SpineRuntimeEditorPlugin(EditorNode::get_singleton()))); +} + + +#endif + +void register_spine_godot_types() { +#ifdef TOOLS_ENABLED + ClassDB::register_class(); + + EditorNode::add_init_callback(editor_init_callback); + +#endif + + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + ClassDB::register_class(); + + atlas_loader.instance(); + ResourceLoader::add_resource_format_loader(atlas_loader); + + atlas_saver.instance(); + ResourceSaver::add_resource_format_saver(atlas_saver); + + json_skeleton_loader.instance(); + ResourceLoader::add_resource_format_loader(json_skeleton_loader); + + json_skeleton_saver.instance(); + ResourceSaver::add_resource_format_saver(json_skeleton_saver); +} + +void unregister_spine_godot_types() { + ResourceLoader::remove_resource_format_loader(atlas_loader); + atlas_loader.unref(); + + ResourceSaver::remove_resource_format_saver(atlas_saver); + atlas_saver.unref(); + + ResourceLoader::remove_resource_format_loader(json_skeleton_loader); + json_skeleton_loader.unref(); + + ResourceSaver::remove_resource_format_saver(json_skeleton_saver); + json_skeleton_saver.unref(); +} \ No newline at end of file diff --git a/spine-godot/spine_godot/register_types.h b/spine-godot/spine_godot/register_types.h new file mode 100644 index 000000000..59ef9515f --- /dev/null +++ b/spine-godot/spine_godot/register_types.h @@ -0,0 +1,31 @@ +/****************************************************************************** + * Spine Runtimes License Agreement + * Last updated January 1, 2020. Replaces all prior versions. + * + * Copyright (c) 2013-2020, Esoteric Software LLC + * + * Integration of the Spine Runtimes into software or otherwise creating + * derivative works of the Spine Runtimes is permitted under the terms and + * conditions of Section 2 of the Spine Editor License Agreement: + * http://esotericsoftware.com/spine-editor-license + * + * Otherwise, it is permitted to integrate the Spine Runtimes into software + * or otherwise create derivative works of the Spine Runtimes (collectively, + * "Products"), provided that each user of the Products must obtain their own + * Spine Editor license and redistribution of the Products in any form must + * include this license and copyright notice. + * + * THE SPINE RUNTIMES ARE PROVIDED BY ESOTERIC SOFTWARE LLC "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL ESOTERIC SOFTWARE LLC BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, + * BUSINESS INTERRUPTION, OR LOSS OF USE, DATA, OR PROFITS) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THE SPINE RUNTIMES, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + *****************************************************************************/ + +void register_spine_godot_types(); +void unregister_spine_godot_types();