mirror of
https://github.com/Orama-Interactive/Pixelorama.git
synced 2025-01-18 17:19:50 +00:00
UndoRedo - Unstable with bugs
Started working on UndoRedo. Currently works with basic drawing/erasing/bucket filling as well as the rectangle selection tool, custom brushes and copying/pasting. May not work with multiple layers and frames and it does not work with the rest of the tools and buttons. Also does not work when pressing both mouse buttons at the same time, or when the cursor is outside the canvas when drawing.
This commit is contained in:
parent
6350995385
commit
7b8c6bbf00
101
Main.tscn
101
Main.tscn
|
@ -16,13 +16,13 @@ anchor_bottom = 1.0
|
||||||
script = ExtResource( 1 )
|
script = ExtResource( 1 )
|
||||||
|
|
||||||
[node name="UI" type="HBoxContainer" parent="."]
|
[node name="UI" type="HBoxContainer" parent="."]
|
||||||
|
editor/display_folded = true
|
||||||
anchor_right = 1.0
|
anchor_right = 1.0
|
||||||
anchor_bottom = 1.0
|
anchor_bottom = 1.0
|
||||||
size_flags_horizontal = 3
|
size_flags_horizontal = 3
|
||||||
custom_constants/separation = 0
|
custom_constants/separation = 0
|
||||||
|
|
||||||
[node name="ToolPanel" type="Panel" parent="UI"]
|
[node name="ToolPanel" type="Panel" parent="UI"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_right = 230.0
|
margin_right = 230.0
|
||||||
margin_bottom = 600.0
|
margin_bottom = 600.0
|
||||||
rect_min_size = Vector2( 230, 0 )
|
rect_min_size = Vector2( 230, 0 )
|
||||||
|
@ -35,13 +35,13 @@ size_flags_horizontal = 3
|
||||||
size_flags_vertical = 3
|
size_flags_vertical = 3
|
||||||
|
|
||||||
[node name="MenusAndTools" type="VBoxContainer" parent="UI/ToolPanel/Tools"]
|
[node name="MenusAndTools" type="VBoxContainer" parent="UI/ToolPanel/Tools"]
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 266.0
|
margin_bottom = 266.0
|
||||||
size_flags_vertical = 3
|
size_flags_vertical = 3
|
||||||
|
|
||||||
[node name="MenuItems" type="HBoxContainer" parent="UI/ToolPanel/Tools/MenusAndTools"]
|
[node name="MenuItems" type="HBoxContainer" parent="UI/ToolPanel/Tools/MenusAndTools"]
|
||||||
editor/display_folded = true
|
editor/display_folded = true
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 20.0
|
margin_bottom = 20.0
|
||||||
|
|
||||||
[node name="FileMenu" type="MenuButton" parent="UI/ToolPanel/Tools/MenusAndTools/MenuItems"]
|
[node name="FileMenu" type="MenuButton" parent="UI/ToolPanel/Tools/MenusAndTools/MenuItems"]
|
||||||
|
@ -72,13 +72,11 @@ mouse_default_cursor_shape = 2
|
||||||
text = "Help"
|
text = "Help"
|
||||||
|
|
||||||
[node name="PaintToolsContainer" type="HBoxContainer" parent="UI/ToolPanel/Tools/MenusAndTools"]
|
[node name="PaintToolsContainer" type="HBoxContainer" parent="UI/ToolPanel/Tools/MenusAndTools"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_top = 24.0
|
margin_top = 24.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 44.0
|
margin_bottom = 44.0
|
||||||
|
|
||||||
[node name="Pencil" type="Button" parent="UI/ToolPanel/Tools/MenusAndTools/PaintToolsContainer"]
|
[node name="Pencil" type="Button" parent="UI/ToolPanel/Tools/MenusAndTools/PaintToolsContainer"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_right = 51.0
|
margin_right = 51.0
|
||||||
margin_bottom = 20.0
|
margin_bottom = 20.0
|
||||||
hint_tooltip = "P for left mouse button
|
hint_tooltip = "P for left mouse button
|
||||||
|
@ -94,7 +92,6 @@ centered = false
|
||||||
offset = Vector2( 0, -10 )
|
offset = Vector2( 0, -10 )
|
||||||
|
|
||||||
[node name="Eraser" type="Button" parent="UI/ToolPanel/Tools/MenusAndTools/PaintToolsContainer"]
|
[node name="Eraser" type="Button" parent="UI/ToolPanel/Tools/MenusAndTools/PaintToolsContainer"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_left = 55.0
|
margin_left = 55.0
|
||||||
margin_right = 106.0
|
margin_right = 106.0
|
||||||
margin_bottom = 20.0
|
margin_bottom = 20.0
|
||||||
|
@ -121,9 +118,8 @@ button_mask = 3
|
||||||
text = "Bucket"
|
text = "Bucket"
|
||||||
|
|
||||||
[node name="ColorToolsContainer" type="HBoxContainer" parent="UI/ToolPanel/Tools/MenusAndTools"]
|
[node name="ColorToolsContainer" type="HBoxContainer" parent="UI/ToolPanel/Tools/MenusAndTools"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_top = 48.0
|
margin_top = 48.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 68.0
|
margin_bottom = 68.0
|
||||||
|
|
||||||
[node name="PaintAllPixelsSameColor" type="Button" parent="UI/ToolPanel/Tools/MenusAndTools/ColorToolsContainer"]
|
[node name="PaintAllPixelsSameColor" type="Button" parent="UI/ToolPanel/Tools/MenusAndTools/ColorToolsContainer"]
|
||||||
|
@ -148,9 +144,8 @@ button_mask = 3
|
||||||
text = "Lighten/Darken"
|
text = "Lighten/Darken"
|
||||||
|
|
||||||
[node name="SelectionToolsContainer2" type="HBoxContainer" parent="UI/ToolPanel/Tools/MenusAndTools"]
|
[node name="SelectionToolsContainer2" type="HBoxContainer" parent="UI/ToolPanel/Tools/MenusAndTools"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_top = 72.0
|
margin_top = 72.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 92.0
|
margin_bottom = 92.0
|
||||||
|
|
||||||
[node name="RectSelect" type="Button" parent="UI/ToolPanel/Tools/MenusAndTools/SelectionToolsContainer2"]
|
[node name="RectSelect" type="Button" parent="UI/ToolPanel/Tools/MenusAndTools/SelectionToolsContainer2"]
|
||||||
|
@ -165,30 +160,29 @@ text = "RectSelect"
|
||||||
|
|
||||||
[node name="HSeparator" type="HSeparator" parent="UI/ToolPanel/Tools"]
|
[node name="HSeparator" type="HSeparator" parent="UI/ToolPanel/Tools"]
|
||||||
margin_top = 270.0
|
margin_top = 270.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 274.0
|
margin_bottom = 274.0
|
||||||
|
|
||||||
[node name="ToolOptions" type="HBoxContainer" parent="UI/ToolPanel/Tools"]
|
[node name="ToolOptions" type="HBoxContainer" parent="UI/ToolPanel/Tools"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_top = 278.0
|
margin_top = 278.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 544.0
|
margin_bottom = 544.0
|
||||||
size_flags_vertical = 3
|
size_flags_vertical = 3
|
||||||
custom_constants/separation = 0
|
custom_constants/separation = 0
|
||||||
|
|
||||||
[node name="LeftToolOptions" type="VBoxContainer" parent="UI/ToolPanel/Tools/ToolOptions"]
|
[node name="LeftToolOptions" type="VBoxContainer" parent="UI/ToolPanel/Tools/ToolOptions"]
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 266.0
|
margin_bottom = 266.0
|
||||||
size_flags_horizontal = 3
|
size_flags_horizontal = 3
|
||||||
|
|
||||||
[node name="LeftLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
[node name="LeftLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 14.0
|
margin_bottom = 14.0
|
||||||
text = "Left tool options"
|
text = "Left tool options"
|
||||||
|
|
||||||
[node name="LeftIndicatorCheckbox" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
[node name="LeftIndicatorCheckbox" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
||||||
margin_top = 18.0
|
margin_top = 18.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 42.0
|
margin_bottom = 42.0
|
||||||
hint_tooltip = "Show left mouse indicator when drawing"
|
hint_tooltip = "Show left mouse indicator when drawing"
|
||||||
mouse_default_cursor_shape = 2
|
mouse_default_cursor_shape = 2
|
||||||
|
@ -207,13 +201,13 @@ size_flags_vertical = 0
|
||||||
|
|
||||||
[node name="BrushSizeLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
[node name="BrushSizeLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
||||||
margin_top = 82.0
|
margin_top = 82.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 96.0
|
margin_bottom = 96.0
|
||||||
text = "Brush size: "
|
text = "Brush size: "
|
||||||
|
|
||||||
[node name="LeftBrushSizeEdit" type="SpinBox" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
[node name="LeftBrushSizeEdit" type="SpinBox" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
||||||
margin_top = 100.0
|
margin_top = 100.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 124.0
|
margin_bottom = 124.0
|
||||||
mouse_default_cursor_shape = 2
|
mouse_default_cursor_shape = 2
|
||||||
min_value = 1.0
|
min_value = 1.0
|
||||||
|
@ -222,14 +216,14 @@ suffix = "px"
|
||||||
|
|
||||||
[node name="ColorComesFrom" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
[node name="ColorComesFrom" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
||||||
margin_top = 128.0
|
margin_top = 128.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 142.0
|
margin_bottom = 142.0
|
||||||
text = "Brush color from"
|
text = "Brush color from"
|
||||||
|
|
||||||
[node name="InterpolateColor" type="HBoxContainer" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
[node name="InterpolateColor" type="HBoxContainer" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
||||||
editor/display_folded = true
|
editor/display_folded = true
|
||||||
margin_top = 146.0
|
margin_top = 146.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 162.0
|
margin_bottom = 162.0
|
||||||
|
|
||||||
[node name="BrushColorLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions/InterpolateColor"]
|
[node name="BrushColorLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions/InterpolateColor"]
|
||||||
|
@ -241,7 +235,7 @@ text = "B"
|
||||||
|
|
||||||
[node name="LeftInterpolateFactor" type="HSlider" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions/InterpolateColor"]
|
[node name="LeftInterpolateFactor" type="HSlider" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions/InterpolateColor"]
|
||||||
margin_left = 13.0
|
margin_left = 13.0
|
||||||
margin_right = 107.0
|
margin_right = 101.0
|
||||||
margin_bottom = 16.0
|
margin_bottom = 16.0
|
||||||
hint_tooltip = "Choose if the brush's color should come from the brush itself (left), or the currently selected color (right)"
|
hint_tooltip = "Choose if the brush's color should come from the brush itself (left), or the currently selected color (right)"
|
||||||
size_flags_horizontal = 3
|
size_flags_horizontal = 3
|
||||||
|
@ -251,44 +245,44 @@ value = 0.5
|
||||||
ticks_on_borders = true
|
ticks_on_borders = true
|
||||||
|
|
||||||
[node name="SelectedColorLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions/InterpolateColor"]
|
[node name="SelectedColorLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions/InterpolateColor"]
|
||||||
margin_left = 111.0
|
margin_left = 105.0
|
||||||
margin_top = 1.0
|
margin_top = 1.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 15.0
|
margin_bottom = 15.0
|
||||||
rect_pivot_offset = Vector2( -90, -47 )
|
rect_pivot_offset = Vector2( -90, -47 )
|
||||||
text = "C"
|
text = "C"
|
||||||
|
|
||||||
[node name="LeftHorizontalMirroring" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
[node name="LeftHorizontalMirroring" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
||||||
margin_top = 166.0
|
margin_top = 166.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 190.0
|
margin_bottom = 190.0
|
||||||
text = "Horiz. Mirror"
|
text = "Horiz. Mirror"
|
||||||
|
|
||||||
[node name="LeftVerticalMirroring" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
[node name="LeftVerticalMirroring" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/LeftToolOptions"]
|
||||||
margin_top = 194.0
|
margin_top = 194.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 218.0
|
margin_bottom = 218.0
|
||||||
text = "Vert. Mirror"
|
text = "Vert. Mirror"
|
||||||
|
|
||||||
[node name="VSeparator" type="VSeparator" parent="UI/ToolPanel/Tools/ToolOptions"]
|
[node name="VSeparator" type="VSeparator" parent="UI/ToolPanel/Tools/ToolOptions"]
|
||||||
margin_left = 119.0
|
margin_left = 113.0
|
||||||
margin_right = 123.0
|
margin_right = 117.0
|
||||||
margin_bottom = 266.0
|
margin_bottom = 266.0
|
||||||
|
|
||||||
[node name="RightToolOptions" type="VBoxContainer" parent="UI/ToolPanel/Tools/ToolOptions"]
|
[node name="RightToolOptions" type="VBoxContainer" parent="UI/ToolPanel/Tools/ToolOptions"]
|
||||||
margin_left = 123.0
|
margin_left = 117.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 266.0
|
margin_bottom = 266.0
|
||||||
size_flags_horizontal = 3
|
size_flags_horizontal = 3
|
||||||
|
|
||||||
[node name="RightLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
[node name="RightLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 14.0
|
margin_bottom = 14.0
|
||||||
text = "Right tool options"
|
text = "Right tool options"
|
||||||
|
|
||||||
[node name="RightIndicatorCheckbox" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
[node name="RightIndicatorCheckbox" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
||||||
margin_top = 18.0
|
margin_top = 18.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 42.0
|
margin_bottom = 42.0
|
||||||
hint_tooltip = "Show right mouse indicator when drawing"
|
hint_tooltip = "Show right mouse indicator when drawing"
|
||||||
mouse_default_cursor_shape = 2
|
mouse_default_cursor_shape = 2
|
||||||
|
@ -306,13 +300,13 @@ size_flags_vertical = 0
|
||||||
|
|
||||||
[node name="BrushSizeLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
[node name="BrushSizeLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
||||||
margin_top = 82.0
|
margin_top = 82.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 96.0
|
margin_bottom = 96.0
|
||||||
text = "Brush size: "
|
text = "Brush size: "
|
||||||
|
|
||||||
[node name="RightBrushSizeEdit" type="SpinBox" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
[node name="RightBrushSizeEdit" type="SpinBox" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
||||||
margin_top = 100.0
|
margin_top = 100.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 124.0
|
margin_bottom = 124.0
|
||||||
mouse_default_cursor_shape = 2
|
mouse_default_cursor_shape = 2
|
||||||
min_value = 1.0
|
min_value = 1.0
|
||||||
|
@ -321,14 +315,14 @@ suffix = "px"
|
||||||
|
|
||||||
[node name="ColorComesFrom" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
[node name="ColorComesFrom" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
||||||
margin_top = 128.0
|
margin_top = 128.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 142.0
|
margin_bottom = 142.0
|
||||||
text = "Brush color from"
|
text = "Brush color from"
|
||||||
|
|
||||||
[node name="InterpolateColor" type="HBoxContainer" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
[node name="InterpolateColor" type="HBoxContainer" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
||||||
editor/display_folded = true
|
editor/display_folded = true
|
||||||
margin_top = 146.0
|
margin_top = 146.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 162.0
|
margin_bottom = 162.0
|
||||||
|
|
||||||
[node name="BrushColorLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions/InterpolateColor"]
|
[node name="BrushColorLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions/InterpolateColor"]
|
||||||
|
@ -340,7 +334,7 @@ text = "B"
|
||||||
|
|
||||||
[node name="RightInterpolateFactor" type="HSlider" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions/InterpolateColor"]
|
[node name="RightInterpolateFactor" type="HSlider" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions/InterpolateColor"]
|
||||||
margin_left = 13.0
|
margin_left = 13.0
|
||||||
margin_right = 107.0
|
margin_right = 101.0
|
||||||
margin_bottom = 16.0
|
margin_bottom = 16.0
|
||||||
hint_tooltip = "Choose if the brush's color should come from the brush itself (left), or the currently selected color (right)"
|
hint_tooltip = "Choose if the brush's color should come from the brush itself (left), or the currently selected color (right)"
|
||||||
size_flags_horizontal = 3
|
size_flags_horizontal = 3
|
||||||
|
@ -350,34 +344,33 @@ value = 0.5
|
||||||
ticks_on_borders = true
|
ticks_on_borders = true
|
||||||
|
|
||||||
[node name="SelectedColorLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions/InterpolateColor"]
|
[node name="SelectedColorLabel" type="Label" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions/InterpolateColor"]
|
||||||
margin_left = 111.0
|
margin_left = 105.0
|
||||||
margin_top = 1.0
|
margin_top = 1.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 15.0
|
margin_bottom = 15.0
|
||||||
rect_pivot_offset = Vector2( -90, -47 )
|
rect_pivot_offset = Vector2( -90, -47 )
|
||||||
text = "C"
|
text = "C"
|
||||||
|
|
||||||
[node name="RightHorizontalMirroring" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
[node name="RightHorizontalMirroring" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
||||||
margin_top = 166.0
|
margin_top = 166.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 190.0
|
margin_bottom = 190.0
|
||||||
text = "Horiz. Mirror"
|
text = "Horiz. Mirror"
|
||||||
|
|
||||||
[node name="RightVerticalMirroring" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
[node name="RightVerticalMirroring" type="CheckBox" parent="UI/ToolPanel/Tools/ToolOptions/RightToolOptions"]
|
||||||
margin_top = 194.0
|
margin_top = 194.0
|
||||||
margin_right = 119.0
|
margin_right = 113.0
|
||||||
margin_bottom = 218.0
|
margin_bottom = 218.0
|
||||||
text = "Vert. Mirror"
|
text = "Vert. Mirror"
|
||||||
|
|
||||||
[node name="HSeparator2" type="HSeparator" parent="UI/ToolPanel/Tools"]
|
[node name="HSeparator2" type="HSeparator" parent="UI/ToolPanel/Tools"]
|
||||||
margin_top = 548.0
|
margin_top = 548.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 552.0
|
margin_bottom = 552.0
|
||||||
|
|
||||||
[node name="BrushesContainer" type="ScrollContainer" parent="UI/ToolPanel/Tools"]
|
[node name="BrushesContainer" type="ScrollContainer" parent="UI/ToolPanel/Tools"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_top = 556.0
|
margin_top = 556.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 592.0
|
margin_bottom = 592.0
|
||||||
size_flags_horizontal = 3
|
size_flags_horizontal = 3
|
||||||
scroll_vertical_enabled = false
|
scroll_vertical_enabled = false
|
||||||
|
@ -402,7 +395,7 @@ offset = Vector2( 28, 0 )
|
||||||
|
|
||||||
[node name="HSeparator3" type="HSeparator" parent="UI/ToolPanel/Tools"]
|
[node name="HSeparator3" type="HSeparator" parent="UI/ToolPanel/Tools"]
|
||||||
margin_top = 596.0
|
margin_top = 596.0
|
||||||
margin_right = 242.0
|
margin_right = 230.0
|
||||||
margin_bottom = 600.0
|
margin_bottom = 600.0
|
||||||
|
|
||||||
[node name="CanvasAndTimeline" type="VBoxContainer" parent="UI"]
|
[node name="CanvasAndTimeline" type="VBoxContainer" parent="UI"]
|
||||||
|
@ -412,6 +405,7 @@ margin_bottom = 600.0
|
||||||
size_flags_horizontal = 3
|
size_flags_horizontal = 3
|
||||||
|
|
||||||
[node name="HBoxContainer" type="HBoxContainer" parent="UI/CanvasAndTimeline"]
|
[node name="HBoxContainer" type="HBoxContainer" parent="UI/CanvasAndTimeline"]
|
||||||
|
editor/display_folded = true
|
||||||
margin_right = 634.0
|
margin_right = 634.0
|
||||||
margin_bottom = 464.0
|
margin_bottom = 464.0
|
||||||
size_flags_horizontal = 3
|
size_flags_horizontal = 3
|
||||||
|
@ -472,7 +466,6 @@ zoom = Vector2( 0.15, 0.15 )
|
||||||
script = ExtResource( 6 )
|
script = ExtResource( 6 )
|
||||||
|
|
||||||
[node name="AnimationTimeline" type="Panel" parent="UI/CanvasAndTimeline"]
|
[node name="AnimationTimeline" type="Panel" parent="UI/CanvasAndTimeline"]
|
||||||
editor/display_folded = true
|
|
||||||
margin_top = 468.0
|
margin_top = 468.0
|
||||||
margin_right = 634.0
|
margin_right = 634.0
|
||||||
margin_bottom = 600.0
|
margin_bottom = 600.0
|
||||||
|
@ -868,8 +861,8 @@ resizable = true
|
||||||
mode = 0
|
mode = 0
|
||||||
access = 2
|
access = 2
|
||||||
filters = PoolStringArray( "*.pxo ; Pixelorama Project" )
|
filters = PoolStringArray( "*.pxo ; Pixelorama Project" )
|
||||||
current_dir = "/home/danielnaoexiste/Documents/Prog/Pixelorama"
|
current_dir = "C:/Users/Overloaded/Dropbox/Orama Founding Members/εταιρικα αρχεια/Godot Projects/Pixelorama"
|
||||||
current_path = "/home/danielnaoexiste/Documents/Prog/Pixelorama/"
|
current_path = "C:/Users/Overloaded/Dropbox/Orama Founding Members/εταιρικα αρχεια/Godot Projects/Pixelorama/"
|
||||||
|
|
||||||
[node name="SaveSprite" type="FileDialog" parent="."]
|
[node name="SaveSprite" type="FileDialog" parent="."]
|
||||||
anchor_left = 0.5
|
anchor_left = 0.5
|
||||||
|
@ -883,8 +876,8 @@ margin_bottom = 48.0
|
||||||
resizable = true
|
resizable = true
|
||||||
access = 2
|
access = 2
|
||||||
filters = PoolStringArray( "*.pxo ; Pixelorama Project" )
|
filters = PoolStringArray( "*.pxo ; Pixelorama Project" )
|
||||||
current_dir = "/home/danielnaoexiste/Documents/Prog/Pixelorama"
|
current_dir = "C:/Users/Overloaded/Dropbox/Orama Founding Members/εταιρικα αρχεια/Godot Projects/Pixelorama"
|
||||||
current_path = "/home/danielnaoexiste/Documents/Prog/Pixelorama/"
|
current_path = "C:/Users/Overloaded/Dropbox/Orama Founding Members/εταιρικα αρχεια/Godot Projects/Pixelorama/"
|
||||||
|
|
||||||
[node name="ImportSprites" type="FileDialog" parent="."]
|
[node name="ImportSprites" type="FileDialog" parent="."]
|
||||||
margin_right = 515.0
|
margin_right = 515.0
|
||||||
|
@ -894,8 +887,8 @@ resizable = true
|
||||||
mode = 1
|
mode = 1
|
||||||
access = 2
|
access = 2
|
||||||
filters = PoolStringArray( "*jpg, *.png ; JPG, PNG Images" )
|
filters = PoolStringArray( "*jpg, *.png ; JPG, PNG Images" )
|
||||||
current_dir = "/home/danielnaoexiste/Documents/Prog/Pixelorama"
|
current_dir = "C:/Users/Overloaded/Dropbox/Orama Founding Members/εταιρικα αρχεια/Godot Projects/Pixelorama"
|
||||||
current_path = "/home/danielnaoexiste/Documents/Prog/Pixelorama/"
|
current_path = "C:/Users/Overloaded/Dropbox/Orama Founding Members/εταιρικα αρχεια/Godot Projects/Pixelorama/"
|
||||||
|
|
||||||
[node name="ExportSprites" type="FileDialog" parent="."]
|
[node name="ExportSprites" type="FileDialog" parent="."]
|
||||||
anchor_left = 0.5
|
anchor_left = 0.5
|
||||||
|
@ -910,8 +903,8 @@ window_title = "Export sprite"
|
||||||
resizable = true
|
resizable = true
|
||||||
access = 2
|
access = 2
|
||||||
filters = PoolStringArray( "*.png ; PNG Image" )
|
filters = PoolStringArray( "*.png ; PNG Image" )
|
||||||
current_dir = "/home/danielnaoexiste/Documents/Prog/Pixelorama"
|
current_dir = "C:/Users/Overloaded/Dropbox/Orama Founding Members/εταιρικα αρχεια/Godot Projects/Pixelorama"
|
||||||
current_path = "/home/danielnaoexiste/Documents/Prog/Pixelorama/"
|
current_path = "C:/Users/Overloaded/Dropbox/Orama Founding Members/εταιρικα αρχεια/Godot Projects/Pixelorama/"
|
||||||
|
|
||||||
[node name="ScaleImage" type="ConfirmationDialog" parent="."]
|
[node name="ScaleImage" type="ConfirmationDialog" parent="."]
|
||||||
editor/display_folded = true
|
editor/display_folded = true
|
||||||
|
|
|
@ -11,7 +11,7 @@ func _on_BrushButton_pressed() -> void:
|
||||||
if custom_brush_index > -1:
|
if custom_brush_index > -1:
|
||||||
Global.custom_left_brush_index = custom_brush_index
|
Global.custom_left_brush_index = custom_brush_index
|
||||||
Global.update_left_custom_brush()
|
Global.update_left_custom_brush()
|
||||||
|
|
||||||
elif Input.is_action_just_released("right_mouse"):
|
elif Input.is_action_just_released("right_mouse"):
|
||||||
Global.current_right_brush_type = brush_type
|
Global.current_right_brush_type = brush_type
|
||||||
Global.right_brush_indicator.get_parent().remove_child(Global.right_brush_indicator)
|
Global.right_brush_indicator.get_parent().remove_child(Global.right_brush_indicator)
|
||||||
|
|
|
@ -11,6 +11,7 @@ var frame_button : VBoxContainer
|
||||||
var frame_texture_rect : TextureRect
|
var frame_texture_rect : TextureRect
|
||||||
|
|
||||||
var previous_mouse_pos := Vector2.ZERO
|
var previous_mouse_pos := Vector2.ZERO
|
||||||
|
var previous_action := "None"
|
||||||
var mouse_inside_canvas := false #used for undo
|
var mouse_inside_canvas := false #used for undo
|
||||||
var sprite_changed_this_frame := false #for optimization purposes
|
var sprite_changed_this_frame := false #for optimization purposes
|
||||||
|
|
||||||
|
@ -24,30 +25,30 @@ func _ready() -> void:
|
||||||
#Background
|
#Background
|
||||||
trans_background = ImageTexture.new()
|
trans_background = ImageTexture.new()
|
||||||
trans_background.create_from_image(load("res://Assets/Graphics/Transparent Background.png"), 0)
|
trans_background.create_from_image(load("res://Assets/Graphics/Transparent Background.png"), 0)
|
||||||
|
|
||||||
#The sprite itself
|
#The sprite itself
|
||||||
if layers.empty():
|
if layers.empty():
|
||||||
var sprite := Image.new()
|
var sprite := Image.new()
|
||||||
sprite.create(size.x, size.y, false, Image.FORMAT_RGBA8)
|
sprite.create(size.x, size.y, false, Image.FORMAT_RGBA8)
|
||||||
|
|
||||||
sprite.lock()
|
sprite.lock()
|
||||||
var tex := ImageTexture.new()
|
var tex := ImageTexture.new()
|
||||||
tex.create_from_image(sprite, 0)
|
tex.create_from_image(sprite, 0)
|
||||||
|
|
||||||
#Store [Image, ImageTexture, Layer Name, Visibity boolean]
|
#Store [Image, ImageTexture, Layer Name, Visibity boolean]
|
||||||
layers.append([sprite, tex, "Layer 0", true])
|
layers.append([sprite, tex, "Layer 0", true])
|
||||||
|
|
||||||
generate_layer_panels()
|
generate_layer_panels()
|
||||||
|
|
||||||
frame_button = load("res://Prefabs/FrameButton.tscn").instance()
|
frame_button = load("res://Prefabs/FrameButton.tscn").instance()
|
||||||
frame_button.name = "Frame_%s" % frame
|
frame_button.name = "Frame_%s" % frame
|
||||||
frame_button.get_node("FrameButton").frame = frame
|
frame_button.get_node("FrameButton").frame = frame
|
||||||
frame_button.get_node("FrameID").text = str(frame + 1)
|
frame_button.get_node("FrameID").text = str(frame + 1)
|
||||||
Global.frame_container.add_child(frame_button)
|
Global.frame_container.add_child(frame_button)
|
||||||
|
|
||||||
frame_texture_rect = Global.find_node_by_name(frame_button, "FrameTexture")
|
frame_texture_rect = Global.find_node_by_name(frame_button, "FrameTexture")
|
||||||
frame_texture_rect.texture = layers[0][1] #ImageTexture current_layer_index
|
frame_texture_rect.texture = layers[0][1] #ImageTexture current_layer_index
|
||||||
|
|
||||||
camera_zoom()
|
camera_zoom()
|
||||||
|
|
||||||
func camera_zoom() -> void:
|
func camera_zoom() -> void:
|
||||||
|
@ -82,7 +83,7 @@ func _process(delta) -> void:
|
||||||
elif Input.is_mouse_button_pressed(BUTTON_RIGHT):
|
elif Input.is_mouse_button_pressed(BUTTON_RIGHT):
|
||||||
current_mouse_button = "right_mouse"
|
current_mouse_button = "right_mouse"
|
||||||
current_action = Global.current_right_tool
|
current_action = Global.current_right_tool
|
||||||
|
|
||||||
if visible:
|
if visible:
|
||||||
if !point_in_rectangle(mouse_pos, location, location + size):
|
if !point_in_rectangle(mouse_pos, location, location + size):
|
||||||
if !Input.is_mouse_button_pressed(BUTTON_LEFT) && !Input.is_mouse_button_pressed(BUTTON_RIGHT):
|
if !Input.is_mouse_button_pressed(BUTTON_LEFT) && !Input.is_mouse_button_pressed(BUTTON_RIGHT):
|
||||||
|
@ -91,8 +92,22 @@ func _process(delta) -> void:
|
||||||
Global.cursor_position_label.text = "[%sx%s]" % [size.x, size.y]
|
Global.cursor_position_label.text = "[%sx%s]" % [size.x, size.y]
|
||||||
else:
|
else:
|
||||||
Global.cursor_position_label.text = "[%sx%s] %s, %s" % [size.x, size.y, mouse_pos_floored.x, mouse_pos_floored.y]
|
Global.cursor_position_label.text = "[%sx%s] %s, %s" % [size.x, size.y, mouse_pos_floored.x, mouse_pos_floored.y]
|
||||||
#Handle current tool
|
|
||||||
match current_action:
|
|
||||||
|
#Handle Undo/Redo
|
||||||
|
if point_in_rectangle(mouse_pos, location, location + size) && Global.can_draw && Global.has_focus:
|
||||||
|
if Input.is_action_just_pressed("left_mouse") || Input.is_action_just_pressed("right_mouse"):
|
||||||
|
if current_action != "None":
|
||||||
|
if current_action == "RectSelect":
|
||||||
|
handle_undo("Rectangle Select")
|
||||||
|
else:
|
||||||
|
handle_undo("Draw")
|
||||||
|
|
||||||
|
elif Input.is_action_just_released("left_mouse") || Input.is_action_just_released("right_mouse"):
|
||||||
|
if previous_action != "None" && previous_action != "RectSelect":
|
||||||
|
handle_redo("Draw")
|
||||||
|
|
||||||
|
match current_action: #Handle current tool
|
||||||
"Pencil":
|
"Pencil":
|
||||||
var current_color : Color
|
var current_color : Color
|
||||||
if current_mouse_button == "left_mouse":
|
if current_mouse_button == "left_mouse":
|
||||||
|
@ -117,7 +132,7 @@ func _process(delta) -> void:
|
||||||
current_color = Global.right_color_picker.color
|
current_color = Global.right_color_picker.color
|
||||||
horizontal_mirror = Global.right_horizontal_mirror
|
horizontal_mirror = Global.right_horizontal_mirror
|
||||||
vertical_mirror = Global.right_vertical_mirror
|
vertical_mirror = Global.right_vertical_mirror
|
||||||
|
|
||||||
flood_fill(mouse_pos, layers[current_layer_index][0].get_pixelv(mouse_pos), current_color)
|
flood_fill(mouse_pos, layers[current_layer_index][0].get_pixelv(mouse_pos), current_color)
|
||||||
if horizontal_mirror:
|
if horizontal_mirror:
|
||||||
var pos := Vector2(mirror_x, mouse_pos.y)
|
var pos := Vector2(mirror_x, mouse_pos.y)
|
||||||
|
@ -128,15 +143,15 @@ func _process(delta) -> void:
|
||||||
if horizontal_mirror && vertical_mirror:
|
if horizontal_mirror && vertical_mirror:
|
||||||
var pos := Vector2(mirror_x, mirror_y)
|
var pos := Vector2(mirror_x, mirror_y)
|
||||||
flood_fill(pos, layers[current_layer_index][0].get_pixelv(pos), current_color)
|
flood_fill(pos, layers[current_layer_index][0].get_pixelv(pos), current_color)
|
||||||
|
|
||||||
"PaintAllPixelsSameColor":
|
"PaintAllPixelsSameColor":
|
||||||
if point_in_rectangle(mouse_pos, location, location + size) && Global.current_frame == frame:
|
if point_in_rectangle(mouse_pos, location, location + size) && Global.can_draw && Global.has_focus && Global.current_frame == frame:
|
||||||
var current_color : Color
|
var current_color : Color
|
||||||
if current_mouse_button == "left_mouse":
|
if current_mouse_button == "left_mouse":
|
||||||
current_color = Global.left_color_picker.color
|
current_color = Global.left_color_picker.color
|
||||||
elif current_mouse_button == "right_mouse":
|
elif current_mouse_button == "right_mouse":
|
||||||
current_color = Global.right_color_picker.color
|
current_color = Global.right_color_picker.color
|
||||||
|
|
||||||
var pixel_color : Color = layers[current_layer_index][0].get_pixelv(mouse_pos)
|
var pixel_color : Color = layers[current_layer_index][0].get_pixelv(mouse_pos)
|
||||||
for xx in size.x:
|
for xx in size.x:
|
||||||
for yy in size.y:
|
for yy in size.y:
|
||||||
|
@ -145,7 +160,7 @@ func _process(delta) -> void:
|
||||||
layers[current_layer_index][0].set_pixel(xx, yy, current_color)
|
layers[current_layer_index][0].set_pixel(xx, yy, current_color)
|
||||||
sprite_changed_this_frame = true
|
sprite_changed_this_frame = true
|
||||||
"LightenDarken":
|
"LightenDarken":
|
||||||
if point_in_rectangle(mouse_pos, location, location + size):
|
if point_in_rectangle(mouse_pos, location, location + size) && Global.can_draw && Global.has_focus && Global.current_frame == frame:
|
||||||
var pixel_color : Color = layers[current_layer_index][0].get_pixelv(mouse_pos)
|
var pixel_color : Color = layers[current_layer_index][0].get_pixelv(mouse_pos)
|
||||||
var amount := 0.05
|
var amount := 0.05
|
||||||
var color_changed := pixel_color.lightened(amount)
|
var color_changed := pixel_color.lightened(amount)
|
||||||
|
@ -177,14 +192,14 @@ func _process(delta) -> void:
|
||||||
Global.selection_rectangle.polygon[1] = Vector2(end_pos.x, start_pos.y)
|
Global.selection_rectangle.polygon[1] = Vector2(end_pos.x, start_pos.y)
|
||||||
Global.selection_rectangle.polygon[2] = end_pos
|
Global.selection_rectangle.polygon[2] = end_pos
|
||||||
Global.selection_rectangle.polygon[3] = Vector2(start_pos.x, end_pos.y)
|
Global.selection_rectangle.polygon[3] = Vector2(start_pos.x, end_pos.y)
|
||||||
|
|
||||||
if !is_making_line:
|
if !is_making_line:
|
||||||
previous_mouse_pos = mouse_pos
|
previous_mouse_pos = mouse_pos
|
||||||
previous_mouse_pos.x = clamp(previous_mouse_pos.x, location.x, location.x + size.x)
|
previous_mouse_pos.x = clamp(previous_mouse_pos.x, location.x, location.x + size.x)
|
||||||
previous_mouse_pos.y = clamp(previous_mouse_pos.y, location.y, location.y + size.y)
|
previous_mouse_pos.y = clamp(previous_mouse_pos.y, location.y, location.y + size.y)
|
||||||
else:
|
else:
|
||||||
line_2d.set_point_position(1, mouse_pos)
|
line_2d.set_point_position(1, mouse_pos)
|
||||||
|
|
||||||
if is_making_selection != "None": #If we're making a selection
|
if is_making_selection != "None": #If we're making a selection
|
||||||
if Input.is_action_just_released(is_making_selection): #Finish selection when button is released
|
if Input.is_action_just_released(is_making_selection): #Finish selection when button is released
|
||||||
var start_pos = Global.selection_rectangle.polygon[0]
|
var start_pos = Global.selection_rectangle.polygon[0]
|
||||||
|
@ -193,30 +208,54 @@ func _process(delta) -> void:
|
||||||
var temp = end_pos.x
|
var temp = end_pos.x
|
||||||
end_pos.x = start_pos.x
|
end_pos.x = start_pos.x
|
||||||
start_pos.x = temp
|
start_pos.x = temp
|
||||||
|
|
||||||
if start_pos.y > end_pos.y:
|
if start_pos.y > end_pos.y:
|
||||||
var temp = end_pos.y
|
var temp = end_pos.y
|
||||||
end_pos.y = start_pos.y
|
end_pos.y = start_pos.y
|
||||||
start_pos.y = temp
|
start_pos.y = temp
|
||||||
|
|
||||||
Global.selection_rectangle.polygon[0] = start_pos
|
Global.selection_rectangle.polygon[0] = start_pos
|
||||||
Global.selection_rectangle.polygon[1] = Vector2(end_pos.x, start_pos.y)
|
Global.selection_rectangle.polygon[1] = Vector2(end_pos.x, start_pos.y)
|
||||||
Global.selection_rectangle.polygon[2] = end_pos
|
Global.selection_rectangle.polygon[2] = end_pos
|
||||||
Global.selection_rectangle.polygon[3] = Vector2(start_pos.x, end_pos.y)
|
Global.selection_rectangle.polygon[3] = Vector2(start_pos.x, end_pos.y)
|
||||||
|
|
||||||
for xx in range(start_pos.x, end_pos.x):
|
for xx in range(start_pos.x, end_pos.x):
|
||||||
for yy in range(start_pos.y, end_pos.y):
|
for yy in range(start_pos.y, end_pos.y):
|
||||||
Global.selected_pixels.append(Vector2(xx, yy))
|
Global.selected_pixels.append(Vector2(xx, yy))
|
||||||
is_making_selection = "None"
|
is_making_selection = "None"
|
||||||
|
handle_redo("Rectangle Select")
|
||||||
|
|
||||||
|
previous_action = current_action
|
||||||
if sprite_changed_this_frame:
|
if sprite_changed_this_frame:
|
||||||
update_texture(current_layer_index)
|
update_texture(current_layer_index)
|
||||||
|
|
||||||
|
func handle_undo(action : String) -> void:
|
||||||
|
#I'm not sure why I have to unlock it, but...
|
||||||
|
#...if I don't, it doesn't work properly
|
||||||
|
layers[current_layer_index][0].unlock()
|
||||||
|
var data = layers[current_layer_index][0].data
|
||||||
|
layers[current_layer_index][0].lock()
|
||||||
|
Global.undo_redo.create_action(action)
|
||||||
|
Global.undo_redo.add_undo_property(layers[current_layer_index][0], "data", data)
|
||||||
|
if action == "Rectangle Select":
|
||||||
|
var selected_pixels = Global.selected_pixels.duplicate()
|
||||||
|
Global.undo_redo.add_undo_property(Global.selection_rectangle, "polygon", Global.selection_rectangle.polygon)
|
||||||
|
Global.undo_redo.add_undo_property(Global, "selected_pixels", selected_pixels)
|
||||||
|
Global.undo_redo.add_undo_method(Global, "undo", self, current_layer_index)
|
||||||
|
|
||||||
|
func handle_redo(action : String) -> void:
|
||||||
|
Global.undo_redo.add_do_property(layers[current_layer_index][0], "data", layers[current_layer_index][0].data)
|
||||||
|
if action == "Rectangle Select":
|
||||||
|
Global.undo_redo.add_do_property(Global.selection_rectangle, "polygon", Global.selection_rectangle.polygon)
|
||||||
|
Global.undo_redo.add_do_property(Global, "selected_pixels", Global.selected_pixels)
|
||||||
|
Global.undo_redo.add_do_method(Global, "redo", self, current_layer_index)
|
||||||
|
Global.undo_redo.commit_action()
|
||||||
|
print("Do: ", Global.undo_redo.get_current_action_name())
|
||||||
|
|
||||||
func update_texture(layer_index : int) -> void:
|
func update_texture(layer_index : int) -> void:
|
||||||
layers[layer_index][1].create_from_image(layers[layer_index][0], 0)
|
layers[layer_index][1].create_from_image(layers[layer_index][0], 0)
|
||||||
get_layer_container(layer_index).get_child(0).get_child(1).texture = layers[layer_index][1]
|
get_layer_container(layer_index).get_child(0).get_child(1).texture = layers[layer_index][1]
|
||||||
|
|
||||||
#This code is used to update the texture in the animation timeline frame button
|
#This code is used to update the texture in the animation timeline frame button
|
||||||
#but blend_rect causes major performance issues on large images
|
#but blend_rect causes major performance issues on large images
|
||||||
var whole_image := Image.new()
|
var whole_image := Image.new()
|
||||||
|
@ -249,7 +288,7 @@ func _draw() -> void:
|
||||||
for texture in Global.canvases[Global.current_frame - i].layers:
|
for texture in Global.canvases[Global.current_frame - i].layers:
|
||||||
color.a = 0.6/i
|
color.a = 0.6/i
|
||||||
draw_texture(texture[1], location, color)
|
draw_texture(texture[1], location, color)
|
||||||
|
|
||||||
#Future
|
#Future
|
||||||
if Global.onion_skinning_future_rate > 0:
|
if Global.onion_skinning_future_rate > 0:
|
||||||
var color : Color
|
var color : Color
|
||||||
|
@ -262,12 +301,12 @@ func _draw() -> void:
|
||||||
for texture in Global.canvases[Global.current_frame + i].layers:
|
for texture in Global.canvases[Global.current_frame + i].layers:
|
||||||
color.a = 0.6/i
|
color.a = 0.6/i
|
||||||
draw_texture(texture[1], location, color)
|
draw_texture(texture[1], location, color)
|
||||||
|
|
||||||
#Draw current frame layers
|
#Draw current frame layers
|
||||||
for texture in layers:
|
for texture in layers:
|
||||||
if texture[3]: #if it's visible
|
if texture[3]: #if it's visible
|
||||||
draw_texture(texture[1], location)
|
draw_texture(texture[1], location)
|
||||||
|
|
||||||
if Global.tile_mode:
|
if Global.tile_mode:
|
||||||
draw_texture(texture[1], Vector2(location.x, location.y + size.y)) #Down
|
draw_texture(texture[1], Vector2(location.x, location.y + size.y)) #Down
|
||||||
draw_texture(texture[1], Vector2(location.x - size.x, location.y + size.y)) #Down Left
|
draw_texture(texture[1], Vector2(location.x - size.x, location.y + size.y)) #Down Left
|
||||||
|
@ -277,14 +316,14 @@ func _draw() -> void:
|
||||||
draw_texture(texture[1], Vector2(location.x + size.x, location.y - size.y)) #Up right
|
draw_texture(texture[1], Vector2(location.x + size.x, location.y - size.y)) #Up right
|
||||||
draw_texture(texture[1], Vector2(location.x + size.x, location.y)) #Right
|
draw_texture(texture[1], Vector2(location.x + size.x, location.y)) #Right
|
||||||
draw_texture(texture[1], location + size) #Down right
|
draw_texture(texture[1], location + size) #Down right
|
||||||
|
|
||||||
#Idea taken from flurick (on GitHub)
|
#Idea taken from flurick (on GitHub)
|
||||||
if Global.draw_grid:
|
if Global.draw_grid:
|
||||||
for x in size.x:
|
for x in size.x:
|
||||||
draw_line(Vector2(x, location.y), Vector2(x, size.y), Color.black, true)
|
draw_line(Vector2(x, location.y), Vector2(x, size.y), Color.black, true)
|
||||||
for y in size.y:
|
for y in size.y:
|
||||||
draw_line(Vector2(location.x, y), Vector2(size.x, y), Color.black, true)
|
draw_line(Vector2(location.x, y), Vector2(size.x, y), Color.black, true)
|
||||||
|
|
||||||
#Draw rectangle to indicate the pixel currently being hovered on
|
#Draw rectangle to indicate the pixel currently being hovered on
|
||||||
var mouse_pos := get_local_mouse_position() + location
|
var mouse_pos := get_local_mouse_position() + location
|
||||||
if point_in_rectangle(mouse_pos, location, location + size):
|
if point_in_rectangle(mouse_pos, location, location + size):
|
||||||
|
@ -299,7 +338,7 @@ func _draw() -> void:
|
||||||
var custom_brush_size = Global.custom_left_brush_image.get_size() - Vector2.ONE
|
var custom_brush_size = Global.custom_left_brush_image.get_size() - Vector2.ONE
|
||||||
var dst := rectangle_center(mouse_pos, custom_brush_size)
|
var dst := rectangle_center(mouse_pos, custom_brush_size)
|
||||||
draw_texture(Global.custom_left_brush_texture, dst)
|
draw_texture(Global.custom_left_brush_texture, dst)
|
||||||
|
|
||||||
if Global.right_square_indicator_visible:
|
if Global.right_square_indicator_visible:
|
||||||
match Global.current_right_brush_type:
|
match Global.current_right_brush_type:
|
||||||
Global.BRUSH_TYPES.PIXEL:
|
Global.BRUSH_TYPES.PIXEL:
|
||||||
|
@ -315,7 +354,7 @@ func generate_layer_panels() -> void:
|
||||||
for child in Global.vbox_layer_container.get_children():
|
for child in Global.vbox_layer_container.get_children():
|
||||||
if child is PanelContainer:
|
if child is PanelContainer:
|
||||||
child.queue_free()
|
child.queue_free()
|
||||||
|
|
||||||
current_layer_index = layers.size() - 1
|
current_layer_index = layers.size() - 1
|
||||||
if layers.size() == 1:
|
if layers.size() == 1:
|
||||||
Global.remove_layer_button.disabled = true
|
Global.remove_layer_button.disabled = true
|
||||||
|
@ -323,7 +362,7 @@ func generate_layer_panels() -> void:
|
||||||
else:
|
else:
|
||||||
Global.remove_layer_button.disabled = false
|
Global.remove_layer_button.disabled = false
|
||||||
Global.remove_layer_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
Global.remove_layer_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
||||||
|
|
||||||
for i in range(layers.size() -1, -1, -1):
|
for i in range(layers.size() -1, -1, -1):
|
||||||
var layer_container = load("res://Prefabs/LayerContainer.tscn").instance()
|
var layer_container = load("res://Prefabs/LayerContainer.tscn").instance()
|
||||||
layers[i][2] = "Layer %s" % i
|
layers[i][2] = "Layer %s" % i
|
||||||
|
@ -365,7 +404,7 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
var brush_index := -1
|
var brush_index := -1
|
||||||
var custom_brush_image : Image
|
var custom_brush_image : Image
|
||||||
var horizontal_mirror := false
|
var horizontal_mirror := false
|
||||||
var vertical_mirror := false
|
var vertical_mirror := false
|
||||||
if current_mouse_button == "left_mouse":
|
if current_mouse_button == "left_mouse":
|
||||||
brush_size = Global.left_brush_size
|
brush_size = Global.left_brush_size
|
||||||
brush_type = Global.current_left_brush_type
|
brush_type = Global.current_left_brush_type
|
||||||
|
@ -380,7 +419,7 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
custom_brush_image = Global.custom_right_brush_image
|
custom_brush_image = Global.custom_right_brush_image
|
||||||
horizontal_mirror = Global.right_horizontal_mirror
|
horizontal_mirror = Global.right_horizontal_mirror
|
||||||
vertical_mirror = Global.right_vertical_mirror
|
vertical_mirror = Global.right_vertical_mirror
|
||||||
|
|
||||||
var west_limit := location.x
|
var west_limit := location.x
|
||||||
var east_limit := location.x + size.x
|
var east_limit := location.x + size.x
|
||||||
var north_limit := location.y
|
var north_limit := location.y
|
||||||
|
@ -390,12 +429,12 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
east_limit = min(east_limit, Global.selection_rectangle.polygon[2].x)
|
east_limit = min(east_limit, Global.selection_rectangle.polygon[2].x)
|
||||||
north_limit = max(north_limit, Global.selection_rectangle.polygon[0].y)
|
north_limit = max(north_limit, Global.selection_rectangle.polygon[0].y)
|
||||||
south_limit = min(south_limit, Global.selection_rectangle.polygon[2].y)
|
south_limit = min(south_limit, Global.selection_rectangle.polygon[2].y)
|
||||||
|
|
||||||
var start_pos_x
|
var start_pos_x
|
||||||
var start_pos_y
|
var start_pos_y
|
||||||
var end_pos_x
|
var end_pos_x
|
||||||
var end_pos_y
|
var end_pos_y
|
||||||
|
|
||||||
match(brush_type):
|
match(brush_type):
|
||||||
Global.BRUSH_TYPES.PIXEL:
|
Global.BRUSH_TYPES.PIXEL:
|
||||||
start_pos_x = pos.x - (brush_size >> 1)
|
start_pos_x = pos.x - (brush_size >> 1)
|
||||||
|
@ -423,7 +462,7 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
if layers[current_layer_index][0].get_pixel(mirror_x, mirror_y) != color: #don't draw the same pixel over and over
|
if layers[current_layer_index][0].get_pixel(mirror_x, mirror_y) != color: #don't draw the same pixel over and over
|
||||||
layers[current_layer_index][0].set_pixel(mirror_x, mirror_y, color)
|
layers[current_layer_index][0].set_pixel(mirror_x, mirror_y, color)
|
||||||
sprite_changed_this_frame = true
|
sprite_changed_this_frame = true
|
||||||
|
|
||||||
Global.BRUSH_TYPES.CUSTOM:
|
Global.BRUSH_TYPES.CUSTOM:
|
||||||
var custom_brush_size := custom_brush_image.get_size() - Vector2.ONE
|
var custom_brush_size := custom_brush_image.get_size() - Vector2.ONE
|
||||||
pos = pos.floor()
|
pos = pos.floor()
|
||||||
|
@ -432,7 +471,7 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
#Rectangle with the same size as the brush, but at cursor's position
|
#Rectangle with the same size as the brush, but at cursor's position
|
||||||
#var pos_rect_position := rectangle_center(pos, custom_brush_size)
|
#var pos_rect_position := rectangle_center(pos, custom_brush_size)
|
||||||
var pos_rect := Rect2(dst, custom_brush_size + Vector2.ONE)
|
var pos_rect := Rect2(dst, custom_brush_size + Vector2.ONE)
|
||||||
|
|
||||||
#The selection rectangle
|
#The selection rectangle
|
||||||
#If there's no rectangle, the whole canvas is considered a selection
|
#If there's no rectangle, the whole canvas is considered a selection
|
||||||
var selection_rect := Rect2()
|
var selection_rect := Rect2()
|
||||||
|
@ -443,7 +482,7 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
#If the size is 0, that means that the brush wasn't positioned inside the selection
|
#If the size is 0, that means that the brush wasn't positioned inside the selection
|
||||||
if pos_rect_clipped.size == Vector2.ZERO:
|
if pos_rect_clipped.size == Vector2.ZERO:
|
||||||
return
|
return
|
||||||
|
|
||||||
#Re-position src_rect and dst based on the clipped position
|
#Re-position src_rect and dst based on the clipped position
|
||||||
var pos_difference := (pos_rect.position - pos_rect_clipped.position).abs()
|
var pos_difference := (pos_rect.position - pos_rect_clipped.position).abs()
|
||||||
#Obviously, if pos_rect and pos_rect_clipped are the same, pos_difference is Vector2.ZERO
|
#Obviously, if pos_rect and pos_rect_clipped are the same, pos_difference is Vector2.ZERO
|
||||||
|
@ -454,11 +493,11 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
#... make sure pixels aren't being drawn outside the selection by adjusting src_rect's size
|
#... make sure pixels aren't being drawn outside the selection by adjusting src_rect's size
|
||||||
src_rect.size.x = min(src_rect.size.x, selection_rect.size.x)
|
src_rect.size.x = min(src_rect.size.x, selection_rect.size.x)
|
||||||
src_rect.size.y = min(src_rect.size.y, selection_rect.size.y)
|
src_rect.size.y = min(src_rect.size.y, selection_rect.size.y)
|
||||||
|
|
||||||
#Handle mirroring
|
#Handle mirroring
|
||||||
var mirror_x := east_limit + west_limit - dst.x - 1
|
var mirror_x := east_limit + west_limit - dst.x - 1
|
||||||
var mirror_y := south_limit + north_limit - dst.y - 1
|
var mirror_y := south_limit + north_limit - dst.y - 1
|
||||||
|
|
||||||
if color.a > 0: #If it's the pencil
|
if color.a > 0: #If it's the pencil
|
||||||
layers[current_layer_index][0].blend_rect(custom_brush_image, src_rect, dst)
|
layers[current_layer_index][0].blend_rect(custom_brush_image, src_rect, dst)
|
||||||
if horizontal_mirror:
|
if horizontal_mirror:
|
||||||
|
@ -467,14 +506,14 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
layers[current_layer_index][0].blend_rect(custom_brush_image, src_rect, Vector2(dst.x, mirror_y))
|
layers[current_layer_index][0].blend_rect(custom_brush_image, src_rect, Vector2(dst.x, mirror_y))
|
||||||
if horizontal_mirror && vertical_mirror:
|
if horizontal_mirror && vertical_mirror:
|
||||||
layers[current_layer_index][0].blend_rect(custom_brush_image, src_rect, Vector2(mirror_x, mirror_y))
|
layers[current_layer_index][0].blend_rect(custom_brush_image, src_rect, Vector2(mirror_x, mirror_y))
|
||||||
|
|
||||||
else: #if it's transparent - if it's the eraser
|
else: #if it's transparent - if it's the eraser
|
||||||
var custom_brush := Image.new()
|
var custom_brush := Image.new()
|
||||||
custom_brush.copy_from(Global.custom_brushes[brush_index])
|
custom_brush.copy_from(Global.custom_brushes[brush_index])
|
||||||
custom_brush_size = custom_brush.get_size()
|
custom_brush_size = custom_brush.get_size()
|
||||||
custom_brush.resize(custom_brush_size.x * brush_size, custom_brush_size.y * brush_size, Image.INTERPOLATE_NEAREST)
|
custom_brush.resize(custom_brush_size.x * brush_size, custom_brush_size.y * brush_size, Image.INTERPOLATE_NEAREST)
|
||||||
var custom_brush_blended = Global.blend_image_with_color(custom_brush, color, 1)
|
var custom_brush_blended = Global.blend_image_with_color(custom_brush, color, 1)
|
||||||
|
|
||||||
layers[current_layer_index][0].blit_rect_mask(custom_brush_blended, custom_brush, src_rect, dst)
|
layers[current_layer_index][0].blit_rect_mask(custom_brush_blended, custom_brush, src_rect, dst)
|
||||||
if horizontal_mirror:
|
if horizontal_mirror:
|
||||||
layers[current_layer_index][0].blit_rect_mask(custom_brush_blended, custom_brush, src_rect, Vector2(mirror_x, dst.y))
|
layers[current_layer_index][0].blit_rect_mask(custom_brush_blended, custom_brush, src_rect, Vector2(mirror_x, dst.y))
|
||||||
|
@ -482,7 +521,7 @@ func draw_pixel(pos : Vector2, color : Color, current_mouse_button : String) ->
|
||||||
layers[current_layer_index][0].blit_rect_mask(custom_brush_blended, custom_brush, src_rect, Vector2(dst.x, mirror_y))
|
layers[current_layer_index][0].blit_rect_mask(custom_brush_blended, custom_brush, src_rect, Vector2(dst.x, mirror_y))
|
||||||
if horizontal_mirror && vertical_mirror:
|
if horizontal_mirror && vertical_mirror:
|
||||||
layers[current_layer_index][0].blit_rect_mask(custom_brush_blended, custom_brush, src_rect, Vector2(mirror_x, mirror_y))
|
layers[current_layer_index][0].blit_rect_mask(custom_brush_blended, custom_brush, src_rect, Vector2(mirror_x, mirror_y))
|
||||||
|
|
||||||
layers[current_layer_index][0].lock()
|
layers[current_layer_index][0].lock()
|
||||||
sprite_changed_this_frame = true
|
sprite_changed_this_frame = true
|
||||||
|
|
||||||
|
@ -529,10 +568,10 @@ func flood_fill(pos : Vector2, target_color : Color, replace_color : Color) -> v
|
||||||
east_limit = min(east_limit, Global.selection_rectangle.polygon[2].x)
|
east_limit = min(east_limit, Global.selection_rectangle.polygon[2].x)
|
||||||
north_limit = max(north_limit, Global.selection_rectangle.polygon[0].y)
|
north_limit = max(north_limit, Global.selection_rectangle.polygon[0].y)
|
||||||
south_limit = min(south_limit, Global.selection_rectangle.polygon[2].y)
|
south_limit = min(south_limit, Global.selection_rectangle.polygon[2].y)
|
||||||
|
|
||||||
if !point_in_rectangle(pos, Vector2(west_limit - 1, north_limit - 1), Vector2(east_limit, south_limit)):
|
if !point_in_rectangle(pos, Vector2(west_limit - 1, north_limit - 1), Vector2(east_limit, south_limit)):
|
||||||
return
|
return
|
||||||
|
|
||||||
var q = [pos]
|
var q = [pos]
|
||||||
for n in q:
|
for n in q:
|
||||||
var west : Vector2 = n
|
var west : Vector2 = n
|
||||||
|
@ -566,4 +605,3 @@ func rectangle_center(pos : Vector2, size : Vector2) -> Vector2:
|
||||||
|
|
||||||
func _on_Timer_timeout() -> void:
|
func _on_Timer_timeout() -> void:
|
||||||
Global.can_draw = true
|
Global.can_draw = true
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
extends Node
|
extends Node
|
||||||
|
|
||||||
|
var undo_redo : UndoRedo
|
||||||
var current_frame := 0 setget set_current_frame_label
|
var current_frame := 0 setget set_current_frame_label
|
||||||
# warning-ignore:unused_class_variable
|
# warning-ignore:unused_class_variable
|
||||||
var can_draw := false
|
var can_draw := false
|
||||||
|
@ -102,6 +103,7 @@ var custom_right_brush_texture := ImageTexture.new()
|
||||||
|
|
||||||
|
|
||||||
func _ready() -> void:
|
func _ready() -> void:
|
||||||
|
undo_redo = UndoRedo.new()
|
||||||
var root = get_tree().get_root()
|
var root = get_tree().get_root()
|
||||||
canvas = find_node_by_name(root, "Canvas")
|
canvas = find_node_by_name(root, "Canvas")
|
||||||
canvases.append(canvas)
|
canvases.append(canvas)
|
||||||
|
@ -111,10 +113,10 @@ func _ready() -> void:
|
||||||
split_screen_button = find_node_by_name(root, "SplitScreenButton")
|
split_screen_button = find_node_by_name(root, "SplitScreenButton")
|
||||||
camera = find_node_by_name(canvas_parent, "Camera2D")
|
camera = find_node_by_name(canvas_parent, "Camera2D")
|
||||||
camera2 = find_node_by_name(canvas_parent.get_parent().get_parent(), "Camera2D2")
|
camera2 = find_node_by_name(canvas_parent.get_parent().get_parent(), "Camera2D2")
|
||||||
|
|
||||||
selection_rectangle = find_node_by_name(root, "SelectionRectangle")
|
selection_rectangle = find_node_by_name(root, "SelectionRectangle")
|
||||||
image_clipboard = Image.new()
|
image_clipboard = Image.new()
|
||||||
|
|
||||||
file_menu = find_node_by_name(root, "FileMenu")
|
file_menu = find_node_by_name(root, "FileMenu")
|
||||||
edit_menu = find_node_by_name(root, "EditMenu")
|
edit_menu = find_node_by_name(root, "EditMenu")
|
||||||
view_menu = find_node_by_name(root, "ViewMenu")
|
view_menu = find_node_by_name(root, "ViewMenu")
|
||||||
|
@ -127,10 +129,10 @@ func _ready() -> void:
|
||||||
right_brush_size_edit = find_node_by_name(root, "RightBrushSizeEdit")
|
right_brush_size_edit = find_node_by_name(root, "RightBrushSizeEdit")
|
||||||
left_interpolate_slider = find_node_by_name(root, "LeftInterpolateFactor")
|
left_interpolate_slider = find_node_by_name(root, "LeftInterpolateFactor")
|
||||||
right_interpolate_slider = find_node_by_name(root, "RightInterpolateFactor")
|
right_interpolate_slider = find_node_by_name(root, "RightInterpolateFactor")
|
||||||
|
|
||||||
left_brush_indicator = find_node_by_name(root, "LeftBrushIndicator")
|
left_brush_indicator = find_node_by_name(root, "LeftBrushIndicator")
|
||||||
right_brush_indicator = find_node_by_name(root, "RightBrushIndicator")
|
right_brush_indicator = find_node_by_name(root, "RightBrushIndicator")
|
||||||
|
|
||||||
loop_animation_button = find_node_by_name(root, "LoopAnim")
|
loop_animation_button = find_node_by_name(root, "LoopAnim")
|
||||||
play_forward = find_node_by_name(root, "PlayForward")
|
play_forward = find_node_by_name(root, "PlayForward")
|
||||||
play_backwards = find_node_by_name(root, "PlayBackwards")
|
play_backwards = find_node_by_name(root, "PlayBackwards")
|
||||||
|
@ -147,18 +149,30 @@ func _ready() -> void:
|
||||||
zoom_level_label = find_node_by_name(root, "ZoomLevel")
|
zoom_level_label = find_node_by_name(root, "ZoomLevel")
|
||||||
current_frame_label = find_node_by_name(root, "CurrentFrame")
|
current_frame_label = find_node_by_name(root, "CurrentFrame")
|
||||||
|
|
||||||
#Thanks to https://godotengine.org/qa/17524/how-to-find-an-instanced-scene-by-its-name
|
#Thanks to https://godotengine.org/qa/17524/how-to-find-an-instanced-scene-by-its-name
|
||||||
func find_node_by_name(root, node_name) -> Node:
|
func find_node_by_name(root, node_name) -> Node:
|
||||||
if root.get_name() == node_name:
|
if root.get_name() == node_name:
|
||||||
return root
|
return root
|
||||||
for child in root.get_children():
|
for child in root.get_children():
|
||||||
if child.get_name() == node_name:
|
if child.get_name() == node_name:
|
||||||
return child
|
return child
|
||||||
var found = find_node_by_name(child, node_name)
|
var found = find_node_by_name(child, node_name)
|
||||||
if found:
|
if found:
|
||||||
return found
|
return found
|
||||||
return null
|
return null
|
||||||
|
|
||||||
|
func undo(canvas : Canvas, layer_index : int) -> void:
|
||||||
|
var action_name : String = undo_redo.get_current_action_name()
|
||||||
|
if action_name == "Draw" || action_name == "Rectangle Select":
|
||||||
|
canvas.update_texture(layer_index)
|
||||||
|
print("Undo: ", action_name)
|
||||||
|
|
||||||
|
func redo(canvas : Canvas, layer_index : int) -> void:
|
||||||
|
var action_name : String = undo_redo.get_current_action_name()
|
||||||
|
if action_name == "Draw" || action_name == "Rectangle Select":
|
||||||
|
canvas.update_texture(layer_index)
|
||||||
|
print("Redo: ", action_name)
|
||||||
|
|
||||||
func change_frame() -> void:
|
func change_frame() -> void:
|
||||||
for c in canvases:
|
for c in canvases:
|
||||||
c.visible = false
|
c.visible = false
|
||||||
|
@ -174,7 +188,7 @@ func handle_layer_order_buttons() -> void:
|
||||||
else:
|
else:
|
||||||
move_left_frame_button.disabled = false
|
move_left_frame_button.disabled = false
|
||||||
move_left_frame_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
move_left_frame_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
||||||
|
|
||||||
if current_frame == canvases.size() - 1:
|
if current_frame == canvases.size() - 1:
|
||||||
move_right_frame_button.disabled = true
|
move_right_frame_button.disabled = true
|
||||||
move_right_frame_button.mouse_default_cursor_shape = Control.CURSOR_FORBIDDEN
|
move_right_frame_button.mouse_default_cursor_shape = Control.CURSOR_FORBIDDEN
|
||||||
|
@ -212,7 +226,7 @@ func update_left_custom_brush() -> void:
|
||||||
custom_brush.resize(custom_brush_size.x * left_brush_size, custom_brush_size.y * left_brush_size, Image.INTERPOLATE_NEAREST)
|
custom_brush.resize(custom_brush_size.x * left_brush_size, custom_brush_size.y * left_brush_size, Image.INTERPOLATE_NEAREST)
|
||||||
custom_left_brush_image = blend_image_with_color(custom_brush, left_color_picker.color, left_interpolate_slider.value)
|
custom_left_brush_image = blend_image_with_color(custom_brush, left_color_picker.color, left_interpolate_slider.value)
|
||||||
custom_left_brush_texture.create_from_image(custom_left_brush_image, 0)
|
custom_left_brush_texture.create_from_image(custom_left_brush_image, 0)
|
||||||
|
|
||||||
func update_right_custom_brush() -> void:
|
func update_right_custom_brush() -> void:
|
||||||
if custom_right_brush_index > -1:
|
if custom_right_brush_index > -1:
|
||||||
var custom_brush := Image.new()
|
var custom_brush := Image.new()
|
||||||
|
|
|
@ -26,14 +26,14 @@ func changed_selection() -> void:
|
||||||
if Global.canvas.current_layer_index == child.i:
|
if Global.canvas.current_layer_index == child.i:
|
||||||
child.currently_selected = true
|
child.currently_selected = true
|
||||||
child.get_stylebox("panel").bg_color = Color("282532")
|
child.get_stylebox("panel").bg_color = Color("282532")
|
||||||
|
|
||||||
if Global.canvas.current_layer_index < Global.canvas.layers.size() - 1:
|
if Global.canvas.current_layer_index < Global.canvas.layers.size() - 1:
|
||||||
Global.move_up_layer_button.disabled = false
|
Global.move_up_layer_button.disabled = false
|
||||||
Global.move_up_layer_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
Global.move_up_layer_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
||||||
else:
|
else:
|
||||||
Global.move_up_layer_button.disabled = true
|
Global.move_up_layer_button.disabled = true
|
||||||
Global.move_up_layer_button.mouse_default_cursor_shape = Control.CURSOR_FORBIDDEN
|
Global.move_up_layer_button.mouse_default_cursor_shape = Control.CURSOR_FORBIDDEN
|
||||||
|
|
||||||
if Global.canvas.current_layer_index > 0:
|
if Global.canvas.current_layer_index > 0:
|
||||||
Global.move_down_layer_button.disabled = false
|
Global.move_down_layer_button.disabled = false
|
||||||
Global.move_down_layer_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
Global.move_down_layer_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
||||||
|
|
100
Scripts/Main.gd
100
Scripts/Main.gd
|
@ -19,7 +19,7 @@ func _ready() -> void:
|
||||||
# Set a minimum window size to prevent UI elements from collapsing on each other.
|
# Set a minimum window size to prevent UI elements from collapsing on each other.
|
||||||
# This property is only available in 3.2alpha or later, so use `set()` to fail gracefully if it doesn't exist.
|
# This property is only available in 3.2alpha or later, so use `set()` to fail gracefully if it doesn't exist.
|
||||||
OS.set("min_window_size", Vector2(1024, 600))
|
OS.set("min_window_size", Vector2(1024, 600))
|
||||||
|
|
||||||
var file_menu_items := {
|
var file_menu_items := {
|
||||||
"New..." : KEY_MASK_CTRL + KEY_N,
|
"New..." : KEY_MASK_CTRL + KEY_N,
|
||||||
"Open..." : KEY_MASK_CTRL + KEY_O,
|
"Open..." : KEY_MASK_CTRL + KEY_O,
|
||||||
|
@ -35,9 +35,9 @@ func _ready() -> void:
|
||||||
"Crop Image" : 0,
|
"Crop Image" : 0,
|
||||||
"Clear Selection" : 0,
|
"Clear Selection" : 0,
|
||||||
"Flip Horizontal": KEY_MASK_SHIFT + KEY_H,
|
"Flip Horizontal": KEY_MASK_SHIFT + KEY_H,
|
||||||
"Flip Vertical": KEY_MASK_SHIFT + KEY_V
|
"Flip Vertical": KEY_MASK_SHIFT + KEY_V,
|
||||||
#"Undo" : KEY_MASK_CTRL + KEY_Z,
|
"Undo" : KEY_MASK_CTRL + KEY_Z,
|
||||||
#"Redo" : KEY_MASK_SHIFT + KEY_MASK_CTRL + KEY_Z,
|
"Redo" : KEY_MASK_SHIFT + KEY_MASK_CTRL + KEY_Z
|
||||||
}
|
}
|
||||||
var view_menu_items := {
|
var view_menu_items := {
|
||||||
"Tile Mode" : KEY_MASK_CTRL + KEY_T,
|
"Tile Mode" : KEY_MASK_CTRL + KEY_T,
|
||||||
|
@ -50,7 +50,7 @@ func _ready() -> void:
|
||||||
var edit_menu : PopupMenu = Global.edit_menu.get_popup()
|
var edit_menu : PopupMenu = Global.edit_menu.get_popup()
|
||||||
view_menu = Global.view_menu.get_popup()
|
view_menu = Global.view_menu.get_popup()
|
||||||
var help_menu : PopupMenu = Global.help_menu.get_popup()
|
var help_menu : PopupMenu = Global.help_menu.get_popup()
|
||||||
|
|
||||||
var i = 0
|
var i = 0
|
||||||
for item in file_menu_items.keys():
|
for item in file_menu_items.keys():
|
||||||
file_menu.add_item(item, i, file_menu_items[item])
|
file_menu.add_item(item, i, file_menu_items[item])
|
||||||
|
@ -67,12 +67,12 @@ func _ready() -> void:
|
||||||
for item in help_menu_items.keys():
|
for item in help_menu_items.keys():
|
||||||
help_menu.add_item(item, i, help_menu_items[item])
|
help_menu.add_item(item, i, help_menu_items[item])
|
||||||
i += 1
|
i += 1
|
||||||
|
|
||||||
file_menu.connect("id_pressed", self, "file_menu_id_pressed")
|
file_menu.connect("id_pressed", self, "file_menu_id_pressed")
|
||||||
edit_menu.connect("id_pressed", self, "edit_menu_id_pressed")
|
edit_menu.connect("id_pressed", self, "edit_menu_id_pressed")
|
||||||
view_menu.connect("id_pressed", self, "view_menu_id_pressed")
|
view_menu.connect("id_pressed", self, "view_menu_id_pressed")
|
||||||
help_menu.connect("id_pressed", self, "help_menu_id_pressed")
|
help_menu.connect("id_pressed", self, "help_menu_id_pressed")
|
||||||
|
|
||||||
var root = get_tree().get_root()
|
var root = get_tree().get_root()
|
||||||
#Node, left mouse shortcut, right mouse shortcut
|
#Node, left mouse shortcut, right mouse shortcut
|
||||||
tools.append([Global.find_node_by_name(root, "Pencil"), "left_pencil_tool", "right_pencil_tool"])
|
tools.append([Global.find_node_by_name(root, "Pencil"), "left_pencil_tool", "right_pencil_tool"])
|
||||||
|
@ -81,15 +81,15 @@ func _ready() -> void:
|
||||||
tools.append([Global.find_node_by_name(root, "PaintAllPixelsSameColor"), "left_paint_all_tool", "right_paint_all_tool"])
|
tools.append([Global.find_node_by_name(root, "PaintAllPixelsSameColor"), "left_paint_all_tool", "right_paint_all_tool"])
|
||||||
tools.append([Global.find_node_by_name(root, "LightenDarken"), "left_lightdark_tool", "right_lightdark_tool"])
|
tools.append([Global.find_node_by_name(root, "LightenDarken"), "left_lightdark_tool", "right_lightdark_tool"])
|
||||||
tools.append([Global.find_node_by_name(root, "RectSelect"), "left_rectangle_select_tool", "right_rectangle_select_tool"])
|
tools.append([Global.find_node_by_name(root, "RectSelect"), "left_rectangle_select_tool", "right_rectangle_select_tool"])
|
||||||
|
|
||||||
for t in tools:
|
for t in tools:
|
||||||
t[0].connect("pressed", self, "_on_Tool_pressed", [t[0]])
|
t[0].connect("pressed", self, "_on_Tool_pressed", [t[0]])
|
||||||
|
|
||||||
#Options for Import
|
#Options for Import
|
||||||
import_as_new_frame = CheckBox.new()
|
import_as_new_frame = CheckBox.new()
|
||||||
import_as_new_frame.text = "Import as new frame?"
|
import_as_new_frame.text = "Import as new frame?"
|
||||||
$ImportSprites.get_vbox().add_child(import_as_new_frame)
|
$ImportSprites.get_vbox().add_child(import_as_new_frame)
|
||||||
|
|
||||||
#Options for Export
|
#Options for Export
|
||||||
export_all_frames = CheckBox.new()
|
export_all_frames = CheckBox.new()
|
||||||
export_all_frames.text = "Export all frames?"
|
export_all_frames.text = "Export all frames?"
|
||||||
|
@ -100,7 +100,7 @@ func _ready() -> void:
|
||||||
$ExportSprites.get_vbox().add_child(export_all_frames)
|
$ExportSprites.get_vbox().add_child(export_all_frames)
|
||||||
$ExportSprites.get_vbox().add_child(export_as_single_file)
|
$ExportSprites.get_vbox().add_child(export_as_single_file)
|
||||||
$ExportSprites.get_vbox().add_child(export_vertical_spritesheet)
|
$ExportSprites.get_vbox().add_child(export_vertical_spritesheet)
|
||||||
|
|
||||||
|
|
||||||
func _input(event):
|
func _input(event):
|
||||||
for t in tools: #Handle tool shortcuts
|
for t in tools: #Handle tool shortcuts
|
||||||
|
@ -156,16 +156,16 @@ func edit_menu_id_pressed(id : int) -> void:
|
||||||
while(i < Global.canvas.layers.size() - 1 && Global.canvas.layers[i][0].get_used_rect() == Rect2(0, 0, 0, 0)):
|
while(i < Global.canvas.layers.size() - 1 && Global.canvas.layers[i][0].get_used_rect() == Rect2(0, 0, 0, 0)):
|
||||||
i += 1
|
i += 1
|
||||||
used_rect = Global.canvas.layers[i][0].get_used_rect()
|
used_rect = Global.canvas.layers[i][0].get_used_rect()
|
||||||
|
|
||||||
#Merge all layers with content
|
#Merge all layers with content
|
||||||
for j in range(Global.canvas.layers.size() - 1, i, -1):
|
for j in range(Global.canvas.layers.size() - 1, i, -1):
|
||||||
if Global.canvas.layers[j][0].get_used_rect() != Rect2(0, 0, 0, 0):
|
if Global.canvas.layers[j][0].get_used_rect() != Rect2(0, 0, 0, 0):
|
||||||
used_rect = used_rect.merge(Global.canvas.layers[j][0].get_used_rect())
|
used_rect = used_rect.merge(Global.canvas.layers[j][0].get_used_rect())
|
||||||
|
|
||||||
#If no layer has any content, just return
|
#If no layer has any content, just return
|
||||||
if used_rect == Rect2(0, 0, 0, 0):
|
if used_rect == Rect2(0, 0, 0, 0):
|
||||||
return
|
return
|
||||||
|
|
||||||
#Loop through all the layers to crop them
|
#Loop through all the layers to crop them
|
||||||
for j in range(Global.canvas.layers.size() - 1, -1, -1):
|
for j in range(Global.canvas.layers.size() - 1, -1, -1):
|
||||||
var sprite := Image.new()
|
var sprite := Image.new()
|
||||||
|
@ -173,7 +173,7 @@ func edit_menu_id_pressed(id : int) -> void:
|
||||||
Global.canvas.layers[j][0] = sprite
|
Global.canvas.layers[j][0] = sprite
|
||||||
Global.canvas.layers[j][0].lock()
|
Global.canvas.layers[j][0].lock()
|
||||||
Global.canvas.update_texture(j)
|
Global.canvas.update_texture(j)
|
||||||
|
|
||||||
var width = Global.canvas.layers[0][0].get_width()
|
var width = Global.canvas.layers[0][0].get_width()
|
||||||
var height = Global.canvas.layers[0][0].get_height()
|
var height = Global.canvas.layers[0][0].get_height()
|
||||||
Global.canvas.size = Vector2(width, height).floor()
|
Global.canvas.size = Vector2(width, height).floor()
|
||||||
|
@ -196,6 +196,10 @@ func edit_menu_id_pressed(id : int) -> void:
|
||||||
canvas.layers[canvas.current_layer_index][0].flip_y()
|
canvas.layers[canvas.current_layer_index][0].flip_y()
|
||||||
canvas.layers[canvas.current_layer_index][0].lock()
|
canvas.layers[canvas.current_layer_index][0].lock()
|
||||||
canvas.update_texture(canvas.current_layer_index)
|
canvas.update_texture(canvas.current_layer_index)
|
||||||
|
5: #Undo
|
||||||
|
Global.undo_redo.undo()
|
||||||
|
6: #Redo
|
||||||
|
Global.undo_redo.redo()
|
||||||
|
|
||||||
func view_menu_id_pressed(id : int) -> void:
|
func view_menu_id_pressed(id : int) -> void:
|
||||||
match id:
|
match id:
|
||||||
|
@ -213,13 +217,13 @@ func help_menu_id_pressed(id : int) -> void:
|
||||||
Global.can_draw = false
|
Global.can_draw = false
|
||||||
|
|
||||||
func _on_CreateNewImage_confirmed() -> void:
|
func _on_CreateNewImage_confirmed() -> void:
|
||||||
var width := float($CreateNewImage/VBoxContainer/WidthCont/WidthValue.value)
|
var width = $CreateNewImage/VBoxContainer/WidthCont/WidthValue.value
|
||||||
var height := float($CreateNewImage/VBoxContainer/HeightCont/HeightValue.value)
|
var height = $CreateNewImage/VBoxContainer/HeightCont/HeightValue.value
|
||||||
var fill_color : Color = $CreateNewImage/VBoxContainer/FillColor/FillColor.color
|
var fill_color : Color = $CreateNewImage/VBoxContainer/FillColor/FillColor.color
|
||||||
clear_canvases()
|
clear_canvases()
|
||||||
Global.canvas = load("res://Prefabs/Canvas.tscn").instance()
|
Global.canvas = load("res://Prefabs/Canvas.tscn").instance()
|
||||||
Global.canvas.size = Vector2(width, height).floor()
|
Global.canvas.size = Vector2(width, height).floor()
|
||||||
|
|
||||||
Global.canvas_parent.add_child(Global.canvas)
|
Global.canvas_parent.add_child(Global.canvas)
|
||||||
Global.canvases.append(Global.canvas)
|
Global.canvases.append(Global.canvas)
|
||||||
Global.current_frame = 0
|
Global.current_frame = 0
|
||||||
|
@ -246,10 +250,10 @@ func _on_OpenSprite_file_selected(path) -> void:
|
||||||
Global.canvas = canvas
|
Global.canvas = canvas
|
||||||
var width := file.get_16()
|
var width := file.get_16()
|
||||||
var height := file.get_16()
|
var height := file.get_16()
|
||||||
|
|
||||||
var layer := 0
|
var layer := 0
|
||||||
var layer_line := file.get_line()
|
var layer_line := file.get_line()
|
||||||
|
|
||||||
while layer_line == "-":
|
while layer_line == "-":
|
||||||
var buffer := file.get_buffer(width * height * 4)
|
var buffer := file.get_buffer(width * height * 4)
|
||||||
var image := Image.new()
|
var image := Image.new()
|
||||||
|
@ -260,14 +264,14 @@ func _on_OpenSprite_file_selected(path) -> void:
|
||||||
canvas.layers.append([image, tex, "Layer %s" % layer, true])
|
canvas.layers.append([image, tex, "Layer %s" % layer, true])
|
||||||
layer_line = file.get_line()
|
layer_line = file.get_line()
|
||||||
layer += 1
|
layer += 1
|
||||||
|
|
||||||
canvas.size = Vector2(width, height)
|
canvas.size = Vector2(width, height)
|
||||||
Global.canvases.append(canvas)
|
Global.canvases.append(canvas)
|
||||||
canvas.frame = frame
|
canvas.frame = frame
|
||||||
Global.canvas_parent.add_child(canvas)
|
Global.canvas_parent.add_child(canvas)
|
||||||
frame_line = file.get_line()
|
frame_line = file.get_line()
|
||||||
frame += 1
|
frame += 1
|
||||||
|
|
||||||
Global.current_frame = frame - 1
|
Global.current_frame = frame - 1
|
||||||
#Load tool options
|
#Load tool options
|
||||||
Global.left_color_picker.color = file.get_var()
|
Global.left_color_picker.color = file.get_var()
|
||||||
|
@ -282,11 +286,11 @@ func _on_OpenSprite_file_selected(path) -> void:
|
||||||
Global.left_color_picker.get_picker().add_preset(color)
|
Global.left_color_picker.get_picker().add_preset(color)
|
||||||
for color in right_palette:
|
for color in right_palette:
|
||||||
Global.right_color_picker.get_picker().add_preset(color)
|
Global.right_color_picker.get_picker().add_preset(color)
|
||||||
|
|
||||||
#Load custom brushes
|
#Load custom brushes
|
||||||
Global.custom_brushes.clear()
|
Global.custom_brushes.clear()
|
||||||
Global.remove_brush_buttons()
|
Global.remove_brush_buttons()
|
||||||
|
|
||||||
var brush_line := file.get_line()
|
var brush_line := file.get_line()
|
||||||
while brush_line == "/":
|
while brush_line == "/":
|
||||||
var b_width := file.get_16()
|
var b_width := file.get_16()
|
||||||
|
@ -297,7 +301,7 @@ func _on_OpenSprite_file_selected(path) -> void:
|
||||||
Global.custom_brushes.append(image)
|
Global.custom_brushes.append(image)
|
||||||
Global.create_brush_button(image)
|
Global.create_brush_button(image)
|
||||||
brush_line = file.get_line()
|
brush_line = file.get_line()
|
||||||
|
|
||||||
file.close()
|
file.close()
|
||||||
|
|
||||||
func _on_SaveSprite_file_selected(path) -> void:
|
func _on_SaveSprite_file_selected(path) -> void:
|
||||||
|
@ -315,7 +319,7 @@ func _on_SaveSprite_file_selected(path) -> void:
|
||||||
file.store_buffer(layer[0].get_data())
|
file.store_buffer(layer[0].get_data())
|
||||||
file.store_line("END_LAYERS")
|
file.store_line("END_LAYERS")
|
||||||
file.store_line("END_FRAMES")
|
file.store_line("END_FRAMES")
|
||||||
|
|
||||||
#Save tool options
|
#Save tool options
|
||||||
var left_color := Global.left_color_picker.color
|
var left_color := Global.left_color_picker.color
|
||||||
var right_color := Global.right_color_picker.color
|
var right_color := Global.right_color_picker.color
|
||||||
|
@ -341,7 +345,7 @@ func _on_SaveSprite_file_selected(path) -> void:
|
||||||
func _on_ImportSprites_files_selected(paths) -> void:
|
func _on_ImportSprites_files_selected(paths) -> void:
|
||||||
if !import_as_new_frame.pressed: #If we're not adding a new frame, delete the previous
|
if !import_as_new_frame.pressed: #If we're not adding a new frame, delete the previous
|
||||||
clear_canvases()
|
clear_canvases()
|
||||||
|
|
||||||
#Find the biggest image and let it handle the camera zoom options
|
#Find the biggest image and let it handle the camera zoom options
|
||||||
var max_size : Vector2
|
var max_size : Vector2
|
||||||
var biggest_canvas : Canvas
|
var biggest_canvas : Canvas
|
||||||
|
@ -369,10 +373,10 @@ func _on_ImportSprites_files_selected(paths) -> void:
|
||||||
else:
|
else:
|
||||||
if canvas.size > max_size:
|
if canvas.size > max_size:
|
||||||
biggest_canvas = canvas
|
biggest_canvas = canvas
|
||||||
|
|
||||||
else:
|
else:
|
||||||
OS.alert("Can't load file")
|
OS.alert("Can't load file")
|
||||||
|
|
||||||
i += 1
|
i += 1
|
||||||
Global.current_frame = i - 1
|
Global.current_frame = i - 1
|
||||||
Global.canvas = Global.canvases[Global.canvases.size() - 1]
|
Global.canvas = Global.canvases[Global.canvases.size() - 1]
|
||||||
|
@ -385,7 +389,7 @@ func _on_ImportSprites_files_selected(paths) -> void:
|
||||||
else:
|
else:
|
||||||
Global.remove_frame_button.disabled = true
|
Global.remove_frame_button.disabled = true
|
||||||
Global.remove_frame_button.mouse_default_cursor_shape = Control.CURSOR_FORBIDDEN
|
Global.remove_frame_button.mouse_default_cursor_shape = Control.CURSOR_FORBIDDEN
|
||||||
|
|
||||||
func clear_canvases() -> void:
|
func clear_canvases() -> void:
|
||||||
for child in Global.vbox_layer_container.get_children():
|
for child in Global.vbox_layer_container.get_children():
|
||||||
if child is PanelContainer:
|
if child is PanelContainer:
|
||||||
|
@ -454,7 +458,7 @@ func save_spritesheet() -> void:
|
||||||
dst += Vector2(0, canvas.size.y)
|
dst += Vector2(0, canvas.size.y)
|
||||||
else:
|
else:
|
||||||
dst += Vector2(canvas.size.x, 0)
|
dst += Vector2(canvas.size.x, 0)
|
||||||
|
|
||||||
var err = whole_image.save_png(current_export_path)
|
var err = whole_image.save_png(current_export_path)
|
||||||
if err != OK:
|
if err != OK:
|
||||||
OS.alert("Can't save file")
|
OS.alert("Can't save file")
|
||||||
|
@ -468,7 +472,7 @@ func _on_ViewportContainer_mouse_entered() -> void:
|
||||||
|
|
||||||
func _on_ViewportContainer_mouse_exited() -> void:
|
func _on_ViewportContainer_mouse_exited() -> void:
|
||||||
Global.has_focus = false
|
Global.has_focus = false
|
||||||
|
|
||||||
func _can_draw_true() -> void:
|
func _can_draw_true() -> void:
|
||||||
Global.can_draw = true
|
Global.can_draw = true
|
||||||
func _can_draw_false() -> void:
|
func _can_draw_false() -> void:
|
||||||
|
@ -486,8 +490,8 @@ func _on_Tool_pressed(tool_pressed : BaseButton, mouse_press := true, key_for_le
|
||||||
tool_pressed.add_child(Global.right_indicator)
|
tool_pressed.add_child(Global.right_indicator)
|
||||||
|
|
||||||
func _on_ScaleImage_confirmed() -> void:
|
func _on_ScaleImage_confirmed() -> void:
|
||||||
var width = float($ScaleImage/VBoxContainer/WidthCont/WidthValue.value)
|
var width = $ScaleImage/VBoxContainer/WidthCont/WidthValue.value
|
||||||
var height = float($ScaleImage/VBoxContainer/HeightCont/HeightValue.value)
|
var height = $ScaleImage/VBoxContainer/HeightCont/HeightValue.value
|
||||||
for i in range(Global.canvas.layers.size() - 1, -1, -1):
|
for i in range(Global.canvas.layers.size() - 1, -1, -1):
|
||||||
var sprite = Image.new()
|
var sprite = Image.new()
|
||||||
sprite = Global.canvas.layers[i][1].get_data()
|
sprite = Global.canvas.layers[i][1].get_data()
|
||||||
|
@ -495,7 +499,7 @@ func _on_ScaleImage_confirmed() -> void:
|
||||||
Global.canvas.layers[i][0] = sprite
|
Global.canvas.layers[i][0] = sprite
|
||||||
Global.canvas.layers[i][0].lock()
|
Global.canvas.layers[i][0].lock()
|
||||||
Global.canvas.update_texture(i)
|
Global.canvas.update_texture(i)
|
||||||
|
|
||||||
Global.canvas.size = Vector2(width, height).floor()
|
Global.canvas.size = Vector2(width, height).floor()
|
||||||
Global.canvas.camera_zoom()
|
Global.canvas.camera_zoom()
|
||||||
|
|
||||||
|
@ -526,15 +530,15 @@ func _on_MoveDownLayer_pressed() -> void:
|
||||||
|
|
||||||
func change_layer_order(rate : int) -> void:
|
func change_layer_order(rate : int) -> void:
|
||||||
var change = Global.canvas.current_layer_index + rate
|
var change = Global.canvas.current_layer_index + rate
|
||||||
|
|
||||||
var temp = Global.canvas.layers[Global.canvas.current_layer_index]
|
var temp = Global.canvas.layers[Global.canvas.current_layer_index]
|
||||||
Global.canvas.layers[Global.canvas.current_layer_index] = Global.canvas.layers[change]
|
Global.canvas.layers[Global.canvas.current_layer_index] = Global.canvas.layers[change]
|
||||||
Global.canvas.layers[change] = temp
|
Global.canvas.layers[change] = temp
|
||||||
|
|
||||||
Global.canvas.generate_layer_panels()
|
Global.canvas.generate_layer_panels()
|
||||||
Global.canvas.current_layer_index = change
|
Global.canvas.current_layer_index = change
|
||||||
Global.canvas.get_layer_container(Global.canvas.current_layer_index).changed_selection()
|
Global.canvas.get_layer_container(Global.canvas.current_layer_index).changed_selection()
|
||||||
|
|
||||||
func _on_CloneLayer_pressed() -> void:
|
func _on_CloneLayer_pressed() -> void:
|
||||||
add_layer(false)
|
add_layer(false)
|
||||||
|
|
||||||
|
@ -570,7 +574,7 @@ func _on_AddFrame_pressed() -> void:
|
||||||
Global.canvases.append(canvas)
|
Global.canvases.append(canvas)
|
||||||
Global.current_frame = Global.canvases.size() - 1
|
Global.current_frame = Global.canvases.size() - 1
|
||||||
Global.canvas = canvas
|
Global.canvas = canvas
|
||||||
|
|
||||||
Global.canvas_parent.add_child(canvas)
|
Global.canvas_parent.add_child(canvas)
|
||||||
Global.remove_frame_button.disabled = false
|
Global.remove_frame_button.disabled = false
|
||||||
Global.remove_frame_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
Global.remove_frame_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
||||||
|
@ -614,7 +618,7 @@ func _on_CloneFrame_pressed() -> void:
|
||||||
Global.canvases.append(canvas)
|
Global.canvases.append(canvas)
|
||||||
Global.current_frame = Global.canvases.size() - 1
|
Global.current_frame = Global.canvases.size() - 1
|
||||||
Global.canvas = canvas
|
Global.canvas = canvas
|
||||||
|
|
||||||
Global.canvas_parent.add_child(canvas)
|
Global.canvas_parent.add_child(canvas)
|
||||||
Global.remove_frame_button.disabled = false
|
Global.remove_frame_button.disabled = false
|
||||||
Global.remove_frame_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
Global.remove_frame_button.mouse_default_cursor_shape = Control.CURSOR_POINTING_HAND
|
||||||
|
@ -630,21 +634,21 @@ func _on_MoveFrameRight_pressed() -> void:
|
||||||
func change_frame_order(rate : int) -> void:
|
func change_frame_order(rate : int) -> void:
|
||||||
var frame_button = Global.frame_container.get_node("Frame_%s" % Global.current_frame)
|
var frame_button = Global.frame_container.get_node("Frame_%s" % Global.current_frame)
|
||||||
var change = Global.current_frame + rate
|
var change = Global.current_frame + rate
|
||||||
|
|
||||||
var temp = Global.canvases[Global.current_frame]
|
var temp = Global.canvases[Global.current_frame]
|
||||||
Global.canvases[Global.current_frame] = Global.canvases[change]
|
Global.canvases[Global.current_frame] = Global.canvases[change]
|
||||||
Global.canvases[change] = temp
|
Global.canvases[change] = temp
|
||||||
|
|
||||||
#Clear frame button names first, to avoid duplicates like two Frame_0s
|
#Clear frame button names first, to avoid duplicates like two Frame_0s
|
||||||
for canvas in Global.canvases:
|
for canvas in Global.canvases:
|
||||||
canvas.frame_button.name = "frame"
|
canvas.frame_button.name = "frame"
|
||||||
|
|
||||||
for canvas in Global.canvases:
|
for canvas in Global.canvases:
|
||||||
canvas.frame = Global.canvases.find(canvas)
|
canvas.frame = Global.canvases.find(canvas)
|
||||||
canvas.frame_button.name = "Frame_%s" % canvas.frame
|
canvas.frame_button.name = "Frame_%s" % canvas.frame
|
||||||
canvas.frame_button.get_node("FrameButton").frame = canvas.frame
|
canvas.frame_button.get_node("FrameButton").frame = canvas.frame
|
||||||
canvas.frame_button.get_node("FrameID").text = str(canvas.frame + 1)
|
canvas.frame_button.get_node("FrameID").text = str(canvas.frame + 1)
|
||||||
|
|
||||||
Global.current_frame = change
|
Global.current_frame = change
|
||||||
Global.frame_container.move_child(frame_button, Global.current_frame)
|
Global.frame_container.move_child(frame_button, Global.current_frame)
|
||||||
Global.canvas_parent.move_child(Global.canvas, Global.current_frame)
|
Global.canvas_parent.move_child(Global.canvas, Global.current_frame)
|
||||||
|
@ -669,7 +673,7 @@ func _on_LoopAnim_pressed() -> void:
|
||||||
func _on_PlayForward_toggled(button_pressed) -> void:
|
func _on_PlayForward_toggled(button_pressed) -> void:
|
||||||
Global.play_backwards.pressed = false
|
Global.play_backwards.pressed = false
|
||||||
Global.play_backwards.text = "Play Backwards"
|
Global.play_backwards.text = "Play Backwards"
|
||||||
|
|
||||||
if button_pressed:
|
if button_pressed:
|
||||||
Global.play_forward.text = "Stop"
|
Global.play_forward.text = "Stop"
|
||||||
$AnimationTimer.wait_time = 1 / fps
|
$AnimationTimer.wait_time = 1 / fps
|
||||||
|
@ -682,7 +686,7 @@ func _on_PlayForward_toggled(button_pressed) -> void:
|
||||||
func _on_PlayBackwards_toggled(button_pressed) -> void:
|
func _on_PlayBackwards_toggled(button_pressed) -> void:
|
||||||
Global.play_forward.pressed = false
|
Global.play_forward.pressed = false
|
||||||
Global.play_forward.text = "Play Forward"
|
Global.play_forward.text = "Play Forward"
|
||||||
|
|
||||||
if button_pressed:
|
if button_pressed:
|
||||||
Global.play_backwards.text = "Stop"
|
Global.play_backwards.text = "Stop"
|
||||||
$AnimationTimer.wait_time = 1 / fps
|
$AnimationTimer.wait_time = 1 / fps
|
||||||
|
@ -709,7 +713,7 @@ func _on_AnimationTimer_timeout() -> void:
|
||||||
2: #Ping pong loop
|
2: #Ping pong loop
|
||||||
animation_forward = false
|
animation_forward = false
|
||||||
_on_AnimationTimer_timeout()
|
_on_AnimationTimer_timeout()
|
||||||
|
|
||||||
else:
|
else:
|
||||||
if Global.current_frame > 0:
|
if Global.current_frame > 0:
|
||||||
Global.current_frame -= 1
|
Global.current_frame -= 1
|
||||||
|
@ -726,7 +730,7 @@ func _on_AnimationTimer_timeout() -> void:
|
||||||
2: #Ping pong loop
|
2: #Ping pong loop
|
||||||
animation_forward = true
|
animation_forward = true
|
||||||
_on_AnimationTimer_timeout()
|
_on_AnimationTimer_timeout()
|
||||||
|
|
||||||
Global.change_frame()
|
Global.change_frame()
|
||||||
|
|
||||||
func _on_FPSValue_value_changed(value) -> void:
|
func _on_FPSValue_value_changed(value) -> void:
|
||||||
|
|
|
@ -12,7 +12,6 @@ var orig_colors := []
|
||||||
|
|
||||||
func _ready() -> void:
|
func _ready() -> void:
|
||||||
img = Image.new()
|
img = Image.new()
|
||||||
#img.create(Global.canvas.size.x, Global.canvas.size.y, false, Image.FORMAT_RGBA8)
|
|
||||||
img.create(1, 1, false, Image.FORMAT_RGBA8)
|
img.create(1, 1, false, Image.FORMAT_RGBA8)
|
||||||
img.lock()
|
img.lock()
|
||||||
tex = ImageTexture.new()
|
tex = ImageTexture.new()
|
||||||
|
@ -24,8 +23,9 @@ func _process(delta) -> void:
|
||||||
var mouse_pos_floored := mouse_pos.floor()
|
var mouse_pos_floored := mouse_pos.floor()
|
||||||
var start_pos := polygon[0]
|
var start_pos := polygon[0]
|
||||||
var end_pos := polygon[2]
|
var end_pos := polygon[2]
|
||||||
var layer : Image = Global.canvas.layers[Global.canvas.current_layer_index][0]
|
var current_layer_index := Global.canvas.current_layer_index
|
||||||
|
var layer : Image = Global.canvas.layers[current_layer_index][0]
|
||||||
|
|
||||||
if point_in_rectangle(mouse_pos, polygon[0], polygon[2]) && Global.selected_pixels.size() > 0 && (Global.current_left_tool == "RectSelect" || Global.current_right_tool == "RectSelect"):
|
if point_in_rectangle(mouse_pos, polygon[0], polygon[2]) && Global.selected_pixels.size() > 0 && (Global.current_left_tool == "RectSelect" || Global.current_right_tool == "RectSelect"):
|
||||||
get_parent().get_parent().mouse_default_cursor_shape = Input.CURSOR_MOVE
|
get_parent().get_parent().mouse_default_cursor_shape = Input.CURSOR_MOVE
|
||||||
if (Global.current_left_tool == "RectSelect" && Input.is_action_just_pressed("left_mouse")) || (Global.current_right_tool == "RectSelect" && Input.is_action_just_pressed("right_mouse")):
|
if (Global.current_left_tool == "RectSelect" && Input.is_action_just_pressed("left_mouse")) || (Global.current_right_tool == "RectSelect" && Input.is_action_just_pressed("right_mouse")):
|
||||||
|
@ -46,25 +46,25 @@ func _process(delta) -> void:
|
||||||
for i in range(Global.selected_pixels.size()):
|
for i in range(Global.selected_pixels.size()):
|
||||||
var curr_px = Global.selected_pixels[i]
|
var curr_px = Global.selected_pixels[i]
|
||||||
if point_in_rectangle(curr_px, Global.canvas.location - Vector2.ONE, Global.canvas.size):
|
if point_in_rectangle(curr_px, Global.canvas.location - Vector2.ONE, Global.canvas.size):
|
||||||
orig_colors.append(layer.get_pixelv(curr_px))
|
orig_colors.append(layer.get_pixelv(curr_px)) #Color of pixel
|
||||||
var px = curr_px - Global.selected_pixels[0]
|
var px = curr_px - Global.selected_pixels[0]
|
||||||
img.set_pixelv(px, orig_colors[i])
|
img.set_pixelv(px, orig_colors[i])
|
||||||
layer.set_pixelv(curr_px, Color(0, 0, 0, 0))
|
layer.set_pixelv(curr_px, Color(0, 0, 0, 0))
|
||||||
else:
|
else: #If part of selection is outside canvas
|
||||||
orig_colors.append(Color(0, 0, 0, 0))
|
orig_colors.append(Color(0, 0, 0, 0))
|
||||||
Global.canvas.update_texture(Global.canvas.current_layer_index)
|
Global.canvas.update_texture(Global.canvas.current_layer_index)
|
||||||
tex.create_from_image(img, 0)
|
tex.create_from_image(img, 0)
|
||||||
update()
|
update()
|
||||||
else:
|
else:
|
||||||
get_parent().get_parent().mouse_default_cursor_shape = Input.CURSOR_CROSS
|
get_parent().get_parent().mouse_default_cursor_shape = Input.CURSOR_CROSS
|
||||||
|
|
||||||
if is_dragging:
|
if is_dragging:
|
||||||
if (Global.current_left_tool == "RectSelect" && Input.is_action_pressed("left_mouse")) || (Global.current_right_tool == "RectSelect" && Input.is_action_pressed("right_mouse")):
|
if (Global.current_left_tool == "RectSelect" && Input.is_action_pressed("left_mouse")) || (Global.current_right_tool == "RectSelect" && Input.is_action_pressed("right_mouse")):
|
||||||
#Drag
|
#Drag
|
||||||
#if orig_x + mouse_pos_floored.x >= Global.canvas.location.x && diff_x + mouse_pos_floored.x <= Global.canvas.size.x:
|
#if orig_x + mouse_pos_floored.x >= Global.canvas.location.x && diff_x + mouse_pos_floored.x <= Global.canvas.size.x:
|
||||||
start_pos.x = orig_x + mouse_pos_floored.x
|
start_pos.x = orig_x + mouse_pos_floored.x
|
||||||
end_pos.x = diff_x + mouse_pos_floored.x
|
end_pos.x = diff_x + mouse_pos_floored.x
|
||||||
|
|
||||||
#if orig_y + mouse_pos_floored.y >= Global.canvas.location.y && diff_y + mouse_pos_floored.y <= Global.canvas.size.y:
|
#if orig_y + mouse_pos_floored.y >= Global.canvas.location.y && diff_y + mouse_pos_floored.y <= Global.canvas.size.y:
|
||||||
start_pos.y = orig_y + mouse_pos_floored.y
|
start_pos.y = orig_y + mouse_pos_floored.y
|
||||||
end_pos.y = diff_y + mouse_pos_floored.y
|
end_pos.y = diff_y + mouse_pos_floored.y
|
||||||
|
@ -72,7 +72,7 @@ func _process(delta) -> void:
|
||||||
polygon[1] = Vector2(end_pos.x, start_pos.y)
|
polygon[1] = Vector2(end_pos.x, start_pos.y)
|
||||||
polygon[2] = end_pos
|
polygon[2] = end_pos
|
||||||
polygon[3] = Vector2(start_pos.x, end_pos.y)
|
polygon[3] = Vector2(start_pos.x, end_pos.y)
|
||||||
|
|
||||||
if (Global.current_left_tool == "RectSelect" && Input.is_action_just_released("left_mouse")) || (Global.current_right_tool == "RectSelect" && Input.is_action_just_released("right_mouse")):
|
if (Global.current_left_tool == "RectSelect" && Input.is_action_just_released("left_mouse")) || (Global.current_right_tool == "RectSelect" && Input.is_action_just_released("right_mouse")):
|
||||||
#Release Drag
|
#Release Drag
|
||||||
is_dragging = false
|
is_dragging = false
|
||||||
|
@ -86,13 +86,15 @@ func _process(delta) -> void:
|
||||||
img.fill(Color(0, 0, 0, 0))
|
img.fill(Color(0, 0, 0, 0))
|
||||||
tex.create_from_image(img, 0)
|
tex.create_from_image(img, 0)
|
||||||
update()
|
update()
|
||||||
|
|
||||||
orig_colors.clear()
|
orig_colors.clear()
|
||||||
Global.selected_pixels.clear()
|
Global.selected_pixels.clear()
|
||||||
for xx in range(start_pos.x, end_pos.x):
|
for xx in range(start_pos.x, end_pos.x):
|
||||||
for yy in range(start_pos.y, end_pos.y):
|
for yy in range(start_pos.y, end_pos.y):
|
||||||
Global.selected_pixels.append(Vector2(xx, yy))
|
Global.selected_pixels.append(Vector2(xx, yy))
|
||||||
|
|
||||||
|
Global.canvas.handle_redo("Rectangle Select") #Redo
|
||||||
|
|
||||||
#Handle copy
|
#Handle copy
|
||||||
if Input.is_action_just_pressed("copy") && Global.selected_pixels.size() > 0:
|
if Input.is_action_just_pressed("copy") && Global.selected_pixels.size() > 0:
|
||||||
Global.image_clipboard = layer.get_rect(Rect2(polygon[0], polygon[2] - polygon[0]))
|
Global.image_clipboard = layer.get_rect(Rect2(polygon[0], polygon[2] - polygon[0]))
|
||||||
|
@ -101,15 +103,16 @@ func _process(delta) -> void:
|
||||||
brush_img = layer.get_rect(Rect2(polygon[0], polygon[2] - polygon[0]))
|
brush_img = layer.get_rect(Rect2(polygon[0], polygon[2] - polygon[0]))
|
||||||
brush_img = brush_img.get_rect(brush_img.get_used_rect()) #save only the visible pixels
|
brush_img = brush_img.get_rect(brush_img.get_used_rect()) #save only the visible pixels
|
||||||
Global.custom_brushes.append(brush_img)
|
Global.custom_brushes.append(brush_img)
|
||||||
|
|
||||||
Global.create_brush_button(brush_img)
|
Global.create_brush_button(brush_img)
|
||||||
|
|
||||||
#Handle paste
|
#Handle paste
|
||||||
#if Input.is_action_just_pressed("paste") && Global.selected_pixels.size() > 0 && !is_dragging:
|
|
||||||
if Input.is_action_just_pressed("paste") && Global.selected_pixels.size() > 0 && Global.image_clipboard.get_size() > Vector2.ZERO:
|
if Input.is_action_just_pressed("paste") && Global.selected_pixels.size() > 0 && Global.image_clipboard.get_size() > Vector2.ZERO:
|
||||||
|
Global.canvas.handle_undo("Draw")
|
||||||
layer.blend_rect(Global.image_clipboard, Rect2(Vector2.ZERO, polygon[2]-polygon[0]), polygon[0])
|
layer.blend_rect(Global.image_clipboard, Rect2(Vector2.ZERO, polygon[2]-polygon[0]), polygon[0])
|
||||||
layer.lock()
|
layer.lock()
|
||||||
Global.canvas.update_texture(Global.canvas.current_layer_index)
|
Global.canvas.handle_redo("Draw")
|
||||||
|
#Global.canvas.update_texture(Global.canvas.current_layer_index)
|
||||||
|
|
||||||
func _draw() -> void:
|
func _draw() -> void:
|
||||||
if img.get_size() == polygon[2] - polygon[0]:
|
if img.get_size() == polygon[2] - polygon[0]:
|
||||||
|
@ -117,4 +120,3 @@ func _draw() -> void:
|
||||||
|
|
||||||
func point_in_rectangle(p : Vector2, coord1 : Vector2, coord2 : Vector2) -> bool:
|
func point_in_rectangle(p : Vector2, coord1 : Vector2, coord2 : Vector2) -> bool:
|
||||||
return p.x > coord1.x && p.y > coord1.y && p.x < coord2.x && p.y < coord2.y
|
return p.x > coord1.x && p.y > coord1.y && p.x < coord2.x && p.y < coord2.y
|
||||||
|
|
|
@ -7,7 +7,7 @@ custom_features=""
|
||||||
export_filter="all_resources"
|
export_filter="all_resources"
|
||||||
include_filter=""
|
include_filter=""
|
||||||
exclude_filter=""
|
exclude_filter=""
|
||||||
export_path="C:/Users/Overloaded/Dropbox/Orama Interactive/Projects/[Programa Labs]/Pixelorama/Stable/Pixelorama.exe"
|
export_path="C:/Users/Overloaded/Dropbox/Orama Interactive/Projects/[Programa Labs]/Pixelorama/Full of bugs/Pixelorama.exe"
|
||||||
patch_list=PoolStringArray( )
|
patch_list=PoolStringArray( )
|
||||||
script_export_mode=1
|
script_export_mode=1
|
||||||
script_encryption_key=""
|
script_encryption_key=""
|
||||||
|
|
|
@ -131,16 +131,6 @@ right_lightdark_tool={
|
||||||
"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":true,"shift":false,"control":false,"meta":false,"command":false,"pressed":false,"scancode":85,"unicode":0,"echo":false,"script":null)
|
"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":true,"shift":false,"control":false,"meta":false,"command":false,"pressed":false,"scancode":85,"unicode":0,"echo":false,"script":null)
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
flip_h={
|
|
||||||
"deadzone": 0.5,
|
|
||||||
"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":false,"shift":true,"control":false,"meta":false,"command":false,"pressed":false,"scancode":72,"unicode":0,"echo":false,"script":null)
|
|
||||||
]
|
|
||||||
}
|
|
||||||
flip_v={
|
|
||||||
"deadzone": 0.5,
|
|
||||||
"events": [ Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":0,"alt":false,"shift":true,"control":false,"meta":false,"command":false,"pressed":false,"scancode":86,"unicode":0,"echo":false,"script":null)
|
|
||||||
]
|
|
||||||
}
|
|
||||||
|
|
||||||
[rendering]
|
[rendering]
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue