mirror of
https://github.com/Ttanasart-pt/Pixel-Composer.git
synced 2025-01-24 03:48:06 +01:00
group ungroup undo
This commit is contained in:
parent
03ad6142d0
commit
dcc07ba19e
11 changed files with 137 additions and 53 deletions
|
@ -77,10 +77,20 @@ function log_clear() { #region
|
|||
file_delete(path);
|
||||
} #endregion
|
||||
|
||||
function os_type_sting() {
|
||||
switch(os_type) {
|
||||
case os_windows : return "Windows";
|
||||
case os_macosx : return "MacOS";
|
||||
case os_linux : return "Linux";
|
||||
}
|
||||
|
||||
return "undefined";
|
||||
}
|
||||
|
||||
function exception_print(e) { #region
|
||||
if(!is_struct(e) || !struct_has(e, "longMessage")) return string(e);
|
||||
|
||||
var str = "\n\n========== Crash log ==========\n\n" + e.longMessage;
|
||||
var str = $"\n\n========== Crash log [PXC {VERSION_STRING}] [{os_type_sting()}] ==========\n\n" + e.longMessage;
|
||||
str += "\n\n========== Stack trace ==========\n\n";
|
||||
|
||||
for( var i = 0, n = array_length(e.stacktrace); i < n; i++ )
|
||||
|
@ -99,13 +109,16 @@ function setException() { #region
|
|||
if(!SAVING && !TESTING && !IS_CMD) SAVE_AT(PROJECT, path);
|
||||
|
||||
var tt = "";
|
||||
tt += "\n-------------------------- OH NO --------------------------\n\n";
|
||||
tt += $"\n-------------------------- Pixel Composer {VERSION_STRING} Crashed --------------------------\n";
|
||||
tt += "\n" + ex.longMessage;
|
||||
tt += "\n" + ex.script;
|
||||
tt += "\n-------------------------- STACK TRACE --------------------------\n\n";
|
||||
tt += "\n\n-------------------------- STACK TRACE --------------------------\n\n";
|
||||
for( var i = 0, n = array_length(ex.stacktrace); i < n; i++ )
|
||||
tt += ex.stacktrace[i] + "\n";
|
||||
tt += "\n---------------------------- :( ----------------------------\n";
|
||||
tt += "\n\n\n\n-------------------------- Device Info --------------------------\n";
|
||||
tt += $"\nVersion: {VERSION_STRING} ({VERSION})";
|
||||
tt += $"\nOperating system: {os_type_sting()} ({os_version})"
|
||||
tt += "\n\n---------------------------- :( ----------------------------\n";
|
||||
|
||||
var path = $"{env_user()}crash_log.txt";
|
||||
|
||||
|
|
|
@ -108,7 +108,29 @@ function Action(_type, _object, _data, _trigger = 0) constructor {
|
|||
|
||||
case ACTION_TYPE.ungroup :
|
||||
obj.restore();
|
||||
groupNodes(data.content, obj, false);
|
||||
groupNodes(data.content, obj, false, false);
|
||||
|
||||
for (var i = 0, n = array_length(data.deleted); i < n; i++) {
|
||||
var _dl = data.deleted[i];
|
||||
var _nd = _dl.node;
|
||||
var _vt = _dl.value_to;
|
||||
_nd.enable();
|
||||
|
||||
for (var j = 0, m = ds_list_size(_nd.outputs); j < m; j++) {
|
||||
var _out = _nd.outputs[| j];
|
||||
var _too = _vt[j];
|
||||
|
||||
for (var k = 0, p = array_length(_too); k < p; k++)
|
||||
_too[k].setFrom(_out);
|
||||
}
|
||||
}
|
||||
|
||||
var _connectTo = data.connectTo;
|
||||
|
||||
for (var i = 0, n = array_length(_connectTo); i < n; i++)
|
||||
for (var j = 0, m = array_length(_connectTo[i]); j < m; j++)
|
||||
_connectTo[i][j].setFrom(obj.outputs[| i]);
|
||||
|
||||
break;
|
||||
|
||||
case ACTION_TYPE.collection_loaded :
|
||||
|
|
|
@ -51,9 +51,9 @@ function groupNodes(nodeArray, _group = noone, record = true, check_connect = tr
|
|||
_content[i] = _ctx_nodes[i];
|
||||
}
|
||||
|
||||
var _io = { inputs: {}, outputs: {}, map: {} };
|
||||
|
||||
if(check_connect) { #region IO creation
|
||||
var _io = { inputs: {}, outputs: {}, map: {} };
|
||||
|
||||
for(var i = 0; i < array_length(nodeArray); i++)
|
||||
nodeArray[i].checkConnectGroup(_io);
|
||||
|
||||
|
@ -119,22 +119,53 @@ function groupNodes(nodeArray, _group = noone, record = true, check_connect = tr
|
|||
} #endregion
|
||||
|
||||
function upgroupNode(collection, record = true) { #region
|
||||
UNDO_HOLDING = true;
|
||||
var _content = [];
|
||||
UNDO_HOLDING = true;
|
||||
var _content = [], _deleted = [];
|
||||
var node_list = collection.getNodeList();
|
||||
var _node_arr = ds_list_to_array(node_list);
|
||||
var _conn_to = collection.getJunctionTos();
|
||||
|
||||
while(!ds_list_empty(node_list)) {
|
||||
var remNode = node_list[| 0];
|
||||
if(!remNode.destroy_when_upgroup)
|
||||
array_push(_content, remNode);
|
||||
var _cx = 0, _cy = 0;
|
||||
var _nn = 0;
|
||||
|
||||
for (var i = 0, n = array_length(_node_arr); i < n; i++) {
|
||||
var _node = _node_arr[i];
|
||||
if(!_node.selectable) continue;
|
||||
|
||||
collection.remove(remNode);
|
||||
_cx += _node.x;
|
||||
_cy += _node.y;
|
||||
_nn++;
|
||||
}
|
||||
|
||||
if(_nn) {
|
||||
_cx = collection.x - _cx / _nn;
|
||||
_cy = collection.y - _cy / _nn;
|
||||
}
|
||||
|
||||
for (var i = 0, n = array_length(_node_arr); i < n; i++) {
|
||||
var remNode = _node_arr[i];
|
||||
|
||||
remNode.x += _cx;
|
||||
remNode.y += _cy;
|
||||
|
||||
if(remNode.destroy_when_upgroup) {
|
||||
var _vto = remNode.getJunctionTos();
|
||||
array_push(_deleted, { node: remNode, value_to : _vto });
|
||||
} else
|
||||
array_push(_content, remNode);
|
||||
collection.remove(remNode);
|
||||
}
|
||||
|
||||
collection.destroy();
|
||||
UNDO_HOLDING = false;
|
||||
|
||||
if(record) recordAction(ACTION_TYPE.ungroup, collection, { content: _content });
|
||||
if(!record) return;
|
||||
|
||||
recordAction(ACTION_TYPE.ungroup, collection, {
|
||||
content : _content,
|
||||
deleted : _deleted,
|
||||
connectTo : _conn_to,
|
||||
});
|
||||
} #endregion
|
||||
|
||||
function Node_Collection(_x, _y, _group = noone) : Node(_x, _y, _group) constructor {
|
||||
|
@ -383,21 +414,23 @@ function Node_Collection(_x, _y, _group = noone) : Node(_x, _y, _group) construc
|
|||
} #endregion
|
||||
|
||||
static remove = function(_node) { #region
|
||||
var node_list = getNodeList();
|
||||
var _pos = ds_list_find_index(node_list, _node);
|
||||
ds_list_delete(node_list, _pos);
|
||||
var list = group == noone? PANEL_GRAPH.nodes_list : group.getNodeList();
|
||||
ds_list_add(list, _node);
|
||||
var _hide = _node.destroy_when_upgroup;
|
||||
|
||||
if(!_hide) {
|
||||
var node_list = getNodeList();
|
||||
var list = group == noone? PANEL_GRAPH.nodes_list : group.getNodeList();
|
||||
|
||||
ds_list_remove(node_list, _node);
|
||||
ds_list_add(list, _node);
|
||||
}
|
||||
|
||||
recordAction(ACTION_TYPE.group_removed, self, _node);
|
||||
|
||||
if(struct_has(_node, "ungroup"))
|
||||
_node.ungroup();
|
||||
if(struct_has(_node, "onUngroup"))
|
||||
_node.onUngroup();
|
||||
|
||||
if(_node.destroy_when_upgroup)
|
||||
_node.destroy();
|
||||
else
|
||||
_node.group = group;
|
||||
if(_hide) _node.disable();
|
||||
else _node.group = group;
|
||||
|
||||
will_refresh = true;
|
||||
node_length = ds_list_size(nodes);
|
||||
|
|
|
@ -2004,6 +2004,15 @@ function Node(_x, _y, _group = noone) : __Node_Base(_x, _y) constructor {
|
|||
|
||||
static drawTools = function(_mx, _my, xx, yy, tool_size, hover, focus) { return 0; }
|
||||
|
||||
static getJunctionTos = function() { #region
|
||||
var _vto = array_create(ds_list_size(outputs));
|
||||
for (var j = 0, m = ds_list_size(outputs); j < m; j++)
|
||||
_vto[j] = array_clone(outputs[| j].value_to);
|
||||
return _vto;
|
||||
} #endregion
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static serialize = function(scale = false, preset = false) { #region >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> SERIALIZE <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
|
||||
if(!active) return;
|
||||
|
||||
|
|
|
@ -375,7 +375,7 @@ function Node_Group_Input(_x, _y, _group = noone) : Node(_x, _y, _group) constru
|
|||
group.refreshNodes();
|
||||
} #endregion
|
||||
|
||||
static ungroup = function() { #region
|
||||
static onUngroup = function() { #region
|
||||
var fr = inParent.value_from;
|
||||
|
||||
for( var i = 0; i < array_length(outputs[| 0].value_to); i++ ) {
|
||||
|
|
|
@ -122,7 +122,7 @@ function Node_Group_Output(_x, _y, _group = noone) : Node(_x, _y, _group) constr
|
|||
group.refreshNodes();
|
||||
} #endregion
|
||||
|
||||
static ungroup = function() { #region
|
||||
static onUngroup = function() { #region
|
||||
var fr = inputs[| 0].value_from;
|
||||
|
||||
for( var i = 0; i < array_length(outParent.value_to); i++ ) {
|
||||
|
|
|
@ -127,9 +127,9 @@ function Node_Path(_x, _y, _group = noone) : Node(_x, _y, _group) constructor {
|
|||
} #endregion
|
||||
|
||||
static drawOverlay = function(hover, active, _x, _y, _s, _mx, _my, _snx, _sny) { #region
|
||||
var sample = PREFERENCES.path_resolution;
|
||||
var loop = getInputData(1);
|
||||
var ansize = ds_list_size(inputs) - input_fix_len;
|
||||
var sample = PREFERENCES.path_resolution;
|
||||
var loop = getInputData(1);
|
||||
var ansize = ds_list_size(inputs) - input_fix_len;
|
||||
var _edited = false;
|
||||
|
||||
var pos = outputs[| 0].getValue();
|
||||
|
@ -596,7 +596,7 @@ function Node_Path(_x, _y, _group = noone) : Node(_x, _y, _group) constructor {
|
|||
var _ax1 = 0, _ay1 = 0;
|
||||
|
||||
if(array_length(_a) < 6) continue;
|
||||
|
||||
|
||||
if(_a[2] != 0 || _a[3] != 0 || _a[4] != 0 || _a[5] != 0) {
|
||||
_ax0 = _x + (_a[0] + _a[2]) * _s;
|
||||
_ay0 = _y + (_a[1] + _a[3]) * _s;
|
||||
|
@ -611,7 +611,7 @@ function Node_Path(_x, _y, _group = noone) : Node(_x, _y, _group) constructor {
|
|||
draw_sprite_colored(THEME.anchor_selector, 2, _ax0, _ay0);
|
||||
draw_sprite_colored(THEME.anchor_selector, 2, _ax1, _ay1);
|
||||
}
|
||||
|
||||
|
||||
draw_sprite_colored(THEME.anchor_selector, 0, xx, yy);
|
||||
draw_set_text(f_p1, fa_left, fa_bottom, COLORS._main_accent);
|
||||
draw_text(xx + ui(4), yy - ui(4), inputs[| input_fix_len + i].name);
|
||||
|
@ -925,11 +925,15 @@ function Node_Path(_x, _y, _group = noone) : Node(_x, _y, _group) constructor {
|
|||
|
||||
var _a = [];
|
||||
for(var i = input_fix_len; i < ds_list_size(inputs); i++) {
|
||||
var _anc = array_clone(getInputData(i));
|
||||
var _val = getInputData(i);
|
||||
var _anc = array_create(7, 0);
|
||||
|
||||
for(var j = 0; j < 7; j++)
|
||||
_anc[j] = array_safe_get(_val, j);
|
||||
|
||||
if(_rnd) {
|
||||
_anc[0] = round(_anc[0]);
|
||||
_anc[1] = round(_anc[1]);
|
||||
_anc[0] = round(_val[0]);
|
||||
_anc[1] = round(_val[1]);
|
||||
}
|
||||
|
||||
array_push(_a, _anc);
|
||||
|
|
|
@ -969,7 +969,7 @@ function __initNodes() {
|
|||
ds_list_add(node, "Groups");
|
||||
addNodeObject(node, "Group", s_node_group, "Node_Group", [1, Node_Group]);
|
||||
addNodeObject(node, "Feedback", s_node_feedback, "Node_Feedback", [1, Node_Feedback],, "Create a group that reuse output from last frame to the current one.");
|
||||
addNodeObject(node, "Loop", s_node_loop, "Node_Iterate", [1, Node_Iterate], ["iterate", "for"], "Create group that reuse output as input repeatedly in one frame.");
|
||||
addNodeObject(node, "Loop", s_node_loop, "Node_Iterate", [1, Node_Iterate], ["iterate", "for"], "Create group that reuse output as input repeatedly in one frame.").isDeprecated();
|
||||
addNodeObject(node, "Loop Array", s_node_loop_array, "Node_Iterate_Each_Inline", [1, Node_Iterate_Each_Inline], ["iterate each", "for each", "array loop"], "Create group that iterate to each member in an array.");
|
||||
addNodeObject(node, "Filter Array", s_node_filter_array, "Node_Iterate_Filter_Inline", [1, Node_Iterate_Filter_Inline],, "Filter array using condition.").setVersion(1140);
|
||||
|
||||
|
|
|
@ -29,7 +29,7 @@ function Node_Render_Sprite_Sheet(_x, _y, _group = noone) : Node(_x, _y, _group)
|
|||
new scrollItem("Vertical", s_node_alignment, 1),
|
||||
new scrollItem("Grid", s_node_alignment, 2), ])
|
||||
.rejectArray();
|
||||
|
||||
|
||||
inputs[| 4] = nodeValue("Grid column", self, JUNCTION_CONNECT.input, VALUE_TYPE.integer, 4)
|
||||
.rejectArray();
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
function Panel_History() : PanelContent() constructor {
|
||||
title = __txt("History");
|
||||
w = ui(400);
|
||||
h = ui(480);
|
||||
w = ui(400);
|
||||
h = ui(480);
|
||||
|
||||
anchor = ANCHOR.left | ANCHOR.top;
|
||||
hold = false;
|
||||
|
@ -34,12 +34,10 @@ function Panel_History() : PanelContent() constructor {
|
|||
refreshList();
|
||||
|
||||
onResize = function() {
|
||||
PANEL_PADDING
|
||||
|
||||
sc_history.resize(w - ui(padding + padding), h - ui(title_height + padding));
|
||||
sc_history.resize(w - padding * 2, h - padding * 2);
|
||||
}
|
||||
|
||||
sc_history = new scrollPane(w - ui(padding + padding), h - ui(title_height + padding), function(_y, _m) {
|
||||
sc_history = new scrollPane(w - padding * 2, h - padding * 2, function(_y, _m) {
|
||||
draw_clear_alpha(COLORS._main_text, 0);
|
||||
|
||||
if((ds_list_size(redo_list) != ds_stack_size(REDO_STACK)) || (ds_list_size(undo_list) != ds_stack_size(UNDO_STACK)))
|
||||
|
@ -153,11 +151,11 @@ function Panel_History() : PanelContent() constructor {
|
|||
function drawContent(panel) {
|
||||
draw_clear_alpha(COLORS.panel_bg_clear, 0);
|
||||
|
||||
var px = ui(padding);
|
||||
var py = ui(padding);
|
||||
var pw = w - ui(padding + padding);
|
||||
var ph = h - ui(padding + padding);
|
||||
|
||||
var px = padding;
|
||||
var py = padding;
|
||||
var pw = w - padding * 2;
|
||||
var ph = h - padding * 2;
|
||||
|
||||
draw_sprite_stretched(THEME.ui_panel_bg, 1, px - ui(8), py - ui(8), pw + ui(16), ph + ui(16));
|
||||
sc_history.setFocusHover(pFOCUS, pHOVER);
|
||||
sc_history.draw(px, py, mx - px, my - py);
|
||||
|
|
|
@ -118,10 +118,13 @@
|
|||
|
||||
function is_surface(s) { #region
|
||||
INLINE
|
||||
|
||||
if(is_instanceof(s, dynaSurf) || is_instanceof(s, SurfaceAtlas)) return true;
|
||||
if(is_numeric(s) && s > 0 && surface_exists(s)) return true;
|
||||
return false;
|
||||
|
||||
return !is_array(s) && (
|
||||
is_instanceof(s, dynaSurf) ||
|
||||
is_instanceof(s, SurfaceAtlas) ||
|
||||
(is_numeric(s) && s > 0 && surface_exists(s))
|
||||
);
|
||||
|
||||
} #endregion
|
||||
|
||||
function surface_verify(surf, w, h, format = surface_rgba8unorm) { #region
|
||||
|
@ -149,6 +152,7 @@
|
|||
function surface_get_width_safe(s, crop = true) { #region
|
||||
INLINE
|
||||
|
||||
if(!is_surface(s)) return 1;
|
||||
if(is_struct(s)) {
|
||||
if(is_instanceof(s, dynaSurf)) return s.getWidth();
|
||||
else if(is_instanceof(s, SurfaceAtlas)) return crop? surface_get_width(s.getSurface()) : s.oriSurf_w;
|
||||
|
@ -161,6 +165,7 @@
|
|||
function surface_get_height_safe(s, crop = true) { #region
|
||||
INLINE
|
||||
|
||||
if(!is_surface(s)) return 1;
|
||||
if(is_struct(s)) {
|
||||
if(is_instanceof(s, dynaSurf)) return s.getHeight();
|
||||
else if(is_instanceof(s, SurfaceAtlas)) return crop? surface_get_height(s.getSurface()) : s.oriSurf_h;
|
||||
|
|
Loading…
Reference in a new issue