Skip to content

Commit 5f193eb

Browse files
authored
Allow creating ResourceProjects through ExtensionsApi (#1345)
* Allow creating resource projects through Api * Fix errors appearing when signal is already connected or disconnected * Formatting * Added a method to the ResourceProject * Formatting * Add docs
1 parent c4e7a97 commit 5f193eb

File tree

4 files changed

+46
-19
lines changed

4 files changed

+46
-19
lines changed

src/Autoload/ExtensionsApi.gd

Lines changed: 21 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -581,18 +581,24 @@ class ProjectAPI:
581581
## name [param name], size [param size], fill color [param fill_color] and
582582
## frames [param frames]. The created project also gets returned.[br][br]
583583
## [param frames] is an [Array] of type [Frame]. Usually it can be left as [code][][/code].
584+
## If [param is_resource] is [code]true[/code] then a [ResourceProject] is created.
584585
func new_project(
585586
frames: Array[Frame] = [],
586587
name := tr("untitled"),
587588
size := Vector2(64, 64),
588-
fill_color := Color.TRANSPARENT
589+
fill_color := Color.TRANSPARENT,
590+
is_resource := false
589591
) -> Project:
590592
if !name.is_valid_filename():
591593
name = tr("untitled")
592594
if size.x <= 0 or size.y <= 0:
593595
size.x = 1
594596
size.y = 1
595-
var new_proj := Project.new(frames, name, size.floor())
597+
var new_proj: Project
598+
if is_resource:
599+
new_proj = ResourceProject.new(frames, name, size.floor())
600+
else:
601+
new_proj = Project.new(frames, name, size.floor())
596602
new_proj.layers.append(PixelLayer.new(new_proj))
597603
new_proj.fill_color = fill_color
598604
new_proj.frames.append(new_proj.new_empty_frame())
@@ -617,8 +623,13 @@ class ProjectAPI:
617623
## Creates and returns a new [Project] in a new tab, with an optional [param name].
618624
## Unlike [method new_project], no starting frame/layer gets created.
619625
## Useful if you want to deserialize project data.
620-
func new_empty_project(name := tr("untitled")) -> Project:
621-
var new_proj := Project.new([], name)
626+
## If [param is_resource] is [code]true[/code] then a [ResourceProject] is created.
627+
func new_empty_project(name := tr("untitled"), is_resource := false) -> Project:
628+
var new_proj: Project
629+
if is_resource:
630+
new_proj = ResourceProject.new([], name)
631+
else:
632+
new_proj = Project.new([], name)
622633
Global.projects.append(new_proj)
623634
return new_proj
624635

@@ -868,11 +879,13 @@ class SignalsAPI:
868879
signal_class: Signal, callable: Callable, is_disconnecting := false
869880
) -> void:
870881
if !is_disconnecting:
871-
signal_class.connect(callable)
872-
ExtensionsApi.add_action("SignalsAPI", signal_class.get_name())
882+
if not signal_class.is_connected(callable):
883+
signal_class.connect(callable)
884+
ExtensionsApi.add_action("SignalsAPI", signal_class.get_name())
873885
else:
874-
signal_class.disconnect(callable)
875-
ExtensionsApi.remove_action("SignalsAPI", signal_class.get_name())
886+
if signal_class.is_connected(callable):
887+
signal_class.disconnect(callable)
888+
ExtensionsApi.remove_action("SignalsAPI", signal_class.get_name())
876889

877890
# APP RELATED SIGNALS
878891
## Connects/disconnects a signal to [param callable], that emits

src/Classes/ResourceProject.gd

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,31 @@
11
class_name ResourceProject
22
extends Project
3+
## A class for easily editing individual project sub-resources like tiles, index maps, etc.
4+
##
5+
## The [ResourceProject] is basically a [Project], except that it doesn't get saved physically
6+
## (as a .pxo file), instead, a [signal resource_updated] signal is emitted which can
7+
## be used to update the resource in the [Project].[br]
38

9+
## Emitted when the [ResourceProject] is saved.
410
@warning_ignore("unused_signal")
5-
signal resource_updated
11+
signal resource_updated(project: Project)
612

713

814
func _init(_frames: Array[Frame] = [], _name := tr("untitled"), _size := Vector2i(64, 64)) -> void:
915
super._init(_frames, _name + " (Virtual Resource)", _size)
16+
17+
18+
## Returns the full image of the [Frame] at [param frame_idx] in resource project.
19+
func get_frame_image(frame_idx: int) -> Image:
20+
var frame_image := Image.create_empty(size.x, size.y, false, Image.FORMAT_RGBA8)
21+
if frame_idx >= 0 and frame_idx < frames.size():
22+
var frame := frames[frame_idx]
23+
DrawingAlgos.blend_layers(frame_image, frame, Vector2i.ZERO, self)
24+
else:
25+
printerr(
26+
(
27+
"frame index: %s not found in ResourceProject, frames.size(): %s"
28+
% [str(frame_idx), str(frames.size())]
29+
)
30+
)
31+
return frame_image

src/Classes/ShaderLoader.gd

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -660,11 +660,7 @@ static func _shader_update_texture(
660660
if resource_proj.layers.size() > 1:
661661
warnings += "\nThis resource is intended to have 1 layer only. layers will be blended."
662662

663-
var updated_image := Image.create_empty(
664-
resource_proj.size.x, resource_proj.size.y, false, Image.FORMAT_RGBA8
665-
)
666-
var frame := resource_proj.frames[0]
667-
DrawingAlgos.blend_layers(updated_image, frame, Vector2i.ZERO, resource_proj)
663+
var updated_image := resource_proj.get_frame_image(0)
668664
value_changed.call(ImageTexture.create_from_image(updated_image), parameter_name)
669665
if not warnings.is_empty():
670666
Global.popup_error(warnings)

src/UI/TilesPanel.gd

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -169,11 +169,7 @@ static func _update_tile(
169169
if resource_proj.layers.size() > 1:
170170
warnings += "\nThis resource is intended to have 1 layer only. layers will be blended."
171171

172-
var updated_image := Image.create_empty(
173-
resource_proj.size.x, resource_proj.size.y, false, Image.FORMAT_RGBA8
174-
)
175-
var frame := resource_proj.frames[0]
176-
DrawingAlgos.blend_layers(updated_image, frame, Vector2i.ZERO, resource_proj)
172+
var updated_image := resource_proj.get_frame_image(0)
177173
if is_instance_valid(target_project) and is_instance_valid(tileset):
178174
if tile_idx < tileset.tiles.size():
179175
if !tileset.tiles[tile_idx].image:

0 commit comments

Comments
 (0)