@xuda.io/runtime-bundle 1.0.1248 → 1.0.1249

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -9889,278 +9889,1203 @@ const get_params_obj_new = async function (SESSION_ID, prog_id, nodeP, dsSession
9889
9889
  return { params_res, params_raw };
9890
9890
  };
9891
9891
 
9892
- func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $root_container, nodeP, $container, paramsP, parent_infoP, jobNoP, keyP, parent_nodeP, xu_func, $elm, val, is_init, refreshed_ds) {
9893
- if (is_skeleton) return;
9892
+ // func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $root_container, nodeP, $container, paramsP, parent_infoP, jobNoP, keyP, parent_nodeP, xu_func, $elm, val, is_init, refreshed_ds) {
9893
+ // if (is_skeleton) return;
9894
+
9895
+ // // console.log(nodeP.id, xu_func, val);
9896
+ // var _ds = SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP];
9897
+ // const tag_fx = {
9898
+ // [`xu-panel`]: {
9899
+ // program: async function ($elm, val) {
9900
+ // var ret = {};
9901
+ // var _session = SESSION_OBJ[SESSION_ID];
9902
+ // var _ds = _session.DS_GLB[paramsP.dsSessionP];
9903
+ // const init_program = async function () {
9904
+ // async function render_panel() {
9905
+ // const prog_id = val.value?.prog || val.value;
9906
+ // const params_obj = await get_params_obj_new(SESSION_ID, prog_id, nodeP, paramsP.dsSessionP);
9907
+ // let ret_panel = await func.UI.screen.init(SESSION_ID, prog_id, paramsP.screenId, _ds, $elm, null, _ds.currentRecordId, null, true, params_obj.params_res, 'initXu_panel', undefined, prog_id !== _ds.prog_id ? null : refreshed_ds, params_obj.params_raw);
9908
+ // ret = { $new_div: ret_panel };
9909
+ // if ($container.data().xuData) {
9910
+ // $container.data().xuData.xuPanelProps = $elm.data().xuAttributes;
9911
+ // $container.data().xuData.xuPanelData = ret_panel.data();
9912
+ // }
9913
+ // return ret;
9914
+ // }
9894
9915
 
9895
- // console.log(nodeP.id, xu_func, val);
9896
- var _ds = SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP];
9897
- const tag_fx = {
9898
- [`xu-panel`]: {
9899
- program: async function ($elm, val) {
9900
- var ret = {};
9901
- var _session = SESSION_OBJ[SESSION_ID];
9902
- var _ds = _session.DS_GLB[paramsP.dsSessionP];
9903
- const init_program = async function () {
9904
- async function render_panel() {
9905
- const prog_id = val.value?.prog || val.value;
9906
- const params_obj = await get_params_obj_new(SESSION_ID, prog_id, nodeP, paramsP.dsSessionP);
9907
- let ret_panel = await func.UI.screen.init(SESSION_ID, prog_id, paramsP.screenId, _ds, $elm, null, _ds.currentRecordId, null, true, params_obj.params_res, 'initXu_panel', undefined, prog_id !== _ds.prog_id ? null : refreshed_ds, params_obj.params_raw);
9908
- ret = { $new_div: ret_panel };
9909
- if ($container.data().xuData) {
9910
- $container.data().xuData.xuPanelProps = $elm.data().xuAttributes;
9911
- $container.data().xuData.xuPanelData = ret_panel.data();
9912
- }
9913
- return ret;
9914
- }
9916
+ // if (!val.value) {
9917
+ // val.value = '_empty_panel_program';
9918
+ // }
9915
9919
 
9916
- if (!val.value) {
9917
- val.value = '_empty_panel_program';
9918
- }
9920
+ // ret = await render_panel();
9919
9921
 
9920
- ret = await render_panel();
9922
+ // return ret;
9923
+ // };
9924
+ // const alter_program = async function () {
9925
+ // var _session = SESSION_OBJ[SESSION_ID];
9926
+ // var _ds = _session.DS_GLB[paramsP.dsSessionP];
9927
+
9928
+ // /////////////////
9929
+ // async function render_panel() {
9930
+ // // // if (!cache_str) {
9931
+ // // // await update_container(screen_ready_function);
9932
+ // // // }
9933
+ // // // if (cache_str && !CACHE_PROG_UI[cache_str]) {
9934
+ // // // await update_container(screen_ready_function);
9935
+ // // // save_cache();
9936
+ // // // }
9937
+ // // // if (callback) callback($div);
9938
+ // // // $container.data().xuData.node.children =
9939
+ // // // $div.data().xuData.node.children;
9940
+ // // // //swiper-wrapper
9941
+ // // // var restore_slides_elements = async function () {
9942
+ // // // if ($tmp_div.children().length) {
9943
+ // // // $tmp_div
9944
+ // // // .find(".swiper-wrapper")
9945
+ // // // .empty()
9946
+ // // // .append($new_div.children());
9947
+ // // // $new_div.append($tmp_div.children());
9948
+ // // // }
9949
+ // // // };
9950
+ // // // // console.log($tmp_div);
9951
+ // // // await restore_slides_elements();
9952
+ // // // // CHANGE_PANEL_BUSY = false;
9953
+ // // // func.events.delete_job(SESSION_ID, jobNo);
9954
+ // // };
9955
+ // const program = val.value?.prog || val.value;
9956
+ // var $wrapper = $('<div>');
9957
+ // var $div = await func.UI.screen.create_container(SESSION_ID, $root_container, nodeP, $container, paramsP, parent_infoP, jobNoP, keyP, parent_nodeP, nodeP.attributes, null, null, null, $wrapper, '');
9958
+ // const params_obj = await get_params_obj_new(SESSION_ID, program, nodeP, paramsP.dsSessionP);
9959
+ // let ret_init = await func.UI.screen.init(SESSION_ID, program, paramsP.screenId, _ds, $div, null, _ds.currentRecordId, jobNoP, true, params_obj.params_res, 'alterXu_panel', undefined, undefined, params_obj.params_raw);
9960
+ // ret = {
9961
+ // $new_div: ret_init,
9962
+ // abort: true,
9963
+ // };
9964
+ // await func.UI.screen.panel_post_render_handler(SESSION_ID, $elm, $new_div, nodeP, $div.clone(true), jobNoP);
9965
+
9966
+ // return ret;
9967
+ // }
9968
+ // if (!val.value) {
9969
+ // return { abort: true };
9970
+ // }
9971
+ // await render_panel();
9972
+ // return ret;
9973
+ // };
9921
9974
 
9922
- return ret;
9923
- };
9924
- const alter_program = async function () {
9925
- var _session = SESSION_OBJ[SESSION_ID];
9926
- var _ds = _session.DS_GLB[paramsP.dsSessionP];
9975
+ // if (is_init) {
9976
+ // let ret = await init_program();
9977
+ // return ret;
9978
+ // }
9979
+ // return alter_program();
9980
+ // },
9927
9981
 
9928
- /////////////////
9929
- async function render_panel() {
9930
- // // if (!cache_str) {
9931
- // // await update_container(screen_ready_function);
9932
- // // }
9933
- // // if (cache_str && !CACHE_PROG_UI[cache_str]) {
9934
- // // await update_container(screen_ready_function);
9935
- // // save_cache();
9936
- // // }
9937
- // // if (callback) callback($div);
9938
- // // $container.data().xuData.node.children =
9939
- // // $div.data().xuData.node.children;
9940
- // // //swiper-wrapper
9941
- // // var restore_slides_elements = async function () {
9942
- // // if ($tmp_div.children().length) {
9943
- // // $tmp_div
9944
- // // .find(".swiper-wrapper")
9945
- // // .empty()
9946
- // // .append($new_div.children());
9947
- // // $new_div.append($tmp_div.children());
9948
- // // }
9949
- // // };
9950
- // // // console.log($tmp_div);
9951
- // // await restore_slides_elements();
9952
- // // // CHANGE_PANEL_BUSY = false;
9953
- // // func.events.delete_job(SESSION_ID, jobNo);
9954
- // };
9955
- const program = val.value?.prog || val.value;
9956
- var $wrapper = $('<div>');
9957
- var $div = await func.UI.screen.create_container(SESSION_ID, $root_container, nodeP, $container, paramsP, parent_infoP, jobNoP, keyP, parent_nodeP, nodeP.attributes, null, null, null, $wrapper, '');
9958
- const params_obj = await get_params_obj_new(SESSION_ID, program, nodeP, paramsP.dsSessionP);
9959
- let ret_init = await func.UI.screen.init(SESSION_ID, program, paramsP.screenId, _ds, $div, null, _ds.currentRecordId, jobNoP, true, params_obj.params_res, 'alterXu_panel', undefined, undefined, params_obj.params_raw);
9960
- ret = {
9961
- $new_div: ret_init,
9962
- abort: true,
9963
- };
9964
- await func.UI.screen.panel_post_render_handler(SESSION_ID, $elm, $new_div, nodeP, $div.clone(true), jobNoP);
9982
+ // 'xu-render': async function ($elm, val) {
9983
+ // let ret = await common_fx['xu-render']($elm, val, true);
9984
+ // return ret;
9985
+ // },
9986
+ // 'xu-ref': async function ($elm, val) {
9987
+ // let ret = await common_fx['xu-ref']($container, val, $container.data().xuData.xuPanelData.xuData.paramsP.dsSessionP);
9988
+ // return ret;
9989
+ // },
9990
+ // },
9991
+ // [`xu-teleport`]: {
9992
+ // to: async function ($elm, val) {
9993
+ // if (!glb.new_xu_render) {
9994
+ // if (val.value) {
9995
+ // // parent_infoP.is_xu_teleport;
9996
+ // if ($elm?.parent()?.data()?.xuData?.length) {
9997
+ // $elm.parent().data('xuTeleportData', []);
9998
+ // for (const [key, node] of Object.entries(nodeP.children)) {
9999
+ // const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $(val.value), node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
10000
+
10001
+ // $elm.parent().data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
10002
+ // $teleport_elm.attr('xu-teleport-parent-id', $elm.parent().attr('xu-ui-id'));
10003
+ // }
10004
+ // $elm.remove();
10005
+ // } else {
10006
+ // $elm.data('xuTeleportData', []).attr('hidden', true);
10007
+ // for (const [key, node] of Object.entries(nodeP.children)) {
10008
+ // const $to_container = $(val.value);
10009
+ // if (!$to_container?.length) {
10010
+ // return console.error(`container ${val.value} for xuTeleportData not found`);
10011
+ // }
10012
+ // const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $to_container, node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
10013
+
10014
+ // $elm.data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
10015
+ // $teleport_elm.attr('xu-teleport-parent-id', $elm.attr('xu-ui-id'));
10016
+ // }
10017
+ // }
10018
+ // }
10019
+ // return { abort: true };
10020
+ // }
9965
10021
 
9966
- return ret;
9967
- }
9968
- if (!val.value) {
9969
- return { abort: true };
9970
- }
9971
- await render_panel();
9972
- return ret;
9973
- };
10022
+ // if (val.value) {
10023
+ // // // parent_infoP.is_xu_teleport;
10024
+ // // if ($elm?.parent()?.data()?.xuData?.length) {
10025
+ // // $elm.parent().data('xuTeleportData', []);
10026
+ // // for (const [key, node] of Object.entries(nodeP.children)) {
10027
+ // // const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $(val.value), node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
10028
+ // // $elm.parent().data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
10029
+ // // $teleport_elm.attr('xu-teleport-parent-id', $elm.parent().attr('xu-ui-id'));
10030
+ // // }
10031
+ // // $elm.remove();
10032
+ // // } else {
10033
+ // // $elm.data('xuTeleportData', []).attr('hidden', true);
10034
+ // // for (const [key, node] of Object.entries(nodeP.children)) {
10035
+ // // const $to_container = $(val.value);
10036
+ // // if (!$to_container?.length) {
10037
+ // // return console.error(`container ${val.value} for xuTeleportData not found`);
10038
+ // // }
10039
+ // // const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $to_container, node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
10040
+ // // $elm.data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
10041
+ // // $teleport_elm.attr('xu-teleport-parent-id', $elm.attr('xu-ui-id'));
10042
+ // // }
10043
+ // // }
10044
+ // }
10045
+ // return {};
10046
+ // },
10047
+ // 'xu-render': async function ($elm, val) {
10048
+ // let ret = await common_fx['xu-render']($elm, val, true);
10049
+ // return ret;
10050
+ // },
10051
+ // 'xu-show': async function ($elm, val) {
10052
+ // let ret = await common_fx['xu-show']($elm, val, true);
10053
+ // return ret;
10054
+ // },
10055
+ // },
10056
+ // };
9974
10057
 
9975
- if (is_init) {
9976
- let ret = await init_program();
9977
- return ret;
9978
- }
9979
- return alter_program();
9980
- },
10058
+ // const load_cdn = async function (resource) {
10059
+ // // console.log("loading cdn", resource);
10060
+ // if (!_.isObject(resource) && _.isString(resource)) {
10061
+ // resource = { src: resource, type: 'js' };
10062
+ // }
10063
+ // if (!_.isObject(resource)) {
10064
+ // throw new Error('cdn resource in wrong format');
10065
+ // }
10066
+ // return new Promise(async (resolve) => {
10067
+ // try {
10068
+ // switch (resource.type) {
10069
+ // case 'js':
10070
+ // await func.utils.load_js_on_demand(resource.src);
10071
+ // break;
10072
+ // case 'css':
10073
+ // await func.utils.load_js_on_demand(resource.src);
10074
+ // break;
10075
+ // case 'module':
10076
+ // func.utils.load_js_on_demand(resource.src, 'module');
10077
+ // break;
10078
+
10079
+ // default:
10080
+ // await func.utils.load_js_on_demand(resource.src);
10081
+ // break;
10082
+ // }
10083
+ // resolve();
10084
+ // } catch (error) {
10085
+ // func.utils.debug_report(SESSION_ID, 'xu-cdn', 'Fail to load: ' + resource, 'W');
10086
+ // resolve();
10087
+ // }
9981
10088
 
9982
- 'xu-render': async function ($elm, val) {
9983
- let ret = await common_fx['xu-render']($elm, val, true);
9984
- return ret;
9985
- },
9986
- 'xu-ref': async function ($elm, val) {
9987
- let ret = await common_fx['xu-ref']($container, val, $container.data().xuData.xuPanelData.xuData.paramsP.dsSessionP);
9988
- return ret;
9989
- },
9990
- },
9991
- [`xu-teleport`]: {
9992
- to: async function ($elm, val) {
9993
- if (!glb.new_xu_render) {
9994
- if (val.value) {
9995
- // parent_infoP.is_xu_teleport;
9996
- if ($elm?.parent()?.data()?.xuData?.length) {
9997
- $elm.parent().data('xuTeleportData', []);
9998
- for (const [key, node] of Object.entries(nodeP.children)) {
9999
- const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $(val.value), node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
10000
-
10001
- $elm.parent().data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
10002
- $teleport_elm.attr('xu-teleport-parent-id', $elm.parent().attr('xu-ui-id'));
10003
- }
10004
- $elm.remove();
10005
- } else {
10006
- $elm.data('xuTeleportData', []).attr('hidden', true);
10007
- for (const [key, node] of Object.entries(nodeP.children)) {
10008
- const $to_container = $(val.value);
10009
- if (!$to_container?.length) {
10010
- return console.error(`container ${val.value} for xuTeleportData not found`);
10011
- }
10012
- const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $to_container, node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
10089
+ // // if (resource.type === "js" || !resource.type) {
10090
+ // // await func.utils.load_js_on_demand(resource.src);
10091
+ // // return resolve();
10092
+ // // }
10093
+ // // if (resource.type === "css") {
10094
+ // // func.utils.load_css_on_demand(resource.src);
10095
+ // // return resolve();
10096
+ // // }
10097
+ // // if (resource.type === "module") {
10098
+ // // func.utils.load_js_on_demand(resource.src, "module");
10099
+ // // return resolve();
10100
+ // // }
10101
+ // // func.utils.debug_report(
10102
+ // // SESSION_ID,
10103
+ // // "xu-cdn",
10104
+ // // "Fail to load: " + resource,
10105
+ // // "W"
10106
+ // // );
10107
+ // // return resolve();
10108
+ // });
10109
+ // };
10013
10110
 
10014
- $elm.data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
10015
- $teleport_elm.attr('xu-teleport-parent-id', $elm.attr('xu-ui-id'));
10016
- }
10017
- }
10018
- }
10019
- return { abort: true };
10020
- }
10111
+ // const common_fx = {
10112
+ // 'xu-attrs': async function ($elm, val) {
10113
+ // if (!val.value) return {};
10114
+ // if (!_.isObject(val.value)) throw 'xu-attrs value us not an object';
10115
+ // for (const [attr_key, attr_val] of Object.entries(val.value)) {
10116
+ // nodeP.attributes[attr_key] = attr_val;
10117
+ // }
10021
10118
 
10022
- if (val.value) {
10023
- // // parent_infoP.is_xu_teleport;
10024
- // if ($elm?.parent()?.data()?.xuData?.length) {
10025
- // $elm.parent().data('xuTeleportData', []);
10026
- // for (const [key, node] of Object.entries(nodeP.children)) {
10027
- // const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $(val.value), node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
10028
- // $elm.parent().data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
10029
- // $teleport_elm.attr('xu-teleport-parent-id', $elm.parent().attr('xu-ui-id'));
10030
- // }
10031
- // $elm.remove();
10032
- // } else {
10033
- // $elm.data('xuTeleportData', []).attr('hidden', true);
10034
- // for (const [key, node] of Object.entries(nodeP.children)) {
10035
- // const $to_container = $(val.value);
10036
- // if (!$to_container?.length) {
10037
- // return console.error(`container ${val.value} for xuTeleportData not found`);
10038
- // }
10039
- // const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $to_container, node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
10040
- // $elm.data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
10041
- // $teleport_elm.attr('xu-teleport-parent-id', $elm.attr('xu-ui-id'));
10042
- // }
10043
- // }
10044
- }
10045
- return {};
10046
- },
10047
- 'xu-render': async function ($elm, val) {
10048
- let ret = await common_fx['xu-render']($elm, val, true);
10049
- return ret;
10050
- },
10051
- 'xu-show': async function ($elm, val) {
10052
- let ret = await common_fx['xu-show']($elm, val, true);
10053
- return ret;
10054
- },
10055
- },
10056
- };
10119
+ // return {};
10120
+ // },
10121
+ // 'xu-ref': async function ($elm, val, dsSession) {
10122
+ // if (!val.value) return {};
10123
+
10124
+ // func.UI.update_xu_ref(SESSION_ID, dsSession || paramsP.dsSessionP, val.value, $elm);
10125
+
10126
+ // // Select the node that will be observed for mutations
10127
+ // const targetNode = $elm[0];
10128
+
10129
+ // if (!targetNode) return;
10130
+
10131
+ // // Options for the observer (which mutations to observe)
10132
+ // const config = { attributes: true, childList: true, subtree: true };
10133
+
10134
+ // // Callback function to execute when mutations are observed
10135
+ // const callback = (mutationList, observer) => {
10136
+ // func.UI.screen.refresh_xu_attributes(SESSION_ID, [val.value]);
10137
+ // };
10138
+
10139
+ // // Create an observer instance linked to the callback function
10140
+ // const observer = new MutationObserver(callback);
10141
+
10142
+ // // Start observing the target node for configured mutations
10143
+ // observer.observe(targetNode, config);
10144
+
10145
+ // // Later, you can stop observing
10146
+ // // observer.disconnect();
10147
+
10148
+ // return {};
10149
+ // },
10150
+ // 'xu-bind': async function ($elm, val) {
10151
+ // if (is_skeleton) return;
10152
+
10153
+ // let val_is_reference_field = false;
10154
+
10155
+ // let _prog_id = $elm.data().xuData.paramsP.prog_id;
10156
+ // let _dsP = $elm.data().xuData.paramsP.dsSessionP;
10157
+ // const view_ret = await func.utils.VIEWS_OBJ.get(SESSION_ID, _prog_id);
10158
+ // if (!view_ret) return {};
10159
+
10160
+ // let is_dynamic_field = false;
10161
+ // let field_prop;
10162
+ // let bind_field_id;
10163
+
10164
+ // const input_field_type = $elm.attr('type');
10165
+
10166
+ // const get_bind_field = async function (field_id) {
10167
+ // if (['_FOR_VAL', '_FOR_KEY'].includes(field_id)) {
10168
+ // is_dynamic_field = true;
10169
+ // field_prop = _ds.dynamic_fields[field_id];
10170
+ // } else {
10171
+ // field_prop = func.common.find_item_by_key(view_ret.progFields, 'field_id', field_id);
10172
+ // if (!field_prop) {
10173
+ // /// find the field everywhere in the chain Aug 30 2024
10174
+ // const ret_get_value = await func.datasource.get_value(SESSION_ID, field_id, _dsP);
10175
+
10176
+ // if (ret_get_value.found) {
10177
+ // _dsP = ret_get_value.dsSessionP;
10178
+ // let _ds = SESSION_OBJ[SESSION_ID].DS_GLB[_dsP];
10179
+ // _prog_id = _ds.prog_id;
10180
+ // const view_ret = await func.utils.VIEWS_OBJ.get(SESSION_ID, _prog_id);
10181
+ // if (!view_ret) return {};
10182
+ // field_prop = func.common.find_item_by_key(view_ret.progFields, 'field_id', field_id);
10183
+ // }
10184
+ // if (!field_prop) {
10185
+ // throw `field ${field_id} not found in the program scope`;
10186
+ // }
10187
+ // }
10188
+ // }
10189
+ // return field_id;
10190
+ // };
10191
+
10192
+ // try {
10193
+ // bind_field_id = await get_bind_field(val.value.split('.')[0]);
10194
+ // val_is_reference_field = true;
10195
+ // } catch (err) {
10196
+ // console.error(err?.message || err);
10197
+ // return {};
10198
+ // }
10199
+
10200
+ // const field_changed = async function (e) {
10201
+ // var _ds = SESSION_OBJ[SESSION_ID].DS_GLB[_dsP];
10202
+
10203
+ // // update array for checkbox that not in xu-for
10204
+ // if (field_prop.props.fieldType === 'array' && input_field_type === 'checkbox' && val_is_reference_field) {
10205
+ // let arr_value_before_cast = _.clone((await func.datasource.get_value(SESSION_ID, bind_field_id, _dsP, _ds.currentRecordId)).ret.value);
10206
+ // let value_from_getter = bind.getter($elm[0]);
10207
+ // let value;
10208
+ // if (arr_value_before_cast.includes(value_from_getter)) {
10209
+ // value = arr_value_before_cast.filter((item) => !_.isEqual(item, value_from_getter));
10210
+ // } else {
10211
+ // arr_value_before_cast.push(value_from_getter);
10212
+ // value = arr_value_before_cast;
10213
+ // }
10214
+
10215
+ // let datasource_changes = {
10216
+ // [_dsP]: {
10217
+ // [_ds.currentRecordId]: {
10218
+ // [bind_field_id]: value,
10219
+ // },
10220
+ // },
10221
+ // };
10222
+
10223
+ // return await func.datasource.update(SESSION_ID, datasource_changes);
10224
+ // }
10225
+
10226
+ // // update array for radio that not in xu-for
10227
+ // if (field_prop.props.fieldType === 'array' && input_field_type === 'radio' && val_is_reference_field) {
10228
+ // let value_from_getter = bind.getter($elm[0]);
10229
+
10230
+ // let datasource_changes = {
10231
+ // [_dsP]: {
10232
+ // [_ds.currentRecordId]: {
10233
+ // [bind_field_id]: [value_from_getter],
10234
+ // },
10235
+ // },
10236
+ // };
10237
+
10238
+ // return await func.datasource.update(SESSION_ID, datasource_changes);
10239
+ // }
10240
+
10241
+ // var value = await func.common.get_cast_val(SESSION_ID, 'xu-bind', 'value', field_prop.props.fieldType, bind.getter($elm[0]));
10242
+
10243
+ // if (field_prop.props.fieldType === 'object') {
10244
+ // value = await func.common.get_cast_val(SESSION_ID, 'xu-bind', 'value', input_field_type, bind.getter($elm[0]));
10245
+ // }
10246
+
10247
+ // if (!_ds.currentRecordId) return;
10248
+
10249
+ // let datasource_changes = {
10250
+ // [_dsP]: {
10251
+ // [_ds.currentRecordId]: {
10252
+ // [bind_field_id]: value,
10253
+ // },
10254
+ // },
10255
+ // };
10256
+
10257
+ // await func.datasource.update(SESSION_ID, datasource_changes);
10258
+ // const iterate_info = $elm?.data()?.xuData?.iterate_info;
10259
+ // const reference_source_obj = iterate_info?.reference_source_obj;
10260
+ // if (reference_source_obj) {
10261
+ // if (reference_source_obj.ret.type === 'array') {
10262
+ // if (iterate_info.iterator_val === bind_field_id) {
10263
+ // const arr_idx = Number($elm?.data()?.xuData?.iterate_info._key);
10264
+
10265
+ // const dataset_arr = await func.datasource.get_value(SESSION_ID, reference_source_obj.fieldIdP, _dsP, reference_source_obj.currentRecordId);
10266
+ // let new_arr = _.cloneDeep(dataset_arr.ret.value);
10267
+
10268
+ // if (field_prop.props.fieldType === 'object' && val_is_reference_field) {
10269
+ // let obj_item = new_arr[arr_idx];
10270
+
10271
+ // let e_exp = val.value.replace(bind_field_id, 'obj_item');
10272
+
10273
+ // let new_val = eval(e_exp + (input_field_type === 'string' ? `="${value}"` : `=${value}`));
10274
+
10275
+ // new_arr[arr_idx] = obj_item;
10276
+ // } else {
10277
+ // new_arr[arr_idx] = value;
10278
+ // }
10279
+ // // datasource_changes[_dsP][_ds.currentRecordId][reference_source_obj.fieldIdP] = new_arr;
10280
+
10281
+ // let datasource_changes = {
10282
+ // [_dsP]: {
10283
+ // [_ds.currentRecordId]: {
10284
+ // [reference_source_obj.fieldIdP]: new_arr,
10285
+ // },
10286
+ // },
10287
+ // };
10288
+
10289
+ // await func.datasource.update(SESSION_ID, datasource_changes, null, true);
10290
+ // }
10291
+ // }
10292
+ // }
10293
+
10294
+ // await func.datasource.update_changes_for_out_parameter(SESSION_ID, _dsP, _ds.parentDataSourceNo);
10295
+ // };
10296
+
10297
+ // const bind = new UI_FRAMEWORK_PLUGIN.bind();
10298
+
10299
+ // bind.listener($elm[0], field_changed);
10300
+
10301
+ // const set_value = function () {
10302
+ // let _ds = SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP];
10303
+ // if (!_ds.currentRecordId) return;
10304
+ // let value;
10305
+ // try {
10306
+ // if (val_is_reference_field) {
10307
+ // if (is_dynamic_field) {
10308
+ // value = _ds.dynamic_fields[bind_field_id].value;
10309
+ // } else {
10310
+ // const row_idx = func.common.find_ROWID_idx(_ds, _ds.currentRecordId);
10311
+ // value = _ds.data_feed.rows?.[row_idx]?.[bind_field_id];
10312
+ // }
10313
+ // if (field_prop.props.fieldType === 'array' && $elm.attr('type') === 'checkbox' && $elm.attr('value')) {
10314
+ // if (value.includes($elm.attr('value'))) {
10315
+ // value = true;
10316
+ // } else {
10317
+ // value = false;
10318
+ // }
10319
+ // } else if (field_prop.props.fieldType === 'array' && $elm.attr('type') === 'radio' && $elm.attr('value')) {
10320
+ // if (value.includes($elm.attr('value'))) {
10321
+ // value = $elm.attr('value');
10322
+ // } else {
10323
+ // value = false;
10324
+ // }
10325
+ // } else if (field_prop.props.fieldType === 'object' && val.value.split('.').length > 1) {
10326
+ // let str = val.value.replace(bind_field_id, '(' + JSON.stringify(value) + ')');
10327
+ // value = eval(str);
10328
+ // }
10329
+ // } else {
10330
+ // value = val.value;
10331
+ // }
10332
+ // if (typeof value === 'undefined') return;
10333
+ // bind.setter($elm[0], value);
10334
+ // } catch (err) {
10335
+ // console.error(err);
10336
+ // }
10337
+ // };
10338
+ // /// init value from ds
10339
+ // $('body').on('xu-bind-refresh.' + _ds.dsSession.toString(), () => {
10340
+ // set_value();
10341
+ // });
10342
+
10343
+ // set_value();
10344
+ // return {};
10345
+ // },
10346
+ // 'xu-render': async function ($elm, val, from_panel) {
10347
+ // const old_render = async function () {
10348
+ // var value = await func.common.get_cast_val(SESSION_ID, 'common fx', 'xu-render', 'bool', val.value);
10349
+ // const init_render = function () {
10350
+ // if (!value) {
10351
+ // var cloned_$div = $elm.clone(true);
10352
+
10353
+ // let $xurender = $('<xurender>').attr('xu-ui-id', $elm.attr('xu-ui-id')).attr('hidden', true).appendTo($container); //.hide();
10354
+ // let original_data_obj = {
10355
+ // $container: cloned_$div,
10356
+ // nodeP: _.cloneDeep(nodeP),
10357
+ // parent_infoP,
10358
+ // paramsP,
10359
+ // keyP,
10360
+ // parent_nodeP,
10361
+ // $root_container,
10362
+ // };
10363
+ // $xurender.data('xuData', cloned_$div.data().xuData);
10364
+ // $xurender.data().xuData.original_data_obj = original_data_obj;
10365
+ // $xurender.data().xuData.xurender_node = cloned_$div;
10366
+ // $xurender.data().xuAttributes = nodeP.attributes || {};
10367
+ // // $xurender.hide();
10368
+
10369
+ // $elm.remove();
10370
+ // return { abort: true };
10371
+ // }
10372
+ // return {};
10373
+ // };
10374
+
10375
+ // const post_render = async function () {
10376
+ // if (value) {
10377
+ // try {
10378
+ // // abort if already rended
10379
+ // if ($elm[0].tagName !== 'XURENDER' && $elm?.length) {
10380
+ // return func.events.delete_job(SESSION_ID, jobNoP);
10381
+ // }
10382
+
10383
+ // let original_data_obj = $elm.data().xuData.original_data_obj;
10384
+
10385
+ // if (!original_data_obj) {
10386
+ // func.events.delete_job(SESSION_ID, jobNoP);
10387
+ // return { delete_job: jobNoP };
10388
+ // }
10389
+
10390
+ // const new_$div = await func.UI.screen.render_ui_tree(
10391
+ // SESSION_ID,
10392
+ // $elm, //original_data_obj.$container,
10393
+ // _.cloneDeep(original_data_obj.nodeP),
10394
+ // original_data_obj.parent_infoP,
10395
+ // original_data_obj.paramsP,
10396
+ // jobNoP,
10397
+ // null,
10398
+ // original_data_obj.keyP,
10399
+ // null,
10400
+ // original_data_obj.parent_nodeP,
10401
+ // null,
10402
+ // original_data_obj.$root_container,
10403
+ // );
10404
+
10405
+ // new_$div.data().xuData.original_data_obj = original_data_obj;
10406
+ // new_$div.data().xuData.xurender_node = $elm.clone(true);
10407
+ // new_$div.data().xuAttributes = $elm.data().xuAttributes || {};
10408
+
10409
+ // const replace = async function () {
10410
+ // $elm.replaceWith(new_$div);
10411
+ // if (from_panel) {
10412
+ // const xuPanelWrapper = _.clone(new_$div.data().xuPanelWrapper);
10413
+ // $elm.parent().data().xuPanelWrapper = xuPanelWrapper;
10414
+ // $elm.replaceWith(new_$div.children());
10415
+ // }
10416
+
10417
+ // if (val.fields_arr) {
10418
+ // return await func.UI.screen.refresh_xu_attributes(SESSION_ID, val.fields_arr, val.jobNoP, new_$div);
10419
+ // }
10420
+ // func.events.delete_job(SESSION_ID, jobNoP);
10421
+ // };
10422
+ // // if ($elm && func.UI.utils.find_in_element_data('xuData', $(SESSION_OBJ[SESSION_ID].root_element), 'xu_id', $elm.data().xuData.xu_id).length) {
10423
+ // if ($elm && $(`[xu-ui-id="${$elm.attr('xu-ui-id')}"]`).length) {
10424
+ // if (new_$div.data().xuData.paramsP) {
10425
+ // return await replace();
10426
+ // }
10427
+
10428
+ // func.events.delete_job(SESSION_ID, jobNoP);
10429
+ // }
10430
+ // } catch (error) {
10431
+ // func.events.delete_job(SESSION_ID, jobNoP);
10432
+ // }
10433
+ // return;
10434
+ // }
10435
+ // // if (!value) {
10436
+ // if ($elm.prop('tagName') === 'XURENDER') {
10437
+ // func.events.delete_job(SESSION_ID, jobNoP);
10438
+ // return;
10439
+ // }
10440
+
10441
+ // let tmp_$div = $('<div>');
10442
+
10443
+ // let $xurender = $('<xurender>').attr('xu-ui-id', $elm.attr('xu-ui-id')).appendTo(tmp_$div); //.hide();
10444
+ // // was true before
10445
+ // if ($elm.data().xuData.xurender_node) {
10446
+ // $xurender.data({
10447
+ // xuAttributes: $elm.data().xuData.xurender_node.data().xuAttributes || {},
10448
+ // xuData: $elm.data().xuData.xurender_node.data().xuData || {},
10449
+ // });
10450
+ // } else {
10451
+ // // default new state
10452
+
10453
+ // $xurender.data({
10454
+ // xuAttributes: $elm.data().xuAttributes || {},
10455
+ // xuData: $elm.data().xuData || {},
10456
+ // });
10457
+ // const original_data_obj = {
10458
+ // nodeP: _.cloneDeep($elm.data().xuData.node_org),
10459
+ // paramsP: $elm.data().xuData.paramsP,
10460
+ // $container: $elm.clone(true),
10461
+ // parent_infoP: parent_infoP,
10462
+ // };
10463
+
10464
+ // $xurender.data().xuData.original_data_obj = original_data_obj;
10465
+ // }
10466
+
10467
+ // //remove xu-teleport trace
10468
+ // $.each($elm.find('xu-teleport'), (key, val) => {
10469
+ // const xuTeleportData = $(val).data().xuTeleportData || [];
10470
+ // for (const teleported_elm_id of xuTeleportData) {
10471
+ // $(`[xu-ui-id="${teleported_elm_id}"]`).remove();
10472
+ // }
10473
+ // });
10474
+
10475
+ // $elm.replaceWith(tmp_$div.children());
10476
+ // func.events.delete_job(SESSION_ID, jobNoP);
10477
+ // // }
10478
+ // };
10479
+ // if (is_init) {
10480
+ // return init_render();
10481
+ // }
10482
+ // return await post_render();
10483
+ // };
10484
+
10485
+ // const new_render = async function () {
10486
+ // var value = await func.common.get_cast_val(SESSION_ID, 'common fx', 'xu-render', 'bool', val.value);
10487
+ // const has_xu_render_attribute = true;
10488
+ // const has_xu_exp_render_attribute = $elm.data()?.xuData?.attr_exp_info?.['xu-render'] ? true : false;
10489
+ // const init_render = async function () {
10490
+ // nodeP.xu_render_made = value;
10491
+ // if (!value) {
10492
+ // if (has_xu_exp_render_attribute) {
10493
+ // return { has_xu_exp_render_attribute, has_xu_render_attribute, xu_render_background_processing: true };
10494
+ // }
10495
+ // return { has_xu_render_attribute, abort: true };
10496
+ // }
10497
+ // return { has_xu_exp_render_attribute, has_xu_render_attribute };
10498
+ // };
10499
+
10500
+ // const post_render = async function () {
10501
+ // // always come from refresh
10502
+ // let nodeP = $container.data().xuData.node.children[keyP];
10503
+ // nodeP.xu_render_made = value;
10504
+ // if (value) {
10505
+ // try {
10506
+ // const xu_render_cache_id = await get_xu_render_cache_str(SESSION_ID, paramsP.dsSessionP, Object.keys($elm.data()?.xuData?.attr_exp_info?.['xu-render']?.fields || {}));
10507
+ // const xu_ui_id = $elm.attr('xu-ui-id');
10508
+ // let new_$div = UI_WORKER_OBJ?.xu_render_cache?.[xu_ui_id + xu_render_cache_id]?.$div.clone(true);
10509
+ // let found_parent_vars = false;
10510
+ // if (new_$div) {
10511
+ // // validate if $div contains fields from parent ds
10512
+ // const parent_data = get_parent_ds_fields(SESSION_ID, paramsP.dsSessionP);
10513
+ // const parent_fields = Object.keys(parent_data);
10514
+
10515
+ // $.each(new_$div.find('*'), (key, val) => {
10516
+ // const _xuAttributes = $(val)?.data()?.xuAttributes;
10517
+ // if (found_parent_vars || !_xuAttributes) return;
10518
+ // for (const [attr_key, attr_val] of Object.entries(_xuAttributes)) {
10519
+ // if (found_parent_vars) break;
10520
+ // for (const [key, val] of Object.entries(parent_fields)) {
10521
+ // if (attr_val.includes('@' + key)) {
10522
+ // found_parent_vars = true;
10523
+ // break;
10524
+ // }
10525
+ // }
10526
+ // }
10527
+ // });
10528
+ // }
10529
+
10530
+ // if (!new_$div || found_parent_vars) {
10531
+ // UI_WORKER_OBJ.xu_render_cache[xu_ui_id + xu_render_cache_id] = { paramsP };
10532
+ // nodeP.xu_render_xu_ui_id = xu_ui_id;
10533
+ // nodeP.xu_render_cache_id = xu_render_cache_id;
10534
+ // new_$div = await func.UI.screen.render_ui_tree(SESSION_ID, $container, nodeP, parent_infoP, paramsP, jobNoP, null, keyP, null, parent_nodeP, null, $root_container);
10535
+ // const _$div = new_$div.clone(true);
10536
+ // UI_WORKER_OBJ.xu_render_cache[xu_ui_id + xu_render_cache_id].$div = _$div;
10537
+ // UI_WORKER_OBJ.xu_render_cache[xu_ui_id + xu_render_cache_id].data = _$div.data();
10538
+ // }
10539
+ // // append order handling
10540
+
10541
+ // if (!$container.children().length) {
10542
+ // new_$div.appendTo($container);
10543
+ // } else {
10544
+ // // iterate the container node
10545
+ // let $last_elm_found = [];
10546
+ // $.each($container.data().xuData.node.children, (item_key, item_val) => {
10547
+ // // const $elm = $(`[xu-node-id="${item_val.id}"]`);
10548
+ // const $elm = func.UI.utils.find_in_element_data('xuData', $(SESSION_OBJ[SESSION_ID].root_element), 'nodeid', item_val.id);
10549
+ // if ($elm.length) {
10550
+ // $last_elm_found = $elm;
10551
+ // }
10552
+ // if (keyP == item_key) {
10553
+ // if ($last_elm_found.length) {
10554
+ // new_$div.after($last_elm_found);
10555
+ // } else {
10556
+ // $container.prepend(new_$div);
10557
+ // }
10558
+ // }
10559
+ // });
10560
+ // }
10561
+ // } catch (error) {
10562
+ // func.events.delete_job(SESSION_ID, jobNoP);
10563
+ // }
10564
+ // return;
10565
+ // }
10566
+
10567
+ // /////////// !value ///////////
10568
+
10569
+ // const xu_ui_id = $elm.attr('xu-ui-id');
10570
+
10571
+ // const cache_str = await get_xu_render_cache_str(SESSION_ID, paramsP.dsSessionP, Object.keys($elm.data()?.xuData?.attr_exp_info?.['xu-render']?.fields || {}));
10572
+ // const _$div = $elm.clone(true);
10573
+ // UI_WORKER_OBJ.xu_render_cache[xu_ui_id + cache_str] = { $div: _$div, data: _$div.data(), paramsP };
10574
+ // $elm.remove();
10575
+ // func.events.delete_job(SESSION_ID, jobNoP);
10576
+ // };
10577
+ // if (is_init) {
10578
+ // return await init_render();
10579
+ // }
10580
+ // return await post_render();
10581
+ // };
10582
+
10583
+ // if (glb.new_xu_render) {
10584
+ // return new_render();
10585
+ // }
10586
+ // return old_render();
10587
+ // },
10588
+ // 'xu-show': async function ($elm, val) {
10589
+ // var value = await func.common.get_cast_val(SESSION_ID, 'common fx', 'xu-show', 'bool', val.value);
10590
+ // if (value) {
10591
+ // $elm.show();
10592
+ // }
10593
+ // if (!value) {
10594
+ // $elm.hide();
10595
+ // }
10596
+ // return {};
10597
+ // },
10598
+ // 'xu-content': async function ($elm, val) {
10599
+ // try {
10600
+ // $elm.html(val.value);
10601
+ // } catch (error) {
10602
+ // console.warn(e);
10603
+ // }
10604
+ // return;
10605
+ // },
10606
+ // 'xu-text': async function ($elm, val) {
10607
+ // try {
10608
+ // $elm.text(val.value);
10609
+ // } catch (error) {
10610
+ // console.warn(e);
10611
+ // }
10612
+ // return;
10613
+ // },
10614
+ // 'xu-html': async function ($elm, val) {
10615
+ // try {
10616
+ // $elm.html(val.value);
10617
+ // } catch (error) {
10618
+ // console.warn(e);
10619
+ // }
10620
+ // return;
10621
+ // },
10622
+ // 'xu-for': async function ($elm, data) {
10623
+ // // exit if call from rendered xu-for item to prevent infante loop (parent_infoP?.iterate_info indicate call from rendered item)
10624
+ // if (parent_infoP?.iterate_info) return {};
10625
+ // if (!data.value) return {};
10626
+ // try {
10627
+ // // data.value (xu-for) can store actual values such as an array, a CSV, or a field_id that references a specific field within the dataset, initialized with values for the iteration.
10628
+ // let arr = data.value;
10629
+
10630
+ // // find reference source field
10631
+ // let reference_source_obj;
10632
+
10633
+ // const _progFields = await func.datasource.get_progFields(SESSION_ID, paramsP.dsSessionP);
10634
+
10635
+ // let view_field_obj = func.common.find_item_by_key(_progFields, 'field_id', data.value);
10636
+ // // detect if data.value (xu-for) is reference field_id by checking if exist in the dataset
10637
+ // if (view_field_obj) {
10638
+ // // xu-for is reference field_id
10639
+ // reference_source_obj = await func.datasource.get_value(SESSION_ID, data.value, paramsP.dsSessionP);
10640
+ // arr = reference_source_obj?.ret?.value;
10641
+ // } else {
10642
+ // // xu-for is actual data
10643
+ // if (typeof data.value === 'string') {
10644
+ // arr = eval(data.value.replaceAll('\\', ''));
10645
+ // }
10646
+ // if (typeof arr === 'number') {
10647
+ // arr = Array.from(Array(arr).keys());
10648
+ // }
10649
+ // }
10650
+
10651
+ // const custom_iterator_key = $elm.data().xuData.iterator_key;
10652
+ // const custom_iterator_val = $elm.data().xuData.iterator_val;
10653
+
10654
+ // let iterator_key = custom_iterator_key;
10655
+ // let iterator_val = custom_iterator_val;
10656
+ // let is_key_dynamic_field, is_val_dynamic_field;
10657
+
10658
+ // // custom FOR_VAL name or namespaced default name
10659
+ // if (!custom_iterator_key) {
10660
+ // is_key_dynamic_field = true;
10661
+
10662
+ // iterator_key = '_FOR_KEY';
10663
+ // }
10664
+
10665
+ // if (!custom_iterator_val) {
10666
+ // is_val_dynamic_field = true;
10667
+
10668
+ // iterator_val = '_FOR_VAL';
10669
+ // }
10670
+
10671
+ // var i = 0;
10672
+ // for await (let [_key, _val] of Object.entries(arr)) {
10673
+ // if (_.isArray(arr)) {
10674
+ // _key = Number(_key);
10675
+ // }
10676
+
10677
+ // const set_value = async function (is_dynamic_field, currentRecordId, field_id, value) {
10678
+ // if (is_dynamic_field) {
10679
+ // func.datasource.add_dynamic_field_to_ds(SESSION_ID, paramsP.dsSessionP, field_id, value);
10680
+ // } else {
10681
+ // const _progFields = await func.datasource.get_progFields(SESSION_ID, paramsP.dsSessionP);
10682
+
10683
+ // let view_field_obj = func.common.find_item_by_key(_progFields, 'field_id', field_id);
10684
+ // if (view_field_obj) {
10685
+ // let _ds = SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP];
10686
+ // try {
10687
+ // const row_idx = func.common.find_ROWID_idx(_ds, currentRecordId);
10688
+ // _ds.data_feed.rows[row_idx][field_id] = value;
10689
+ // } catch (err) {
10690
+ // console.error(err);
10691
+ // }
10692
+ // } else {
10693
+ // console.error('field not exist in dataset for xu-for method');
10694
+ // }
10695
+ // }
10696
+ // };
10697
+
10698
+ // var currentRecordId = SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP].currentRecordId.toString();
10699
+
10700
+ // await set_value(is_key_dynamic_field, currentRecordId, iterator_key, _key);
10701
+ // await set_value(is_val_dynamic_field, currentRecordId, iterator_val, _val);
10702
+
10703
+ // var iterate_info = {
10704
+ // _val,
10705
+ // _key,
10706
+ // iterator_key,
10707
+ // iterator_val,
10708
+ // is_key_dynamic_field,
10709
+ // is_val_dynamic_field,
10710
+ // reference_source_obj,
10711
+ // };
10712
+ // // let _parent_info = _.cloneDeep(parent_infoP) || {};
10713
+ // let _parent_info = klona.klona(parent_infoP) || {};
10714
+ // _parent_info.iterate_info = iterate_info;
10715
+
10716
+ // const $divP = await func.UI.screen.render_ui_tree(
10717
+ // SESSION_ID,
10718
+ // $container,
10719
+ // nodeP,
10720
+ // _parent_info, //parent_infoP ? _.cloneDeep(_parent_info) : null,
10721
+ // paramsP,
10722
+ // jobNoP,
10723
+ // null,
10724
+ // i,
10725
+ // null,
10726
+ // nodeP,
10727
+ // null,
10728
+ // $root_container,
10729
+ // );
10730
+
10731
+ // $.each($divP.children(), function (key, val) {
10732
+ // if ($(val)?.data()?.xuData) {
10733
+ // $(val).data().xuData.iterate_info = iterate_info;
10734
+ // }
10735
+ // });
10736
+
10737
+ // i++;
10738
+ // }
10739
+ // $elm.remove();
10740
+ // return { abort: true };
10741
+ // } catch (e) {
10742
+ // console.error(' Iterator Arr parse error');
10743
+ // return { abort: true };
10744
+ // }
10745
+ // },
10746
+ // 'xu-for-key': async function ($elm, val) {
10747
+ // $elm.data().xuData.iterator_key = val.value;
10748
+ // return {};
10749
+ // },
10750
+ // 'xu-for-val': async function ($elm, val) {
10751
+ // $elm.data().xuData.iterator_val = val.value;
10752
+ // return {};
10753
+ // },
10754
+ // 'xu-class': async function ($elm, val) {
10755
+ // try {
10756
+ // const classes_string = val.value;
10757
+ // // let obj = _.isString(classes_string) ? JSON.parse(classes_string) : _.defaults(classes_string, {});
10758
+
10759
+ // const classes_obj = _.isString(classes_string) ? JSON.parse(classes_string) : _.defaults(classes_string, {});
10760
+ // for await (const [cla, cond] of Object.entries(classes_obj)) {
10761
+ // let res = await func.expression.get(
10762
+ // SESSION_ID,
10763
+ // cond,
10764
+ // paramsP.dsSessionP,
10765
+ // 'UI Attr EXP',
10766
+ // $elm.data().xuData.currentRecordId, // SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP].currentRecordId
10767
+ // null,
10768
+ // null,
10769
+ // null,
10770
+ // null,
10771
+ // null,
10772
+ // $elm.data().xuData.iterate_info,
10773
+ // );
10774
+
10775
+ // if (res.result) {
10776
+ // $elm.addClass(cla);
10777
+ // } else {
10778
+ // $elm.removeClass(cla);
10779
+ // }
10780
+
10781
+ // $elm.data().xuData.debug_info.attribute_stat['xu-class'] = $elm.attr('class');
10782
+ // }
10783
+ // return {};
10784
+ // } catch (e) {
10785
+ // console.warn('parse error:' + val.value);
10786
+ // return { abort: true };
10787
+ // }
10788
+ // },
10789
+ // 'xu-exp': async function ($elm, val) {
10790
+ // let exp = val.value === null ? true : val.value;
10791
+
10792
+ // let exp_ret = await func.expression.get(SESSION_ID, exp, paramsP.dsSessionP, 'UI Attr EXP', SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP].currentRecordId, null, null, null, null, null, $elm.data().xuData.iterate_info);
10793
+
10794
+ // let value = func.UI.screen.fix_val_defaults(val.key, exp_ret.result);
10795
+
10796
+ // var new_val = {
10797
+ // key: val.key,
10798
+ // value,
10799
+ // };
10800
+
10801
+ // if (nodeP.tagName.substr(0, 3) === 'xu-') {
10802
+ // if (tag_fx[nodeP.tagName][new_val.key]) {
10803
+ // return await tag_fx[nodeP.tagName][new_val.key]($elm, new_val);
10804
+ // }
10805
+ // console.warn(`attribute ${new_val.key} not found for ${nodeP.tagName}`);
10806
+ // return {};
10807
+ // }
10808
+ // if (!$elm.data().xuData) return;
10809
+
10810
+ // $elm.data().xuData.debug_info.attribute_stat[new_val.key] = new_val.value;
10811
+
10812
+ // // IGNORE UNDEFINED or NULL ATTRIBUTES
10813
+ // if (typeof new_val.value === 'undefined' || new_val.value === null) {
10814
+ // return {};
10815
+ // }
10816
+
10817
+ // // IGNORE ATTRIBUTES WITH EMPTY VALUES
10818
+ // if (glb.solid_attributes.includes(new_val.key) && !new_val.value) {
10819
+ // return {};
10820
+ // }
10821
+
10822
+ // if (new_val.key.substr(0, 2) === 'xu') {
10823
+ // return await common_fx[new_val.key]($elm, new_val);
10824
+ // }
10825
+
10826
+ // $elm.attr(new_val.key, ($elm.attr(new_val.key) || '') + new_val.value);
10827
+ // return {};
10828
+ // },
10829
+ // 'xu-on': async function ($elm, val) {
10830
+ // CLIENT_ACTIVITY_TS = Date.now();
10831
+ // const trigger = val.key.split('xu-on:')[1].toLowerCase();
10832
+ // $elm.on(trigger, async function (evt) {
10833
+ // const _$elm = $(evt.currentTarget);
10834
+ // if (_.isEmpty(_$elm.data().xuAttributes)) return;
10835
+
10836
+ // for await (const [key, val] of Object.entries(_$elm.data().xuAttributes['xu-on:' + evt.type])) {
10837
+ // if (!_.isEmpty(val.props.condition)) {
10838
+ // const expCond = await func.expression.get(SESSION_ID, val.props.condition, paramsP.dsSessionP, 'condition', paramsP.recordid); // execute expression
10839
+ // if (!expCond.result) continue;
10840
+ // }
10841
+
10842
+ // if (val.event_modifiers && evt[val.event_modifiers]) {
10843
+ // evt[val.event_modifiers]();
10844
+ // }
10845
+
10846
+ // // if (val.handler === 'custom') {
10847
+ // if (val.workflow) {
10848
+ // // do BL
10849
+ // for await (const [key2, val2] of Object.entries(val.workflow)) {
10850
+ // // var cond = val2.data.enabled;
10851
+ // // if (val2.data.enabled && val2.props.condition) {
10852
+ // // expCond = await func.expression.get(SESSION_ID, val2.props.condition, paramsP.dsSessionP, 'condition', paramsP.recordid); // execute expression
10853
+ // // cond = expCond.result;
10854
+ // // }
10855
+ // // if (!cond) continue;
10856
+
10857
+ // if (!val2.data.enabled) continue; // added Jul 3, 25 - condition validate on execution
10858
+
10859
+ // func.events.add_to_queue(SESSION_ID, 'element event', val2.id, evt.type, val2.data.action, val2.data.name, null, _$elm.attr('xu-ui-id'), null, evt, null, null, null, paramsP.dsSessionP, null, null, null, evt.type, val2.data.name, null, null, val2, null, null, null, null, null, null);
10860
+ // }
10861
+ // }
10862
+ // }
10863
+ // });
10864
+ // return {};
10865
+ // },
10866
+ // 'xu-script': async function ($elm, val) {
10867
+ // var checkExist = setInterval(async function () {
10868
+ // if ($elm.is(':visible')) {
10869
+ // try {
10870
+ // // var res = eval('(' + val.value + ')');
10871
+ // // const fn = `(function(el) {
10872
+ // // ${val.value}
10873
+ // // })(document.querySelector(\`[xu-ui-id="${$elm.attr('xu-ui-id')}"]\`));`;
10874
+
10875
+ // const fn = `async (el)=>{${val.value} };`;
10876
+
10877
+ // var res = eval(fn);
10878
+ // await res($elm[0]);
10879
+ // // if (typeof res === 'function') {
10880
+ // // res($elm[0]);
10881
+ // // }
10882
+ // } catch (e) {
10883
+ // eval(val.value);
10884
+ // }
10885
+
10886
+ // clearInterval(checkExist);
10887
+ // }
10888
+ // }, 100); // check every 100ms
10889
+
10890
+ // return {};
10891
+ // },
10892
+ // 'xu-style-global': async function ($elm, val) {
10893
+ // $('head').append(`<style>${val.value}</style>`);
10894
+ // return {};
10895
+ // },
10896
+ // 'xu-style': async function ($elm, val) {
10897
+ // var cssString = val.value;
10898
+
10899
+ // var parser = new cssjs();
10900
+
10901
+ // var parsed = parser.parseCSS(cssString);
10902
+ // var xuUiId = `[xu-ui-id="${$elm.attr('xu-ui-id')}"]`;
10903
+
10904
+ // $.each(parsed, function (key, val) {
10905
+ // var selectors_arr = val.selector.split(',');
10906
+
10907
+ // $.each(selectors_arr, function (key2, val2) {
10908
+ // selectors_arr[key2] = `${xuUiId} ${val2}, ${xuUiId}${val2}`;
10909
+ // // console.log(new_selector);
10910
+ // });
10911
+
10912
+ // val.selector = selectors_arr.join(',');
10913
+ // // console.log(parsed);
10914
+ // });
10915
+
10916
+ // var newCSSString = parser.getCSSForEditor(parsed);
10917
+
10918
+ // $('head').append(`<style>${newCSSString}</style>`);
10919
+ // return {};
10920
+ // },
10921
+ // 'xu-cdn': async function ($elm, val) {
10922
+ // for await (const [key, resource] of Object.entries(val.value)) {
10923
+ // await load_cdn(resource);
10924
+ // }
10925
+
10926
+ // return {};
10927
+ // },
10928
+ // 'xu-ui-plugin': async function ($elm, val) {
10929
+ // var _session = SESSION_OBJ[SESSION_ID];
10930
+
10931
+ // for await (const [plugin_name, value] of Object.entries(val.value)) {
10932
+ // const _plugin = APP_OBJ[_session.app_id]?.app_plugins_purchased?.[plugin_name];
10933
+ // if (_plugin?.installed && _plugin?.manifest?.['runtime.mjs']?.exist && _plugin?.manifest?.['index.mjs']?.exist && value.enabled) {
10934
+ // if (_plugin?.manifest?.['runtime.mjs'].dist && _plugin?.manifest?.['runtime.mjs']?.css) {
10935
+ // const plugin_runtime_css_url = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, 'dist/runtime.css');
10936
+ // func.utils.load_css_on_demand(plugin_runtime_css_url);
10937
+ // }
10938
+
10939
+ // const plugin_index_src = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, `${_plugin.manifest['index.mjs'].dist ? 'dist/' : ''}index.mjs`);
10940
+
10941
+ // const plugin_index_resources = await import(plugin_index_src);
10942
+
10943
+ // let properties = _.cloneDeep(plugin_index_resources.properties);
10944
+ // for await (let [prop_name, prop_val] of Object.entries(properties)) {
10945
+ // prop_val.value = value?.attributes?.[prop_name];
10946
+ // if (value?.attributes?.[`xu-exp:${prop_name}`]) {
10947
+ // const res = await func.expression.get(SESSION_ID, value?.attributes?.[`xu-exp:${prop_name}`], paramsP.dsSessionP, 'UI Attr EXP');
10948
+ // prop_val.value = res.result;
10949
+ // }
10950
+ // }
10951
+ // // $elm.data().xu_ui_plugin = { properties };
10952
+ // const plugin_runtime_src = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, `${_plugin.manifest['runtime.mjs'].dist ? 'dist/' : ''}runtime.mjs`);
10953
+
10954
+ // const plugin_runtime_resources = await import(plugin_runtime_src);
10955
+
10956
+ // if (plugin_runtime_resources.cdn && typeof _.isArray(plugin_runtime_resources.cdn)) {
10957
+ // for await (const resource of plugin_runtime_resources.cdn) {
10958
+ // await load_cdn(resource);
10959
+ // }
10960
+ // }
10961
+
10962
+ // if (plugin_runtime_resources.fn) {
10963
+ // await plugin_runtime_resources.fn(plugin_name, $elm?.[0], properties);
10964
+ // // await plugin_runtime_resources.fn(plugin_name, $elm?.[0], $elm.data().xu_ui_plugin.properties);
10965
+ // }
10966
+ // }
10967
+ // }
10968
+
10969
+ // return {};
10970
+ // },
10971
+ // 'xu-store': async function ($elm, val) {
10972
+ // try {
10973
+ // const fields_obj = JSON5.parse(val.value);
10974
+ // for (const [field_id, value] of Object.entries(fields_obj)) {
10975
+ // func.datasource.add_dynamic_field_to_ds(SESSION_ID, paramsP.dsSessionP, field_id, value);
10976
+ // }
10977
+ // } catch (err) {
10978
+ // console.error(err);
10979
+ // }
10980
+ // return {};
10981
+ // },
10982
+ // 'xu-viewport': async function ($elm, val) {
10983
+ // // functionality in draw_html_element
10984
+ // return {};
10985
+ // },
10986
+ // };
10987
+
10988
+ // if (nodeP.tagName.substr(0, 3) === 'xu-') {
10989
+ // if (xu_func === 'xu-exp') {
10990
+ // return common_fx[xu_func]($elm, val);
10991
+ // }
10992
+
10993
+ // if (tag_fx?.[nodeP.tagName]?.[xu_func]) {
10994
+ // let ret = await tag_fx[nodeP.tagName][xu_func]($elm, val);
10995
+ // return ret;
10996
+ // }
10997
+ // // if (xu_func !== "tree_id")
10998
+ // console.warn(`attribute ${xu_func} not found for ${nodeP.tagName}`);
10999
+ // return {};
11000
+ // }
11001
+ // if (_.isEmpty($elm.data())) {
11002
+ // return {};
11003
+ // }
11004
+ // if (!$elm.data().xuData.debug_info.attribute_stat) {
11005
+ // $elm.data().xuData.debug_info.attribute_stat = {};
11006
+ // }
11007
+ // if (xu_func !== 'xu-exp') {
11008
+ // $elm.data().xuData.debug_info.attribute_stat[xu_func] = val.value;
11009
+ // }
11010
+ // try {
11011
+ // if (!common_fx[xu_func]) {
11012
+ // console.warn('invalid xu-tag', xu_func, error);
11013
+ // return {};
11014
+ // }
11015
+
11016
+ // return await common_fx[xu_func]($elm, val);
11017
+ // } catch (error) {
11018
+ // debugger;
11019
+ // }
11020
+ // };
11021
+
11022
+ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $root_container, nodeP, $container, paramsP, parent_infoP, jobNoP, keyP, parent_nodeP, xu_func, $elm, val, is_init, refreshed_ds) {
11023
+ if (is_skeleton) return;
11024
+
11025
+ // Cache frequently accessed values
11026
+ const _session = SESSION_OBJ[SESSION_ID];
11027
+ const _ds = _session.DS_GLB[paramsP.dsSessionP];
11028
+ const elmData = $elm.data();
11029
+ const xuData = elmData.xuData;
11030
+ const nodeTag = nodeP.tagName;
11031
+ const isXuTag = nodeTag && nodeTag.startsWith('xu-');
10057
11032
 
10058
11033
  const load_cdn = async function (resource) {
10059
- // console.log("loading cdn", resource);
10060
- if (!_.isObject(resource) && _.isString(resource)) {
10061
- resource = { src: resource, type: 'js' };
10062
- }
10063
11034
  if (!_.isObject(resource)) {
11035
+ resource = _.isString(resource) ? { src: resource, type: 'js' } : null;
11036
+ }
11037
+ if (!resource) {
10064
11038
  throw new Error('cdn resource in wrong format');
10065
11039
  }
10066
- return new Promise(async (resolve) => {
10067
- try {
10068
- switch (resource.type) {
10069
- case 'js':
10070
- await func.utils.load_js_on_demand(resource.src);
10071
- break;
10072
- case 'css':
10073
- await func.utils.load_js_on_demand(resource.src);
10074
- break;
10075
- case 'module':
10076
- func.utils.load_js_on_demand(resource.src, 'module');
10077
- break;
10078
11040
 
10079
- default:
10080
- await func.utils.load_js_on_demand(resource.src);
10081
- break;
10082
- }
10083
- resolve();
10084
- } catch (error) {
10085
- func.utils.debug_report(SESSION_ID, 'xu-cdn', 'Fail to load: ' + resource, 'W');
10086
- resolve();
10087
- }
10088
-
10089
- // if (resource.type === "js" || !resource.type) {
10090
- // await func.utils.load_js_on_demand(resource.src);
10091
- // return resolve();
10092
- // }
10093
- // if (resource.type === "css") {
10094
- // func.utils.load_css_on_demand(resource.src);
10095
- // return resolve();
10096
- // }
10097
- // if (resource.type === "module") {
10098
- // func.utils.load_js_on_demand(resource.src, "module");
10099
- // return resolve();
10100
- // }
10101
- // func.utils.debug_report(
10102
- // SESSION_ID,
10103
- // "xu-cdn",
10104
- // "Fail to load: " + resource,
10105
- // "W"
10106
- // );
10107
- // return resolve();
10108
- });
11041
+ try {
11042
+ const loadFn = resource.type === 'css' ? func.utils.load_css_on_demand : func.utils.load_js_on_demand;
11043
+ const moduleArg = resource.type === 'module' ? 'module' : undefined;
11044
+ await loadFn(resource.src, moduleArg);
11045
+ } catch (error) {
11046
+ func.utils.debug_report(SESSION_ID, 'xu-cdn', 'Fail to load: ' + resource.src, 'W');
11047
+ }
10109
11048
  };
10110
11049
 
10111
11050
  const common_fx = {
10112
11051
  'xu-attrs': async function ($elm, val) {
10113
- if (!val.value) return {};
10114
- if (!_.isObject(val.value)) throw 'xu-attrs value us not an object';
10115
- for (const [attr_key, attr_val] of Object.entries(val.value)) {
10116
- nodeP.attributes[attr_key] = attr_val;
11052
+ if (!val.value || !_.isObject(val.value)) {
11053
+ if (val.value) throw 'xu-attrs value is not an object';
11054
+ return {};
10117
11055
  }
10118
-
11056
+ Object.assign(nodeP.attributes, val.value);
10119
11057
  return {};
10120
11058
  },
11059
+
10121
11060
  'xu-ref': async function ($elm, val, dsSession) {
10122
11061
  if (!val.value) return {};
10123
11062
 
10124
11063
  func.UI.update_xu_ref(SESSION_ID, dsSession || paramsP.dsSessionP, val.value, $elm);
10125
11064
 
10126
- // Select the node that will be observed for mutations
10127
11065
  const targetNode = $elm[0];
11066
+ if (!targetNode) return {};
10128
11067
 
10129
- if (!targetNode) return;
10130
-
10131
- // Options for the observer (which mutations to observe)
10132
- const config = { attributes: true, childList: true, subtree: true };
10133
-
10134
- // Callback function to execute when mutations are observed
10135
- const callback = (mutationList, observer) => {
11068
+ const observer = new MutationObserver(() => {
10136
11069
  func.UI.screen.refresh_xu_attributes(SESSION_ID, [val.value]);
10137
- };
10138
-
10139
- // Create an observer instance linked to the callback function
10140
- const observer = new MutationObserver(callback);
10141
-
10142
- // Start observing the target node for configured mutations
10143
- observer.observe(targetNode, config);
10144
-
10145
- // Later, you can stop observing
10146
- // observer.disconnect();
11070
+ });
10147
11071
 
11072
+ observer.observe(targetNode, { attributes: true, childList: true, subtree: true });
10148
11073
  return {};
10149
11074
  },
11075
+
10150
11076
  'xu-bind': async function ($elm, val) {
10151
- if (is_skeleton) return;
11077
+ if (is_skeleton) return {};
10152
11078
 
10153
11079
  let val_is_reference_field = false;
11080
+ let _prog_id = xuData.paramsP.prog_id;
11081
+ let _dsP = xuData.paramsP.dsSessionP;
10154
11082
 
10155
- let _prog_id = $elm.data().xuData.paramsP.prog_id;
10156
- let _dsP = $elm.data().xuData.paramsP.dsSessionP;
10157
11083
  const view_ret = await func.utils.VIEWS_OBJ.get(SESSION_ID, _prog_id);
10158
11084
  if (!view_ret) return {};
10159
11085
 
10160
11086
  let is_dynamic_field = false;
10161
11087
  let field_prop;
10162
11088
  let bind_field_id;
10163
-
10164
11089
  const input_field_type = $elm.attr('type');
10165
11090
 
10166
11091
  const get_bind_field = async function (field_id) {
@@ -10170,16 +11095,14 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10170
11095
  } else {
10171
11096
  field_prop = func.common.find_item_by_key(view_ret.progFields, 'field_id', field_id);
10172
11097
  if (!field_prop) {
10173
- /// find the field everywhere in the chain Aug 30 2024
10174
11098
  const ret_get_value = await func.datasource.get_value(SESSION_ID, field_id, _dsP);
10175
-
10176
11099
  if (ret_get_value.found) {
10177
11100
  _dsP = ret_get_value.dsSessionP;
10178
- let _ds = SESSION_OBJ[SESSION_ID].DS_GLB[_dsP];
10179
- _prog_id = _ds.prog_id;
10180
- const view_ret = await func.utils.VIEWS_OBJ.get(SESSION_ID, _prog_id);
10181
- if (!view_ret) return {};
10182
- field_prop = func.common.find_item_by_key(view_ret.progFields, 'field_id', field_id);
11101
+ const ds = _session.DS_GLB[_dsP];
11102
+ _prog_id = ds.prog_id;
11103
+ const new_view_ret = await func.utils.VIEWS_OBJ.get(SESSION_ID, _prog_id);
11104
+ if (!new_view_ret) return {};
11105
+ field_prop = func.common.find_item_by_key(new_view_ret.progFields, 'field_id', field_id);
10183
11106
  }
10184
11107
  if (!field_prop) {
10185
11108
  throw `field ${field_id} not found in the program scope`;
@@ -10198,160 +11121,125 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10198
11121
  }
10199
11122
 
10200
11123
  const field_changed = async function (e) {
10201
- var _ds = SESSION_OBJ[SESSION_ID].DS_GLB[_dsP];
10202
-
10203
- // update array for checkbox that not in xu-for
10204
- if (field_prop.props.fieldType === 'array' && input_field_type === 'checkbox' && val_is_reference_field) {
10205
- let arr_value_before_cast = _.clone((await func.datasource.get_value(SESSION_ID, bind_field_id, _dsP, _ds.currentRecordId)).ret.value);
10206
- let value_from_getter = bind.getter($elm[0]);
10207
- let value;
10208
- if (arr_value_before_cast.includes(value_from_getter)) {
10209
- value = arr_value_before_cast.filter((item) => !_.isEqual(item, value_from_getter));
10210
- } else {
10211
- arr_value_before_cast.push(value_from_getter);
10212
- value = arr_value_before_cast;
10213
- }
10214
-
10215
- let datasource_changes = {
10216
- [_dsP]: {
10217
- [_ds.currentRecordId]: {
10218
- [bind_field_id]: value,
10219
- },
10220
- },
10221
- };
10222
-
10223
- return await func.datasource.update(SESSION_ID, datasource_changes);
11124
+ const ds = _session.DS_GLB[_dsP];
11125
+ const fieldType = field_prop.props.fieldType;
11126
+ const isCheckbox = input_field_type === 'checkbox';
11127
+ const isRadio = input_field_type === 'radio';
11128
+
11129
+ // Handle array field with checkbox
11130
+ if (fieldType === 'array' && isCheckbox && val_is_reference_field) {
11131
+ const arr_value = _.clone((await func.datasource.get_value(SESSION_ID, bind_field_id, _dsP, ds.currentRecordId)).ret.value);
11132
+ const value_from_getter = bind.getter($elm[0]);
11133
+ const value = arr_value.includes(value_from_getter) ? arr_value.filter((item) => !_.isEqual(item, value_from_getter)) : [...arr_value, value_from_getter];
11134
+
11135
+ return await func.datasource.update(SESSION_ID, {
11136
+ [_dsP]: { [ds.currentRecordId]: { [bind_field_id]: value } },
11137
+ });
10224
11138
  }
10225
11139
 
10226
- // update array for radio that not in xu-for
10227
- if (field_prop.props.fieldType === 'array' && input_field_type === 'radio' && val_is_reference_field) {
10228
- let value_from_getter = bind.getter($elm[0]);
10229
-
10230
- let datasource_changes = {
10231
- [_dsP]: {
10232
- [_ds.currentRecordId]: {
10233
- [bind_field_id]: [value_from_getter],
10234
- },
10235
- },
10236
- };
10237
-
10238
- return await func.datasource.update(SESSION_ID, datasource_changes);
11140
+ // Handle array field with radio
11141
+ if (fieldType === 'array' && isRadio && val_is_reference_field) {
11142
+ return await func.datasource.update(SESSION_ID, {
11143
+ [_dsP]: { [ds.currentRecordId]: { [bind_field_id]: [bind.getter($elm[0])] } },
11144
+ });
10239
11145
  }
10240
11146
 
10241
- var value = await func.common.get_cast_val(SESSION_ID, 'xu-bind', 'value', field_prop.props.fieldType, bind.getter($elm[0]));
11147
+ let value = await func.common.get_cast_val(SESSION_ID, 'xu-bind', 'value', fieldType, bind.getter($elm[0]));
10242
11148
 
10243
- if (field_prop.props.fieldType === 'object') {
11149
+ if (fieldType === 'object') {
10244
11150
  value = await func.common.get_cast_val(SESSION_ID, 'xu-bind', 'value', input_field_type, bind.getter($elm[0]));
10245
11151
  }
10246
11152
 
10247
- if (!_ds.currentRecordId) return;
11153
+ if (!ds.currentRecordId) return;
10248
11154
 
10249
- let datasource_changes = {
10250
- [_dsP]: {
10251
- [_ds.currentRecordId]: {
10252
- [bind_field_id]: value,
10253
- },
10254
- },
10255
- };
11155
+ await func.datasource.update(SESSION_ID, {
11156
+ [_dsP]: { [ds.currentRecordId]: { [bind_field_id]: value } },
11157
+ });
10256
11158
 
10257
- await func.datasource.update(SESSION_ID, datasource_changes);
10258
- const iterate_info = $elm?.data()?.xuData?.iterate_info;
11159
+ const iterate_info = xuData?.iterate_info;
10259
11160
  const reference_source_obj = iterate_info?.reference_source_obj;
10260
- if (reference_source_obj) {
10261
- if (reference_source_obj.ret.type === 'array') {
10262
- if (iterate_info.iterator_val === bind_field_id) {
10263
- const arr_idx = Number($elm?.data()?.xuData?.iterate_info._key);
10264
11161
 
10265
- const dataset_arr = await func.datasource.get_value(SESSION_ID, reference_source_obj.fieldIdP, _dsP, reference_source_obj.currentRecordId);
10266
- let new_arr = _.cloneDeep(dataset_arr.ret.value);
11162
+ if (reference_source_obj?.ret?.type === 'array' && iterate_info.iterator_val === bind_field_id) {
11163
+ const arr_idx = Number(iterate_info._key);
11164
+ const dataset_arr = await func.datasource.get_value(SESSION_ID, reference_source_obj.fieldIdP, _dsP, reference_source_obj.currentRecordId);
11165
+ const new_arr = _.cloneDeep(dataset_arr.ret.value);
10267
11166
 
10268
- if (field_prop.props.fieldType === 'object' && val_is_reference_field) {
10269
- let obj_item = new_arr[arr_idx];
10270
-
10271
- let e_exp = val.value.replace(bind_field_id, 'obj_item');
10272
-
10273
- let new_val = eval(e_exp + (input_field_type === 'string' ? `="${value}"` : `=${value}`));
10274
-
10275
- new_arr[arr_idx] = obj_item;
10276
- } else {
10277
- new_arr[arr_idx] = value;
10278
- }
10279
- // datasource_changes[_dsP][_ds.currentRecordId][reference_source_obj.fieldIdP] = new_arr;
10280
-
10281
- let datasource_changes = {
10282
- [_dsP]: {
10283
- [_ds.currentRecordId]: {
10284
- [reference_source_obj.fieldIdP]: new_arr,
10285
- },
10286
- },
10287
- };
10288
-
10289
- await func.datasource.update(SESSION_ID, datasource_changes, null, true);
10290
- }
11167
+ if (fieldType === 'object' && val_is_reference_field) {
11168
+ let obj_item = new_arr[arr_idx];
11169
+ const e_exp = val.value.replace(bind_field_id, 'obj_item');
11170
+ eval(e_exp + (input_field_type === 'string' ? `="${value}"` : `=${value}`));
11171
+ new_arr[arr_idx] = obj_item;
11172
+ } else {
11173
+ new_arr[arr_idx] = value;
10291
11174
  }
11175
+
11176
+ await func.datasource.update(
11177
+ SESSION_ID,
11178
+ {
11179
+ [_dsP]: { [ds.currentRecordId]: { [reference_source_obj.fieldIdP]: new_arr } },
11180
+ },
11181
+ null,
11182
+ true,
11183
+ );
10292
11184
  }
10293
11185
 
10294
- await func.datasource.update_changes_for_out_parameter(SESSION_ID, _dsP, _ds.parentDataSourceNo);
11186
+ await func.datasource.update_changes_for_out_parameter(SESSION_ID, _dsP, ds.parentDataSourceNo);
10295
11187
  };
10296
11188
 
10297
11189
  const bind = new UI_FRAMEWORK_PLUGIN.bind();
10298
-
10299
11190
  bind.listener($elm[0], field_changed);
10300
11191
 
10301
11192
  const set_value = function () {
10302
- let _ds = SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP];
10303
- if (!_ds.currentRecordId) return;
10304
- let value;
11193
+ const ds = _session.DS_GLB[paramsP.dsSessionP];
11194
+ if (!ds.currentRecordId) return;
11195
+
10305
11196
  try {
11197
+ let value;
10306
11198
  if (val_is_reference_field) {
10307
11199
  if (is_dynamic_field) {
10308
- value = _ds.dynamic_fields[bind_field_id].value;
11200
+ value = ds.dynamic_fields[bind_field_id].value;
10309
11201
  } else {
10310
- const row_idx = func.common.find_ROWID_idx(_ds, _ds.currentRecordId);
10311
- value = _ds.data_feed.rows?.[row_idx]?.[bind_field_id];
11202
+ const row_idx = func.common.find_ROWID_idx(ds, ds.currentRecordId);
11203
+ value = ds.data_feed.rows?.[row_idx]?.[bind_field_id];
10312
11204
  }
10313
- if (field_prop.props.fieldType === 'array' && $elm.attr('type') === 'checkbox' && $elm.attr('value')) {
10314
- if (value.includes($elm.attr('value'))) {
10315
- value = true;
10316
- } else {
10317
- value = false;
10318
- }
10319
- } else if (field_prop.props.fieldType === 'array' && $elm.attr('type') === 'radio' && $elm.attr('value')) {
10320
- if (value.includes($elm.attr('value'))) {
10321
- value = $elm.attr('value');
10322
- } else {
10323
- value = false;
10324
- }
10325
- } else if (field_prop.props.fieldType === 'object' && val.value.split('.').length > 1) {
10326
- let str = val.value.replace(bind_field_id, '(' + JSON.stringify(value) + ')');
10327
- value = eval(str);
11205
+
11206
+ const fieldType = field_prop.props.fieldType;
11207
+ const elmValue = $elm.attr('value');
11208
+
11209
+ if (fieldType === 'array' && input_field_type === 'checkbox' && elmValue) {
11210
+ value = value.includes(elmValue);
11211
+ } else if (fieldType === 'array' && input_field_type === 'radio' && elmValue) {
11212
+ value = value.includes(elmValue) ? elmValue : false;
11213
+ } else if (fieldType === 'object' && val.value.split('.').length > 1) {
11214
+ value = eval(val.value.replace(bind_field_id, '(' + JSON.stringify(value) + ')'));
10328
11215
  }
10329
11216
  } else {
10330
11217
  value = val.value;
10331
11218
  }
10332
- if (typeof value === 'undefined') return;
10333
- bind.setter($elm[0], value);
11219
+
11220
+ if (value !== undefined) {
11221
+ bind.setter($elm[0], value);
11222
+ }
10334
11223
  } catch (err) {
10335
11224
  console.error(err);
10336
11225
  }
10337
11226
  };
10338
- /// init value from ds
10339
- $('body').on('xu-bind-refresh.' + _ds.dsSession.toString(), () => {
10340
- set_value();
10341
- });
10342
11227
 
11228
+ $('body').on('xu-bind-refresh.' + _ds.dsSession, set_value);
10343
11229
  set_value();
10344
11230
  return {};
10345
11231
  },
11232
+
10346
11233
  'xu-render': async function ($elm, val, from_panel) {
10347
- const old_render = async function () {
10348
- var value = await func.common.get_cast_val(SESSION_ID, 'common fx', 'xu-render', 'bool', val.value);
11234
+ const value = await func.common.get_cast_val(SESSION_ID, 'common fx', 'xu-render', 'bool', val.value);
11235
+
11236
+ if (!glb.new_xu_render) {
11237
+ // Old render logic (kept as is for compatibility)
10349
11238
  const init_render = function () {
10350
11239
  if (!value) {
10351
- var cloned_$div = $elm.clone(true);
10352
-
10353
- let $xurender = $('<xurender>').attr('xu-ui-id', $elm.attr('xu-ui-id')).attr('hidden', true).appendTo($container); //.hide();
10354
- let original_data_obj = {
11240
+ const cloned_$div = $elm.clone(true);
11241
+ const $xurender = $('<xurender>').attr('xu-ui-id', $elm.attr('xu-ui-id')).attr('hidden', true).appendTo($container);
11242
+ const original_data_obj = {
10355
11243
  $container: cloned_$div,
10356
11244
  nodeP: _.cloneDeep(nodeP),
10357
11245
  parent_infoP,
@@ -10364,8 +11252,6 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10364
11252
  $xurender.data().xuData.original_data_obj = original_data_obj;
10365
11253
  $xurender.data().xuData.xurender_node = cloned_$div;
10366
11254
  $xurender.data().xuAttributes = nodeP.attributes || {};
10367
- // $xurender.hide();
10368
-
10369
11255
  $elm.remove();
10370
11256
  return { abort: true };
10371
11257
  }
@@ -10375,271 +11261,207 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10375
11261
  const post_render = async function () {
10376
11262
  if (value) {
10377
11263
  try {
10378
- // abort if already rended
10379
- if ($elm[0].tagName !== 'XURENDER' && $elm?.length) {
11264
+ if ($elm[0].tagName !== 'XURENDER' || !$elm?.length) {
10380
11265
  return func.events.delete_job(SESSION_ID, jobNoP);
10381
11266
  }
10382
11267
 
10383
- let original_data_obj = $elm.data().xuData.original_data_obj;
10384
-
11268
+ const original_data_obj = $elm.data().xuData.original_data_obj;
10385
11269
  if (!original_data_obj) {
10386
11270
  func.events.delete_job(SESSION_ID, jobNoP);
10387
11271
  return { delete_job: jobNoP };
10388
11272
  }
10389
11273
 
10390
- const new_$div = await func.UI.screen.render_ui_tree(
10391
- SESSION_ID,
10392
- $elm, //original_data_obj.$container,
10393
- _.cloneDeep(original_data_obj.nodeP),
10394
- original_data_obj.parent_infoP,
10395
- original_data_obj.paramsP,
10396
- jobNoP,
10397
- null,
10398
- original_data_obj.keyP,
10399
- null,
10400
- original_data_obj.parent_nodeP,
10401
- null,
10402
- original_data_obj.$root_container,
10403
- );
11274
+ const new_$div = await func.UI.screen.render_ui_tree(SESSION_ID, $elm, _.cloneDeep(original_data_obj.nodeP), original_data_obj.parent_infoP, original_data_obj.paramsP, jobNoP, null, original_data_obj.keyP, null, original_data_obj.parent_nodeP, null, original_data_obj.$root_container);
10404
11275
 
10405
11276
  new_$div.data().xuData.original_data_obj = original_data_obj;
10406
11277
  new_$div.data().xuData.xurender_node = $elm.clone(true);
10407
11278
  new_$div.data().xuAttributes = $elm.data().xuAttributes || {};
10408
11279
 
10409
11280
  const replace = async function () {
10410
- $elm.replaceWith(new_$div);
11281
+ $elm.replaceWith(from_panel ? new_$div.children() : new_$div);
10411
11282
  if (from_panel) {
10412
- const xuPanelWrapper = _.clone(new_$div.data().xuPanelWrapper);
10413
- $elm.parent().data().xuPanelWrapper = xuPanelWrapper;
10414
- $elm.replaceWith(new_$div.children());
11283
+ $elm.parent().data().xuPanelWrapper = _.clone(new_$div.data().xuPanelWrapper);
10415
11284
  }
10416
-
10417
11285
  if (val.fields_arr) {
10418
11286
  return await func.UI.screen.refresh_xu_attributes(SESSION_ID, val.fields_arr, val.jobNoP, new_$div);
10419
11287
  }
10420
11288
  func.events.delete_job(SESSION_ID, jobNoP);
10421
11289
  };
10422
- // if ($elm && func.UI.utils.find_in_element_data('xuData', $(SESSION_OBJ[SESSION_ID].root_element), 'xu_id', $elm.data().xuData.xu_id).length) {
10423
- if ($elm && $(`[xu-ui-id="${$elm.attr('xu-ui-id')}"]`).length) {
10424
- if (new_$div.data().xuData.paramsP) {
10425
- return await replace();
10426
- }
10427
11290
 
10428
- func.events.delete_job(SESSION_ID, jobNoP);
11291
+ if ($elm && $(`[xu-ui-id="${$elm.attr('xu-ui-id')}"]`).length && new_$div.data().xuData.paramsP) {
11292
+ return await replace();
10429
11293
  }
11294
+ func.events.delete_job(SESSION_ID, jobNoP);
10430
11295
  } catch (error) {
10431
11296
  func.events.delete_job(SESSION_ID, jobNoP);
10432
11297
  }
10433
11298
  return;
10434
11299
  }
10435
- // if (!value) {
11300
+
10436
11301
  if ($elm.prop('tagName') === 'XURENDER') {
10437
11302
  func.events.delete_job(SESSION_ID, jobNoP);
10438
11303
  return;
10439
11304
  }
10440
11305
 
10441
- let tmp_$div = $('<div>');
11306
+ const $xurender = $('<xurender>').attr('xu-ui-id', $elm.attr('xu-ui-id'));
10442
11307
 
10443
- let $xurender = $('<xurender>').attr('xu-ui-id', $elm.attr('xu-ui-id')).appendTo(tmp_$div); //.hide();
10444
- // was true before
10445
11308
  if ($elm.data().xuData.xurender_node) {
10446
11309
  $xurender.data({
10447
11310
  xuAttributes: $elm.data().xuData.xurender_node.data().xuAttributes || {},
10448
11311
  xuData: $elm.data().xuData.xurender_node.data().xuData || {},
10449
11312
  });
10450
11313
  } else {
10451
- // default new state
10452
-
10453
11314
  $xurender.data({
10454
11315
  xuAttributes: $elm.data().xuAttributes || {},
10455
11316
  xuData: $elm.data().xuData || {},
10456
11317
  });
10457
- const original_data_obj = {
11318
+ $xurender.data().xuData.original_data_obj = {
10458
11319
  nodeP: _.cloneDeep($elm.data().xuData.node_org),
10459
11320
  paramsP: $elm.data().xuData.paramsP,
10460
11321
  $container: $elm.clone(true),
10461
11322
  parent_infoP: parent_infoP,
10462
11323
  };
10463
-
10464
- $xurender.data().xuData.original_data_obj = original_data_obj;
10465
11324
  }
10466
11325
 
10467
- //remove xu-teleport trace
10468
11326
  $.each($elm.find('xu-teleport'), (key, val) => {
10469
11327
  const xuTeleportData = $(val).data().xuTeleportData || [];
10470
- for (const teleported_elm_id of xuTeleportData) {
10471
- $(`[xu-ui-id="${teleported_elm_id}"]`).remove();
10472
- }
11328
+ xuTeleportData.forEach((id) => $(`[xu-ui-id="${id}"]`).remove());
10473
11329
  });
10474
11330
 
10475
- $elm.replaceWith(tmp_$div.children());
11331
+ $elm.replaceWith($xurender);
10476
11332
  func.events.delete_job(SESSION_ID, jobNoP);
10477
- // }
10478
11333
  };
10479
- if (is_init) {
10480
- return init_render();
10481
- }
10482
- return await post_render();
10483
- };
10484
11334
 
10485
- const new_render = async function () {
10486
- var value = await func.common.get_cast_val(SESSION_ID, 'common fx', 'xu-render', 'bool', val.value);
10487
- const has_xu_render_attribute = true;
10488
- const has_xu_exp_render_attribute = $elm.data()?.xuData?.attr_exp_info?.['xu-render'] ? true : false;
10489
- const init_render = async function () {
10490
- nodeP.xu_render_made = value;
10491
- if (!value) {
10492
- if (has_xu_exp_render_attribute) {
10493
- return { has_xu_exp_render_attribute, has_xu_render_attribute, xu_render_background_processing: true };
10494
- }
10495
- return { has_xu_render_attribute, abort: true };
10496
- }
10497
- return { has_xu_exp_render_attribute, has_xu_render_attribute };
10498
- };
11335
+ return is_init ? init_render() : await post_render();
11336
+ }
10499
11337
 
10500
- const post_render = async function () {
10501
- // always come from refresh
10502
- let nodeP = $container.data().xuData.node.children[keyP];
10503
- nodeP.xu_render_made = value;
10504
- if (value) {
10505
- try {
10506
- const xu_render_cache_id = await get_xu_render_cache_str(SESSION_ID, paramsP.dsSessionP, Object.keys($elm.data()?.xuData?.attr_exp_info?.['xu-render']?.fields || {}));
10507
- const xu_ui_id = $elm.attr('xu-ui-id');
10508
- let new_$div = UI_WORKER_OBJ?.xu_render_cache?.[xu_ui_id + xu_render_cache_id]?.$div.clone(true);
10509
- let found_parent_vars = false;
10510
- if (new_$div) {
10511
- // validate if $div contains fields from parent ds
10512
- const parent_data = get_parent_ds_fields(SESSION_ID, paramsP.dsSessionP);
10513
- const parent_fields = Object.keys(parent_data);
10514
-
10515
- $.each(new_$div.find('*'), (key, val) => {
10516
- const _xuAttributes = $(val)?.data()?.xuAttributes;
10517
- if (found_parent_vars || !_xuAttributes) return;
10518
- for (const [attr_key, attr_val] of Object.entries(_xuAttributes)) {
10519
- if (found_parent_vars) break;
10520
- for (const [key, val] of Object.entries(parent_fields)) {
10521
- if (attr_val.includes('@' + key)) {
10522
- found_parent_vars = true;
10523
- break;
10524
- }
10525
- }
10526
- }
10527
- });
10528
- }
11338
+ // New render logic
11339
+ const has_xu_render_attribute = true;
11340
+ const has_xu_exp_render_attribute = !!xuData?.attr_exp_info?.['xu-render'];
10529
11341
 
10530
- if (!new_$div || found_parent_vars) {
10531
- UI_WORKER_OBJ.xu_render_cache[xu_ui_id + xu_render_cache_id] = { paramsP };
10532
- nodeP.xu_render_xu_ui_id = xu_ui_id;
10533
- nodeP.xu_render_cache_id = xu_render_cache_id;
10534
- new_$div = await func.UI.screen.render_ui_tree(SESSION_ID, $container, nodeP, parent_infoP, paramsP, jobNoP, null, keyP, null, parent_nodeP, null, $root_container);
10535
- const _$div = new_$div.clone(true);
10536
- UI_WORKER_OBJ.xu_render_cache[xu_ui_id + xu_render_cache_id].$div = _$div;
10537
- UI_WORKER_OBJ.xu_render_cache[xu_ui_id + xu_render_cache_id].data = _$div.data();
10538
- }
10539
- // append order handling
11342
+ const init_render = async function () {
11343
+ nodeP.xu_render_made = value;
11344
+ if (!value) {
11345
+ return has_xu_exp_render_attribute ? { has_xu_exp_render_attribute, has_xu_render_attribute, xu_render_background_processing: true } : { has_xu_render_attribute, abort: true };
11346
+ }
11347
+ return { has_xu_exp_render_attribute, has_xu_render_attribute };
11348
+ };
10540
11349
 
10541
- if (!$container.children().length) {
10542
- new_$div.appendTo($container);
10543
- } else {
10544
- // iterate the container node
10545
- let $last_elm_found = [];
10546
- $.each($container.data().xuData.node.children, (item_key, item_val) => {
10547
- // const $elm = $(`[xu-node-id="${item_val.id}"]`);
10548
- const $elm = func.UI.utils.find_in_element_data('xuData', $(SESSION_OBJ[SESSION_ID].root_element), 'nodeid', item_val.id);
10549
- if ($elm.length) {
10550
- $last_elm_found = $elm;
10551
- }
10552
- if (keyP == item_key) {
10553
- if ($last_elm_found.length) {
10554
- new_$div.after($last_elm_found);
10555
- } else {
10556
- $container.prepend(new_$div);
10557
- }
11350
+ const post_render = async function () {
11351
+ const containerNodeP = $container.data().xuData.node.children[keyP];
11352
+ containerNodeP.xu_render_made = value;
11353
+
11354
+ if (value) {
11355
+ try {
11356
+ const xu_render_cache_id = await get_xu_render_cache_str(SESSION_ID, paramsP.dsSessionP, Object.keys(xuData?.attr_exp_info?.['xu-render']?.fields || {}));
11357
+ const xu_ui_id = $elm.attr('xu-ui-id');
11358
+ const cache_key = xu_ui_id + xu_render_cache_id;
11359
+ let new_$div = UI_WORKER_OBJ?.xu_render_cache?.[cache_key]?.$div?.clone(true);
11360
+ let found_parent_vars = false;
11361
+
11362
+ if (new_$div) {
11363
+ const parent_data = get_parent_ds_fields(SESSION_ID, paramsP.dsSessionP);
11364
+ const parent_fields = Object.keys(parent_data);
11365
+
11366
+ $.each(new_$div.find('*'), (key, val) => {
11367
+ if (found_parent_vars) return;
11368
+ const _xuAttributes = $(val)?.data()?.xuAttributes;
11369
+ if (!_xuAttributes) return;
11370
+
11371
+ for (const attr_val of Object.values(_xuAttributes)) {
11372
+ if (parent_fields.some((field) => attr_val.includes('@' + field))) {
11373
+ found_parent_vars = true;
11374
+ break;
10558
11375
  }
10559
- });
10560
- }
10561
- } catch (error) {
10562
- func.events.delete_job(SESSION_ID, jobNoP);
11376
+ }
11377
+ });
10563
11378
  }
10564
- return;
10565
- }
10566
11379
 
10567
- /////////// !value ///////////
11380
+ if (!new_$div || found_parent_vars) {
11381
+ UI_WORKER_OBJ.xu_render_cache[cache_key] = { paramsP };
11382
+ containerNodeP.xu_render_xu_ui_id = xu_ui_id;
11383
+ containerNodeP.xu_render_cache_id = xu_render_cache_id;
10568
11384
 
10569
- const xu_ui_id = $elm.attr('xu-ui-id');
11385
+ new_$div = await func.UI.screen.render_ui_tree(SESSION_ID, $container, containerNodeP, parent_infoP, paramsP, jobNoP, null, keyP, null, parent_nodeP, null, $root_container);
10570
11386
 
10571
- const cache_str = await get_xu_render_cache_str(SESSION_ID, paramsP.dsSessionP, Object.keys($elm.data()?.xuData?.attr_exp_info?.['xu-render']?.fields || {}));
10572
- const _$div = $elm.clone(true);
10573
- UI_WORKER_OBJ.xu_render_cache[xu_ui_id + cache_str] = { $div: _$div, data: _$div.data(), paramsP };
10574
- $elm.remove();
10575
- func.events.delete_job(SESSION_ID, jobNoP);
10576
- };
10577
- if (is_init) {
10578
- return await init_render();
11387
+ const _$div = new_$div.clone(true);
11388
+ UI_WORKER_OBJ.xu_render_cache[cache_key] = { $div: _$div, data: _$div.data(), paramsP };
11389
+ }
11390
+
11391
+ // Append order handling
11392
+ if (!$container.children().length) {
11393
+ new_$div.appendTo($container);
11394
+ } else {
11395
+ let $last_elm_found = [];
11396
+ $.each($container.data().xuData.node.children, (item_key, item_val) => {
11397
+ const $elm = func.UI.utils.find_in_element_data('xuData', $(_session.root_element), 'nodeid', item_val.id);
11398
+ if ($elm.length) $last_elm_found = $elm;
11399
+ if (keyP == item_key) {
11400
+ $last_elm_found.length ? new_$div.after($last_elm_found) : $container.prepend(new_$div);
11401
+ }
11402
+ });
11403
+ }
11404
+ } catch (error) {
11405
+ func.events.delete_job(SESSION_ID, jobNoP);
11406
+ }
11407
+ return;
10579
11408
  }
10580
- return await post_render();
11409
+
11410
+ // !value
11411
+ const xu_ui_id = $elm.attr('xu-ui-id');
11412
+ const cache_str = await get_xu_render_cache_str(SESSION_ID, paramsP.dsSessionP, Object.keys(xuData?.attr_exp_info?.['xu-render']?.fields || {}));
11413
+ const _$div = $elm.clone(true);
11414
+ UI_WORKER_OBJ.xu_render_cache[xu_ui_id + cache_str] = { $div: _$div, data: _$div.data(), paramsP };
11415
+ $elm.remove();
11416
+ func.events.delete_job(SESSION_ID, jobNoP);
10581
11417
  };
10582
11418
 
10583
- if (glb.new_xu_render) {
10584
- return new_render();
10585
- }
10586
- return old_render();
11419
+ return is_init ? await init_render() : await post_render();
10587
11420
  },
11421
+
10588
11422
  'xu-show': async function ($elm, val) {
10589
- var value = await func.common.get_cast_val(SESSION_ID, 'common fx', 'xu-show', 'bool', val.value);
10590
- if (value) {
10591
- $elm.show();
10592
- }
10593
- if (!value) {
10594
- $elm.hide();
10595
- }
11423
+ const value = await func.common.get_cast_val(SESSION_ID, 'common fx', 'xu-show', 'bool', val.value);
11424
+ $elm.toggle(value);
10596
11425
  return {};
10597
11426
  },
11427
+
10598
11428
  'xu-content': async function ($elm, val) {
10599
11429
  try {
10600
11430
  $elm.html(val.value);
10601
11431
  } catch (error) {
10602
- console.warn(e);
11432
+ console.warn(error);
10603
11433
  }
10604
- return;
10605
11434
  },
11435
+
10606
11436
  'xu-text': async function ($elm, val) {
10607
11437
  try {
10608
11438
  $elm.text(val.value);
10609
11439
  } catch (error) {
10610
- console.warn(e);
11440
+ console.warn(error);
10611
11441
  }
10612
- return;
10613
11442
  },
11443
+
10614
11444
  'xu-html': async function ($elm, val) {
10615
11445
  try {
10616
11446
  $elm.html(val.value);
10617
11447
  } catch (error) {
10618
- console.warn(e);
11448
+ console.warn(error);
10619
11449
  }
10620
- return;
10621
11450
  },
11451
+
10622
11452
  'xu-for': async function ($elm, data) {
10623
- // exit if call from rendered xu-for item to prevent infante loop (parent_infoP?.iterate_info indicate call from rendered item)
10624
- if (parent_infoP?.iterate_info) return {};
10625
- if (!data.value) return {};
11453
+ if (parent_infoP?.iterate_info || !data.value) return {};
11454
+
10626
11455
  try {
10627
- // data.value (xu-for) can store actual values such as an array, a CSV, or a field_id that references a specific field within the dataset, initialized with values for the iteration.
10628
11456
  let arr = data.value;
10629
-
10630
- // find reference source field
10631
11457
  let reference_source_obj;
10632
-
10633
11458
  const _progFields = await func.datasource.get_progFields(SESSION_ID, paramsP.dsSessionP);
11459
+ const view_field_obj = func.common.find_item_by_key(_progFields, 'field_id', data.value);
10634
11460
 
10635
- let view_field_obj = func.common.find_item_by_key(_progFields, 'field_id', data.value);
10636
- // detect if data.value (xu-for) is reference field_id by checking if exist in the dataset
10637
11461
  if (view_field_obj) {
10638
- // xu-for is reference field_id
10639
11462
  reference_source_obj = await func.datasource.get_value(SESSION_ID, data.value, paramsP.dsSessionP);
10640
11463
  arr = reference_source_obj?.ret?.value;
10641
11464
  } else {
10642
- // xu-for is actual data
10643
11465
  if (typeof data.value === 'string') {
10644
11466
  arr = eval(data.value.replaceAll('\\', ''));
10645
11467
  }
@@ -10648,59 +11470,44 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10648
11470
  }
10649
11471
  }
10650
11472
 
10651
- const custom_iterator_key = $elm.data().xuData.iterator_key;
10652
- const custom_iterator_val = $elm.data().xuData.iterator_val;
10653
-
10654
- let iterator_key = custom_iterator_key;
10655
- let iterator_val = custom_iterator_val;
10656
- let is_key_dynamic_field, is_val_dynamic_field;
10657
-
10658
- // custom FOR_VAL name or namespaced default name
10659
- if (!custom_iterator_key) {
10660
- is_key_dynamic_field = true;
10661
-
10662
- iterator_key = '_FOR_KEY';
10663
- }
10664
-
10665
- if (!custom_iterator_val) {
10666
- is_val_dynamic_field = true;
11473
+ const custom_iterator_key = xuData.iterator_key;
11474
+ const custom_iterator_val = xuData.iterator_val;
11475
+ const iterator_key = custom_iterator_key || '_FOR_KEY';
11476
+ const iterator_val = custom_iterator_val || '_FOR_VAL';
11477
+ const is_key_dynamic_field = !custom_iterator_key;
11478
+ const is_val_dynamic_field = !custom_iterator_val;
10667
11479
 
10668
- iterator_val = '_FOR_VAL';
10669
- }
10670
-
10671
- var i = 0;
10672
- for await (let [_key, _val] of Object.entries(arr)) {
10673
- if (_.isArray(arr)) {
10674
- _key = Number(_key);
10675
- }
11480
+ const set_value = async function (is_dynamic_field, currentRecordId, field_id, value) {
11481
+ if (is_dynamic_field) {
11482
+ func.datasource.add_dynamic_field_to_ds(SESSION_ID, paramsP.dsSessionP, field_id, value);
11483
+ } else {
11484
+ const _progFields = await func.datasource.get_progFields(SESSION_ID, paramsP.dsSessionP);
11485
+ const view_field_obj = func.common.find_item_by_key(_progFields, 'field_id', field_id);
10676
11486
 
10677
- const set_value = async function (is_dynamic_field, currentRecordId, field_id, value) {
10678
- if (is_dynamic_field) {
10679
- func.datasource.add_dynamic_field_to_ds(SESSION_ID, paramsP.dsSessionP, field_id, value);
10680
- } else {
10681
- const _progFields = await func.datasource.get_progFields(SESSION_ID, paramsP.dsSessionP);
10682
-
10683
- let view_field_obj = func.common.find_item_by_key(_progFields, 'field_id', field_id);
10684
- if (view_field_obj) {
10685
- let _ds = SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP];
10686
- try {
10687
- const row_idx = func.common.find_ROWID_idx(_ds, currentRecordId);
10688
- _ds.data_feed.rows[row_idx][field_id] = value;
10689
- } catch (err) {
10690
- console.error(err);
10691
- }
10692
- } else {
10693
- console.error('field not exist in dataset for xu-for method');
11487
+ if (view_field_obj) {
11488
+ const ds = _session.DS_GLB[paramsP.dsSessionP];
11489
+ try {
11490
+ const row_idx = func.common.find_ROWID_idx(ds, currentRecordId);
11491
+ ds.data_feed.rows[row_idx][field_id] = value;
11492
+ } catch (err) {
11493
+ console.error(err);
10694
11494
  }
11495
+ } else {
11496
+ console.error('field not exist in dataset for xu-for method');
10695
11497
  }
10696
- };
11498
+ }
11499
+ };
11500
+
11501
+ const currentRecordId = _ds.currentRecordId.toString();
11502
+ let i = 0;
10697
11503
 
10698
- var currentRecordId = SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP].currentRecordId.toString();
11504
+ for (let [_key, _val] of Object.entries(arr)) {
11505
+ if (_.isArray(arr)) _key = Number(_key);
10699
11506
 
10700
11507
  await set_value(is_key_dynamic_field, currentRecordId, iterator_key, _key);
10701
11508
  await set_value(is_val_dynamic_field, currentRecordId, iterator_val, _val);
10702
11509
 
10703
- var iterate_info = {
11510
+ const iterate_info = {
10704
11511
  _val,
10705
11512
  _key,
10706
11513
  iterator_key,
@@ -10709,26 +11516,13 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10709
11516
  is_val_dynamic_field,
10710
11517
  reference_source_obj,
10711
11518
  };
10712
- // let _parent_info = _.cloneDeep(parent_infoP) || {};
10713
- let _parent_info = klona.klona(parent_infoP) || {};
11519
+
11520
+ const _parent_info = klona.klona(parent_infoP) || {};
10714
11521
  _parent_info.iterate_info = iterate_info;
10715
11522
 
10716
- const $divP = await func.UI.screen.render_ui_tree(
10717
- SESSION_ID,
10718
- $container,
10719
- nodeP,
10720
- _parent_info, //parent_infoP ? _.cloneDeep(_parent_info) : null,
10721
- paramsP,
10722
- jobNoP,
10723
- null,
10724
- i,
10725
- null,
10726
- nodeP,
10727
- null,
10728
- $root_container,
10729
- );
11523
+ const $divP = await func.UI.screen.render_ui_tree(SESSION_ID, $container, nodeP, _parent_info, paramsP, jobNoP, null, i, null, nodeP, null, $root_container);
10730
11524
 
10731
- $.each($divP.children(), function (key, val) {
11525
+ $.each($divP.children(), (key, val) => {
10732
11526
  if ($(val)?.data()?.xuData) {
10733
11527
  $(val).data().xuData.iterate_info = iterate_info;
10734
11528
  }
@@ -10736,106 +11530,87 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10736
11530
 
10737
11531
  i++;
10738
11532
  }
11533
+
10739
11534
  $elm.remove();
10740
11535
  return { abort: true };
10741
11536
  } catch (e) {
10742
- console.error(' Iterator Arr parse error');
11537
+ console.error('Iterator Arr parse error', e);
10743
11538
  return { abort: true };
10744
11539
  }
10745
11540
  },
11541
+
10746
11542
  'xu-for-key': async function ($elm, val) {
10747
- $elm.data().xuData.iterator_key = val.value;
11543
+ xuData.iterator_key = val.value;
10748
11544
  return {};
10749
11545
  },
11546
+
10750
11547
  'xu-for-val': async function ($elm, val) {
10751
- $elm.data().xuData.iterator_val = val.value;
11548
+ xuData.iterator_val = val.value;
10752
11549
  return {};
10753
11550
  },
11551
+
10754
11552
  'xu-class': async function ($elm, val) {
10755
11553
  try {
10756
- const classes_string = val.value;
10757
- // let obj = _.isString(classes_string) ? JSON.parse(classes_string) : _.defaults(classes_string, {});
10758
-
10759
- const classes_obj = _.isString(classes_string) ? JSON.parse(classes_string) : _.defaults(classes_string, {});
10760
- for await (const [cla, cond] of Object.entries(classes_obj)) {
10761
- let res = await func.expression.get(
10762
- SESSION_ID,
10763
- cond,
10764
- paramsP.dsSessionP,
10765
- 'UI Attr EXP',
10766
- $elm.data().xuData.currentRecordId, // SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP].currentRecordId
10767
- null,
10768
- null,
10769
- null,
10770
- null,
10771
- null,
10772
- $elm.data().xuData.iterate_info,
10773
- );
11554
+ const classes_obj = _.isString(val.value) ? JSON.parse(val.value) : _.defaults(val.value, {});
10774
11555
 
10775
- if (res.result) {
10776
- $elm.addClass(cla);
10777
- } else {
10778
- $elm.removeClass(cla);
10779
- }
11556
+ for (const [cla, cond] of Object.entries(classes_obj)) {
11557
+ const res = await func.expression.get(SESSION_ID, cond, paramsP.dsSessionP, 'UI Attr EXP', xuData.currentRecordId, null, null, null, null, null, xuData.iterate_info);
10780
11558
 
10781
- $elm.data().xuData.debug_info.attribute_stat['xu-class'] = $elm.attr('class');
11559
+ $elm.toggleClass(cla, res.result);
10782
11560
  }
11561
+
11562
+ xuData.debug_info.attribute_stat['xu-class'] = $elm.attr('class');
10783
11563
  return {};
10784
11564
  } catch (e) {
10785
11565
  console.warn('parse error:' + val.value);
10786
11566
  return { abort: true };
10787
11567
  }
10788
11568
  },
10789
- 'xu-exp': async function ($elm, val) {
10790
- let exp = val.value === null ? true : val.value;
10791
11569
 
10792
- let exp_ret = await func.expression.get(SESSION_ID, exp, paramsP.dsSessionP, 'UI Attr EXP', SESSION_OBJ[SESSION_ID].DS_GLB[paramsP.dsSessionP].currentRecordId, null, null, null, null, null, $elm.data().xuData.iterate_info);
10793
-
10794
- let value = func.UI.screen.fix_val_defaults(val.key, exp_ret.result);
11570
+ 'xu-exp': async function ($elm, val) {
11571
+ const exp = val.value === null ? true : val.value;
11572
+ const exp_ret = await func.expression.get(SESSION_ID, exp, paramsP.dsSessionP, 'UI Attr EXP', _ds.currentRecordId, null, null, null, null, null, xuData.iterate_info);
10795
11573
 
10796
- var new_val = {
10797
- key: val.key,
10798
- value,
10799
- };
11574
+ const value = func.UI.screen.fix_val_defaults(val.key, exp_ret.result);
11575
+ const new_val = { key: val.key, value };
10800
11576
 
10801
- if (nodeP.tagName.substr(0, 3) === 'xu-') {
10802
- if (tag_fx[nodeP.tagName][new_val.key]) {
10803
- return await tag_fx[nodeP.tagName][new_val.key]($elm, new_val);
11577
+ if (isXuTag) {
11578
+ if (tag_fx[nodeTag]?.[new_val.key]) {
11579
+ return await tag_fx[nodeTag][new_val.key]($elm, new_val);
10804
11580
  }
10805
- console.warn(`attribute ${new_val.key} not found for ${nodeP.tagName}`);
11581
+ console.warn(`attribute ${new_val.key} not found for ${nodeTag}`);
10806
11582
  return {};
10807
11583
  }
10808
- if (!$elm.data().xuData) return;
10809
-
10810
- $elm.data().xuData.debug_info.attribute_stat[new_val.key] = new_val.value;
10811
11584
 
10812
- // IGNORE UNDEFINED or NULL ATTRIBUTES
10813
- if (typeof new_val.value === 'undefined' || new_val.value === null) {
10814
- return {};
10815
- }
11585
+ if (!xuData) return {};
11586
+ xuData.debug_info.attribute_stat[new_val.key] = new_val.value;
10816
11587
 
10817
- // IGNORE ATTRIBUTES WITH EMPTY VALUES
10818
- if (glb.solid_attributes.includes(new_val.key) && !new_val.value) {
10819
- return {};
10820
- }
11588
+ if (new_val.value === undefined || new_val.value === null) return {};
11589
+ if (glb.solid_attributes.includes(new_val.key) && !new_val.value) return {};
10821
11590
 
10822
- if (new_val.key.substr(0, 2) === 'xu') {
11591
+ if (new_val.key.startsWith('xu')) {
10823
11592
  return await common_fx[new_val.key]($elm, new_val);
10824
11593
  }
10825
11594
 
10826
11595
  $elm.attr(new_val.key, ($elm.attr(new_val.key) || '') + new_val.value);
10827
11596
  return {};
10828
11597
  },
11598
+
10829
11599
  'xu-on': async function ($elm, val) {
10830
11600
  CLIENT_ACTIVITY_TS = Date.now();
10831
11601
  const trigger = val.key.split('xu-on:')[1].toLowerCase();
11602
+
10832
11603
  $elm.on(trigger, async function (evt) {
10833
11604
  const _$elm = $(evt.currentTarget);
10834
- if (_.isEmpty(_$elm.data().xuAttributes)) return;
11605
+ const xuAttributes = _$elm.data().xuAttributes;
11606
+ if (_.isEmpty(xuAttributes)) return;
10835
11607
 
10836
- for await (const [key, val] of Object.entries(_$elm.data().xuAttributes['xu-on:' + evt.type])) {
11608
+ const handlers = xuAttributes['xu-on:' + evt.type];
11609
+ if (!handlers) return;
11610
+
11611
+ for (const [key, val] of Object.entries(handlers)) {
10837
11612
  if (!_.isEmpty(val.props.condition)) {
10838
- const expCond = await func.expression.get(SESSION_ID, val.props.condition, paramsP.dsSessionP, 'condition', paramsP.recordid); // execute expression
11613
+ const expCond = await func.expression.get(SESSION_ID, val.props.condition, paramsP.dsSessionP, 'condition', paramsP.recordid);
10839
11614
  if (!expCond.result) continue;
10840
11615
  }
10841
11616
 
@@ -10843,18 +11618,9 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10843
11618
  evt[val.event_modifiers]();
10844
11619
  }
10845
11620
 
10846
- // if (val.handler === 'custom') {
10847
11621
  if (val.workflow) {
10848
- // do BL
10849
- for await (const [key2, val2] of Object.entries(val.workflow)) {
10850
- // var cond = val2.data.enabled;
10851
- // if (val2.data.enabled && val2.props.condition) {
10852
- // expCond = await func.expression.get(SESSION_ID, val2.props.condition, paramsP.dsSessionP, 'condition', paramsP.recordid); // execute expression
10853
- // cond = expCond.result;
10854
- // }
10855
- // if (!cond) continue;
10856
-
10857
- if (!val2.data.enabled) continue; // added Jul 3, 25 - condition validate on execution
11622
+ for (const [key2, val2] of Object.entries(val.workflow)) {
11623
+ if (!val2.data.enabled) continue;
10858
11624
 
10859
11625
  func.events.add_to_queue(SESSION_ID, 'element event', val2.id, evt.type, val2.data.action, val2.data.name, null, _$elm.attr('xu-ui-id'), null, evt, null, null, null, paramsP.dsSessionP, null, null, null, evt.type, val2.data.name, null, null, val2, null, null, null, null, null, null);
10860
11626
  }
@@ -10863,111 +11629,91 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10863
11629
  });
10864
11630
  return {};
10865
11631
  },
11632
+
10866
11633
  'xu-script': async function ($elm, val) {
10867
- var checkExist = setInterval(async function () {
11634
+ const checkExist = setInterval(async function () {
10868
11635
  if ($elm.is(':visible')) {
10869
11636
  try {
10870
- // var res = eval('(' + val.value + ')');
10871
- // const fn = `(function(el) {
10872
- // ${val.value}
10873
- // })(document.querySelector(\`[xu-ui-id="${$elm.attr('xu-ui-id')}"]\`));`;
10874
-
10875
- const fn = `async (el)=>{${val.value} };`;
10876
-
10877
- var res = eval(fn);
10878
- await res($elm[0]);
10879
- // if (typeof res === 'function') {
10880
- // res($elm[0]);
10881
- // }
11637
+ const fn = eval(`async (el)=>{${val.value}}`);
11638
+ await fn($elm[0]);
10882
11639
  } catch (e) {
10883
11640
  eval(val.value);
10884
11641
  }
10885
-
10886
11642
  clearInterval(checkExist);
10887
11643
  }
10888
- }, 100); // check every 100ms
10889
-
11644
+ }, 100);
10890
11645
  return {};
10891
11646
  },
11647
+
10892
11648
  'xu-style-global': async function ($elm, val) {
10893
11649
  $('head').append(`<style>${val.value}</style>`);
10894
11650
  return {};
10895
11651
  },
10896
- 'xu-style': async function ($elm, val) {
10897
- var cssString = val.value;
10898
-
10899
- var parser = new cssjs();
10900
-
10901
- var parsed = parser.parseCSS(cssString);
10902
- var xuUiId = `[xu-ui-id="${$elm.attr('xu-ui-id')}"]`;
10903
-
10904
- $.each(parsed, function (key, val) {
10905
- var selectors_arr = val.selector.split(',');
10906
-
10907
- $.each(selectors_arr, function (key2, val2) {
10908
- selectors_arr[key2] = `${xuUiId} ${val2}, ${xuUiId}${val2}`;
10909
- // console.log(new_selector);
10910
- });
10911
11652
 
10912
- val.selector = selectors_arr.join(',');
10913
- // console.log(parsed);
11653
+ 'xu-style': async function ($elm, val) {
11654
+ const parser = new cssjs();
11655
+ const parsed = parser.parseCSS(val.value);
11656
+ const xuUiId = `[xu-ui-id="${$elm.attr('xu-ui-id')}"]`;
11657
+
11658
+ parsed.forEach((rule) => {
11659
+ rule.selector = rule.selector
11660
+ .split(',')
11661
+ .map((sel) => `${xuUiId} ${sel}, ${xuUiId}${sel}`)
11662
+ .join(',');
10914
11663
  });
10915
11664
 
10916
- var newCSSString = parser.getCSSForEditor(parsed);
10917
-
10918
- $('head').append(`<style>${newCSSString}</style>`);
11665
+ $('head').append(`<style>${parser.getCSSForEditor(parsed)}</style>`);
10919
11666
  return {};
10920
11667
  },
11668
+
10921
11669
  'xu-cdn': async function ($elm, val) {
10922
- for await (const [key, resource] of Object.entries(val.value)) {
11670
+ for (const resource of Object.values(val.value)) {
10923
11671
  await load_cdn(resource);
10924
11672
  }
10925
-
10926
11673
  return {};
10927
11674
  },
10928
- 'xu-ui-plugin': async function ($elm, val) {
10929
- var _session = SESSION_OBJ[SESSION_ID];
10930
11675
 
10931
- for await (const [plugin_name, value] of Object.entries(val.value)) {
11676
+ 'xu-ui-plugin': async function ($elm, val) {
11677
+ for (const [plugin_name, value] of Object.entries(val.value)) {
10932
11678
  const _plugin = APP_OBJ[_session.app_id]?.app_plugins_purchased?.[plugin_name];
10933
- if (_plugin?.installed && _plugin?.manifest?.['runtime.mjs']?.exist && _plugin?.manifest?.['index.mjs']?.exist && value.enabled) {
10934
- if (_plugin?.manifest?.['runtime.mjs'].dist && _plugin?.manifest?.['runtime.mjs']?.css) {
10935
- const plugin_runtime_css_url = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, 'dist/runtime.css');
10936
- func.utils.load_css_on_demand(plugin_runtime_css_url);
10937
- }
10938
11679
 
10939
- const plugin_index_src = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, `${_plugin.manifest['index.mjs'].dist ? 'dist/' : ''}index.mjs`);
11680
+ if (!_plugin?.installed || !_plugin?.manifest?.['runtime.mjs']?.exist || !_plugin?.manifest?.['index.mjs']?.exist || !value.enabled) continue;
10940
11681
 
10941
- const plugin_index_resources = await import(plugin_index_src);
11682
+ if (_plugin.manifest['runtime.mjs'].dist && _plugin.manifest['runtime.mjs'].css) {
11683
+ const css_url = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, 'dist/runtime.css');
11684
+ func.utils.load_css_on_demand(css_url);
11685
+ }
10942
11686
 
10943
- let properties = _.cloneDeep(plugin_index_resources.properties);
10944
- for await (let [prop_name, prop_val] of Object.entries(properties)) {
10945
- prop_val.value = value?.attributes?.[prop_name];
10946
- if (value?.attributes?.[`xu-exp:${prop_name}`]) {
10947
- const res = await func.expression.get(SESSION_ID, value?.attributes?.[`xu-exp:${prop_name}`], paramsP.dsSessionP, 'UI Attr EXP');
10948
- prop_val.value = res.result;
10949
- }
10950
- }
10951
- // $elm.data().xu_ui_plugin = { properties };
10952
- const plugin_runtime_src = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, `${_plugin.manifest['runtime.mjs'].dist ? 'dist/' : ''}runtime.mjs`);
11687
+ const plugin_index_src = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, `${_plugin.manifest['index.mjs'].dist ? 'dist/' : ''}index.mjs`);
10953
11688
 
10954
- const plugin_runtime_resources = await import(plugin_runtime_src);
11689
+ const plugin_index_resources = await import(plugin_index_src);
11690
+ const properties = _.cloneDeep(plugin_index_resources.properties);
10955
11691
 
10956
- if (plugin_runtime_resources.cdn && typeof _.isArray(plugin_runtime_resources.cdn)) {
10957
- for await (const resource of plugin_runtime_resources.cdn) {
10958
- await load_cdn(resource);
10959
- }
11692
+ for (const [prop_name, prop_val] of Object.entries(properties)) {
11693
+ prop_val.value = value?.attributes?.[prop_name];
11694
+ if (value?.attributes?.[`xu-exp:${prop_name}`]) {
11695
+ const res = await func.expression.get(SESSION_ID, value.attributes[`xu-exp:${prop_name}`], paramsP.dsSessionP, 'UI Attr EXP');
11696
+ prop_val.value = res.result;
10960
11697
  }
11698
+ }
10961
11699
 
10962
- if (plugin_runtime_resources.fn) {
10963
- await plugin_runtime_resources.fn(plugin_name, $elm?.[0], properties);
10964
- // await plugin_runtime_resources.fn(plugin_name, $elm?.[0], $elm.data().xu_ui_plugin.properties);
11700
+ const plugin_runtime_src = await func.utils.get_plugin_npm_cdn(SESSION_ID, plugin_name, `${_plugin.manifest['runtime.mjs'].dist ? 'dist/' : ''}runtime.mjs`);
11701
+
11702
+ const plugin_runtime_resources = await import(plugin_runtime_src);
11703
+
11704
+ if (plugin_runtime_resources.cdn && _.isArray(plugin_runtime_resources.cdn)) {
11705
+ for (const resource of plugin_runtime_resources.cdn) {
11706
+ await load_cdn(resource);
10965
11707
  }
10966
11708
  }
10967
- }
10968
11709
 
11710
+ if (plugin_runtime_resources.fn) {
11711
+ await plugin_runtime_resources.fn(plugin_name, $elm?.[0], properties);
11712
+ }
11713
+ }
10969
11714
  return {};
10970
11715
  },
11716
+
10971
11717
  'xu-store': async function ($elm, val) {
10972
11718
  try {
10973
11719
  const fields_obj = JSON5.parse(val.value);
@@ -10979,43 +11725,135 @@ func.UI.screen.execute_xu_functions = async function (SESSION_ID, is_skeleton, $
10979
11725
  }
10980
11726
  return {};
10981
11727
  },
11728
+
10982
11729
  'xu-viewport': async function ($elm, val) {
10983
- // functionality in draw_html_element
10984
11730
  return {};
10985
11731
  },
10986
11732
  };
10987
11733
 
10988
- if (nodeP.tagName.substr(0, 3) === 'xu-') {
11734
+ const tag_fx = {
11735
+ 'xu-panel': {
11736
+ program: async function ($elm, val) {
11737
+ const init_program = async function () {
11738
+ async function render_panel() {
11739
+ const prog_id = val.value?.prog || val.value;
11740
+ const params_obj = await get_params_obj_new(SESSION_ID, prog_id, nodeP, paramsP.dsSessionP);
11741
+ const ret_panel = await func.UI.screen.init(SESSION_ID, prog_id, paramsP.screenId, _ds, $elm, null, _ds.currentRecordId, null, true, params_obj.params_res, 'initXu_panel', undefined, prog_id !== _ds.prog_id ? null : refreshed_ds, params_obj.params_raw);
11742
+
11743
+ const containerData = $container.data();
11744
+ if (containerData.xuData) {
11745
+ containerData.xuData.xuPanelProps = elmData.xuAttributes;
11746
+ containerData.xuData.xuPanelData = ret_panel.data();
11747
+ }
11748
+ return { $new_div: ret_panel };
11749
+ }
11750
+
11751
+ if (!val.value) val.value = '_empty_panel_program';
11752
+ return await render_panel();
11753
+ };
11754
+
11755
+ const alter_program = async function () {
11756
+ async function render_panel() {
11757
+ const program = val.value?.prog || val.value;
11758
+ const $wrapper = $('<div>');
11759
+ const $div = await func.UI.screen.create_container(SESSION_ID, $root_container, nodeP, $container, paramsP, parent_infoP, jobNoP, keyP, parent_nodeP, nodeP.attributes, null, null, null, $wrapper, '');
11760
+
11761
+ const params_obj = await get_params_obj_new(SESSION_ID, program, nodeP, paramsP.dsSessionP);
11762
+ const ret_init = await func.UI.screen.init(SESSION_ID, program, paramsP.screenId, _ds, $div, null, _ds.currentRecordId, jobNoP, true, params_obj.params_res, 'alterXu_panel', undefined, undefined, params_obj.params_raw);
11763
+
11764
+ await func.UI.screen.panel_post_render_handler(SESSION_ID, $elm, ret_init, nodeP, $div.clone(true), jobNoP);
11765
+
11766
+ return { $new_div: ret_init, abort: true };
11767
+ }
11768
+
11769
+ if (!val.value) return { abort: true };
11770
+ await render_panel();
11771
+ return { abort: true };
11772
+ };
11773
+
11774
+ return is_init ? await init_program() : await alter_program();
11775
+ },
11776
+
11777
+ 'xu-render': async function ($elm, val) {
11778
+ return await common_fx['xu-render']($elm, val, true);
11779
+ },
11780
+
11781
+ 'xu-ref': async function ($elm, val) {
11782
+ return await common_fx['xu-ref']($container, val, $container.data().xuData.xuPanelData.xuData.paramsP.dsSessionP);
11783
+ },
11784
+ },
11785
+
11786
+ 'xu-teleport': {
11787
+ to: async function ($elm, val) {
11788
+ if (!glb.new_xu_render && val.value) {
11789
+ if ($elm?.parent()?.data()?.xuData?.length) {
11790
+ $elm.parent().data('xuTeleportData', []);
11791
+ for (const [key, node] of Object.entries(nodeP.children)) {
11792
+ const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $(val.value), node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
11793
+ $elm.parent().data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
11794
+ $teleport_elm.attr('xu-teleport-parent-id', $elm.parent().attr('xu-ui-id'));
11795
+ }
11796
+ $elm.remove();
11797
+ } else {
11798
+ $elm.data('xuTeleportData', []).attr('hidden', true);
11799
+ for (const [key, node] of Object.entries(nodeP.children)) {
11800
+ const $to_container = $(val.value);
11801
+ if (!$to_container?.length) {
11802
+ return console.error(`container ${val.value} for xuTeleportData not found`);
11803
+ }
11804
+ const $teleport_elm = await func.UI.screen.render_ui_tree(SESSION_ID, $to_container, node, parent_infoP, paramsP, jobNoP, is_skeleton, Number(key), null, node, null, $root_container);
11805
+ $elm.data().xuTeleportData.push($teleport_elm.attr('xu-ui-id'));
11806
+ $teleport_elm.attr('xu-teleport-parent-id', $elm.attr('xu-ui-id'));
11807
+ }
11808
+ }
11809
+ return { abort: true };
11810
+ }
11811
+ return {};
11812
+ },
11813
+
11814
+ 'xu-render': async function ($elm, val) {
11815
+ return await common_fx['xu-render']($elm, val, true);
11816
+ },
11817
+
11818
+ 'xu-show': async function ($elm, val) {
11819
+ return await common_fx['xu-show']($elm, val, true);
11820
+ },
11821
+ },
11822
+ };
11823
+
11824
+ // Main execution logic
11825
+ if (isXuTag) {
10989
11826
  if (xu_func === 'xu-exp') {
10990
11827
  return common_fx[xu_func]($elm, val);
10991
11828
  }
10992
11829
 
10993
- if (tag_fx?.[nodeP.tagName]?.[xu_func]) {
10994
- let ret = await tag_fx[nodeP.tagName][xu_func]($elm, val);
10995
- return ret;
11830
+ if (tag_fx?.[nodeTag]?.[xu_func]) {
11831
+ return await tag_fx[nodeTag][xu_func]($elm, val);
10996
11832
  }
10997
- // if (xu_func !== "tree_id")
10998
- console.warn(`attribute ${xu_func} not found for ${nodeP.tagName}`);
10999
- return {};
11000
- }
11001
- if (_.isEmpty($elm.data())) {
11833
+
11834
+ console.warn(`attribute ${xu_func} not found for ${nodeTag}`);
11002
11835
  return {};
11003
11836
  }
11004
- if (!$elm.data().xuData.debug_info.attribute_stat) {
11005
- $elm.data().xuData.debug_info.attribute_stat = {};
11837
+
11838
+ if (_.isEmpty(elmData)) return {};
11839
+
11840
+ if (!xuData.debug_info.attribute_stat) {
11841
+ xuData.debug_info.attribute_stat = {};
11006
11842
  }
11843
+
11007
11844
  if (xu_func !== 'xu-exp') {
11008
- $elm.data().xuData.debug_info.attribute_stat[xu_func] = val.value;
11845
+ xuData.debug_info.attribute_stat[xu_func] = val.value;
11009
11846
  }
11847
+
11010
11848
  try {
11011
11849
  if (!common_fx[xu_func]) {
11012
- console.warn('invalid xu-tag', xu_func, error);
11850
+ console.warn('invalid xu-tag', xu_func);
11013
11851
  return {};
11014
11852
  }
11015
-
11016
11853
  return await common_fx[xu_func]($elm, val);
11017
11854
  } catch (error) {
11018
- debugger;
11855
+ console.error('execute_xu_functions error:', error);
11856
+ return {};
11019
11857
  }
11020
11858
  };
11021
11859