@wavemaker/app-ng-runtime 11.14.1-1.6289 → 11.14.1-10.6348
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.
- package/components/base/bundles/index.umd.js +86 -17
- package/components/base/esm2022/pipes/custom-pipes.mjs +10 -10
- package/components/base/esm2022/utils/widget-utils.mjs +3 -3
- package/components/base/esm2022/widgets/common/base/base.component.mjs +67 -7
- package/components/base/esm2022/widgets/common/lazy-load/lazy-load.directive.mjs +7 -3
- package/components/base/esm2022/widgets/framework/property-change-handler.mjs +7 -2
- package/components/base/fesm2022/index.mjs +87 -18
- package/components/base/fesm2022/index.mjs.map +1 -1
- package/components/base/pipes/custom-pipes.d.ts +5 -5
- package/components/basic/label/bundles/index.umd.js +9 -1
- package/components/basic/label/esm2022/label.directive.mjs +10 -2
- package/components/basic/label/fesm2022/index.mjs +9 -1
- package/components/basic/label/fesm2022/index.mjs.map +1 -1
- package/components/data/pagination/bundles/index.umd.js +4 -0
- package/components/data/pagination/esm2022/pagination.component.mjs +5 -1
- package/components/data/pagination/fesm2022/index.mjs +4 -0
- package/components/data/pagination/fesm2022/index.mjs.map +1 -1
- package/components/data/table/bundles/index.umd.js +371 -15
- package/components/data/table/esm2022/table-action/table-action.directive.mjs +8 -1
- package/components/data/table/esm2022/table-column/table-column.directive.mjs +107 -3
- package/components/data/table/esm2022/table-column-group/table-column-group.directive.mjs +9 -1
- package/components/data/table/esm2022/table-cud.directive.mjs +8 -2
- package/components/data/table/esm2022/table-filter.directive.mjs +12 -2
- package/components/data/table/esm2022/table-row/table-row.directive.mjs +8 -1
- package/components/data/table/esm2022/table-row-action/table-row-action.directive.mjs +8 -1
- package/components/data/table/esm2022/table.component.mjs +219 -12
- package/components/data/table/fesm2022/index.mjs +371 -15
- package/components/data/table/fesm2022/index.mjs.map +1 -1
- package/components/data/table/table-action/table-action.directive.d.ts +3 -2
- package/components/data/table/table-column/table-column.directive.d.ts +3 -2
- package/components/data/table/table-column-group/table-column-group.directive.d.ts +3 -2
- package/components/data/table/table-cud.directive.d.ts +3 -1
- package/components/data/table/table-filter.directive.d.ts +3 -1
- package/components/data/table/table-row/table-row.directive.d.ts +3 -2
- package/components/data/table/table-row-action/table-row-action.directive.d.ts +3 -2
- package/components/data/table/table.component.d.ts +6 -2
- package/components/navigation/menu/bundles/index.umd.js +5 -0
- package/components/navigation/menu/esm2022/menu.component.mjs +6 -1
- package/components/navigation/menu/fesm2022/index.mjs +5 -0
- package/components/navigation/menu/fesm2022/index.mjs.map +1 -1
- package/components/navigation/popover/bundles/index.umd.js +6 -6
- package/components/navigation/popover/esm2022/popover.component.mjs +4 -4
- package/components/navigation/popover/fesm2022/index.mjs +3 -3
- package/components/navigation/popover/fesm2022/index.mjs.map +1 -1
- package/components/navigation/popover/popover.component.d.ts +6 -0
- package/core/bundles/index.umd.js +411 -82
- package/core/esm2022/public_api.mjs +3 -3
- package/core/esm2022/utils/utils.mjs +6 -2
- package/core/esm2022/utils/watcher.mjs +402 -81
- package/core/fesm2022/index.mjs +410 -84
- package/core/fesm2022/index.mjs.map +1 -1
- package/core/public_api.d.ts +2 -2
- package/core/utils/utils.d.ts +1 -0
- package/core/utils/watcher.d.ts +28 -5
- package/npm-shrinkwrap.json +2 -2
- package/package-lock.json +2 -2
- package/package.json +1 -1
- package/runtime/base/bundles/index.umd.js +22 -2
- package/runtime/base/esm2022/components/app-component/app.component.mjs +4 -2
- package/runtime/base/esm2022/components/base-page.component.mjs +6 -2
- package/runtime/base/esm2022/components/base-partial.component.mjs +7 -2
- package/runtime/base/esm2022/components/base-prefab.component.mjs +7 -2
- package/runtime/base/esm2022/components/base-spa-page.component.mjs +6 -2
- package/runtime/base/esm2022/services/pipe-provider.service.mjs +4 -4
- package/runtime/base/fesm2022/index.mjs +23 -3
- package/runtime/base/fesm2022/index.mjs.map +1 -1
- package/scripts/datatable/datatable.js +101 -15
package/core/fesm2022/index.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Attribute, ImplicitReceiver, PropertyRead, LiteralPrimitive, LiteralArray, LiteralMap, PropertyWrite, KeyedRead, PrefixNot, Unary, Binary, Conditional, Call, Chain, BindingPipe, Parser, Lexer } from '@angular/compiler';
|
|
2
|
-
import { isArray, startsWith, includes, get, flatten, isEqual, isObject as isObject$1,
|
|
2
|
+
import { isArray, startsWith, includes, get, flatten, isEqual, clone, isObject as isObject$1, camelCase, split, map, attempt, isError, isFunction, isDate, isString, cloneDeep, identity, intersection, omit, keys, toLower, replace as replace$1, forEach, trim, isEqualWith, every, indexOf, isNumber, filter, isUndefined, isNull, noop as noop$2, toUpper, assign, merge, isEmpty, debounce as debounce$1, isNil } from 'lodash-es';
|
|
3
3
|
import { Subject } from 'rxjs';
|
|
4
4
|
import X2JS from 'x2js';
|
|
5
5
|
import * as momentLib from 'moment-timezone/moment-timezone';
|
|
@@ -1432,11 +1432,11 @@ const CURRENCY_INFO = {
|
|
|
1432
1432
|
}
|
|
1433
1433
|
};
|
|
1434
1434
|
|
|
1435
|
-
const $RAF
|
|
1435
|
+
const $RAF = window.requestAnimationFrame;
|
|
1436
1436
|
const $RAFQueue = [];
|
|
1437
1437
|
const invokeLater = fn => {
|
|
1438
1438
|
if (!$RAFQueue.length) {
|
|
1439
|
-
$RAF
|
|
1439
|
+
$RAF(() => {
|
|
1440
1440
|
$RAFQueue.forEach(f => f());
|
|
1441
1441
|
$RAFQueue.length = 0;
|
|
1442
1442
|
});
|
|
@@ -2173,14 +2173,99 @@ const getFnForEventExpr = (expr) => {
|
|
|
2173
2173
|
return fnExecutor(expr, ExpressionType.Action);
|
|
2174
2174
|
};
|
|
2175
2175
|
|
|
2176
|
+
// Constants
|
|
2177
|
+
const WIDGET_ID_REGEX = /^(widget-[^_]+)/;
|
|
2178
|
+
const WIDGET_PROPERTY_REGEX = /^widget-[^_]+_(.+)$/;
|
|
2179
|
+
const ARRAY_INDEX_PLACEHOLDER = '[$i]';
|
|
2180
|
+
const ARRAY_INDEX_ZERO = '[0]';
|
|
2181
|
+
const DEBOUNCE_WAIT = 100;
|
|
2182
|
+
const MAX_WATCH_CYCLES = 5;
|
|
2176
2183
|
const registry = new Map();
|
|
2177
2184
|
const watchIdGenerator = new IDGenerator('watch-id-');
|
|
2178
|
-
const FIRST_TIME_WATCH = {};
|
|
2179
|
-
|
|
2180
|
-
const isFirstTimeChange = v => v === FIRST_TIME_WATCH;
|
|
2185
|
+
const FIRST_TIME_WATCH = Object.freeze({});
|
|
2186
|
+
// State
|
|
2181
2187
|
let muted = false;
|
|
2188
|
+
let changedByWatch = false;
|
|
2189
|
+
let skipWatchers = false;
|
|
2190
|
+
let ngZone;
|
|
2182
2191
|
let appRef;
|
|
2183
|
-
|
|
2192
|
+
/********************************************************************
|
|
2193
|
+
* CLEANUP SCHEDULER WITH:
|
|
2194
|
+
* - Significant watcher delta trigger (+/-)
|
|
2195
|
+
* - UI stabilization delay (1–2 seconds)
|
|
2196
|
+
* - Cooldown to prevent repeated scheduling
|
|
2197
|
+
********************************************************************/
|
|
2198
|
+
const CLEANUP_TRIGGER_DELTA = 300; // watcher change threshold
|
|
2199
|
+
const CLEANUP_DELAY = 1500; // delay before running cleanup
|
|
2200
|
+
const CLEANUP_COOLDOWN = 4000; // prevent re-scheduling for 4s
|
|
2201
|
+
let lastWatcherCount = 0;
|
|
2202
|
+
let scheduledCleanup = null;
|
|
2203
|
+
let lastScheduledTime = 0;
|
|
2204
|
+
function getWatcherCount() {
|
|
2205
|
+
let count = 0;
|
|
2206
|
+
registry.forEach((value) => {
|
|
2207
|
+
// Check if it's a grouped structure (widget groups) or a direct watchInfo
|
|
2208
|
+
if (value && typeof value === 'object' && !value.fn) {
|
|
2209
|
+
// It's a widget group - count the properties (excluding metadata)
|
|
2210
|
+
count += Object.keys(value).filter(k => k !== 'scopeType' && k !== 'scopeName').length;
|
|
2211
|
+
}
|
|
2212
|
+
else {
|
|
2213
|
+
// It's a direct watchInfo
|
|
2214
|
+
count += 1;
|
|
2215
|
+
}
|
|
2216
|
+
});
|
|
2217
|
+
return count;
|
|
2218
|
+
}
|
|
2219
|
+
const cleanupStaleWatchers = () => {
|
|
2220
|
+
// console.log(".........Cleaning up stale watchers...registry.size....", registry.size);
|
|
2221
|
+
let removed = 0;
|
|
2222
|
+
registry.forEach((bucket, widgetId) => {
|
|
2223
|
+
if (!document.querySelector(`[widget-id="${widgetId}"]`)) {
|
|
2224
|
+
for (const key in bucket) {
|
|
2225
|
+
if (bucket.hasOwnProperty(key) && key !== "scopeType" && key !== "scopeName" && typeof bucket[key] !== "function") {
|
|
2226
|
+
let watchInfo = bucket[key];
|
|
2227
|
+
if (watchInfo && watchInfo.destroyFn) {
|
|
2228
|
+
watchInfo.destroyFn();
|
|
2229
|
+
}
|
|
2230
|
+
}
|
|
2231
|
+
}
|
|
2232
|
+
removed++;
|
|
2233
|
+
registry.delete(widgetId);
|
|
2234
|
+
return;
|
|
2235
|
+
}
|
|
2236
|
+
});
|
|
2237
|
+
return removed;
|
|
2238
|
+
};
|
|
2239
|
+
const scheduleThresholdCleanup = () => {
|
|
2240
|
+
const now = performance.now();
|
|
2241
|
+
let lastTriggerPeriod = now - lastScheduledTime;
|
|
2242
|
+
// If a cleanup was scheduled recently, skip scheduling
|
|
2243
|
+
if (lastTriggerPeriod < CLEANUP_COOLDOWN) {
|
|
2244
|
+
return;
|
|
2245
|
+
}
|
|
2246
|
+
const current = getWatcherCount();
|
|
2247
|
+
const delta = Math.abs(current - lastWatcherCount); // significant + or -
|
|
2248
|
+
// If change not large enough, skip scheduling
|
|
2249
|
+
if (delta <= CLEANUP_TRIGGER_DELTA) {
|
|
2250
|
+
lastWatcherCount = current;
|
|
2251
|
+
return;
|
|
2252
|
+
}
|
|
2253
|
+
// Prevent re-scheduling: set timestamp early
|
|
2254
|
+
lastScheduledTime = now;
|
|
2255
|
+
// Clear previous scheduled cleanup (if any)
|
|
2256
|
+
if (scheduledCleanup) {
|
|
2257
|
+
clearTimeout(scheduledCleanup);
|
|
2258
|
+
}
|
|
2259
|
+
// Schedule cleanup after UI stabilizes (delay prevents aggressive cleanup)
|
|
2260
|
+
scheduledCleanup = setTimeout(() => {
|
|
2261
|
+
cleanupStaleWatchers();
|
|
2262
|
+
scheduledCleanup = null;
|
|
2263
|
+
}, CLEANUP_DELAY);
|
|
2264
|
+
lastWatcherCount = current;
|
|
2265
|
+
};
|
|
2266
|
+
// Utility functions
|
|
2267
|
+
const isFirstTimeChange = (v) => v === FIRST_TIME_WATCH;
|
|
2268
|
+
const debounce = (fn, wait = DEBOUNCE_WAIT) => {
|
|
2184
2269
|
let timeout;
|
|
2185
2270
|
return (...args) => {
|
|
2186
2271
|
window['__zone_symbol__clearTimeout'](timeout);
|
|
@@ -2194,115 +2279,350 @@ const unMuteWatchers = () => {
|
|
|
2194
2279
|
muted = false;
|
|
2195
2280
|
triggerWatchers();
|
|
2196
2281
|
};
|
|
2282
|
+
/**
|
|
2283
|
+
* Extracts widget ID from identifier (e.g., "widget-id23_eventsource" -> "widget-id23")
|
|
2284
|
+
*/
|
|
2285
|
+
const getWidgetId = (identifier) => {
|
|
2286
|
+
if (!identifier || typeof identifier !== 'string') {
|
|
2287
|
+
return null;
|
|
2288
|
+
}
|
|
2289
|
+
const match = identifier.match(WIDGET_ID_REGEX);
|
|
2290
|
+
return match ? match[1] : null;
|
|
2291
|
+
};
|
|
2292
|
+
/**
|
|
2293
|
+
* Extracts property name from identifier (e.g., "widget-id23_eventsource" -> "eventsource")
|
|
2294
|
+
*/
|
|
2295
|
+
const getPropertyName = (identifier) => {
|
|
2296
|
+
if (!identifier || typeof identifier !== 'string') {
|
|
2297
|
+
return identifier;
|
|
2298
|
+
}
|
|
2299
|
+
const match = identifier.match(WIDGET_PROPERTY_REGEX);
|
|
2300
|
+
return match ? match[1] : identifier;
|
|
2301
|
+
};
|
|
2302
|
+
/**
|
|
2303
|
+
* Array consumer wrapper for array-based expressions
|
|
2304
|
+
*/
|
|
2197
2305
|
const arrayConsumer = (listenerFn, restExpr, newVal, oldVal) => {
|
|
2198
|
-
|
|
2199
|
-
|
|
2200
|
-
formattedData = data.map(function (datum) {
|
|
2201
|
-
return findValueOf(datum, restExpr);
|
|
2202
|
-
});
|
|
2203
|
-
// If resulting structure is an array of array, flatten it
|
|
2204
|
-
if (isArray(formattedData[0])) {
|
|
2205
|
-
formattedData = flatten(formattedData);
|
|
2206
|
-
}
|
|
2207
|
-
listenerFn(formattedData, oldVal);
|
|
2306
|
+
if (!isArray(newVal)) {
|
|
2307
|
+
return;
|
|
2208
2308
|
}
|
|
2309
|
+
let formattedData = newVal.map(datum => findValueOf(datum, restExpr));
|
|
2310
|
+
// Flatten if result is array of arrays
|
|
2311
|
+
if (isArray(formattedData[0])) {
|
|
2312
|
+
formattedData = flatten(formattedData);
|
|
2313
|
+
}
|
|
2314
|
+
listenerFn(formattedData, oldVal);
|
|
2209
2315
|
};
|
|
2210
|
-
|
|
2211
|
-
|
|
2212
|
-
|
|
2213
|
-
|
|
2316
|
+
/**
|
|
2317
|
+
* Updates watch info for array expressions
|
|
2318
|
+
*/
|
|
2319
|
+
const getUpdatedWatchInfo = (expr, acceptsArray, listener) => {
|
|
2320
|
+
const regex = /\[\$i\]/g;
|
|
2214
2321
|
if (!acceptsArray) {
|
|
2215
2322
|
return {
|
|
2216
|
-
|
|
2217
|
-
|
|
2323
|
+
expr: expr.replace(regex, ARRAY_INDEX_ZERO),
|
|
2324
|
+
listener
|
|
2218
2325
|
};
|
|
2219
2326
|
}
|
|
2220
|
-
|
|
2221
|
-
|
|
2222
|
-
|
|
2223
|
-
|
|
2224
|
-
|
|
2225
|
-
|
|
2327
|
+
const lastIndex = expr.lastIndexOf(ARRAY_INDEX_PLACEHOLDER);
|
|
2328
|
+
const baseExpr = expr.substring(0, lastIndex).replace(ARRAY_INDEX_PLACEHOLDER, ARRAY_INDEX_ZERO);
|
|
2329
|
+
const restExpr = expr.substring(lastIndex + 5);
|
|
2330
|
+
const arrayConsumerFn = restExpr
|
|
2331
|
+
? arrayConsumer.bind(undefined, listener, restExpr)
|
|
2332
|
+
: listener;
|
|
2226
2333
|
return {
|
|
2227
|
-
|
|
2228
|
-
|
|
2334
|
+
expr: baseExpr,
|
|
2335
|
+
listener: arrayConsumerFn
|
|
2229
2336
|
};
|
|
2230
2337
|
};
|
|
2338
|
+
/**
|
|
2339
|
+
* Determines if an expression is static (doesn't need to be watched)
|
|
2340
|
+
*/
|
|
2341
|
+
const STATIC_EXPRESSION_NAMES = [
|
|
2342
|
+
"row.getProperty('investment')",
|
|
2343
|
+
"row.getProperty('factsheetLink')",
|
|
2344
|
+
"row.getProperty('isRebalanceEligible')"
|
|
2345
|
+
];
|
|
2346
|
+
const isStaticExpression = (expr) => {
|
|
2347
|
+
if (typeof expr !== 'string') {
|
|
2348
|
+
return false;
|
|
2349
|
+
}
|
|
2350
|
+
const trimmedExpr = expr.trim();
|
|
2351
|
+
// Expressions that always evaluate to localization strings
|
|
2352
|
+
// if (trimmedExpr.includes('appLocale')) {
|
|
2353
|
+
// return true;
|
|
2354
|
+
// }
|
|
2355
|
+
// Hard-coded static expression names
|
|
2356
|
+
if (STATIC_EXPRESSION_NAMES.includes(trimmedExpr)) {
|
|
2357
|
+
return true;
|
|
2358
|
+
}
|
|
2359
|
+
return false;
|
|
2360
|
+
};
|
|
2361
|
+
/**
|
|
2362
|
+
* Gets the scope type from the scope object
|
|
2363
|
+
*/
|
|
2364
|
+
const getScopeType = ($scope) => {
|
|
2365
|
+
if (!$scope) {
|
|
2366
|
+
return null;
|
|
2367
|
+
}
|
|
2368
|
+
if ($scope.pageName)
|
|
2369
|
+
return 'Page';
|
|
2370
|
+
if ($scope.prefabName)
|
|
2371
|
+
return 'Prefab';
|
|
2372
|
+
if ($scope.partialName)
|
|
2373
|
+
return 'Partial';
|
|
2374
|
+
// Check for App scope
|
|
2375
|
+
if ($scope.Variables !== undefined &&
|
|
2376
|
+
$scope.Actions !== undefined &&
|
|
2377
|
+
!$scope.pageName &&
|
|
2378
|
+
!$scope.prefabName &&
|
|
2379
|
+
!$scope.partialName) {
|
|
2380
|
+
return 'App';
|
|
2381
|
+
}
|
|
2382
|
+
if ($scope.constructor?.name === 'AppRef') {
|
|
2383
|
+
return 'App';
|
|
2384
|
+
}
|
|
2385
|
+
return null;
|
|
2386
|
+
};
|
|
2387
|
+
/**
|
|
2388
|
+
* Gets scope name based on scope type
|
|
2389
|
+
*/
|
|
2390
|
+
const getScopeName = ($scope, scopeType) => {
|
|
2391
|
+
if (!scopeType || !$scope) {
|
|
2392
|
+
return null;
|
|
2393
|
+
}
|
|
2394
|
+
switch (scopeType) {
|
|
2395
|
+
case 'Prefab': return $scope.prefabName || null;
|
|
2396
|
+
case 'Partial': return $scope.partialName || null;
|
|
2397
|
+
case 'Page': return $scope.pageName || null;
|
|
2398
|
+
default: return null;
|
|
2399
|
+
}
|
|
2400
|
+
};
|
|
2401
|
+
/**
|
|
2402
|
+
* Main watch function
|
|
2403
|
+
*/
|
|
2231
2404
|
const $watch = (expr, $scope, $locals, listener, identifier = watchIdGenerator.nextUid(), doNotClone = false, config = {}, isMuted) => {
|
|
2232
|
-
|
|
2233
|
-
|
|
2405
|
+
// Handle array expressions
|
|
2406
|
+
if (expr.includes(ARRAY_INDEX_PLACEHOLDER)) {
|
|
2407
|
+
const watchInfo = getUpdatedWatchInfo(expr, config.arrayType || config.isList || false, listener);
|
|
2234
2408
|
expr = watchInfo.expr;
|
|
2235
2409
|
listener = watchInfo.listener;
|
|
2236
2410
|
}
|
|
2411
|
+
// Handle static expressions
|
|
2412
|
+
if (isStaticExpression(expr)) {
|
|
2413
|
+
try {
|
|
2414
|
+
const fn = $parseExpr(expr);
|
|
2415
|
+
const staticValue = fn($scope, $locals);
|
|
2416
|
+
listener(staticValue, FIRST_TIME_WATCH);
|
|
2417
|
+
}
|
|
2418
|
+
catch (e) {
|
|
2419
|
+
console.warn(`Error evaluating static expression '${expr}':`, e);
|
|
2420
|
+
listener(undefined, FIRST_TIME_WATCH);
|
|
2421
|
+
}
|
|
2422
|
+
return () => { }; // No-op unsubscribe
|
|
2423
|
+
}
|
|
2237
2424
|
const fn = $parseExpr(expr);
|
|
2238
|
-
|
|
2239
|
-
|
|
2425
|
+
const scopeType = getScopeType($scope);
|
|
2426
|
+
const scopeName = getScopeName($scope, scopeType);
|
|
2427
|
+
const destroyFn = () => $unwatch(identifier);
|
|
2428
|
+
const watchInfo = {
|
|
2429
|
+
fn: fn.bind(null, $scope, $locals),
|
|
2240
2430
|
listener,
|
|
2241
2431
|
expr,
|
|
2242
2432
|
last: FIRST_TIME_WATCH,
|
|
2243
2433
|
doNotClone,
|
|
2244
|
-
isMuted
|
|
2434
|
+
isMuted,
|
|
2435
|
+
scopeType,
|
|
2436
|
+
scopeName,
|
|
2437
|
+
destroyFn
|
|
2438
|
+
};
|
|
2439
|
+
// Store in registry
|
|
2440
|
+
const widgetId = getWidgetId(identifier);
|
|
2441
|
+
if (widgetId) {
|
|
2442
|
+
const propertyName = getPropertyName(identifier);
|
|
2443
|
+
if (!registry.has(widgetId)) {
|
|
2444
|
+
registry.set(widgetId, {});
|
|
2445
|
+
}
|
|
2446
|
+
const widgetGroup = registry.get(widgetId);
|
|
2447
|
+
widgetGroup[propertyName] = watchInfo;
|
|
2448
|
+
}
|
|
2449
|
+
else {
|
|
2450
|
+
registry.set(identifier, watchInfo);
|
|
2451
|
+
}
|
|
2452
|
+
return destroyFn;
|
|
2453
|
+
};
|
|
2454
|
+
/**
|
|
2455
|
+
* Unwatches a single identifier
|
|
2456
|
+
*/
|
|
2457
|
+
const $unwatch = (identifier) => {
|
|
2458
|
+
const widgetId = getWidgetId(identifier);
|
|
2459
|
+
if (widgetId) {
|
|
2460
|
+
const propertyName = getPropertyName(identifier);
|
|
2461
|
+
const widgetGroup = registry.get(widgetId);
|
|
2462
|
+
//@ts-ignore
|
|
2463
|
+
if (widgetGroup && typeof widgetGroup === 'object' && !widgetGroup.fn) {
|
|
2464
|
+
const watchInfo = widgetGroup[propertyName];
|
|
2465
|
+
if (watchInfo) {
|
|
2466
|
+
delete widgetGroup[propertyName];
|
|
2467
|
+
// Clean up empty widget groups
|
|
2468
|
+
if (Object.keys(widgetGroup).length === 0) {
|
|
2469
|
+
registry.delete(widgetId);
|
|
2470
|
+
}
|
|
2471
|
+
return true;
|
|
2472
|
+
}
|
|
2473
|
+
}
|
|
2474
|
+
}
|
|
2475
|
+
// Fallback to direct lookup
|
|
2476
|
+
if (registry.has(identifier)) {
|
|
2477
|
+
registry.delete(identifier);
|
|
2478
|
+
return true;
|
|
2479
|
+
}
|
|
2480
|
+
return false;
|
|
2481
|
+
};
|
|
2482
|
+
/**
|
|
2483
|
+
* Unwatches all watchers for a specific widget ID
|
|
2484
|
+
*/
|
|
2485
|
+
const $unwatchAll = (widgetId) => {
|
|
2486
|
+
if (!widgetId || typeof widgetId !== 'string') {
|
|
2487
|
+
return 0;
|
|
2488
|
+
}
|
|
2489
|
+
const widgetGroup = registry.get(widgetId);
|
|
2490
|
+
if (widgetGroup && typeof widgetGroup === 'object' && !widgetGroup.fn) {
|
|
2491
|
+
const count = Object.keys(widgetGroup).length;
|
|
2492
|
+
registry.delete(widgetId);
|
|
2493
|
+
return count;
|
|
2494
|
+
}
|
|
2495
|
+
// Fallback: find all identifiers starting with this widget ID
|
|
2496
|
+
let removedCount = 0;
|
|
2497
|
+
const identifiersToRemove = [];
|
|
2498
|
+
registry.forEach((_, key) => {
|
|
2499
|
+
if (key.startsWith(widgetId + '_')) {
|
|
2500
|
+
identifiersToRemove.push(key);
|
|
2501
|
+
}
|
|
2502
|
+
});
|
|
2503
|
+
identifiersToRemove.forEach(identifier => {
|
|
2504
|
+
if ($unwatch(identifier)) {
|
|
2505
|
+
removedCount++;
|
|
2506
|
+
}
|
|
2245
2507
|
});
|
|
2246
|
-
return
|
|
2508
|
+
return removedCount;
|
|
2247
2509
|
};
|
|
2248
|
-
|
|
2249
|
-
|
|
2250
|
-
|
|
2251
|
-
|
|
2252
|
-
const
|
|
2510
|
+
/**
|
|
2511
|
+
* Unwatches all watchers for a specific scope (Page, Prefab, Partial, or App)
|
|
2512
|
+
* Now works directly with the main registry instead of separate scoped registries
|
|
2513
|
+
*/
|
|
2514
|
+
const $unwatchAllByScope = (scopeType, scopeName) => {
|
|
2515
|
+
if (!scopeType) {
|
|
2516
|
+
return 0;
|
|
2517
|
+
}
|
|
2518
|
+
let removedCount = 0;
|
|
2519
|
+
const identifiersToRemove = [];
|
|
2520
|
+
registry.forEach((value, key) => {
|
|
2521
|
+
// Handle grouped structure (widget groups)
|
|
2522
|
+
if (value && typeof value === 'object' && !value.fn) {
|
|
2523
|
+
Object.entries(value).forEach(([propertyName, watchInfo]) => {
|
|
2524
|
+
if (watchInfo?.scopeType === scopeType &&
|
|
2525
|
+
(!scopeName || watchInfo.scopeName === scopeName)) {
|
|
2526
|
+
identifiersToRemove.push(`${key}_${propertyName}`);
|
|
2527
|
+
}
|
|
2528
|
+
});
|
|
2529
|
+
}
|
|
2530
|
+
else {
|
|
2531
|
+
// Direct watchInfo
|
|
2532
|
+
const watchInfo = value;
|
|
2533
|
+
if (watchInfo?.scopeType === scopeType &&
|
|
2534
|
+
(!scopeName || watchInfo.scopeName === scopeName)) {
|
|
2535
|
+
identifiersToRemove.push(key);
|
|
2536
|
+
}
|
|
2537
|
+
}
|
|
2538
|
+
});
|
|
2539
|
+
// Unwatch all collected identifiers
|
|
2540
|
+
identifiersToRemove.forEach(identifier => {
|
|
2541
|
+
if ($unwatch(identifier)) {
|
|
2542
|
+
removedCount++;
|
|
2543
|
+
}
|
|
2544
|
+
});
|
|
2545
|
+
return removedCount;
|
|
2546
|
+
};
|
|
2547
|
+
/**
|
|
2548
|
+
* Processes a single watch info during trigger cycle
|
|
2549
|
+
*/
|
|
2550
|
+
const processWatchInfo = (watchInfo) => {
|
|
2551
|
+
if (!watchInfo?.fn || (watchInfo.isMuted?.() ?? false)) {
|
|
2552
|
+
return false;
|
|
2553
|
+
}
|
|
2554
|
+
let newValue;
|
|
2555
|
+
try {
|
|
2556
|
+
newValue = watchInfo.fn();
|
|
2557
|
+
}
|
|
2558
|
+
catch (e) {
|
|
2559
|
+
console.warn(`Error executing expression: '${watchInfo.expr}'`, e);
|
|
2560
|
+
return false;
|
|
2561
|
+
}
|
|
2562
|
+
if (isEqual(newValue, watchInfo.last)) {
|
|
2563
|
+
return false;
|
|
2564
|
+
}
|
|
2565
|
+
// Change detected
|
|
2566
|
+
changedByWatch = true;
|
|
2567
|
+
watchInfo.last = isObject$1(newValue) && !watchInfo.doNotClone
|
|
2568
|
+
? clone(newValue)
|
|
2569
|
+
: newValue;
|
|
2570
|
+
watchInfo.listener(newValue, watchInfo.last === newValue ? FIRST_TIME_WATCH : watchInfo.last);
|
|
2571
|
+
changedByWatch = false;
|
|
2572
|
+
return true;
|
|
2573
|
+
};
|
|
2574
|
+
/**
|
|
2575
|
+
* Triggers all watchers
|
|
2576
|
+
*/
|
|
2577
|
+
const triggerWatchers = (ignoreMuted = false) => {
|
|
2253
2578
|
if (muted && !ignoreMuted) {
|
|
2254
2579
|
return;
|
|
2255
2580
|
}
|
|
2256
|
-
const limit = 5;
|
|
2257
2581
|
let pass = 1;
|
|
2258
2582
|
let changeDetected;
|
|
2259
2583
|
do {
|
|
2260
2584
|
changeDetected = false;
|
|
2261
|
-
registry.forEach(
|
|
2262
|
-
|
|
2263
|
-
|
|
2264
|
-
|
|
2265
|
-
|
|
2266
|
-
|
|
2267
|
-
|
|
2268
|
-
|
|
2269
|
-
try {
|
|
2270
|
-
nv = fn();
|
|
2271
|
-
}
|
|
2272
|
-
catch (e) {
|
|
2273
|
-
console.warn(`error in executing expression: '${watchInfo.expr}'`);
|
|
2585
|
+
registry.forEach((value) => {
|
|
2586
|
+
// Handle grouped structure
|
|
2587
|
+
if (value && typeof value === 'object' && !value.fn) {
|
|
2588
|
+
Object.values(value).forEach((watchInfo) => {
|
|
2589
|
+
if (processWatchInfo(watchInfo)) {
|
|
2590
|
+
changeDetected = true;
|
|
2591
|
+
}
|
|
2592
|
+
});
|
|
2274
2593
|
}
|
|
2275
|
-
|
|
2276
|
-
|
|
2277
|
-
|
|
2278
|
-
|
|
2279
|
-
// @ts-ignore
|
|
2280
|
-
if (isObject$1(nv) && !watchInfo.doNotClone && nv.__cloneable__ !== false) {
|
|
2281
|
-
watchInfo.last = clone(nv);
|
|
2594
|
+
else {
|
|
2595
|
+
// Direct watchInfo
|
|
2596
|
+
if (processWatchInfo(value)) {
|
|
2597
|
+
changeDetected = true;
|
|
2282
2598
|
}
|
|
2283
|
-
listener(nv, ov);
|
|
2284
|
-
resetChangeFromWatch();
|
|
2285
2599
|
}
|
|
2286
2600
|
});
|
|
2287
2601
|
pass++;
|
|
2288
|
-
} while (changeDetected && pass <
|
|
2289
|
-
|
|
2290
|
-
|
|
2602
|
+
} while (changeDetected && pass < MAX_WATCH_CYCLES);
|
|
2603
|
+
// Schedule cleanup after watchers are triggered
|
|
2604
|
+
scheduleThresholdCleanup();
|
|
2605
|
+
if (changeDetected && pass === MAX_WATCH_CYCLES) {
|
|
2606
|
+
console.warn(`Watch cycles exceeded limit of ${MAX_WATCH_CYCLES}`);
|
|
2291
2607
|
}
|
|
2292
2608
|
};
|
|
2293
|
-
|
|
2294
|
-
const
|
|
2609
|
+
// Angular zone integration
|
|
2610
|
+
const setNgZone = (zone) => {
|
|
2611
|
+
ngZone = zone;
|
|
2612
|
+
};
|
|
2613
|
+
const setAppRef = (ref) => {
|
|
2295
2614
|
appRef = ref;
|
|
2296
2615
|
};
|
|
2297
2616
|
const isChangeFromWatch = () => changedByWatch;
|
|
2298
|
-
const resetChangeFromWatch = () =>
|
|
2299
|
-
|
|
2300
|
-
|
|
2617
|
+
const resetChangeFromWatch = () => {
|
|
2618
|
+
changedByWatch = false;
|
|
2619
|
+
};
|
|
2620
|
+
// Debounced trigger
|
|
2301
2621
|
const debouncedTriggerWatchers = debounce(() => {
|
|
2302
2622
|
skipWatchers = true;
|
|
2303
2623
|
ngZone.run(() => triggerWatchers());
|
|
2304
|
-
},
|
|
2305
|
-
const $invokeWatchers = (force, ignoreMuted) => {
|
|
2624
|
+
}, DEBOUNCE_WAIT);
|
|
2625
|
+
const $invokeWatchers = (force = false, ignoreMuted = false) => {
|
|
2306
2626
|
if (force) {
|
|
2307
2627
|
triggerWatchers(ignoreMuted);
|
|
2308
2628
|
}
|
|
@@ -2316,7 +2636,8 @@ const $invokeWatchers = (force, ignoreMuted) => {
|
|
|
2316
2636
|
};
|
|
2317
2637
|
const $appDigest = (() => {
|
|
2318
2638
|
let queued = false;
|
|
2319
|
-
|
|
2639
|
+
const $RAF = window.requestAnimationFrame;
|
|
2640
|
+
return (force = false) => {
|
|
2320
2641
|
if (!appRef) {
|
|
2321
2642
|
return;
|
|
2322
2643
|
}
|
|
@@ -2328,16 +2649,16 @@ const $appDigest = (() => {
|
|
|
2328
2649
|
if (queued) {
|
|
2329
2650
|
return;
|
|
2330
2651
|
}
|
|
2331
|
-
|
|
2332
|
-
|
|
2333
|
-
|
|
2334
|
-
|
|
2335
|
-
|
|
2336
|
-
});
|
|
2337
|
-
}
|
|
2652
|
+
queued = true;
|
|
2653
|
+
$RAF(() => {
|
|
2654
|
+
ngZone.run(() => appRef.tick());
|
|
2655
|
+
queued = false;
|
|
2656
|
+
});
|
|
2338
2657
|
}
|
|
2339
2658
|
};
|
|
2340
2659
|
})();
|
|
2660
|
+
// Export registry for debugging
|
|
2661
|
+
window.watchRegistry = registry;
|
|
2341
2662
|
|
|
2342
2663
|
var ComponentType;
|
|
2343
2664
|
(function (ComponentType) {
|
|
@@ -2440,6 +2761,7 @@ const REGEX = {
|
|
|
2440
2761
|
MIN_PAGE_RESOURCE_PATH: /.*(page.min.html)$/,
|
|
2441
2762
|
VALID_EMAIL: /^[a-zA-Z][\w.+]+@[a-zA-Z_]+?\.[a-zA-Z.]{1,4}[a-zA-Z]$/,
|
|
2442
2763
|
VALID_WEB_URL: /^(http[s]?:\/\/)(www\.){0,1}[a-zA-Z0-9=:?\/\.\-]+(\.[a-zA-Z]{2,5}[\.]{0,1})?/,
|
|
2764
|
+
VALID_IMAGE_URL: /^(https?|blob|data|file|ftp):/i,
|
|
2443
2765
|
VALID_WEBSOCKET_URL: /^(ws[s]?:\/\/)(www\.){0,1}[a-zA-Z0-9=:?\/\.\-]+(\.[a-zA-Z]{2,5}[\.]{0,1})?/,
|
|
2444
2766
|
VALID_RELATIVE_URL: /^(?!www\.|(?:http|ftp)s?:\/\/|[A-Za-z]:\\|\/\/).*/,
|
|
2445
2767
|
REPLACE_PATTERN: /\$\{([^\}]+)\}/g,
|
|
@@ -2673,6 +2995,9 @@ const isVideoFile = (fileName) => {
|
|
|
2673
2995
|
const isValidWebURL = (url) => {
|
|
2674
2996
|
return (REGEX.VALID_WEB_URL).test(url);
|
|
2675
2997
|
};
|
|
2998
|
+
const isValidImageUrl = (url) => {
|
|
2999
|
+
return (REGEX.VALID_IMAGE_URL).test(url?.trim());
|
|
3000
|
+
};
|
|
2676
3001
|
/*This function returns the url to the resource after checking the validity of url*/
|
|
2677
3002
|
const getResourceURL = (urlString) => {
|
|
2678
3003
|
if (isValidWebURL(urlString)) {
|
|
@@ -3938,6 +4263,7 @@ var Utils = /*#__PURE__*/Object.freeze({
|
|
|
3938
4263
|
isPageable: isPageable,
|
|
3939
4264
|
isSafari: isSafari,
|
|
3940
4265
|
isTablet: isTablet,
|
|
4266
|
+
isValidImageUrl: isValidImageUrl,
|
|
3941
4267
|
isValidWebURL: isValidWebURL,
|
|
3942
4268
|
isVideoFile: isVideoFile,
|
|
3943
4269
|
loadScript: loadScript,
|
|
@@ -5177,5 +5503,5 @@ class LRUCache {
|
|
|
5177
5503
|
* Generated bundle index. Do not edit.
|
|
5178
5504
|
*/
|
|
5179
5505
|
|
|
5180
|
-
export { $appDigest, $invokeWatchers, $parseEvent, $parseExpr, $unwatch, $watch, AbstractDialogService, AbstractHttpService, AbstractI18nService, AbstractNavigationService, AbstractSpinnerService, AbstractToasterService, App, AppConstants, AppDefaults, CURRENCY_INFO, ComponentType, ConstantService, CustomIconsLoaderService, CustomPipeManager, CustomWidgetRefProvider, DEFAULT_FORMATS, DataSource, DataType, DynamicComponentRefProvider, EventNotifier, FIRST_TIME_WATCH, FieldTypeService, FieldWidgetService, FormWidgetType, IDGenerator, IDataSource, LRUCache, MatchMode, PaginationService, PartialRefProvider, ScriptLoaderService, ScriptStore, StatePersistence, UserDefinedExecutionContext, UtilsService, VALIDATOR, Viewport, _WM_APP_PROJECT, addClass, addEventListenerOnElement, addForIdAttributes, adjustContainerPosition, adjustContainerRightEdges, appendNode, appendScriptToHead, checkIsCustomPipeExpression, closePopover, convertToBlob, createCSSRule, createElement, deHyphenate, debounce, defer, detectChanges, encodeUrl, encodeUrlParams, executePromiseChain, extendProto, extractCurrentItemExpr, extractType, fetchContent, findParent, findRootContainer, findValueOf, generateGUId, getAbortableDefer, getAndroidVersion, getAppSetting, getBlob, getClonedObject, getDatasourceFromExpr, getDateObj, getDisplayDateTimeFormat, getEvaluatedExprValue, getFiles, getFnByExpr, getFnForBindExpr, getFnForEventExpr, getFormWidgetTemplate, getFormattedDate, getMomentLocaleObject, getNativeDateObject, getNavClass, getNgModelAttr, getPreviewProperties, getRequiredFormWidget, getResourceURL, getRouteNameFromLink, getRowActionAttrs, getSessionStorageItem, getSheetPositionClass, getUrlParams, getValidDateObject, getValidJSON, getWebkitTraslationMatrix, getWmProjectProperties, hasOffsetStr, initCaps, insertAfter, insertBefore, isAndroid, isAndroidTablet, isAppleProduct, isAudioFile, isChangeFromWatch, isDataSourceEqual, isDateTimeType, isDefined, isElementInViewport, isEmptyObject, isEqualWithFields, isFirstTimeChange, isIE, isImageFile, isInsecureContentRequest, isIos, isIpad, isIphone, isIpod, isKitkatDevice, isLargeTabletLandscape, isLargeTabletPortrait, isMobile, isNumberType, isObject, isPageable, isSafari, isValidWebURL, isVideoFile, loadScript, loadScripts, loadStyleSheet, loadStyleSheets, muteWatchers, noop, openLink, periodSeparate, prettifyLabel, prettifyLabels, processFilterExpBindNode, registerFnByExpr, removeAttr, removeClass, removeExtraSlashes, removeNode, replace, replaceAt, resetChangeFromWatch, retryIfFails, scrollToElement, setAppRef, setAttr, setCSS, setCSSFromObj, setHtml, setListClass, setNgZone, setPipeProvider, setPreviewProperties, setProperty, setSessionStorageItem, setTranslation3dPosition, setWmProjectProperties, spaceSeparate, stringStartsWith, switchClass, toBoolean, toDimension, toPromise, toggleClass, transformFileURI, triggerFn, triggerItemAction, unMuteWatchers, updateTemplateAttrs, validateAccessRoles, validateDataSourceCtx, xmlToJson };
|
|
5506
|
+
export { $appDigest, $invokeWatchers, $parseEvent, $parseExpr, $unwatch, $unwatchAll, $unwatchAllByScope, $watch, AbstractDialogService, AbstractHttpService, AbstractI18nService, AbstractNavigationService, AbstractSpinnerService, AbstractToasterService, App, AppConstants, AppDefaults, CURRENCY_INFO, ComponentType, ConstantService, CustomIconsLoaderService, CustomPipeManager, CustomWidgetRefProvider, DEFAULT_FORMATS, DataSource, DataType, DynamicComponentRefProvider, EventNotifier, FIRST_TIME_WATCH, FieldTypeService, FieldWidgetService, FormWidgetType, IDGenerator, IDataSource, LRUCache, MatchMode, PaginationService, PartialRefProvider, ScriptLoaderService, ScriptStore, StatePersistence, UserDefinedExecutionContext, UtilsService, VALIDATOR, Viewport, _WM_APP_PROJECT, addClass, addEventListenerOnElement, addForIdAttributes, adjustContainerPosition, adjustContainerRightEdges, appendNode, appendScriptToHead, checkIsCustomPipeExpression, closePopover, convertToBlob, createCSSRule, createElement, deHyphenate, debounce, defer, detectChanges, encodeUrl, encodeUrlParams, executePromiseChain, extendProto, extractCurrentItemExpr, extractType, fetchContent, findParent, findRootContainer, findValueOf, generateGUId, getAbortableDefer, getAndroidVersion, getAppSetting, getBlob, getClonedObject, getDatasourceFromExpr, getDateObj, getDisplayDateTimeFormat, getEvaluatedExprValue, getFiles, getFnByExpr, getFnForBindExpr, getFnForEventExpr, getFormWidgetTemplate, getFormattedDate, getMomentLocaleObject, getNativeDateObject, getNavClass, getNgModelAttr, getPreviewProperties, getRequiredFormWidget, getResourceURL, getRouteNameFromLink, getRowActionAttrs, getSessionStorageItem, getSheetPositionClass, getUrlParams, getValidDateObject, getValidJSON, getWebkitTraslationMatrix, getWmProjectProperties, hasOffsetStr, initCaps, insertAfter, insertBefore, isAndroid, isAndroidTablet, isAppleProduct, isAudioFile, isChangeFromWatch, isDataSourceEqual, isDateTimeType, isDefined, isElementInViewport, isEmptyObject, isEqualWithFields, isFirstTimeChange, isIE, isImageFile, isInsecureContentRequest, isIos, isIpad, isIphone, isIpod, isKitkatDevice, isLargeTabletLandscape, isLargeTabletPortrait, isMobile, isNumberType, isObject, isPageable, isSafari, isValidImageUrl, isValidWebURL, isVideoFile, loadScript, loadScripts, loadStyleSheet, loadStyleSheets, muteWatchers, noop, openLink, periodSeparate, prettifyLabel, prettifyLabels, processFilterExpBindNode, registerFnByExpr, removeAttr, removeClass, removeExtraSlashes, removeNode, replace, replaceAt, resetChangeFromWatch, retryIfFails, scrollToElement, setAppRef, setAttr, setCSS, setCSSFromObj, setHtml, setListClass, setNgZone, setPipeProvider, setPreviewProperties, setProperty, setSessionStorageItem, setTranslation3dPosition, setWmProjectProperties, spaceSeparate, stringStartsWith, switchClass, toBoolean, toDimension, toPromise, toggleClass, transformFileURI, triggerFn, triggerItemAction, unMuteWatchers, updateTemplateAttrs, validateAccessRoles, validateDataSourceCtx, xmlToJson };
|
|
5181
5507
|
//# sourceMappingURL=index.mjs.map
|