From e0533c8fe5a09f54c5c2e0500c8ee67eb0c914c9 Mon Sep 17 00:00:00 2001 From: Tanasart Date: Wed, 4 Dec 2024 18:20:29 +0700 Subject: [PATCH] tester --- PixelComposer.resource_order | 1 + PixelComposer.yyp | 1 + scripts/globals/globals.gml | 6 +- scripts/load_function/load_function.gml | 3 +- scripts/node_assert/node_assert.gml | 141 ++++++ scripts/node_assert/node_assert.yy | 13 + scripts/node_assert/node_outline.yy | 12 + scripts/node_checker/node_checker.gml | 4 +- scripts/node_data/node_data.gml | 35 +- scripts/node_functions/node_functions.gml | 1 + scripts/node_registry/node_registry.gml | 5 +- scripts/node_value/node_value.gml | 3 +- scripts/panel_menu/panel_menu.gml | 5 +- scripts/panel_test/panel_test.gml | 406 +++++++++++++++--- scripts/project_data/project_data.gml | 5 +- scripts/render_data/render_data.gml | 2 +- scripts/save_function/save_function.gml | 10 +- .../surface_functions/surface_functions.gml | 9 +- scripts/var_comparison/var_comparison.gml | 12 +- 19 files changed, 574 insertions(+), 100 deletions(-) create mode 100644 scripts/node_assert/node_assert.gml create mode 100644 scripts/node_assert/node_assert.yy create mode 100644 scripts/node_assert/node_outline.yy diff --git a/PixelComposer.resource_order b/PixelComposer.resource_order index e7a0cebae..24fea2e3e 100644 --- a/PixelComposer.resource_order +++ b/PixelComposer.resource_order @@ -697,6 +697,7 @@ {"name":"node_array","order":5,"path":"scripts/node_array/node_array.yy",}, {"name":"node_ase_layer","order":1,"path":"scripts/node_ase_layer/node_ase_layer.yy",}, {"name":"node_ase_tag","order":2,"path":"scripts/node_ase_tag/node_ase_tag.yy",}, + {"name":"node_assert","order":30,"path":"scripts/node_assert/node_assert.yy",}, {"name":"node_atlas_get","order":1,"path":"scripts/node_atlas_get/node_atlas_get.yy",}, {"name":"node_atlas_set","order":2,"path":"scripts/node_atlas_set/node_atlas_set.yy",}, {"name":"node_atlas_to_struct","order":3,"path":"scripts/node_atlas_to_struct/node_atlas_to_struct.yy",}, diff --git a/PixelComposer.yyp b/PixelComposer.yyp index 839c136df..36e528d3c 100644 --- a/PixelComposer.yyp +++ b/PixelComposer.yyp @@ -1235,6 +1235,7 @@ {"id":{"name":"node_ase_file_read","path":"scripts/node_ase_file_read/node_ase_file_read.yy",},}, {"id":{"name":"node_ase_layer","path":"scripts/node_ase_layer/node_ase_layer.yy",},}, {"id":{"name":"node_ase_tag","path":"scripts/node_ase_tag/node_ase_tag.yy",},}, + {"id":{"name":"node_assert","path":"scripts/node_assert/node_assert.yy",},}, {"id":{"name":"node_atlas_draw","path":"scripts/node_atlas_draw/node_atlas_draw.yy",},}, {"id":{"name":"node_atlas_get","path":"scripts/node_atlas_get/node_atlas_get.yy",},}, {"id":{"name":"node_atlas_set","path":"scripts/node_atlas_set/node_atlas_set.yy",},}, diff --git a/scripts/globals/globals.gml b/scripts/globals/globals.gml index 14ca01488..33a80ca5c 100644 --- a/scripts/globals/globals.gml +++ b/scripts/globals/globals.gml @@ -44,9 +44,9 @@ NIGHTLY = true; LATEST_VERSION = 1_18_00_0; - VERSION = 1_18_04_0; - SAVE_VERSION = 1_18_04_0; - VERSION_STRING = MAC? "1.18.003m" : "1.18.5.010"; + VERSION = 1_18_05_0; + SAVE_VERSION = 1_18_05_0; + VERSION_STRING = MAC? "1.18.003m" : "1.18.5.011"; BUILD_NUMBER = 1_18_04_1; HOTKEYS = ds_map_create(); diff --git a/scripts/load_function/load_function.gml b/scripts/load_function/load_function.gml index e449ea4e1..c49588a8d 100644 --- a/scripts/load_function/load_function.gml +++ b/scripts/load_function/load_function.gml @@ -28,7 +28,8 @@ function TEST_PATH(path) { PROJECT = new Project(); LOAD_AT(path); - PANEL_GRAPH.setProject(PROJECT); + Render(); + closeProject(PROJECT); } function LOAD_PATH(path, readonly = false, safe_mode = false) { diff --git a/scripts/node_assert/node_assert.gml b/scripts/node_assert/node_assert.gml new file mode 100644 index 000000000..d750e6c51 --- /dev/null +++ b/scripts/node_assert/node_assert.gml @@ -0,0 +1,141 @@ +function Node_Assert(_x, _y, _group = noone) : Node(_x, _y, _group) constructor { + name = "Assert"; + setDimension(96, 32 + 24 * 1); + + draw_padding = 8; + + newInput(0, nodeValue_Text("Name", self, "")); + + newInput(1, nodeValue("Value", self, CONNECT_TYPE.input, VALUE_TYPE.any, 0)) + .setVisible(true, true); + + newInput(2, nodeValue("Target", self, CONNECT_TYPE.input, VALUE_TYPE.any, 0)) + .setVisible(true, true); + + function checkSurface(s1, s2) { + if(!is_surface(s1)) return false; + if(!is_surface(s2)) return false; + + if(surface_get_width(s1) != surface_get_width(s2)) return false; + if(surface_get_height(s1) != surface_get_height(s2)) return false; + if(surface_get_format(s1) != surface_get_format(s2)) return false; + + var b1 = buffer_from_surface(s1, false); buffer_to_start(b1); + var b2 = buffer_from_surface(s2, false); buffer_to_start(b2); + + var ss = buffer_get_size(b1); + var ii = 0; + var eq = true; + + repeat(ss) { + var r1 = buffer_read(b1, buffer_u8); + var r2 = buffer_read(b2, buffer_u8); + + if(r1 != r2) { + eq = false; + break; + } + } + + buffer_delete(b1); + buffer_delete(b2); + + return eq; + } + + static update = function() { + var name = getInputData(0); + var val = getInputData(1); + var tar = getInputData(2); + + var _typ = inputs[2].value_from != noone? inputs[2].value_from.type : VALUE_TYPE.any; + inputs[1].setType(_typ); + inputs[2].setType(_typ); + + if(!ASSERTING) return; + ASSERT_AMOUNT++; + + var _pass = false; + var _ast = { + type : -1, + text : $"Assertion {name} failed: get {val} instead of target {tar}.", + tooltip : -1, + } + + switch(_typ) { + case VALUE_TYPE.surface : + if(is_array(tar)) { + for( var i = 0, n = array_length(tar); i < n; i++ ) { + if(checkSurface(array_safe_get(val, i), tar[i])) continue; + _pass = false; + break; + } + + } else + _pass = checkSurface(val, tar); + + _ast.text = $"Assertion {name} failed: surface not match the target."; + _ast.tooltip = new tooltipSurfaceAssetion(surface_array_clone(tar), surface_array_clone(val)); + break; + + default : _pass = isEqual(val, tar); + } + + if(_pass) ASSERT_PASSED++; + else array_append(ASSERT_LOG, _ast); + + } + + static onDrawNode = function(xx, yy, _mx, _my, _s, _hover, _focus) { + var name = getInputData(0); + var bbox = drawGetBbox(xx, yy, _s); + + draw_set_text(f_sdf, fa_center, fa_center, COLORS._main_text); + draw_text_bbox(bbox, name); + } +} + +function tooltipSurfaceAssetion(expect, got) constructor { + self.expect = is_array(expect)? expect : [ expect ]; + self.got = is_array(got)? got : [ got ]; + + static drawTooltip = function() { + var ss = ui(100); + var tw = ss * 2 + ui(8); + var th = (ss + ui(4)) * array_length(expect) + ui(20) - ui(4); + + var mx = min(__mouse_tx + ui(16), __win_tw - (tw + ui(16))); + var my = min(__mouse_ty + ui(16), __win_th - (th + ui(16))); + + draw_sprite_stretched(THEME.textbox, 3, mx, my, tw + ui(16), th + ui(16)); + draw_sprite_stretched(THEME.textbox, 0, mx, my, tw + ui(16), th + ui(16)); + + var xe = mx + ui(8); + var xg = mx + ui(8) + ss + ui(8); + + draw_set_text(f_p2, fa_center, fa_top, COLORS._main_text_sub); + draw_text(xe + ss / 2, my + ui(4), "Expected"); + draw_text(xg + ss / 2, my + ui(4), "Got"); + + for( var i = 0, n = array_length(expect); i < n; i++ ) { + var _e = array_safe_get(expect, i); + var _g = array_safe_get(got, i); + + var _ew = surface_get_width_safe(_e); + var _eh = surface_get_height_safe(_e); + + var _gw = surface_get_width_safe(_g); + var _gh = surface_get_height_safe(_g); + + var yy = my + ui(8 + 20) + i * (ss + ui(4)); + + var sc = min(ss / _ew, ss / _eh); + draw_surface_ext_safe(_e, xe + ss / 2 - _ew * sc / 2, yy + ss / 2 - _eh * sc / 2, sc, sc); + draw_sprite_stretched_add(THEME.s_box_r2, 1, xe, yy, ss, ss, c_white, .15); + + var sc = min(ss / _gw, ss / _gh); + draw_surface_ext_safe(_g, xg + ss / 2 - _gw * sc / 2, yy + ss / 2 - _gh * sc / 2, sc, sc); + draw_sprite_stretched_add(THEME.s_box_r2, 1, xg, yy, ss, ss, c_white, .15); + } + } +} \ No newline at end of file diff --git a/scripts/node_assert/node_assert.yy b/scripts/node_assert/node_assert.yy new file mode 100644 index 000000000..448285f61 --- /dev/null +++ b/scripts/node_assert/node_assert.yy @@ -0,0 +1,13 @@ +{ + "$GMScript":"v1", + "%Name":"node_assert", + "isCompatibility":false, + "isDnD":false, + "name":"node_assert", + "parent":{ + "name":"misc", + "path":"folders/nodes/data/misc.yy", + }, + "resourceType":"GMScript", + "resourceVersion":"2.0", +} \ No newline at end of file diff --git a/scripts/node_assert/node_outline.yy b/scripts/node_assert/node_outline.yy new file mode 100644 index 000000000..86468bc09 --- /dev/null +++ b/scripts/node_assert/node_outline.yy @@ -0,0 +1,12 @@ +{ + "isDnD": false, + "isCompatibility": false, + "parent": { + "name": "process", + "path": "folders/nodes/data/process.yy", + }, + "resourceVersion": "1.0", + "name": "node_outline", + "tags": [], + "resourceType": "GMScript", +} \ No newline at end of file diff --git a/scripts/node_checker/node_checker.gml b/scripts/node_checker/node_checker.gml index 58ed2663a..5d00272fa 100644 --- a/scripts/node_checker/node_checker.gml +++ b/scripts/node_checker/node_checker.gml @@ -49,10 +49,10 @@ function Node_Checker(_x, _y, _group = noone) : Node_Processor(_x, _y, _group) c return _hov; } - static step = function() { #region + static step = function() { inputs[1].mappableStep(); inputs[2].mappableStep(); - } #endregion + } static processData = function(_outSurf, _data, _output_index, _array_index) { var _dim = _data[0]; diff --git a/scripts/node_data/node_data.gml b/scripts/node_data/node_data.gml index da5d733fb..d79f04493 100644 --- a/scripts/node_data/node_data.gml +++ b/scripts/node_data/node_data.gml @@ -1188,9 +1188,17 @@ function Node(_x, _y, _group = noone) : __Node_Base(_x, _y) constructor { static getPreviousNodes = function() { var prev = []; + var prMp = {}; + var _n; - if(attributes.show_update_trigger && updatedInTrigger.value_from) - array_push(prev, updatedInTrigger.value_from.node); + if(attributes.show_update_trigger && updatedInTrigger.value_from) { + _n = updatedInTrigger.value_from.node; + + if(!struct_has(prMp, _n.node_id)) { + array_push(prev, _n); + prMp[$ _n.node_id] = 1; + } + } for( var i = 0, n = array_length(inputs); i < n; i++ ) { var _in = inputs[i]; @@ -1198,15 +1206,30 @@ function Node(_x, _y, _group = noone) : __Node_Base(_x, _y) constructor { if(_in.value_from != noone) { if(in_VFX && !_in.value_from.node.in_VFX) { array_push(in_VFX.prev_nodes, _in.value_from.node); - array_push(prev, in_VFX); + + if(!struct_has(prMp, in_VFX.node_id)) { + array_push(prev, in_VFX); + prMp[$ in_VFX.node_id] = 1; + } + continue; } - array_push_unique(prev, _in.value_from.node); + _n = _in.value_from.node; + if(!struct_has(prMp, _n.node_id)) { + array_push(prev, _n); + prMp[$ _n.node_id] = 1; + } + } - if(_in.value_from_loop != noone) - array_push_unique(prev, _in.value_from_loop); + if(_in.value_from_loop != noone) { + _n = _in.value_from_loop; + if(!struct_has(prMp, _n.node_id)) { + array_push(prev, _n); + prMp[$ _n.node_id] = 1; + } + } } onGetPreviousNodes(prev); diff --git a/scripts/node_functions/node_functions.gml b/scripts/node_functions/node_functions.gml index 4ead00597..93ff59539 100644 --- a/scripts/node_functions/node_functions.gml +++ b/scripts/node_functions/node_functions.gml @@ -188,6 +188,7 @@ } function refreshNodeMap() { + if(!ds_exists(PROJECT.nodeNameMap, ds_type_map)) return; ds_map_clear(PROJECT.nodeNameMap); for (var i = 0, n = array_length(PROJECT.allNodes); i < n; i++) { diff --git a/scripts/node_registry/node_registry.gml b/scripts/node_registry/node_registry.gml index b794e79cf..4646a96a7 100644 --- a/scripts/node_registry/node_registry.gml +++ b/scripts/node_registry/node_registry.gml @@ -1068,7 +1068,7 @@ function __initNodes() { addNodeObject(animation, "Audio Volume", s_node_audio_volume, "Node_Audio_Loudness", [1, Node_Audio_Loudness],, "Calculate volume of an audio bit array.").setVersion(11540); #endregion - #region node + #region misc var node = ds_list_create(); addNodeCatagory("Misc", node); ds_list_add(node, "Control"); @@ -1122,7 +1122,8 @@ function __initNodes() { addNodeObject(node, "Execute Shell", s_node_shell_excecute, "Node_Shell", [1, Node_Shell], ["terminal", "execute", "run"], "Execute shell script.").setVersion(11530); addNodeObject(node, "Monitor Capture", s_node_monitor_capture, "Node_Monitor_Capture", [1, Node_Monitor_Capture]).notTest(); addNodeObject(node, "GUI In", s_node_gui_in, "Node_Application_In", [1, Node_Application_In]).notTest(); - addNodeObject(node, "GUI Out", s_node_gui_out, "Node_Application_Out", [1, Node_Application_Out]).notTest(); + addNodeObject(node, "GUI Out", s_node_gui_out, "Node_Application_Out", [1, Node_Application_Out]).notTest(); + addNodeObject(node, "Assert", s_node_shell_excecute, "Node_Assert", [1, Node_Assert]); // addNodeObject(node, "DLL", s_node_gui_out, "Node_DLL", [1, Node_DLL]).setVersion(11750); #endregion diff --git a/scripts/node_value/node_value.gml b/scripts/node_value/node_value.gml index ffe3894bd..557aa85a5 100644 --- a/scripts/node_value/node_value.gml +++ b/scripts/node_value/node_value.gml @@ -1625,7 +1625,6 @@ function NodeValue(_name, _node, _connect, _type, _value, _tooltip = "") constru } static isConnectable = function(_valueFrom, checkRecur = true, _log = false) { - if(LOADING || APPENDING) return 1; if(_valueFrom == -1 || _valueFrom == undefined || _valueFrom == noone) { if(_log) noti_warning($"LOAD: Cannot set node connection from {_valueFrom} to {name} of node {node.name}.",, node); @@ -1662,6 +1661,8 @@ function NodeValue(_name, _node, _connect, _type, _value, _tooltip = "") constru return -7; } + if(LOADING || APPENDING) return 1; + if(!accept_array && isArray(_valueFrom.getValue())) { noti_warning($"Connection error: {name} does not support array input.",, node); return -8; diff --git a/scripts/panel_menu/panel_menu.gml b/scripts/panel_menu/panel_menu.gml index 1aceebddd..2b1841ff6 100644 --- a/scripts/panel_menu/panel_menu.gml +++ b/scripts/panel_menu/panel_menu.gml @@ -253,10 +253,13 @@ function Panel_Menu() : PanelContent() constructor { array_push(menus, [ __txt("Dev"), [ MENU_ITEMS.console_panel, menuItem(__txtx("panel_debug_overlay", "Debug overlay"), function() /*=>*/ { show_debug_overlay(true); }), - menuItem(__txtx("panel_menu_tester", "Tester"), function() /*=>*/ { var dia = dialogPanelCall(new Panel_Test()); }), menuItem(__txtx("panel_menu_profile_render", "Render Profiler"), function() /*=>*/ { var dia = dialogPanelCall(new Panel_Profile_Render()); }), -1, + menuItem(__txtx("panel_menu_tester", "Save frozen"), function() /*=>*/ { PROJECT.freeze = true; SAVE(); }), + menuItem(__txtx("panel_menu_tester", "Tester"), function() /*=>*/ { var dia = dialogPanelCall(new Panel_Test()); }), + -1, + menuItem(__txtx("panel_menu_test_load_all", "Load all current collections"), function() /*=>*/ { __test_load_current_collections(); }), menuItem(__txtx("panel_menu_test_update_all", "Update all current collections"), function() /*=>*/ { __test_update_current_collections(); }), menuItem(__txtx("panel_menu_test_add_meta", "Add metadata to current collections"), function() /*=>*/ { __test_metadata_current_collections(); }), diff --git a/scripts/panel_test/panel_test.gml b/scripts/panel_test/panel_test.gml index ef0c27951..7c6a43061 100644 --- a/scripts/panel_test/panel_test.gml +++ b/scripts/panel_test/panel_test.gml @@ -1,40 +1,204 @@ +globalvar ASSERTING, ASSERT_LOG, ASSERT_AMOUNT, ASSERT_PASSED; +ASSERTING = false; +ASSERT_LOG = []; +ASSERT_AMOUNT = 0; +ASSERT_PASSED = 0; + function Panel_Test() : PanelContent() constructor { - w = ui(480); - h = ui(160); - title = "Tester"; - auto_pin = true; + w = ui(960); + h = ui(480); - test_dir = "D:/Project/MakhamDev/LTS-PixelComposer/TEST"; - tb_test_dir = new textBox(TEXTBOX_INPUT.text, function(txt) { test_dir = txt; }); - tb_index = new textBox(TEXTBOX_INPUT.number, function(txt) { start_index = txt; }); - tb_amount = new textBox(TEXTBOX_INPUT.number, function(txt) { test_amount = txt; }); + title = "Tester"; + auto_pin = true; + padding = ui(4); + content_w = ui(320); + + test_dir = ""; + tb_test_dir = new textBox(TEXTBOX_INPUT.text, function(txt) /*=>*/ { setTestDir(txt); }); + tb_index = new textBox(TEXTBOX_INPUT.number, function(txt) /*=>*/ { start_index = txt; }); + tb_amount = new textBox(TEXTBOX_INPUT.number, function(txt) /*=>*/ { test_amount = txt; }); testing = false; test_files = []; start_index = 0; + end_index = 0; test_amount = 100; test_index = start_index; + test_step = 0; + test_result = []; - test_button_surface = surface_create(1, 1); + test_result_total = { + projects: 0, + project_pass: 0, + + assertion: 0, + assertion_pass: 0, + } + + wait_step = 5; + waiting = 0; + + load_param = new __loadParams(true); + + function onResize() { sc_content.resize(content_w, h - padding * 2 - ui(8 * 2) - ui(24)); } + + sc_content = new scrollPane(content_w, h - padding * 2 - ui(8 * 2) - ui(24), function(_y, _m) { + draw_clear_alpha(COLORS.panel_bg_clear_inner, 1); + var _h = 0; + var yy = _y; + var ww = sc_content.surface_w; + var wh = ui(20); + + for( var i = 0, n = array_length(test_files); i < n; i++ ) { + var _f = test_files[i]; + var _d = test_files[i][1]; + var _n = filename_name_only(_f[0]); + + var cc = COLORS._main_text_sub; + if(start_index <= i && i < start_index + test_amount) + cc = COLORS._main_text; + + var _hover = sc_content.hover && point_in_rectangle(_m[0], _m[1], 0, yy, ww, yy + wh - 1); + if(_hover) { + draw_sprite_stretched_ext(THEME.s_box_r2_clr, 0, 0, yy, ww, wh, c_white, 1); + if(mouse_press(mb_left, pFOCUS)) + LOAD_AT(_f[0]); + } + + if(testing && i == test_index) { + cc = COLORS._main_accent; + draw_sprite_stretched_ext(THEME.s_box_r2, 0, 0, yy, ww * test_step / 4, wh, cc, 0.1); + + sc_content.scroll_y_to = -_h + sc_content.surface_h / 2; + + } else { + var _res = array_safe_get(test_result, i); + if(is_array(_res)) { + var _a_amo = _res[0]; + var _a_pas = _res[1]; + var c = _a_pas == _a_amo? COLORS._main_value_positive : COLORS._main_value_negative; + cc = merge_color(c, c_white, 0.5); + + if(_a_amo == 0) draw_sprite_stretched_ext(THEME.s_box_r2, 0, 0, yy, ww, wh, c, 0.1); + else draw_sprite_stretched_ext(THEME.s_box_r2, 0, 0, yy, ww * _a_pas / _a_amo, wh, c, 0.1); + + draw_set_text(f_p3, fa_right, fa_center, cc); + draw_text_add(ww - ui(8), yy + wh / 2, $"{_a_pas} / {_a_amo}"); + + } + } + + draw_set_text(f_p3, fa_left, fa_center, cc); + draw_text_add(ui(8), yy + wh / 2, _n); + + draw_set_text(f_p3, fa_left, fa_center, COLORS._main_text_sub, 0.5); + draw_text_add(ui(8 + 144), yy + wh / 2, _d); + draw_set_alpha(1); + + _h += wh; + yy += wh; + } + + _h += wh; + + return _h; + }); + + sc_log = new scrollPane(content_w, h - padding * 2 - ui(8 * 2), function(_y, _m) { + draw_clear_alpha(COLORS.panel_bg_clear_inner, 1); + var _h = 0; + var yy = _y; + var ww = sc_log.surface_w - ui(32); + + for( var i = 0, n = array_length(ASSERT_LOG); i < n; i++ ) { + var _f = ASSERT_LOG[i]; + + if(_f.type == 0) { + if(i >= n - 1) continue; + if(ASSERT_LOG[i + 1].type >= 0) continue; + + if(i) { + _h += ui(4); + yy += ui(4); + } + } + + draw_set_font(f_p3); + var wh = string_height_ext(_f.text, -1, ww); + var cc = COLORS._main_text_sub; + var tx = ui(8); + var hv = sc_log.hover && point_in_rectangle(_m[0], _m[1], 0, yy, sc_log.surface_w, yy + wh - 1); + + if(hv) draw_sprite_stretched_ext(THEME.s_box_r2_clr, 0, 0, yy, sc_log.surface_w, wh, c_white, 1); + + switch(_f.type) { + case -1 : + cc = merge_color(COLORS._main_value_negative, c_white, 0.5); + tx = ui(16); + + if(hv && _f.tooltip != -1) TOOLTIP = _f.tooltip; + break; + + case 0 : + cc = COLORS._main_text_sub; + tx = ui(8); + + if(hv && mouse_press(mb_left, pFOCUS)) + LOAD_AT(_f.file); + break; + + case 1 : + cc = merge_color(COLORS._main_value_positive, c_white, 0.5); + tx = ui(16); + break; + + } + + draw_set_text(f_p3, fa_left, fa_top, cc); + draw_text_ext_add(tx, yy, _f.text, -1, ww); + + _h += wh + ui(0); + yy += wh + ui(0); + } + + _h += ui(16); + + return _h; + }); + + function setTestDir(dir) { + test_dir = dir; + test_files = []; + + scanDir(test_dir); + } function scanDir(dir) { - var f = file_find_first(dir + "/*", fa_none); + if(!directory_exists(dir)) return; + + var f = file_find_first($"{dir}/*", fa_none); + var v = filename_name_only(dir); + while(f != "") { - var path = dir + "/" + f; - if(filename_ext_raw(path) == "pxc") - array_push(test_files, path); + var path = $"{dir}/{f}"; f = file_find_next(); + + if(filename_ext_raw(path) == "pxc") + array_push(test_files, [ path, v ]); } + file_find_close(); - var f = file_find_first(dir + "/*", fa_directory); + var f = file_find_first($"{dir}/*", fa_directory); var _dir = []; while(f != "") { - var path = dir + "/" + f; - array_push(_dir, path); + var path = $"{dir}/{f}"; f = file_find_next(); + + array_push(_dir, path); } + file_find_close(); for( var i = 0, n = array_length(_dir); i < n; i++ ) @@ -44,80 +208,194 @@ function Panel_Test() : PanelContent() constructor { function startTesting() { if(testing) return; - testing = true; - test_index = start_index; + end_index = min(start_index + test_amount, array_length(test_files)); + testing = true; + test_index = start_index; + test_result = array_create(array_length(test_files)); - test_files = []; - scanDir(test_dir); + ASSERT_LOG = []; + TEST_ERROR = true; + test_result_total.projects = 0; + test_result_total.project_pass = 0; + + test_result_total.assertion = 0; + test_result_total.assertion_pass = 0; + __start_time = get_timer(); + } + + function doTesting() { + var _cur = test_files[test_index][0]; - for( var i = start_index, n = min(start_index + test_amount, array_length(test_files)); i < n; i++ ) { - run_in(1 + (i - start_index) * 3, function(i) { - try { - show_debug_message($"TESTING {i}/{array_length(test_files)}: {test_files[i]}"); - TEST_PATH(test_files[i]); - test_index = i; - show_debug_message($" > Test complete : {(get_timer() - __start_time) / 1_000_000} s"); - } catch(e) { - show_debug_message($" > Test failed"); - exception_print(e); - } - }, [i]); + try { + switch(test_step) { + case 0 : + array_append(ASSERT_LOG, { + type: 0, + text: $"Testing {filename_name_only(_cur)}", + file: _cur, + }); + + test_result_total.projects++; + test_step++; + break; + + case 1 : + LOAD_AT(_cur, load_param); + test_step++; + waiting = 0; + break; + + case 2 : + if(waiting++ > wait_step) test_step++; + break; + + case 3 : + if(!instance_exists(project_loader)) { + ASSERTING = true; + Render(); + ASSERTING = false; + test_step++; + } + break; + + case 4 : + closeProject(PROJECT); + test_result[test_index] = [ ASSERT_AMOUNT, ASSERT_PASSED ]; + + test_result_total.assertion += ASSERT_AMOUNT; + test_result_total.assertion_pass += ASSERT_PASSED; + + if(ASSERT_AMOUNT == ASSERT_PASSED) test_result_total.project_pass++; + + ASSERT_AMOUNT = 0; + ASSERT_PASSED = 0; + test_step++; + break; + } + + } catch(e) { + array_append(ASSERT_LOG, { + type: -1, + text: $"Test failed: {e}", + }); } + + if(test_step < 5) return; + + test_step = 0; + test_index++; + + if(test_index < end_index) return; + + testing = false; + TEST_ERROR = false; + var ts = test_result_total; + + var _time = (get_timer() - __start_time) / 1000; + var _summ = $"Testing completed in {_time}ms. "; + _summ += $"\n{ts.project_pass}/{ts.projects} projects passed [{ts.project_pass / ts.projects * 100}%]."; + _summ += $"\n{ts.assertion_pass}/{ts.assertion} assertions passed [{ts.assertion == 0? "-" : ts.assertion_pass / ts.assertion * 100}%]."; + + array_append(ASSERT_LOG, { + type: 1, + text: _summ, + }); } function drawContent(panel) { - draw_clear_alpha(COLORS.panel_bg_clear, 0); + draw_clear_alpha(COLORS.panel_bg_clear, 1); - var yy = 8; + // Lists + + var _pd = padding; + var ndx = _pd; + var ndy = _pd + ui(24); + var ndw = content_w + ui(16); + var ndh = h - _pd * 2 - ui(24); + + draw_sprite_stretched(THEME.ui_panel_bg, 1, ndx, ndy, ndw, ndh); + + draw_set_text(f_p2, fa_left, fa_top, COLORS._main_text_sub); + draw_text_add(ndx + ui(8), ui(4), $"{test_amount} / {array_length(test_files)} Files"); + + sc_content.setFocusHover(pFOCUS, pHOVER); + sc_content.draw(ndx + ui(8), ndy + ui(8), mx - ndx - ui(8), my - ndy - ui(8)); + + // Data + + var yy = ui(8); + var lx = ndx + ndw + ui(8); + var lw = ui(100); + var dw = w - lx - lw - _pd; var hh = TEXTBOX_HEIGHT; tb_test_dir.setFocusHover(pFOCUS, pHOVER); tb_index.setFocusHover(pFOCUS, pHOVER); tb_amount.setFocusHover(pFOCUS, pHOVER); - draw_set_text(f_p0, fa_left, fa_center, COLORS._main_text); - draw_text(8, yy + hh / 2, "Directory"); + draw_set_text(f_p2, fa_left, fa_center, COLORS._main_text_sub); + draw_text_add(lx + ui(8), yy + hh / 2, "Directory"); - tb_test_dir.draw(128, yy, w - 8 - 128, hh, test_dir, [ mx, my ]); - yy += hh + 8; + tb_test_dir.draw(lx + lw, yy, dw, hh, test_dir, [ mx, my ]); + yy += hh + ui(8); - draw_set_text(f_p0, fa_left, fa_center, COLORS._main_text); - draw_text(8, yy + hh / 2, "Start"); + draw_set_text(f_p2, fa_left, fa_center, COLORS._main_text_sub); + draw_text_add(lx + ui(8), yy + hh / 2, "Start"); - tb_index.draw(128, yy, w - 8 - 128, hh, start_index, [ mx, my ]); - yy += hh + 8; + tb_index.draw(lx + lw, yy, dw, hh, start_index, [ mx, my ]); + yy += hh + ui(8); - draw_set_text(f_p0, fa_left, fa_center, COLORS._main_text); - draw_text(8, yy + hh / 2, "Amount"); + draw_set_text(f_p2, fa_left, fa_center, COLORS._main_text_sub); + draw_text_add(lx + ui(8), yy + hh / 2, "Amount"); + + tb_amount.draw(lx + lw, yy, dw, hh, test_amount, [ mx, my ]); + yy += hh + ui(8); + + // Log + + var ndx = lx; + var ndy = yy; + var ndw = w - _pd - lx; + var ndh = h - _pd - ndy - hh - ui(8); + + draw_sprite_stretched(THEME.ui_panel_bg, 1, ndx, ndy, ndw, ndh); + + var log_w = ndw - ui(16); + var log_h = ndh - ui(16); + + if(sc_log.w != log_w || sc_log.h != log_h) sc_log.resize(log_w, log_h); + + sc_log.setFocusHover(pFOCUS, pHOVER); + sc_log.draw(ndx + ui(8), ndy + ui(8), mx - ndx - ui(8), my - ndy - ui(8)); + + // Button + + var bw = w - _pd - lx; + var bh = hh; + var bx = lx; + var by = h - _pd - bh; - tb_amount.draw(128, yy, w - 8 - 128, hh, test_amount, [ mx, my ]); - yy += hh + 8; - if(testing) { - var _w = (w - 16) * test_index / array_length(test_files); - draw_sprite_stretched(THEME.progress_bar, 0, 8, yy, w - 16, hh); - draw_sprite_stretched(THEME.progress_bar, 1, 8, yy, _w, hh); + var _a = end_index - start_index; + var _w = bw * (test_index - start_index) / _a; + draw_sprite_stretched(THEME.progress_bar, 0, bx, by, bw, bh); + draw_sprite_stretched(THEME.progress_bar, 1, bx, by, _w, bh); - draw_set_text(f_p0, fa_center, fa_center, COLORS._main_text); - draw_text(w / 2, yy + hh / 2, $"Testing {test_index + 1}/{array_length(test_files)}"); + draw_set_text(f_p2, fa_center, fa_center, COLORS._main_text_sub); + draw_text_add(bx + bw / 2, by + bh / 2, $"Testing {test_index - start_index}/{_a}"); - test_button_surface = surface_verify(test_button_surface, w - 16, hh); - surface_set_target(test_button_surface); - DRAW_CLEAR - draw_set_text(f_p0, fa_center, fa_center, COLORS._main_text_on_accent); - draw_text((w - 16) / 2, hh / 2, $"Testing {test_index + 1}/{array_length(test_files)}"); - surface_reset_target(); - draw_surface_part(test_button_surface, 0, 0, _w, hh, 8, yy); + doTesting(); - if(test_index >= array_length(test_files) - 1) - testing = false; } else { - if(buttonInstant(THEME.button_def, 8, yy, w - 16, hh, [ mx, my ], pFOCUS, pHOVER) == 2) + if(buttonInstant(THEME.button_def, bx, by, bw, bh, [ mx, my ], pFOCUS, pHOVER) == 2) startTesting(); - draw_set_text(f_p0, fa_center, fa_center, COLORS._main_text); - draw_text(w / 2, yy + hh / 2, "Start test"); + + draw_set_text(f_p2, fa_center, fa_center, COLORS._main_text); + draw_text_add(bx + bw / 2, by + bh / 2, "Start test"); } } + + setTestDir("D:/Project/MakhamDev/LTS-PixelComposer/TEST/Tester"); } \ No newline at end of file diff --git a/scripts/project_data/project_data.gml b/scripts/project_data/project_data.gml index 10222abef..f84d4248f 100644 --- a/scripts/project_data/project_data.gml +++ b/scripts/project_data/project_data.gml @@ -14,12 +14,13 @@ function Project() constructor { active = true; + seed = irandom_range(100000, 999999); meta = __getdefaultMetaData(); path = ""; thumbnail = ""; version = SAVE_VERSION; is_nightly = NIGHTLY; - seed = irandom_range(100000, 999999); + freeze = false; modified = false; readonly = false; @@ -230,6 +231,7 @@ var _map = {}; _map.version = SAVE_VERSION; _map.is_nightly = NIGHTLY; + _map.freeze = freeze; var _anim_map = {}; _anim_map.frames_total = animator.frames_total; @@ -294,6 +296,7 @@ if(struct_has(_map, "attributes")) struct_override(attributes, _map.attributes); if(struct_has(_map, "metadata")) meta.deserialize(_map.metadata); if(struct_has(_map, "composer")) composer = _map.composer; + if(struct_has(_map, "freeze")) freeze = _map.freeze; if(struct_has(_map, "graph_display_parameter")) struct_override(graph_display_parameter, _map.graph_display_parameter); diff --git a/scripts/render_data/render_data.gml b/scripts/render_data/render_data.gml index 5828f5304..0edd6d032 100644 --- a/scripts/render_data/render_data.gml +++ b/scripts/render_data/render_data.gml @@ -61,7 +61,7 @@ function NodeListSort(_nodeList) { function __sortNode(_arr, _node) { if(_node.topoSorted) return; - + var _parents = []; var _prev = _node.getPreviousNodes(); diff --git a/scripts/save_function/save_function.gml b/scripts/save_function/save_function.gml index 15061c975..036785d9f 100644 --- a/scripts/save_function/save_function.gml +++ b/scripts/save_function/save_function.gml @@ -15,11 +15,12 @@ function NEW() { function SERIALIZE_PROJECT(project = PROJECT) { var _map = project.serialize(); - return PREFERENCES.save_file_minify? json_stringify_minify(_map) : json_stringify(_map, true); } function SET_PATH(project, path) { + if(ASSERTING) return; + if(path == "") { project.readonly = false; @@ -43,7 +44,7 @@ function SAVE_ALL() { function SAVE(project = PROJECT) { if(DEMO) return false; - if(project.path == "" || project.readonly || path_is_backup(project.path)) + if(project.path == "" || project.freeze || project.readonly || path_is_backup(project.path)) return SAVE_AS(project); return SAVE_AT(project, project.path); @@ -78,10 +79,9 @@ function SAVE_AT(project = PROJECT, path = "", log = "save at ") { if(PREFERENCES.save_backup) { for(var i = PREFERENCES.save_backup - 1; i >= 0; i--) { var _p = path; - if(i) _p = $"{path}{string(i)}" + if(i) _p = $"{path}{i}" - if(file_exists(_p)) - file_rename(_p, $"{path}{string(i + 1)}"); + if(file_exists(_p)) file_rename(_p, $"{path}{i + 1}"); } } diff --git a/scripts/surface_functions/surface_functions.gml b/scripts/surface_functions/surface_functions.gml index e5d0aa9fd..a4263ec65 100644 --- a/scripts/surface_functions/surface_functions.gml +++ b/scripts/surface_functions/surface_functions.gml @@ -499,13 +499,8 @@ function surface_reset_target_override() { __surface_reset_target(); winwin_draw } function surface_array_clone(arr) { - if(!is_array(arr)) { - if(is_surface(arr)) - return surface_clone(arr); - else - return arr; - } - + if(!is_array(arr)) return is_surface(arr)? surface_clone(arr) : arr; + var _arr = []; for( var i = 0, n = array_length(arr); i < n; i++ ) diff --git a/scripts/var_comparison/var_comparison.gml b/scripts/var_comparison/var_comparison.gml index b633b56aa..19a1ef3e8 100644 --- a/scripts/var_comparison/var_comparison.gml +++ b/scripts/var_comparison/var_comparison.gml @@ -1,4 +1,4 @@ -function isEqual(val1, val2, struct_expand = false, _depth = 0) { #region +function isEqual(val1, val2, struct_expand = false, _depth = 0) { INLINE if(_depth > 8) return false; @@ -10,9 +10,9 @@ function isEqual(val1, val2, struct_expand = false, _depth = 0) { #region return struct_equal(val1, val2, _depth); return val1 == val2; -} #endregion +} -function array_member_equal(arr1, arr2, _depth = 0) { #region +function array_member_equal(arr1, arr2, _depth = 0) { INLINE if(array_length(arr1) != array_length(arr2)) return false; @@ -21,9 +21,9 @@ function array_member_equal(arr1, arr2, _depth = 0) { #region if(!isEqual(arr1[i], arr2[i],, _depth + 1)) return false; return true; -} #endregion +} -function struct_equal(str1, str2, _depth = 0) { #region +function struct_equal(str1, str2, _depth = 0) { INLINE var key1 = variable_struct_get_names(str1); @@ -35,4 +35,4 @@ function struct_equal(str1, str2, _depth = 0) { #region if(!isEqual(str1[$ key1[i]], str2[$ key1[i]],, _depth + 1)) return false; return true; -} #endregion \ No newline at end of file +} \ No newline at end of file