Skip to content

Commit

Permalink
Merge pull request #2943 from QuantumCoderQC/tilesheet-improvements
Browse files Browse the repository at this point in the history
Tilesheet improvements
  • Loading branch information
luboslenco committed Oct 10, 2023
2 parents 8009b94 + c28d762 commit fd47e1b
Show file tree
Hide file tree
Showing 14 changed files with 120 additions and 10 deletions.
10 changes: 6 additions & 4 deletions Sources/armory/logicnode/GetTilesheetStateNode.hx
Expand Up @@ -13,12 +13,14 @@ class GetTilesheetStateNode extends LogicNode {

if (object == null) return null;

var tilesheet = object.tilesheet;
var tilesheet = object.activeTilesheet;

return switch (from) {
case 0: tilesheet.action.name;
case 1: tilesheet.frame;
case 2: tilesheet.paused;
case 0: tilesheet.raw.name;
case 1: tilesheet.action.name;
case 2: tilesheet.getFrameOffset();
case 3: tilesheet.frame;
case 4: tilesheet.paused;
default: null;
}
}
Expand Down
2 changes: 1 addition & 1 deletion Sources/armory/logicnode/PauseTilesheetNode.hx
Expand Up @@ -13,7 +13,7 @@ class PauseTilesheetNode extends LogicNode {

if (object == null) return;

object.tilesheet.pause();
object.activeTilesheet.pause();

runOutput(0);
}
Expand Down
2 changes: 1 addition & 1 deletion Sources/armory/logicnode/PlayTilesheetNode.hx
Expand Up @@ -14,7 +14,7 @@ class PlayTilesheetNode extends LogicNode {

if (object == null) return;

object.tilesheet.play(action, function() {
object.activeTilesheet.play(action, function() {
runOutput(1);
});

Expand Down
23 changes: 23 additions & 0 deletions Sources/armory/logicnode/SetActiveTilesheetNode.hx
@@ -0,0 +1,23 @@
package armory.logicnode;

import iron.Scene;
import iron.object.MeshObject;

class SetActiveTilesheetNode extends LogicNode {

public function new(tree: LogicTree) {
super(tree);
}

override function run(from: Int) {
var object: MeshObject = inputs[1].get();
var tilesheet: String = inputs[2].get();
var action: String = inputs[3].get();

if (object == null) return;

object.setActiveTilesheet(Scene.active.raw.name, tilesheet, action);

runOutput(0);
}
}
21 changes: 21 additions & 0 deletions Sources/armory/logicnode/SetTilesheetFrameNode.hx
@@ -0,0 +1,21 @@
package armory.logicnode;

import iron.object.MeshObject;

class SetTilesheetFrameNode extends LogicNode {

public function new(tree: LogicTree) {
super(tree);
}

override function run(from: Int) {
var object: MeshObject = inputs[1].get();
var frame: Int = inputs[2].get();

if (object == null) return;

object.activeTilesheet.setFrameOffset(frame);

runOutput(0);
}
}
3 changes: 2 additions & 1 deletion blender/arm/exporter.py
Expand Up @@ -590,7 +590,8 @@ def create_material_variants(scene: bpy.types.Scene) -> Tuple[List[bpy.types.Mat
variant_suffix = '_armskin'
# Tilesheets
elif bobject.arm_tilesheet != '':
variant_suffix = '_armtile'
if not bobject.arm_use_custom_tilesheet_node:
variant_suffix = '_armtile'
elif arm.utils.export_morph_targets(bobject):
variant_suffix = '_armskey'

Expand Down
3 changes: 3 additions & 0 deletions blender/arm/handlers.py
Expand Up @@ -248,6 +248,9 @@ def reload_blend_data():
armory_pbr = bpy.data.node_groups.get('Armory PBR')
if armory_pbr is None:
load_library('Armory PBR')
custom_tilesheet = bpy.data.node_groups.get('CustomTilesheet')
if custom_tilesheet is None:
load_library('CustomTilesheet')


def load_library(asset_name):
Expand Down
28 changes: 25 additions & 3 deletions blender/arm/logicnode/animation/LN_get_tilesheet_state.py
@@ -1,15 +1,37 @@
from arm.logicnode.arm_nodes import *

class GetTilesheetStateNode(ArmLogicTreeNode):
"""Returns the information about the current tilesheet of the given object."""
"""Returns the information about the current tilesheet of the given object.
@output Active Tilesheet: Current active tilesheet.
@output Active Action: Current action in the tilesheet.
@output Frame: Frame offset with 0 as the first frame of the active action.
@output Absolute Frame: Absolute frame index in this tilesheet.
@output Is Paused: Tilesheet action paused.
"""
bl_idname = 'LNGetTilesheetStateNode'
bl_label = 'Get Tilesheet State'
arm_version = 1
arm_version = 2
arm_section = 'tilesheet'

def arm_init(self, context):
self.add_input('ArmNodeSocketObject', 'Object')

self.add_output('ArmStringSocket', 'Name')
self.add_output('ArmStringSocket', 'Active Tilesheet')
self.add_output('ArmStringSocket', 'Active Action')
self.add_output('ArmIntSocket', 'Frame')
self.add_output('ArmIntSocket', 'Absolute Frame')
self.add_output('ArmBoolSocket', 'Is Paused')

def get_replacement_node(self, node_tree: bpy.types.NodeTree):
if self.arm_version not in (0, 1):
raise LookupError()

return NodeReplacement(
'LNGetTilesheetStateNode', self.arm_version, 'LNGetTilesheetStateNode', 2,
in_socket_mapping={}, out_socket_mapping={0:1, 1:3, 2:4}
)
16 changes: 16 additions & 0 deletions blender/arm/logicnode/animation/LN_set_active_tilesheet.py
@@ -0,0 +1,16 @@
from arm.logicnode.arm_nodes import *

class SetActiveTilesheetNode(ArmLogicTreeNode):
"""Set the active tilesheet."""
bl_idname = 'LNSetActiveTilesheetNode'
bl_label = 'Set Active Tilesheet'
arm_version = 1
arm_section = 'tilesheet'

def arm_init(self, context):
self.add_input('ArmNodeSocketAction', 'In')
self.add_input('ArmNodeSocketObject', 'Object')
self.add_input('ArmStringSocket', 'Tilesheet')
self.add_input('ArmStringSocket', 'Action')

self.add_output('ArmNodeSocketAction', 'Out')
17 changes: 17 additions & 0 deletions blender/arm/logicnode/animation/LN_set_tilesheet_frame.py
@@ -0,0 +1,17 @@
from arm.logicnode.arm_nodes import *

class SetTilesheetFrame(ArmLogicTreeNode):
"""Set the frame of the current tilesheet action.
@input Frame: Frame offset to set with 0 as the first frame of the active action.
"""
bl_idname = 'LNSetTilesheetFrameNode'
bl_label = 'Set Tilesheet Frame'
arm_version = 1
arm_section = 'tilesheet'

def arm_init(self, context):
self.add_input('ArmNodeSocketAction', 'In')
self.add_input('ArmNodeSocketObject', 'Object')
self.add_input('ArmIntSocket', 'Frame')

self.add_output('ArmNodeSocketAction', 'Out')
3 changes: 3 additions & 0 deletions blender/arm/material/arm_nodes/shader_data_node.py
Expand Up @@ -84,6 +84,9 @@ def __parse(self, out_socket: NodeSocket, state: ParserState) -> str:
state.frag.add_uniform('vec2 screenSize', link='_screenSize')
return f'textureLod({self.variable_name}, gl_FragCoord.xy / screenSize, 0.0).rgb'

if self.variable_type == "vec2":
return f'vec3({self.variable_name}.xy, 0)'

return self.variable_name

else:
Expand Down
1 change: 1 addition & 0 deletions blender/arm/props.py
Expand Up @@ -360,6 +360,7 @@ def init_properties():
bpy.types.Object.arm_animation_enabled = BoolProperty(name="Animation", description="Enable skinning & timeline animation", default=True)
bpy.types.Object.arm_tilesheet = StringProperty(name="Tilesheet", description="Set tilesheet animation", default='')
bpy.types.Object.arm_tilesheet_action = StringProperty(name="Tilesheet Action", description="Set startup action", default='')
bpy.types.Object.arm_use_custom_tilesheet_node = BoolProperty(name="Use custom tilesheet node", description="Use custom tilesheet shader node", default=False)
# For speakers
bpy.types.Speaker.arm_play_on_start = BoolProperty(name="Play on Start", description="Play this sound automatically", default=False)
bpy.types.Speaker.arm_loop = BoolProperty(name="Loop", description="Loop this sound", default=False)
Expand Down
1 change: 1 addition & 0 deletions blender/arm/props_ui.py
Expand Up @@ -80,6 +80,7 @@ def draw(self, context):
selected_ts = ts
break
layout.prop_search(obj, "arm_tilesheet_action", selected_ts, "arm_tilesheetactionlist", text="Action")
layout.prop(obj, "arm_use_custom_tilesheet_node")

# Properties list
arm.props_properties.draw_properties(layout, obj)
Expand Down
Binary file modified blender/data/arm_data.blend
Binary file not shown.

0 comments on commit fd47e1b

Please sign in to comment.