From 895629a00770df725f2190f6a430c639c6c7e765 Mon Sep 17 00:00:00 2001 From: mac <241206824@qq.com> Date: Thu, 21 May 2026 20:51:32 +0800 Subject: [PATCH] feat: add baby and teen projects, update sample data --- README.md | 3 +- baby/baby_idle_behavior copy.cpp | 115 ++ baby/example.json | 443 ++++++ baby/generate_behavior_cpp.py | 1487 ++++++++++++++++++ baby/node-config.b3-setting | 1066 +++++++++++++ baby/workspace.b3-workspace | 13 + package-lock.json | 1967 ++---------------------- sample/workdir/monster.json | 98 +- sample/workdir/sub/subtree1.json | 46 +- sample/workdir/subtree1.json | 49 +- sample/workdir/subtree2.json | 44 +- teen/example.json | 44 + teen/node-config.b3-setting | 856 +++++++++++ teen/workspace.b3-workspace | 4 + test1/example.json | 429 ++++++ test1/node-config.b3-setting | 856 +++++++++++ test1/workspace.b3-workspace | 13 + test1/行为树需求_幼年期行为树 (1).xlsx | Bin 0 -> 7507 bytes 18 files changed, 5587 insertions(+), 1946 deletions(-) create mode 100644 baby/baby_idle_behavior copy.cpp create mode 100644 baby/example.json create mode 100644 baby/generate_behavior_cpp.py create mode 100644 baby/node-config.b3-setting create mode 100644 baby/workspace.b3-workspace create mode 100644 teen/example.json create mode 100644 teen/node-config.b3-setting create mode 100644 teen/workspace.b3-workspace create mode 100644 test1/example.json create mode 100644 test1/node-config.b3-setting create mode 100644 test1/workspace.b3-workspace create mode 100644 test1/行为树需求_幼年期行为树 (1).xlsx diff --git a/README.md b/README.md index 5d26d79..af39382 100644 --- a/README.md +++ b/README.md @@ -89,7 +89,8 @@ export interface NodeDef { ```shell npm install # 安装依赖 -npm start # 运行测试 +npm test # 运行测试 +npm run dev # 启动开发环境 npm run build # 编译可执行文件 ``` diff --git a/baby/baby_idle_behavior copy.cpp b/baby/baby_idle_behavior copy.cpp new file mode 100644 index 0000000..3e37dc0 --- /dev/null +++ b/baby/baby_idle_behavior copy.cpp @@ -0,0 +1,115 @@ +#include "baby_idle_behavior.h" +#include "esp_log.h" +#include "esp_random.h" +#include "esp_timer.h" + +static const char* TAG = "BabyIdleBehavior"; + +namespace sweekar { +namespace demo7 { + +namespace { +constexpr int64_t kFirstRandomIdleDelayUs = 5000000; // 5s after entering idle +constexpr int64_t kRandomIdleCooldownUs = 7000000; // 7s after a random idle script +constexpr const char* kBaseIdleScript = "baby/idle/look_around"; +constexpr const char* kCuriousIdleScript = "baby/interaction/curious"; +constexpr const char* kShyIdleScript = "baby/interaction/shy"; +} // namespace + +void BabyIdleBehavior::OnEnter(IPetContext* ctx) { + PlayBaseIdle(ctx); + ScheduleRandomIdle(kFirstRandomIdleDelayUs); + phase_ = Phase::WAITING_RANDOM_IDLE; +} + +void BabyIdleBehavior::OnExit(IPetContext* ctx) { + ctx->StopScript(); + next_random_idle_us_ = 0; + phase_ = Phase::PLAYING_BASE_IDLE; +} + +bool BabyIdleBehavior::HandleEvent(IPetContext* ctx, const Event& evt) { + switch (evt.type) { + case EventType::EVT_TOUCH_TAP: + ESP_LOGI(TAG, "Baby got touched. Play surprised."); + ctx->PlayScript("interaction/surprised"); + phase_ = Phase::PLAYING_RANDOM_IDLE; + return true; + + case EventType::EVT_KEY_LEFT_CLICK: + ESP_LOGI(TAG, "Left clicked in BabyIdle. Opening Baby Menu."); + ctx->RequestModeSwitch(PetModeType::MODE_MENU); + return true; + + case EventType::EVT_KEY_RIGHT_CLICK: + ESP_LOGI(TAG, "Right clicked in BabyIdle. Learn to talk."); + ctx->PlayScript("interaction/learned_to_talk"); + phase_ = Phase::PLAYING_RANDOM_IDLE; + return true; + + case EventType::EVT_GYRO_SHAKE: + ESP_LOGI(TAG, "Baby shaken. Play dizzy."); + ctx->PlayScript("interaction/dizzy"); + phase_ = Phase::PLAYING_RANDOM_IDLE; + return true; + + case EventType::EVT_TOUCH_SWIPE_LEFT: + ESP_LOGI(TAG, "Baby touch swipe left. Play hurt."); + ctx->PlayScript("baby/interaction/hurt"); + phase_ = Phase::PLAYING_RANDOM_IDLE; + return true; + + case EventType::EVT_TOUCH_SWIPE_RIGHT: + ESP_LOGI(TAG, "Baby touch swipe right. Play curious."); + ctx->PlayScript(kCuriousIdleScript); + phase_ = Phase::PLAYING_RANDOM_IDLE; + return true; + + case EventType::EVT_SCRIPT_DONE: + ESP_LOGI(TAG, "Baby idle script done."); + PlayBaseIdle(ctx); + if (phase_ == Phase::PLAYING_RANDOM_IDLE) { + ScheduleRandomIdle(kRandomIdleCooldownUs); + phase_ = Phase::COOLDOWN_AFTER_RANDOM; + } + return true; + + default: + return false; + } +} + +void BabyIdleBehavior::OnTick(IPetContext* ctx) { + if (!IsRandomIdleDue()) { + return; + } + + PlayRandomIdle(ctx); + phase_ = Phase::PLAYING_RANDOM_IDLE; +} + +void BabyIdleBehavior::PlayBaseIdle(IPetContext* ctx) { + ESP_LOGI(TAG, "Play base idle script: %s", kBaseIdleScript); + ctx->PlayScript(kBaseIdleScript); +} + +void BabyIdleBehavior::PlayRandomIdle(IPetContext* ctx) { + uint32_t roll = esp_random() % 100; + const char* script = roll < 50 ? kCuriousIdleScript : kShyIdleScript; + ESP_LOGI(TAG, "Play random idle script: %s, roll=%lu", script, static_cast(roll)); + ctx->PlayScript(script); +} + +void BabyIdleBehavior::ScheduleRandomIdle(int64_t delay_us) { + next_random_idle_us_ = esp_timer_get_time() + delay_us; +} + +bool BabyIdleBehavior::IsRandomIdleDue() const { + if (phase_ != Phase::WAITING_RANDOM_IDLE && phase_ != Phase::COOLDOWN_AFTER_RANDOM) { + return false; + } + return next_random_idle_us_ > 0 && esp_timer_get_time() >= next_random_idle_us_; +} + +} // namespace demo7 +} // namespace sweekar diff --git a/baby/example.json b/baby/example.json new file mode 100644 index 0000000..a968f80 --- /dev/null +++ b/baby/example.json @@ -0,0 +1,443 @@ +{ + "$override": { + }, + "custom": { + }, + "desc": "宝宝待机行为树 v2:Selector 优先级级联 + 效用曲线 + 双层脑信号(WARNING/CRITICAL)。优先级:精力耗尽 > 饥饿 > 悲伤 > 开心 > 好奇 > 默认待机。", + "export": true, + "group": [ + ], + "import": [ + ], + "name": "example", + "prefix": "", + "root": { + "$id": "root001", + "children": [ + { + "$id": "idleRepeat001", + "args": { + }, + "children": [ + { + "$id": "idleSeq001", + "children": [ + { + "$id": "idleWaitRhythm", + "args": { + "random": 1.5, + "time": 2 + }, + "id": "40", + "name": "Wait" + }, + { + "$id": "idleSelector001", + "children": [ + { + "$id": "exhaustedSeq", + "children": [ + { + "$id": "exhaustedCheck", + "args": { "attr": "energy", "op": "<=", "value": 15 }, + "id": "43", + "name": "CheckPhysio" + }, + { + "$id": "exhaustedScript", + "args": { "script": "baby/need/sleepy" }, + "id": "44", + "name": "PlayScript" + } + ], + "id": "42", + "name": "Sequence" + }, + { + "$id": "hungrySeq", + "children": [ + { + "$id": "hungryCheck", + "args": { "attr": "fullness", "op": "<=", "value": 25 }, + "id": "46", + "name": "CheckPhysio" + }, + { + "$id": "hungryScript", + "args": { "script": "baby/need/hungry" }, + "id": "48", + "name": "PlayScript" + }, + { + "$id": "hungryMoodDrop", + "args": { "attr": "happiness", "amount": -2 }, + "id": "49", + "name": "AddPhysio" + } + ], + "id": "45", + "name": "Sequence" + }, + { + "$id": "sadSeq", + "children": [ + { + "$id": "sadCheck", + "args": { "attr": "sad", "op": ">", "value": 0.5 }, + "id": "51", + "name": "CheckUtility" + }, + { + "$id": "sadScript", + "args": { "script": "baby/need/sad_mild" }, + "id": "52", + "name": "PlayScript" + } + ], + "id": "50", + "name": "Sequence" + }, + { + "$id": "laughSeq", + "children": [ + { + "$id": "laughCheck", + "args": { "attr": "laugh", "op": ">", "value": 0.5 }, + "id": "54", + "name": "CheckUtility" + }, + { + "$id": "laughScript", + "args": { "script": "baby/interaction/laugh" }, + "id": "55", + "name": "PlayScript" + } + ], + "id": "53", + "name": "Sequence" + }, + { + "$id": "curiousSeq", + "children": [ + { + "$id": "curiousCheck", + "args": { "attr": "curious", "op": ">", "value": 0.4 }, + "id": "57", + "name": "CheckUtility" + }, + { + "$id": "curiousScript", + "args": { "script": "baby/interaction/curious" }, + "id": "58", + "name": "PlayScript" + } + ], + "id": "56", + "name": "Sequence" + }, + { + "$id": "idleFallback", + "args": { "script": "baby/interaction/shy" }, + "id": "59", + "name": "PlayScript" + } + ], + "id": "41", + "name": "Selector" + } + ], + "id": "3", + "name": "Sequence" + } + ], + "id": "2", + "name": "Repeat" + }, + { + "$id": "listenTriple001", + "args": { + "event": "EVT_TOUCH_TRIPLE_TAP" + }, + "children": [ + { + "$id": "shyScript001", + "args": { + "script": "baby/interaction/shy" + }, + "id": "17", + "name": "PlayScript" + } + ], + "id": "16", + "name": "Listen" + }, + { + "$id": "listenTap001", + "args": { + "event": "EVT_TOUCH_TAP" + }, + "children": [ + { + "$id": "tapSelector001", + "children": [ + { + "$id": "dirtyTapSeq", + "children": [ + { + "$id": "dirtyTapCheck", + "args": { "attr": "cleanliness", "op": "<=", "value": 20 }, + "id": "62", + "name": "CheckPhysio" + }, + { + "$id": "dirtyTapScript", + "args": { "script": "baby/interaction/hurt" }, + "id": "64", + "name": "PlayScript" + }, + { + "$id": "dirtyTapMoodDrop", + "args": { "attr": "happiness", "amount": -1 }, + "id": "65", + "name": "AddPhysio" + } + ], + "id": "61", + "name": "Sequence" + }, + { + "$id": "curiousTapSeq", + "children": [ + { + "$id": "curiousTapCheck", + "args": { "attr": "curious", "op": ">", "value": 0.55 }, + "id": "67", + "name": "CheckUtility" + }, + { + "$id": "wantedScript001", + "args": { "script": "baby/interaction/wanted" }, + "id": "69", + "name": "PlayScript" + }, + { + "$id": "tapHappinessUp", + "args": { "attr": "happiness", "amount": 3 }, + "id": "70", + "name": "AddPhysio" + } + ], + "id": "66", + "name": "Sequence" + }, + { + "$id": "sadTapSeq", + "children": [ + { + "$id": "sadTapCheck", + "args": { "attr": "sad", "op": ">", "value": 0.4 }, + "id": "72", + "name": "CheckUtility" + }, + { + "$id": "comfortScript", + "args": { "script": "baby/need/sad_mild" }, + "id": "73", + "name": "PlayScript" + } + ], + "id": "71", + "name": "Sequence" + }, + { + "$id": "tapFallback", + "args": { "script": "baby/interaction/hurt" }, + "id": "74", + "name": "PlayScript" + } + ], + "id": "60", + "name": "Selector" + } + ], + "id": "18", + "name": "Listen" + }, + { + "$id": "listenLeftEar001", + "args": { + "abortType": "interrupt", + "event": "EVT_KEY_LEFT_CLICK" + }, + "children": [ + { + "$id": "openMenu001", + "args": { + "mode": "MODE_MENU" + }, + "id": "24", + "name": "RequestModeSwitch" + } + ], + "id": "23", + "name": "Listen" + }, + { + "$id": "listenBrainFullnessWarning", + "args": { "event": "EVT_INTERNAL_BRAIN_FULLNESS_WARNING" }, + "children": [ + { + "$id": "hungryWarnScript", + "args": { "script": "baby/need/hungry" }, + "id": "30", + "name": "PlayScript" + } + ], + "id": "29", + "name": "Listen" + }, + { + "$id": "listenBrainEnergyWarning", + "args": { "event": "EVT_INTERNAL_BRAIN_ENERGY_WARNING" }, + "children": [ + { + "$id": "sleepyWarnScript", + "args": { "script": "baby/need/sleepy" }, + "id": "32", + "name": "PlayScript" + } + ], + "id": "31", + "name": "Listen" + }, + { + "$id": "listenBrainHappinessWarning", + "args": { "event": "EVT_INTERNAL_BRAIN_HAPPINESS_WARNING" }, + "children": [ + { + "$id": "sadWarnScript", + "args": { "script": "baby/need/sad_mild" }, + "id": "34", + "name": "PlayScript" + } + ], + "id": "33", + "name": "Listen" + }, + { + "$id": "listenBrainCleanlinessWarning", + "args": { "event": "EVT_INTERNAL_BRAIN_CLEANLINESS_WARNING" }, + "children": [ + { + "$id": "dirtyWarnScript", + "args": { "script": "baby/need/dirty" }, + "id": "36", + "name": "PlayScript" + } + ], + "id": "35", + "name": "Listen" + }, + { + "$id": "listenBrainFullnessCritical", + "args": { "event": "EVT_INTERNAL_BRAIN_FULLNESS_CRITICAL", "abortType": "interrupt" }, + "children": [ + { + "$id": "hungryCriticalSeq", + "children": [ + { + "$id": "hungryCriticalScript", + "args": { "script": "baby/need/hungry" }, + "id": "82", + "name": "PlayScript" + }, + { + "$id": "hungryCriticalMoodDrop", + "args": { "attr": "happiness", "amount": -5 }, + "id": "83", + "name": "AddPhysio" + } + ], + "id": "81", + "name": "Sequence" + } + ], + "id": "80", + "name": "Listen" + }, + { + "$id": "listenBrainEnergyCritical", + "args": { "event": "EVT_INTERNAL_BRAIN_ENERGY_CRITICAL", "abortType": "interrupt" }, + "children": [ + { + "$id": "energyCriticalSeq", + "children": [ + { + "$id": "energyCriticalScript", + "args": { "script": "baby/need/sleepy" }, + "id": "86", + "name": "PlayScript" + }, + { + "$id": "energyCriticalMoodDrop", + "args": { "attr": "happiness", "amount": -5 }, + "id": "87", + "name": "AddPhysio" + } + ], + "id": "85", + "name": "Sequence" + } + ], + "id": "84", + "name": "Listen" + }, + { + "$id": "listenBrainHappinessCritical", + "args": { "event": "EVT_INTERNAL_BRAIN_HAPPINESS_CRITICAL", "abortType": "interrupt" }, + "children": [ + { + "$id": "sadCriticalScript", + "args": { "script": "baby/need/sad_mild" }, + "id": "89", + "name": "PlayScript" + } + ], + "id": "88", + "name": "Listen" + }, + { + "$id": "listenBrainCleanlinessCritical", + "args": { "event": "EVT_INTERNAL_BRAIN_CLEANLINESS_CRITICAL", "abortType": "interrupt" }, + "children": [ + { + "$id": "dirtyCriticalSeq", + "children": [ + { + "$id": "dirtyCriticalScript", + "args": { "script": "baby/need/dirty" }, + "id": "92", + "name": "PlayScript" + }, + { + "$id": "dirtyCriticalMoodDrop", + "args": { "attr": "happiness", "amount": -3 }, + "id": "93", + "name": "AddPhysio" + } + ], + "id": "91", + "name": "Sequence" + } + ], + "id": "90", + "name": "Listen" + } + ], + "id": "1", + "name": "Parallel" + }, + "vars": [ + ], + "version": "2.0.0" +} \ No newline at end of file diff --git a/baby/generate_behavior_cpp.py b/baby/generate_behavior_cpp.py new file mode 100644 index 0000000..27a0d24 --- /dev/null +++ b/baby/generate_behavior_cpp.py @@ -0,0 +1,1487 @@ +#!/usr/bin/env python3 +"""Generate a Pet Game behavior .cpp file from a JSON behavior tree. + +The generator intentionally targets the lightweight IPetContext based behavior +classes used by the demo7 pet game stages. It supports the node subset present +in example.json: + + Parallel, Repeat, Sequence, IfElse, Check, Listen, Log, Wait + +Unknown nodes are emitted as ESP_LOGW statements so the generated C++ remains +buildable while making missing mappings visible during runtime. +""" + +from __future__ import annotations + +import argparse +import json +import math +import re +import sys +from dataclasses import dataclass +from pathlib import Path +from typing import Any, Iterable + + +DEFAULT_CLASS_NAME = "JsonBehaviorRunner" +DEFAULT_HEADER = "json_behavior_runner.h" +DEFAULT_CPP = "json_behavior_runner.cpp" +DEFAULT_NAMESPACE = "sweekar::demo7" +DEFAULT_EVENT_BUS = "../../../../09_core/event_bus/event_bus.h" + +EVENT_RE = re.compile(r"^EVT_[A-Z0-9_]+$") +MATH_RANDOM_RE = re.compile(r"^Math\.random\(\)\s*<\s*([0-9]*\.?[0-9]+)\s*$") +INTERNAL_EVENT_RE = re.compile(r"^EVT_INTERNAL_[A-Z0-9_]+$") + +# PetInternalEventType 中定义的伪装事件(0x8000+),不在 EventType 枚举中,但共用同一传递通道 +PET_INTERNAL_EVENT_NAMES: list[str] = [ + "EVT_INTERNAL_BRAIN_FULLNESS_WARNING", + "EVT_INTERNAL_BRAIN_FULLNESS_CRITICAL", + "EVT_INTERNAL_BRAIN_CLEANLINESS_WARNING", + "EVT_INTERNAL_BRAIN_CLEANLINESS_CRITICAL", + "EVT_INTERNAL_BRAIN_HAPPINESS_WARNING", + "EVT_INTERNAL_BRAIN_HAPPINESS_CRITICAL", + "EVT_INTERNAL_BRAIN_ENERGY_WARNING", + "EVT_INTERNAL_BRAIN_ENERGY_CRITICAL", +] + + +@dataclass(frozen=True) +class Node: + node_id: str + name: str + args: dict[str, Any] + children: list["Node"] + + +@dataclass(frozen=True) +class ListenBranch: + event: str + children: list[Node] + + +@dataclass(frozen=True) +class IdleBranch: + base_nodes: list[Node] # played immediately on enter / script-done (base idle display) + wait_seconds: float # main idle loop wait time + random_seconds: float # random jitter on wait + random_nodes: list[Node] # played when random idle timer fires (mood picker etc.) + + +def parse_args() -> argparse.Namespace: + parser = argparse.ArgumentParser( + description="Convert a JSON behavior tree into a pet behavior C++ source file.", + ) + parser.add_argument( + "input", + nargs="?", + default="example.json", + type=Path, + help="Input JSON behavior tree. Defaults to ./example.json.", + ) + parser.add_argument( + "-o", + "--output", + type=Path, + default=None, + help=f"Output .cpp path. Defaults to ./{DEFAULT_CPP}.", + ) + parser.add_argument( + "--output-header", + type=Path, + default=None, + help=f"Output .h path. Defaults to ./{DEFAULT_HEADER}.", + ) + parser.add_argument( + "--event-bus", + type=Path, + default=None, + help=f"Path to event_bus.h. Defaults to {DEFAULT_EVENT_BUS}.", + ) + parser.add_argument( + "--header", + default=DEFAULT_HEADER, + help=f"Header included by the generated .cpp. Defaults to {DEFAULT_HEADER}.", + ) + parser.add_argument( + "--class-name", + default=DEFAULT_CLASS_NAME, + help=f"Behavior class name. Defaults to {DEFAULT_CLASS_NAME}.", + ) + parser.add_argument( + "--namespace", + default=DEFAULT_NAMESPACE, + help=f"C++ namespace, separated with ::. Defaults to {DEFAULT_NAMESPACE}.", + ) + parser.add_argument( + "--tag", + default=None, + help="ESP log tag. Defaults to the class name.", + ) + parser.add_argument( + "--force", + action="store_true", + help="Overwrite the output file if it already exists.", + ) + parser.add_argument( + "--condition", + action="append", + default=[], + metavar="CHECK=CPP_EXPR", + help=( + "Bind a Check value to a C++ expression, for example " + "--condition 'emotionHigh=ctx->GetEnergy() > 50'. Can be used multiple times." + ), + ) + parser.add_argument( + "--dry-run", + action="store_true", + help="Print generated C++ to stdout instead of writing a file.", + ) + return parser.parse_args() + + +def load_tree(path: Path) -> tuple[dict[str, Any], Node]: + with path.open("r", encoding="utf-8") as f: + document = json.load(f) + + if not isinstance(document, dict): + raise ValueError("JSON root must be an object") + + root_value = document.get("root") + if not isinstance(root_value, dict): + raise ValueError("JSON must contain an object field named 'root'") + + return document, parse_node(root_value) + + +def parse_node(value: dict[str, Any]) -> Node: + name = value.get("name") + if not isinstance(name, str) or not name: + raise ValueError(f"Node is missing a non-empty string name: {value!r}") + + node_id = str(value.get("$id") or value.get("id") or name) + + args = value.get("args", {}) + if args is None: + args = {} + if not isinstance(args, dict): + raise ValueError(f"Node {node_id} args must be an object") + + raw_children = value.get("children", []) + if raw_children is None: + raw_children = [] + if not isinstance(raw_children, list): + raise ValueError(f"Node {node_id} children must be an array") + + children = [] + for child in raw_children: + if not isinstance(child, dict): + raise ValueError(f"Node {node_id} contains a non-object child: {child!r}") + children.append(parse_node(child)) + + return Node(node_id=node_id, name=name, args=args, children=children) + + +def split_behavior(root: Node) -> tuple[IdleBranch | None, list[ListenBranch], list[Node]]: + """Separate startup/tick work from event listeners. + + Root Parallel nodes commonly contain one repeatable idle branch and multiple + Listen branches. Other root shapes are still accepted and treated as idle + body nodes. + """ + + candidates = root.children if root.name == "Parallel" else [root] + idle_candidates: list[Node] = [] + listen_branches: list[ListenBranch] = [] + extra_nodes: list[Node] = [] + + for child in candidates: + if child.name == "Listen": + event = child.args.get("event") + if not isinstance(event, str) or not EVENT_RE.match(event): + raise ValueError(f"Listen node {child.node_id} has invalid event: {event!r}") + listen_branches.append(ListenBranch(event=event, children=child.children)) + elif child.name == "Repeat": + idle_candidates.extend(child.children) + else: + extra_nodes.append(child) + + if not idle_candidates and extra_nodes: + idle_candidates = extra_nodes + extra_nodes = [] + + idle_branch = None + if idle_candidates: + flat = flatten_single_sequence(idle_candidates) + base_nodes, wait_seconds, random_seconds, random_nodes = split_idle_body(flat) + idle_branch = IdleBranch( + base_nodes=base_nodes, + wait_seconds=wait_seconds, + random_seconds=random_seconds, + random_nodes=random_nodes, + ) + + return idle_branch, listen_branches, extra_nodes + + +def flatten_single_sequence(nodes: list[Node]) -> list[Node]: + if len(nodes) == 1 and nodes[0].name == "Sequence": + return nodes[0].children + return nodes + + +def find_wait_window(nodes: Iterable[Node]) -> tuple[float, float]: + for node in walk_nodes(nodes): + if node.name == "Wait": + return number_arg(node, "time", 1.0), number_arg(node, "random", 0.0) + return 1.0, 0.0 + + +def split_idle_body(nodes: list[Node]) -> tuple[list[Node], float, float, list[Node]]: + """Split an idle Sequence into (base_nodes, wait_sec, random_sec, random_nodes). + + Scans top-level nodes for the first Wait. Everything before it becomes the + base-idle content (played immediately on enter / script-done); everything + after it becomes the random-idle content (played when the timer fires). + """ + base: list[Node] = [] + random_nodes: list[Node] = [] + wait_s = 1.0 + random_s = 0.0 + found_wait = False + for node in nodes: + if not found_wait and node.name == "Wait": + wait_s = number_arg(node, "time", 1.0) + random_s = number_arg(node, "random", 0.0) + found_wait = True + elif not found_wait: + base.append(node) + else: + random_nodes.append(node) + return base, wait_s, random_s, random_nodes + + +def walk_nodes(nodes: Iterable[Node]) -> Iterable[Node]: + for node in nodes: + yield node + yield from walk_nodes(node.children) + + +def number_arg(node: Node, key: str, default: float) -> float: + value = node.args.get(key, default) + if isinstance(value, bool) or not isinstance(value, (int, float)): + raise ValueError(f"{node.name} node {node.node_id} arg {key!r} must be a number") + if not math.isfinite(float(value)) or float(value) < 0: + raise ValueError(f"{node.name} node {node.node_id} arg {key!r} must be >= 0") + return float(value) + + +def generate_cpp( + document: dict[str, Any], + root: Node, + *, + header: str, + class_name: str, + namespace: str, + tag: str, + condition_bindings: dict[str, str] | None = None, +) -> str: + condition_bindings = condition_bindings or {} + idle_branch, listen_branches, extra_nodes = split_behavior(root) + namespace_parts = [part for part in namespace.split("::") if part] + if not namespace_parts: + raise ValueError("namespace must not be empty") + + out: list[str] = [] + emit = out.append + + emit(f'#include "{escape_cpp_string(header)}"') + emit('#include "esp_log.h"') + emit('#include "esp_random.h"') + emit('#include "esp_timer.h"') + emit("") + emit(f'static const char* TAG = "{escape_cpp_string(tag)}";') + emit("") + for part in namespace_parts: + emit(f"namespace {part} {{") + emit("") + emit("namespace {") + emit(f"// Generated from behavior tree: {cpp_comment(str(document.get('name', '')))}") + emit(f"// Description: {cpp_comment(str(document.get('desc', '')))}") + emit("constexpr int64_t kUsPerSecond = 1000000;") + emit("") + emit("int64_t SecondsToUs(float seconds) {") + emit(" return static_cast(seconds * kUsPerSecond);") + emit("}") + emit("") + emit("bool RandomLessThan(float threshold) {") + emit(" if (threshold <= 0.0f) {") + emit(" return false;") + emit(" }") + emit(" if (threshold >= 1.0f) {") + emit(" return true;") + emit(" }") + emit(" return (esp_random() % 10000) < static_cast(threshold * 10000.0f);") + emit("}") + emit("") + emit("int64_t WaitWindowUs(float base_seconds, float random_seconds) {") + emit(" int64_t delay_us = SecondsToUs(base_seconds);") + emit(" if (random_seconds > 0.0f) {") + emit(" delay_us += esp_random() % static_cast(SecondsToUs(random_seconds) + 1);") + emit(" }") + emit(" return delay_us;") + emit("}") + emit("") + emit("bool EvaluateCondition(IPetContext* ctx, const char* expression) {") + emit(" (void)ctx;") + emit(" ESP_LOGW(TAG, \"No C++ binding for Check expression: %s\", expression);") + emit(" return false;") + emit("}") + emit("") + emit("} // namespace") + emit("") + + emit(f"void {class_name}::OnEnter(IPetContext* ctx) {{") + if idle_branch: + emit(" PlayBaseIdle(ctx);") + emit_idle_schedule(idle_branch, emit, " ") + emit(" phase_ = Phase::WAITING_RANDOM_IDLE;") + else: + emit(" (void)ctx;") + emit(' ESP_LOGI(TAG, "Enter generated behavior with no idle branch");') + emit(" phase_ = Phase::PLAYING_BASE_IDLE;") + emit("}") + emit("") + + emit(f"void {class_name}::OnExit(IPetContext* ctx) {{") + emit(" ctx->StopScript();") + emit(" next_random_idle_us_ = 0;") + emit(" phase_ = Phase::PLAYING_BASE_IDLE;") + emit("}") + emit("") + + emit(f"bool {class_name}::HandleEvent(IPetContext* ctx, const Event& evt) {{") + if listen_branches: + emit(" switch (evt.type) {") + for branch in listen_branches: + emit(f" case EventType::{branch.event}:") + emit(f' ESP_LOGI(TAG, "Handle event: {escape_cpp_string(branch.event)}");') + emit_node_list(branch.children, emit, " ", condition_bindings) + emit(" return true;") + emit("") + emit(" case EventType::EVT_SCRIPT_DONE:") + emit(' ESP_LOGI(TAG, "Generated behavior script done");') + if idle_branch: + emit(" PlayBaseIdle(ctx);") + emit_idle_schedule(idle_branch, emit, " ") + emit(" phase_ = Phase::COOLDOWN_AFTER_RANDOM;") + emit(" return true;") + emit("") + emit(" default:") + emit(" return false;") + emit(" }") + else: + emit(" (void)ctx;") + emit(" (void)evt;") + emit(" return false;") + emit("}") + emit("") + + emit(f"void {class_name}::OnTick(IPetContext* ctx) {{") + if idle_branch: + emit(" if (!IsRandomIdleDue()) {") + emit(" return;") + emit(" }") + emit(" PlayRandomIdle(ctx);") + emit(" phase_ = Phase::WAITING_RANDOM_IDLE;") + else: + emit(" (void)ctx;") + emit("}") + emit("") + + emit(f"void {class_name}::PlayBaseIdle(IPetContext* ctx) {{") + if idle_branch and idle_branch.base_nodes: + emit_node_list(idle_branch.base_nodes, emit, " ", condition_bindings) + else: + emit(" (void)ctx;") + emit("}") + emit("") + + emit(f"void {class_name}::PlayRandomIdle(IPetContext* ctx) {{") + if idle_branch and idle_branch.random_nodes: + emit_node_list(idle_branch.random_nodes, emit, " ", condition_bindings) + else: + emit(" (void)ctx;") + emit("}") + emit("") + + emit(f"void {class_name}::ScheduleRandomIdle(int64_t delay_us) {{") + emit(" next_random_idle_us_ = esp_timer_get_time() + delay_us;") + emit("}") + emit("") + + emit(f"bool {class_name}::IsRandomIdleDue() const {{") + emit(" if (phase_ != Phase::WAITING_RANDOM_IDLE && phase_ != Phase::COOLDOWN_AFTER_RANDOM) {") + emit(" return false;") + emit(" }") + emit(" return next_random_idle_us_ > 0 && esp_timer_get_time() >= next_random_idle_us_;") + emit("}") + emit("") + + for part in reversed(namespace_parts): + emit(f"}} // namespace {part}") + emit("") + + if extra_nodes: + emit("// The following root nodes were not emitted because they are outside Repeat/Listen:") + for node in extra_nodes: + emit(f"// - {cpp_comment(node.name)} ({cpp_comment(node.node_id)})") + + return "\n".join(out) + + +def emit_idle_schedule(branch: IdleBranch, emit: Any, indent: str) -> None: + emit( + f"{indent}ScheduleRandomIdle(WaitWindowUs({float_literal(branch.wait_seconds)}, " + f"{float_literal(branch.random_seconds)}));" + ) + + +def emit_node_list(nodes: list[Node], emit: Any, indent: str, condition_bindings: dict[str, str]) -> None: + for node in nodes: + emit_node(node, emit, indent, condition_bindings) + + +def emit_node(node: Node, emit: Any, indent: str, condition_bindings: dict[str, str]) -> None: + if node.name in {"Sequence", "Repeat", "Parallel"}: + emit_node_list(node.children, emit, indent, condition_bindings) + return + + if node.name == "Log": + level = str(node.args.get("level", "info")).lower() + message = str(node.args.get("message", "")) + log_macro = { + "debug": "ESP_LOGD", + "info": "ESP_LOGI", + "warn": "ESP_LOGW", + "warning": "ESP_LOGW", + "error": "ESP_LOGE", + }.get(level, "ESP_LOGI") + emit(f'{indent}{log_macro}(TAG, "{escape_cpp_string(message)}");') + return + + if node.name == "Wait": + time_seconds = number_arg(node, "time", 0.0) + random_seconds = number_arg(node, "random", 0.0) + emit( + f"{indent}ScheduleRandomIdle(WaitWindowUs({float_literal(time_seconds)}, " + f"{float_literal(random_seconds)}));" + ) + return + + if node.name == "IfElse": + if not node.children: + emit(f'{indent}ESP_LOGW(TAG, "IfElse node {escape_cpp_string(node.node_id)} has no condition");') + return + + condition = condition_expr(node.children[0], condition_bindings) + then_nodes = flatten_single_sequence(node.children[1:2]) + else_nodes = flatten_single_sequence(node.children[2:3]) + + emit(f"{indent}if ({condition}) {{") + emit_node_list(then_nodes, emit, indent + " ", condition_bindings) + if else_nodes: + emit(f"{indent}}} else {{") + emit_node_list(else_nodes, emit, indent + " ", condition_bindings) + emit(f"{indent}}}") + return + + if node.name == "Check": + emit(f"{indent}(void)({condition_expr(node, condition_bindings)});") + return + + if node.name == "Listen": + emit(f'{indent}ESP_LOGW(TAG, "Nested Listen node is ignored: {escape_cpp_string(node.node_id)}");') + return + + if node.name == "PlayScript": + script = node.args.get("script") or node.args.get("name") or node.args.get("path") + if not isinstance(script, str) or not script: + emit(f'{indent}ESP_LOGW(TAG, "PlayScript node {escape_cpp_string(node.node_id)} is missing script");') + else: + emit(f'{indent}ctx->PlayScript("{escape_cpp_string(script)}");') + return + + emit(f'{indent}ESP_LOGW(TAG, "Unsupported behavior node: {escape_cpp_string(node.name)}");') + + +def condition_expr(node: Node, condition_bindings: dict[str, str]) -> str: + if node.name != "Check": + return "false" + + value = node.args.get("value", "") + if isinstance(value, bool): + return "true" if value else "false" + if not isinstance(value, str): + return "false" + + value = value.strip() + match = MATH_RANDOM_RE.match(value) + if match: + return f"RandomLessThan({float_literal(float(match.group(1)))})" + + if value in {"true", "false"}: + return value + + if value in condition_bindings: + return f"({condition_bindings[value]})" + + return f'EvaluateCondition(ctx, "{escape_cpp_string(value)}")' + + +def parse_condition_bindings(items: list[str]) -> dict[str, str]: + bindings: dict[str, str] = {} + for item in items: + if "=" not in item: + raise ValueError(f"--condition must use CHECK=CPP_EXPR format: {item!r}") + key, expression = item.split("=", 1) + key = key.strip() + expression = expression.strip() + if not key or not expression: + raise ValueError(f"--condition must include both CHECK and CPP_EXPR: {item!r}") + bindings[key] = expression + return bindings + + +def float_literal(value: float) -> str: + text = f"{value:.6g}" + if "e" not in text.lower() and "." not in text: + text += ".0" + return f"{text}f" + + +def escape_cpp_string(value: str) -> str: + return ( + value.replace("\\", "\\\\") + .replace('"', '\\"') + .replace("\n", "\\n") + .replace("\r", "\\r") + .replace("\t", "\\t") + ) + + +def cpp_comment(value: str) -> str: + return value.replace("*/", "* /").replace("\n", " ") + + +def parse_event_types(event_bus_path: Path) -> list[str]: + text = event_bus_path.read_text(encoding="utf-8") + match = re.search(r"enum\s+class\s+EventType\s*:[^{]+{(?P.*?)};", text, re.S) + if not match: + raise ValueError(f"Cannot find enum class EventType in {event_bus_path}") + + body = re.sub(r"//.*", "", match.group("body")) + events: list[str] = [] + for item in body.split(","): + name = item.split("=", 1)[0].strip() + if EVENT_RE.match(name): + events.append(name) + + if not events: + raise ValueError(f"No EVT_* entries found in {event_bus_path}") + return events + + +def collect_listen_events(node: Node) -> list[str]: + events: list[str] = [] + if node.name == "Listen": + event = node.args.get("event") + if isinstance(event, str): + events.append(event) + for child in node.children: + events.extend(collect_listen_events(child)) + return events + + +def validate_listen_events(root: Node, event_names: list[str]) -> None: + valid = set(event_names) + # PetInternalEventType 的值(0x8000+)不在 EventType 枚举里,但运行时通过 static_cast 共用同一通道,跳过验证 + invalid = sorted({ + event for event in collect_listen_events(root) + if event not in valid and not INTERNAL_EVENT_RE.match(event) + }) + if invalid: + raise ValueError( + "Listen event(s) not present in EventType: " + + ", ".join(invalid) + + ". Update example.json or event_bus.h first." + ) + + +def namespace_open(namespace: str) -> list[str]: + parts = [part for part in namespace.split("::") if part] + if not parts: + raise ValueError("namespace must not be empty") + return [f"namespace {part} {{" for part in parts] + + +def namespace_close(namespace: str) -> list[str]: + parts = [part for part in namespace.split("::") if part] + return [f"}} // namespace {part}" for part in reversed(parts)] + + +def generate_runner_header(namespace: str) -> str: + out: list[str] = [ + "#pragma once", + "", + "#include ", + "#include ", + "#include ", + '#include "11_apps/pet_game_app/pet_state_interfaces.h"', + "", + "struct cJSON;", + "", + ] + out.extend(namespace_open(namespace)) + out.extend([ + "", + "class JsonBehaviorRunner {", + "public:", + " JsonBehaviorRunner(const char* json_data, size_t json_size);", + " ~JsonBehaviorRunner();", + "", + " JsonBehaviorRunner(const JsonBehaviorRunner&) = delete;", + " JsonBehaviorRunner& operator=(const JsonBehaviorRunner&) = delete;", + "", + " void OnEnter(IPetContext* ctx);", + " void OnExit(IPetContext* ctx);", + " bool HandleEvent(IPetContext* ctx, const Event& evt);", + " void OnTick(IPetContext* ctx);", + "", + "private:", + " struct Frame {", + " const cJSON* children = nullptr;", + " int index = 0;", + " bool loop = false;", + " };", + "", + " bool EnsureLoaded();", + " const cJSON* FindIdleRoot() const;", + " const cJSON* FindListenBranch(EventType event_type) const;", + "", + " void StartIdle(IPetContext* ctx);", + " void RunIdleUntilBlocked(IPetContext* ctx);", + " bool ExecuteImmediate(IPetContext* ctx, const cJSON* node);", + " void ExecuteImmediateChildren(IPetContext* ctx, const cJSON* children);", + " void ExecuteLeaf(IPetContext* ctx, const cJSON* node);", + " bool TryPlayScript(IPetContext* ctx, const char* script, const char* source);", + "", + " bool EvaluateCondition(IPetContext* ctx, const cJSON* node);", + " void ScheduleWait(const cJSON* wait_node);", + " void ApplyMessageAction(IPetContext* ctx, const char* message);", + "", + " const char* json_data_ = nullptr;", + " size_t json_size_ = 0;", + " cJSON* document_ = nullptr;", + " const cJSON* root_ = nullptr;", + " std::vector idle_stack_;", + " int64_t next_wakeup_us_ = 0;", + " bool script_playing_ = false;", + "};", + "", + ]) + out.extend(namespace_close(namespace)) + out.append("") + return "\n".join(out) + + +def generate_event_type_name_cases(event_names: list[str]) -> list[str]: + out: list[str] = [] + for event_name in event_names: + out.append(f" case EventType::{event_name}:") + out.append(f' return "{event_name}";') + out.append(" // ------ PetInternalEventType (\u5927\u8111\u4ee3\u8c22\u4fe1\u53f7, 0x8000+) ------") + for event_name in PET_INTERNAL_EVENT_NAMES: + out.append(f" case static_cast({event_name}):") + out.append(f' return "{event_name}";') + return out + + +def generate_runner_cpp(*, header: str, namespace: str, event_names: list[str], tag: str) -> str: + out: list[str] = [ + f'#include "{escape_cpp_string(header)}"', + "", + "#include ", + "#include ", + '#include "cJSON.h"', + '#include "esp_log.h"', + '#include "esp_random.h"', + '#include "esp_timer.h"', + '#include "11_apps/pet_game_app/pet_types.h"', + "", + f'static const char* TAG = "{escape_cpp_string(tag)}";', + "", + ] + out.extend(namespace_open(namespace)) + out.extend([ + "", + "namespace {", + "", + "constexpr int64_t kUsPerSecond = 1000000;", + "constexpr int64_t kFallbackDelayUs = 1000000;", + "", + "const cJSON* GetObject(const cJSON* object, const char* key) {", + " const cJSON* item = cJSON_GetObjectItemCaseSensitive(object, key);", + " return cJSON_IsObject(item) ? item : nullptr;", + "}", + "", + "const cJSON* GetArray(const cJSON* object, const char* key) {", + " const cJSON* item = cJSON_GetObjectItemCaseSensitive(object, key);", + " return cJSON_IsArray(item) ? item : nullptr;", + "}", + "", + "const char* GetString(const cJSON* object, const char* key) {", + " const cJSON* item = cJSON_GetObjectItemCaseSensitive(object, key);", + " return cJSON_IsString(item) ? item->valuestring : nullptr;", + "}", + "", + "double GetNumber(const cJSON* object, const char* key, double default_value) {", + " const cJSON* item = cJSON_GetObjectItemCaseSensitive(object, key);", + " return cJSON_IsNumber(item) ? item->valuedouble : default_value;", + "}", + "", + "const char* NodeName(const cJSON* node) {", + ' const char* name = GetString(node, "name");', + ' return name ? name : "";', + "}", + "", + "bool NameIs(const cJSON* node, const char* expected) {", + " return strcmp(NodeName(node), expected) == 0;", + "}", + "", + "const cJSON* NodeArgs(const cJSON* node) {", + ' return GetObject(node, "args");', + "}", + "", + "const cJSON* NodeChildren(const cJSON* node) {", + ' return GetArray(node, "children");', + "}", + "", + "bool StringContains(const char* text, const char* needle) {", + " return text && strstr(text, needle) != nullptr;", + "}", + "", + "bool RandomLessThan(double threshold) {", + " if (threshold <= 0.0) {", + " return false;", + " }", + " if (threshold >= 1.0) {", + " return true;", + " }", + " return (esp_random() % 10000) < static_cast(threshold * 10000.0);", + "}", + "", + "bool StringEquals(const char* left, const char* right) {", + " return left && right && strcmp(left, right) == 0;", + "}", + "", + "int GetPhysioValue(IPetContext* ctx, const char* attr) {", + ' if (StringEquals(attr, "fullness") || StringEquals(attr, "hunger")) {', + " return ctx->GetFullness();", + " }", + ' if (StringEquals(attr, "cleanliness")) {', + " return ctx->GetCleanliness();", + " }", + ' if (StringEquals(attr, "energy")) {', + " return ctx->GetEnergy();", + " }", + ' if (StringEquals(attr, "happiness") || StringEquals(attr, "mood")) {', + " return ctx->GetHappiness();", + " }", + ' ESP_LOGW(TAG, "Unknown physiology attr: %s", attr ? attr : "");', + " return 0;", + "}", + "", + "void AddPhysioValue(IPetContext* ctx, const char* attr, int amount) {", + ' if (StringEquals(attr, "fullness") || StringEquals(attr, "hunger")) {', + " ctx->AddFullness(amount);", + " return;", + " }", + ' if (StringEquals(attr, "cleanliness")) {', + " ctx->AddCleanliness(amount);", + " return;", + " }", + ' if (StringEquals(attr, "energy")) {', + " ctx->AddEnergy(amount);", + " return;", + " }", + ' if (StringEquals(attr, "happiness") || StringEquals(attr, "mood")) {', + " ctx->AddHappiness(amount);", + " return;", + " }", + ' ESP_LOGW(TAG, "Unknown physiology attr: %s", attr ? attr : "");', + "}", + "", + "void SetPhysioValue(IPetContext* ctx, const char* attr, int target) {", + " int current = GetPhysioValue(ctx, attr);", + " int delta = target - current;", + " if (delta != 0) {", + " AddPhysioValue(ctx, attr, delta);", + " }", + "}", + "", + "bool CompareInt(int left, const char* op, int right) {", + ' if (!op || StringEquals(op, "<=")) {', + " return left <= right;", + " }", + ' if (StringEquals(op, "<")) {', + " return left < right;", + " }", + ' if (StringEquals(op, ">=")) {', + " return left >= right;", + " }", + ' if (StringEquals(op, ">")) {', + " return left > right;", + " }", + ' if (StringEquals(op, "==") || StringEquals(op, "=")) {', + " return left == right;", + " }", + ' if (StringEquals(op, "!=")) {', + " return left != right;", + " }", + ' ESP_LOGW(TAG, "Unknown comparison op: %s", op);', + " return false;", + "}", + "", + "bool CompareFloat(float left, const char* op, float right) {", + ' if (!op || StringEquals(op, "<=")) {', + " return left <= right;", + " }", + ' if (StringEquals(op, "<")) {', + " return left < right;", + " }", + ' if (StringEquals(op, ">=")) {', + " return left >= right;", + " }", + ' if (StringEquals(op, ">")) {', + " return left > right;", + " }", + ' if (StringEquals(op, "==") || StringEquals(op, "=")) {', + " return left == right;", + " }", + ' if (StringEquals(op, "!=")) {', + " return left != right;", + " }", + ' ESP_LOGW(TAG, "Unknown comparison op: %s", op);', + " return false;", + "}", + "", + "const char* EventTypeName(EventType type) {", + " switch (type) {", + ]) + out.extend(generate_event_type_name_cases(event_names)) + out.extend([ + " default:", + ' return "";', + " }", + "}", + "", + "} // namespace", + "", + "JsonBehaviorRunner::JsonBehaviorRunner(const char* json_data, size_t json_size)", + " : json_data_(json_data), json_size_(json_size) {}", + "", + "JsonBehaviorRunner::~JsonBehaviorRunner() {", + " if (document_) {", + " cJSON_Delete(document_);", + " document_ = nullptr;", + " }", + "}", + "", + "void JsonBehaviorRunner::OnEnter(IPetContext* ctx) {", + " if (!EnsureLoaded()) {", + " return;", + " }", + ' ESP_LOGI(TAG, "Enter JSON behavior");', + " script_playing_ = false;", + " StartIdle(ctx);", + "}", + "", + "void JsonBehaviorRunner::OnExit(IPetContext* ctx) {", + " ctx->StopScript();", + " idle_stack_.clear();", + " next_wakeup_us_ = 0;", + " script_playing_ = false;", + "}", + "", + "bool JsonBehaviorRunner::HandleEvent(IPetContext* ctx, const Event& evt) {", + " if (!EnsureLoaded()) {", + " return false;", + " }", + "", + " if (evt.type == EventType::EVT_SCRIPT_DONE) {", + " script_playing_ = false;", + " if (idle_stack_.empty()) {", + ' ESP_LOGD(TAG, "[BT] Script done, idle stack empty — restarting idle");', + " StartIdle(ctx);", + " }", + " return false;", + " }", + "", + " const cJSON* listen = FindListenBranch(evt.type);", + " if (!listen) {", + " return false;", + " }", + "", + " const cJSON* listen_args = NodeArgs(listen);", + ' const char* abort_type = listen_args ? GetString(listen_args, "abortType") : nullptr;', + ' const bool is_interrupt = abort_type && strcmp(abort_type, "interrupt") == 0;', + "", + " if (is_interrupt) {", + ' ESP_LOGI(TAG, "[BT] Interrupt: aborting idle for %s", EventTypeName(evt.type));', + " ctx->StopScript();", + " script_playing_ = false;", + " idle_stack_.clear();", + " next_wakeup_us_ = 0;", + " }", + "", + ' ESP_LOGI(TAG, "Handle JSON behavior event: %s", EventTypeName(evt.type));', + " ExecuteImmediateChildren(ctx, NodeChildren(listen));", + " return true;", + "}", + "", + "void JsonBehaviorRunner::OnTick(IPetContext* ctx) {", + " if (script_playing_) {", + " return;", + " }", + "", + " if (next_wakeup_us_ <= 0 || esp_timer_get_time() < next_wakeup_us_) {", + " return;", + " }", + "", + " next_wakeup_us_ = 0;", + " RunIdleUntilBlocked(ctx);", + "}", + "", + "bool JsonBehaviorRunner::EnsureLoaded() {", + " if (document_) {", + " return root_ != nullptr;", + " }", + "", + " if (!json_data_ || json_size_ == 0) {", + ' ESP_LOGE(TAG, "Behavior JSON data is empty");', + " return false;", + " }", + "", + " document_ = cJSON_ParseWithLength(json_data_, json_size_);", + " if (!document_) {", + ' ESP_LOGE(TAG, "Failed to parse behavior JSON");', + " return false;", + " }", + "", + ' root_ = GetObject(document_, "root");', + " if (!root_) {", + ' ESP_LOGE(TAG, "Behavior JSON has no object field named root");', + " return false;", + " }", + "", + ' const char* behavior_name = GetString(document_, "name");', + ' ESP_LOGI(TAG, "Loaded behavior tree: %s", behavior_name ? behavior_name : "");', + " return true;", + "}", + "", + "const cJSON* JsonBehaviorRunner::FindIdleRoot() const {", + " if (!root_) {", + " return nullptr;", + " }", + "", + ' if (NameIs(root_, "Repeat")) {', + " return root_;", + " }", + "", + " const cJSON* children = NodeChildren(root_);", + " if (!children) {", + " return root_;", + " }", + "", + " const int size = cJSON_GetArraySize(children);", + " for (int i = 0; i < size; ++i) {", + " const cJSON* child = cJSON_GetArrayItem(children, i);", + ' if (NameIs(child, "Repeat")) {', + " return child;", + " }", + " }", + "", + " return root_;", + "}", + "", + "const cJSON* JsonBehaviorRunner::FindListenBranch(EventType event_type) const {", + " const char* event_name = EventTypeName(event_type);", + " if (!event_name[0] || !root_) {", + " return nullptr;", + " }", + "", + " const cJSON* children = NodeChildren(root_);", + " if (!children) {", + " return nullptr;", + " }", + "", + " const int size = cJSON_GetArraySize(children);", + " for (int i = 0; i < size; ++i) {", + " const cJSON* child = cJSON_GetArrayItem(children, i);", + ' if (!NameIs(child, "Listen")) {', + " continue;", + " }", + "", + " const cJSON* args = NodeArgs(child);", + ' const char* event = args ? GetString(args, "event") : nullptr;', + " if (event && strcmp(event, event_name) == 0) {", + " return child;", + " }", + " }", + "", + " return nullptr;", + "}", + "", + "void JsonBehaviorRunner::StartIdle(IPetContext* ctx) {", + " idle_stack_.clear();", + " next_wakeup_us_ = 0;", + "", + " const cJSON* idle_root = FindIdleRoot();", + " const cJSON* children = NodeChildren(idle_root);", + " if (!children) {", + " ExecuteLeaf(ctx, idle_root);", + " return;", + " }", + "", + " Frame frame;", + " frame.children = children;", + " frame.index = 0;", + ' frame.loop = NameIs(idle_root, "Repeat");', + " idle_stack_.push_back(frame);", + " RunIdleUntilBlocked(ctx);", + "}", + "", + "void JsonBehaviorRunner::RunIdleUntilBlocked(IPetContext* ctx) {", + " while (!idle_stack_.empty()) {", + " Frame& frame = idle_stack_.back();", + " const int size = cJSON_GetArraySize(frame.children);", + "", + " if (frame.index >= size) {", + " if (frame.loop) {", + " frame.index = 0;", + " } else {", + " idle_stack_.pop_back();", + " }", + " continue;", + " }", + "", + " const cJSON* node = cJSON_GetArrayItem(frame.children, frame.index);", + ' if (NameIs(node, "Wait")) {', + " ScheduleWait(node);", + " frame.index++;", + " return;", + " }", + "", + ' if (NameIs(node, "Sequence") || NameIs(node, "Parallel") || NameIs(node, "Repeat")) {', + " frame.index++;", + " const cJSON* children = NodeChildren(node);", + " if (children) {", + " Frame child_frame;", + " child_frame.children = children;", + " child_frame.index = 0;", + ' child_frame.loop = NameIs(node, "Repeat");', + " idle_stack_.push_back(child_frame);", + " }", + " continue;", + " }", + "", + ' if (NameIs(node, "IfElse")) {', + " frame.index++;", + " const cJSON* children = NodeChildren(node);", + " const cJSON* condition = children ? cJSON_GetArrayItem(children, 0) : nullptr;", + " const int branch_index = EvaluateCondition(ctx, condition) ? 1 : 2;", + " const cJSON* branch = children ? cJSON_GetArrayItem(children, branch_index) : nullptr;", + " const cJSON* branch_children = NodeChildren(branch);", + " if (branch_children) {", + " Frame branch_frame;", + " branch_frame.children = branch_children;", + " branch_frame.index = 0;", + " branch_frame.loop = false;", + " idle_stack_.push_back(branch_frame);", + " } else if (branch) {", + " ExecuteLeaf(ctx, branch);", + " }", + " continue;", + " }", + "", + ' if (NameIs(node, "Selector")) {', + " frame.index++;", + " const cJSON* sel_children = NodeChildren(node);", + " if (!sel_children) { continue; }", + " const int sel_size = cJSON_GetArraySize(sel_children);", + " for (int s = 0; s < sel_size; ++s) {", + " const cJSON* candidate = cJSON_GetArrayItem(sel_children, s);", + ' if (NameIs(candidate, "Sequence")) {', + " const cJSON* seq_ch = NodeChildren(candidate);", + " if (!seq_ch) continue;", + " const cJSON* first = cJSON_GetArrayItem(seq_ch, 0);", + " if (!EvaluateCondition(ctx, first)) continue;", + " Frame sel_frame;", + " sel_frame.children = seq_ch;", + " sel_frame.index = 1;", + " sel_frame.loop = false;", + " idle_stack_.push_back(sel_frame);", + " break;", + " } else {", + " ExecuteLeaf(ctx, candidate);", + " break;", + " }", + " }", + " if (script_playing_) return;", + " continue;", + " }", + "", + ' if (NameIs(node, "PlayScript")) {', + ' if (script_playing_) {', + ' ESP_LOGD(TAG, "[BT] Pause idle tree: waiting current script to finish before next PlayScript");', + " return;", + " }", + "", + " ExecuteLeaf(ctx, node);", + " if (script_playing_) {", + " frame.index++;", + " return;", + " }", + "", + " frame.index++;", + " continue;", + " }", + "", + " ExecuteLeaf(ctx, node);", + " frame.index++;", + " }", + "}", + "", + "bool JsonBehaviorRunner::ExecuteImmediate(IPetContext* ctx, const cJSON* node) {", + " if (!node) return false;", + "", + ' if (NameIs(node, "Sequence")) {', + " const cJSON* children = NodeChildren(node);", + " if (!children) return true;", + " const int size = cJSON_GetArraySize(children);", + " for (int i = 0; i < size; ++i) {", + " if (!ExecuteImmediate(ctx, cJSON_GetArrayItem(children, i))) return false;", + " }", + " return true;", + " }", + "", + ' if (NameIs(node, "Selector")) {', + " const cJSON* children = NodeChildren(node);", + " if (!children) return false;", + " const int size = cJSON_GetArraySize(children);", + " for (int i = 0; i < size; ++i) {", + " if (ExecuteImmediate(ctx, cJSON_GetArrayItem(children, i))) return true;", + " }", + " return false;", + " }", + "", + ' if (NameIs(node, "Parallel") || NameIs(node, "Repeat") || NameIs(node, "Listen")) {', + " const cJSON* children = NodeChildren(node);", + " if (!children) return true;", + " const int size = cJSON_GetArraySize(children);", + " for (int i = 0; i < size; ++i) {", + " ExecuteImmediate(ctx, cJSON_GetArrayItem(children, i));", + " }", + " return true;", + " }", + "", + ' if (NameIs(node, "IfElse")) {', + " const cJSON* children = NodeChildren(node);", + " const cJSON* condition = children ? cJSON_GetArrayItem(children, 0) : nullptr;", + " const int branch_index = EvaluateCondition(ctx, condition) ? 1 : 2;", + " return ExecuteImmediate(ctx, children ? cJSON_GetArrayItem(children, branch_index) : nullptr);", + " }", + "", + ' if (NameIs(node, "CheckPhysio") || NameIs(node, "CheckUtility") || NameIs(node, "Check")) {', + " return EvaluateCondition(ctx, node);", + " }", + "", + " ExecuteLeaf(ctx, node);", + " return true;", + "}", + "", + "void JsonBehaviorRunner::ExecuteImmediateChildren(IPetContext* ctx, const cJSON* children) {", + " if (!children) return;", + " const int size = cJSON_GetArraySize(children);", + " for (int i = 0; i < size; ++i) {", + " ExecuteImmediate(ctx, cJSON_GetArrayItem(children, i));", + " }", + "}", + "", + "void JsonBehaviorRunner::ExecuteLeaf(IPetContext* ctx, const cJSON* node) {", + " if (!node) {", + " return;", + " }", + "", + ' ESP_LOGD(TAG, "[BT] Execute: %s", NodeName(node));', + "", + " const cJSON* args = NodeArgs(node);", + ' if (NameIs(node, "Log")) {', + ' const char* message = args ? GetString(args, "message") : nullptr;', + ' ESP_LOGI(TAG, "%s", message ? message : "");', + " ApplyMessageAction(ctx, message);", + " return;", + " }", + "", + ' if (NameIs(node, "Wait")) {', + " ScheduleWait(node);", + " return;", + " }", + "", + ' if (NameIs(node, "Check")) {', + " (void)EvaluateCondition(ctx, node);", + " return;", + " }", + "", + ' if (NameIs(node, "AddPhysio")) {', + ' const char* attr = args ? GetString(args, "attr") : nullptr;', + ' const int amount = static_cast(args ? GetNumber(args, "amount", 0.0) : 0.0);', + ' ESP_LOGD(TAG, "[BT] AddPhysio %s %+d (before=%d)", attr ? attr : "?", amount, GetPhysioValue(ctx, attr));', + " AddPhysioValue(ctx, attr, amount);", + " return;", + " }", + "", + ' if (NameIs(node, "SetPhysio")) {', + ' const char* attr = args ? GetString(args, "attr") : nullptr;', + ' const int value = static_cast(args ? GetNumber(args, "value", 0.0) : 0.0);', + ' ESP_LOGD(TAG, "[BT] SetPhysio %s => %d (before=%d)", attr ? attr : "?", value, GetPhysioValue(ctx, attr));', + " SetPhysioValue(ctx, attr, value);", + " return;", + " }", + "", + ' if (NameIs(node, "PlayScript")) {', + ' const char* script = args ? GetString(args, "script") : nullptr;', + " if (!script && args) {", + ' script = GetString(args, "path");', + " }", + " if (!script && args) {", + ' script = GetString(args, "name");', + " }", + " if (script) {", + ' (void)TryPlayScript(ctx, script, "PlayScript");', + " } else {", + ' ESP_LOGW(TAG, "PlayScript node is missing script/path/name");', + " }", + " return;", + " }", + "", + ' if (NameIs(node, "RequestModeSwitch")) {', + ' const char* mode = args ? GetString(args, "mode") : nullptr;', + ' if (mode && strcmp(mode, "MODE_MENU") == 0) {', + " ctx->RequestModeSwitch(PetModeType::MODE_MENU);", + ' } else if (mode && strcmp(mode, "MODE_IDLE") == 0) {', + " ctx->RequestModeSwitch(PetModeType::MODE_IDLE);", + ' } else if (mode && strcmp(mode, "MODE_SLEEPING") == 0) {', + " ctx->RequestModeSwitch(PetModeType::MODE_SLEEPING);", + " } else {", + ' ESP_LOGW(TAG, "Unsupported RequestModeSwitch mode: %s", mode ? mode : "");', + " }", + " return;", + " }", + "", + ' ESP_LOGW(TAG, "Unsupported JSON behavior node: %s", NodeName(node));', + "}", + "", + "bool JsonBehaviorRunner::EvaluateCondition(IPetContext* ctx, const cJSON* node) {", + " if (!node) {", + " return false;", + " }", + "", + " const cJSON* args = NodeArgs(node);", + "", + ' if (NameIs(node, "CheckPhysio")) {', + ' const char* attr = args ? GetString(args, "attr") : nullptr;', + ' const char* op = args ? GetString(args, "op") : nullptr;', + ' const int target = static_cast(args ? GetNumber(args, "value", 0.0) : 0.0);', + " bool result = CompareInt(GetPhysioValue(ctx, attr), op, target);", + ' ESP_LOGD(TAG, "[BT] CheckPhysio %s %s %d => current=%d result=%s",', + ' attr ? attr : "?", op ? op : "<=", target,', + ' GetPhysioValue(ctx, attr), result ? "true" : "false");', + " return result;", + " }", + "", + ' if (NameIs(node, "CheckUtility")) {', + ' const char* attr = args ? GetString(args, "attr") : nullptr;', + ' const char* op = args ? GetString(args, "op") : nullptr;', + ' const float thr = static_cast(args ? GetNumber(args, "value", 0.0) : 0.0);', + " if (!attr) {", + ' ESP_LOGW(TAG, "[BT] CheckUtility missing attr");', + " return false;", + " }", + " const BehaviorUtility u = ctx->GetBehaviorUtilities();", + " float actual = 0.0f;", + ' if (StringEquals(attr, "hungry")) { actual = u.hungry; }', + ' else if (StringEquals(attr, "sleepy")) { actual = u.sleepy; }', + ' else if (StringEquals(attr, "dirty")) { actual = u.dirty; }', + ' else if (StringEquals(attr, "laugh")) { actual = u.laugh; }', + ' else if (StringEquals(attr, "curious")) { actual = u.curious; }', + ' else if (StringEquals(attr, "sad")) { actual = u.sad; }', + " else {", + ' ESP_LOGW(TAG, "[BT] CheckUtility unknown attr: %s", attr);', + " return false;", + " }", + " bool result = CompareFloat(actual, op, thr);", + ' ESP_LOGD(TAG, "[BT] CheckUtility %s %s %.2f => actual=%.2f result=%s",', + ' attr, op ? op : ">=", thr, actual, result ? "true" : "false");', + " return result;", + " }", + "", + ' if (!NameIs(node, "Check")) {', + " return false;", + " }", + "", + ' const char* value = args ? GetString(args, "value") : nullptr;', + " if (!value) {", + " return false;", + " }", + "", + " double threshold = 0.0;", + ' if (sscanf(value, "Math.random() < %lf", &threshold) == 1) {', + " return RandomLessThan(threshold);", + " }", + "", + ' if (strcmp(value, "energyHigh") == 0 || strcmp(value, "emotionHigh") == 0) {', + " return ctx->GetEnergy() >= 50;", + " }", + "", + ' if (strcmp(value, "hungerHigh") == 0) {', + " return ctx->GetHunger() >= 50;", + " }", + "", + ' if (strcmp(value, "true") == 0) {', + " return true;", + " }", + "", + ' ESP_LOGW(TAG, "Unknown Check expression: %s", value);', + " return false;", + "}", + "", + "void JsonBehaviorRunner::ScheduleWait(const cJSON* wait_node) {", + " const cJSON* args = NodeArgs(wait_node);", + ' const double base_seconds = args ? GetNumber(args, "time", 0.0) : 0.0;', + ' const double random_seconds = args ? GetNumber(args, "random", 0.0) : 0.0;', + " int64_t delay_us = static_cast(base_seconds * kUsPerSecond);", + "", + " if (random_seconds > 0.0) {", + " const uint32_t random_us = static_cast(random_seconds * kUsPerSecond);", + " delay_us += esp_random() % (random_us + 1);", + " }", + "", + " if (delay_us <= 0) {", + " delay_us = kFallbackDelayUs;", + " }", + "", + " next_wakeup_us_ = esp_timer_get_time() + delay_us;", + "}", + "", + "void JsonBehaviorRunner::ApplyMessageAction(IPetContext* ctx, const char* message) {", + " if (!message) {", + " return;", + " }", + "", + ' if (StringContains(message, "OPEN_MENU")) {', + " ctx->RequestModeSwitch(PetModeType::MODE_MENU);", + " return;", + " }", + "", + ' if (StringContains(message, "PET_IDLE")) {', + ' (void)TryPlayScript(ctx, "baby/idle/look_around", "Log/PET_IDLE");', + ' } else if (StringContains(message, "PET_CURIOUS")) {', + ' (void)TryPlayScript(ctx, "baby/interaction/curious", "Log/PET_CURIOUS");', + ' } else if (StringContains(message, "PET_SHY")) {', + ' (void)TryPlayScript(ctx, "baby/interaction/shy", "Log/PET_SHY");', + ' } else if (StringContains(message, "PET_HURT")) {', + ' (void)TryPlayScript(ctx, "baby/interaction/hurt", "Log/PET_HURT");', + ' } else if (StringContains(message, "PET_HAPPY")) {', + ' (void)TryPlayScript(ctx, "baby/interaction/happy", "Log/PET_HAPPY");', + ' } else if (StringContains(message, "PET_CLINGY")) {', + ' (void)TryPlayScript(ctx, "baby/interaction/clingy", "Log/PET_CLINGY");', + " }", + "}", + "", + "bool JsonBehaviorRunner::TryPlayScript(IPetContext* ctx, const char* script, const char* source) {", + " if (!script || !script[0]) {", + " return false;", + " }", + "", + " if (script_playing_) {", + ' ESP_LOGD(TAG, "[BT] Skip PlayScript while another script is running: source=%s script=%s",', + ' source ? source : "", script);', + " return false;", + " }", + "", + " script_playing_ = true;", + ' ESP_LOGD(TAG, "[BT] PlayScript => %s (source=%s)", script, source ? source : "");', + " ctx->PlayScript(script);", + " return true;", + "}", + "", + ]) + out.extend(namespace_close(namespace)) + out.append("") + return "\n".join(out) + + +def main() -> int: + args = parse_args() + script_dir = Path(__file__).resolve().parent + input_path = args.input.resolve() if args.input.is_absolute() else (script_dir / args.input).resolve() + output_cpp_path = args.output.resolve() if args.output else input_path.with_name(DEFAULT_CPP) + output_header_path = ( + args.output_header.resolve() if args.output_header else input_path.with_name(DEFAULT_HEADER) + ) + event_bus_path = ( + args.event_bus.resolve() + if args.event_bus + else (script_dir / DEFAULT_EVENT_BUS).resolve() + ) + + try: + document, root = load_tree(input_path) + event_names = parse_event_types(event_bus_path) + validate_listen_events(root, event_names) + cpp = generate_runner_cpp( + header=args.header, + namespace=args.namespace, + tag=args.tag or args.class_name, + event_names=event_names, + ) + header = generate_runner_header(args.namespace) + + if args.dry_run: + print(cpp) + print(header, file=sys.stderr) + return 0 + + for path in (output_cpp_path, output_header_path): + if path.exists() and not args.force: + print(f"Refusing to overwrite existing file: {path}", file=sys.stderr) + print("Use --force to overwrite it.", file=sys.stderr) + return 2 + + output_cpp_path.parent.mkdir(parents=True, exist_ok=True) + output_header_path.parent.mkdir(parents=True, exist_ok=True) + output_cpp_path.write_text(cpp, encoding="utf-8") + output_header_path.write_text(header, encoding="utf-8") + print(f"Generated {output_cpp_path}") + print(f"Generated {output_header_path}") + return 0 + except (OSError, ValueError, json.JSONDecodeError) as exc: + print(f"error: {exc}", file=sys.stderr) + return 1 + + +if __name__ == "__main__": + raise SystemExit(main()) diff --git a/baby/node-config.b3-setting b/baby/node-config.b3-setting new file mode 100644 index 0000000..9d9292f --- /dev/null +++ b/baby/node-config.b3-setting @@ -0,0 +1,1066 @@ +[ + { + "name": "AlwaysFailure", + "type": "Decorator", + "children": 1, + "status": [ + "failure", + "|running" + ], + "desc": "始终返回失败", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `running` 时,返回 `running`\n+ 其它情况,不管子节点是否成功都返回 `failure`\n" + }, + { + "name": "AlwaysRunning", + "type": "Decorator", + "children": 1, + "status": [ + "running" + ], + "desc": "始终返回运行中状态", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 始终返回 `running`\n" + }, + { + "name": "AlwaysSuccess", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running" + ], + "desc": "始终返回成功", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `running` 时,返回 `running`\n+ 其它情况,不管子节点是否成功都返回 `success`\n" + }, + { + "name": "Assert", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "断言", + "args": [ + { + "name": "message", + "type": "string", + "desc": "消息" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `failure` 时,抛出异常\n+ 其余情况返回子节点的执行状态\n" + }, + { + "name": "Calculate", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "简单的数值公式计算", + "args": [ + { + "name": "value", + "type": "expr", + "desc": "计算公式" + } + ], + "output": [ + "计算结果" + ], + "doc": "+ 做简单的数值公式计算,返回结果到输出\n" + }, + { + "name": "Case", + "type": "Composite", + "children": 2, + "status": [ + "&success", + "|failure", + "|running" + ], + "desc": "分支选择", + "doc": "+ 必须有两个子节点\n+ 第一个子节点为判断条件\n+ 第二个子节点为判断为 `success` 时执行的节点\n+ 此节点不会真正意义的执行,而是交由 `Switch` 节点来执行\n" + }, + { + "name": "Check", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "检查True或False", + "args": [ + { + "name": "value", + "type": "expr", + "desc": "值" + } + ], + "doc": "+ 做简单数值公式判定,返回 `success` 或 `failure`\n" + }, + { + "name": "Concat", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "将两个输入合并为一个数组,并返回新数组", + "input": [ + "数组1", + "数组2" + ], + "output": [ + "新数组" + ], + "doc": "+ 如果输入不是数组,则返回 `failure`\n" + }, + { + "name": "Delay", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "延时执行子节点", + "input": [ + "延时时间?" + ], + "args": [ + { + "name": "delay", + "type": "float?", + "desc": "延时时间", + "oneof": "延时时间" + }, + { + "name": "cacheVars", + "type": "string[]?", + "desc": "暂存环境变量" + } + ], + "doc": "+ 当延时触发时,执行第一个子节点,多个仅执行第一个\n+ 如果子节点返回 `running`,会中断执行并清理执行栈" + }, + { + "name": "Filter", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "failure", + "|running" + ], + "desc": "返回满足条件的元素", + "input": [ + "输入数组" + ], + "output": [ + "变量", + "新数组" + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 遍历输入数组,将当前元素写入`变量`,满足条件的元素放入新数组\n+ 只有当新数组不为空时,才返回 `success`\n" + }, + { + "name": "ForEach", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running", + "|failure" + ], + "desc": "遍历数组", + "input": [ + "数组" + ], + "output": [ + "变量", + "索引?" + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 遍历输入数组,将当前元素写入`变量`\n+ 当子节点返回 `failure` 时,退出遍历并返回 `failure` 状态\n+ 执行完所有子节点后,返回 `success`" + }, + { + "name": "GetField", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "获取对象的字段值", + "args": [ + { + "name": "field", + "type": "string?", + "desc": "字段(field)", + "oneof": "字段(field)" + } + ], + "input": [ + "对象", + "字段(field)?" + ], + "output": [ + "字段值(value)" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 只有获取到合法元素时候才会返回 `success`,否则返回 `failure`\n" + }, + { + "name": "IfElse", + "type": "Composite", + "children": 3, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "条件执行", + "doc": "+ 必须有三个子节点\n+ 第一个子节点为条件节点\n+ 第二个子节点为条件为 `success` 时执行的节点\n+ 第三个子节点为条件为 `failure` 时执行的节点,\n" + }, + { + "name": "Includes", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断元素是否在数组中", + "input": [ + "数组", + "元素" + ], + "doc": "+ 若输入的元素不合法,返回 `failure`\n+ 只有数组包含元素时返回 `success`,否则返回 `failure`\n" + }, + { + "name": "Index", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "索引输入的数组", + "args": [ + { + "name": "index", + "type": "int?", + "desc": "索引", + "oneof": "索引" + } + ], + "input": [ + "数组", + "索引?" + ], + "output": [ + "值" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 索引数组的时候,第一个元素的索引为 0\n+ 只有索引到有合法元素时候才会返回 `success`,否则返回 `failure`\n" + }, + { + "name": "Invert", + "type": "Decorator", + "children": 1, + "status": [ + "!success", + "!failure", + "|running" + ], + "desc": "反转子节点运行结果", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `success` 时返回 `failure`\n+ 当子节点返回 `failure` 时返回 `success`\n+ 当子节点返回 `error` 时返回 `error`\n" + }, + { + "name": "IsNull", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断变量是否不存在", + "input": [ + "判断的变量" + ] + }, + { + "name": "JustFailure", + "type": "Action", + "children": 0, + "status": [ + "failure" + ], + "desc": "什么都不干,只返回失败" + }, + { + "name": "JustSuccess", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "什么都不干,只返回成功" + }, + { + "name": "Let", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "定义新的变量名", + "input": [ + "已存在变量名?" + ], + "args": [ + { + "name": "value", + "type": "json?", + "desc": "值(value)", + "oneof": "已存在变量名" + } + ], + "output": [ + "新变量名" + ], + "doc": "+ 如果有输入变量,则给已有变量重新定义一个名字\n+ 如果`值(value)`为 `null`,则清除变量\n" + }, + { + "name": "Listen", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "侦听事件", + "input": [ + "目标对象?" + ], + "output": [ + "事件目标?", + "事件参数..." + ], + "args": [ + { + "name": "event", + "type": "string", + "desc": "事件", + "options": [ + { + "source": [ + { "name": "左键单击", "value": "EVT_KEY_LEFT_CLICK" }, + { "name": "左键双击", "value": "EVT_KEY_LEFT_DOUBLE_CLICK" }, + { "name": "左键长按", "value": "EVT_KEY_LEFT_LONG_PRESS" }, + { "name": "右键单击", "value": "EVT_KEY_RIGHT_CLICK" }, + { "name": "右键双击", "value": "EVT_KEY_RIGHT_DOUBLE_CLICK" }, + { "name": "右键长按", "value": "EVT_KEY_RIGHT_LONG_PRESS" }, + { "name": "右键三击", "value": "EVT_KEY_RIGHT_TRIPLE_CLICK" }, + { "name": "左右键同时长按", "value": "EVT_KEY_BOTH_LONG_PRESS" }, + { "name": "触摸单击", "value": "EVT_TOUCH_TAP" }, + { "name": "触摸三击", "value": "EVT_TOUCH_TRIPLE_TAP" }, + { "name": "摇晃", "value": "EVT_GYRO_SHAKE" }, + { "name": "人靠近", "value": "EVT_RADAR_PERSON_APPROACH" }, + { "name": "人离开", "value": "EVT_RADAR_PERSON_LEAVE" }, + { "name": "电量危险", "value": "EVT_BATTERY_CRITICAL" }, + { "name": "Wi-Fi 已连接", "value": "EVT_WIFI_CONNECTED" }, + { "name": "Wi-Fi 已断开", "value": "EVT_WIFI_DISCONNECTED" }, + { "name": "剧本播放完成", "value": "EVT_SCRIPT_DONE" }, + { "name": "饱食度变化", "value": "EVT_PHYSIOLOGY_FULLNESS_CHANGED" }, + { "name": "清洁度变化", "value": "EVT_PHYSIOLOGY_CLEANLINESS_CHANGED" }, + { "name": "精力值变化", "value": "EVT_PHYSIOLOGY_ENERGY_CHANGED" }, + { "name": "开心值变化", "value": "EVT_PHYSIOLOGY_HAPPINESS_CHANGED" } + ] + } + ] + } + ], + "doc": "+ 当事件触发时,执行第一个子节点,多个仅执行第一个\n+ 如果子节点返回 `running`,会中断执行并清理执行栈" + }, + { + "name": "Log", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "打印日志", + "input": [ + "日志?" + ], + "args": [ + { + "name": "message", + "type": "string", + "desc": "日志" + }, + { + "name": "level", + "type": "string", + "desc": "日志级别", + "default": "log", + "options": [ + { + "source": [ + { + "name": "LOG", + "value": "log" + }, + { + "name": "INFO", + "value": "info" + }, + { + "name": "DEBUG", + "value": "debug" + }, + { + "name": "WARN", + "value": "warn" + }, + { + "name": "ERROR", + "value": "error" + } + ] + } + ] + } + ] + }, + { + "name": "Math", + "type": "Action", + "desc": "执行数学运算", + "input": [ + "参数..." + ], + "output": [ + "结果" + ], + "status": [ + "success", + "failure" + ], + "args": [ + { + "name": "op", + "type": "string", + "desc": "数学运算类型", + "options": [ + { + "source": [ + { + "name": "绝对值", + "value": "abs" + }, + { + "name": "向上取整", + "value": "ceil" + }, + { + "name": "向下取整", + "value": "floor" + }, + { + "name": "四舍五入", + "value": "round" + }, + { + "name": "符号", + "value": "sign" + }, + { + "name": "正弦", + "value": "sin" + }, + { + "name": "余弦", + "value": "cos" + }, + { + "name": "正切", + "value": "tan" + }, + { + "name": "反正切2", + "value": "atan2" + }, + { + "name": "幂运算", + "value": "pow" + }, + { + "name": "平方根", + "value": "sqrt" + }, + { + "name": "自然对数", + "value": "log" + }, + { + "name": "最小值", + "value": "min" + }, + { + "name": "最大值", + "value": "max" + }, + { + "name": "随机数", + "value": "random" + }, + { + "name": "随机整数", + "value": "randInt" + }, + { + "name": "随机浮点数", + "value": "randFloat" + }, + { + "name": "求和", + "value": "sum" + }, + { + "name": "平均值", + "value": "average" + }, + { + "name": "乘积", + "value": "product" + } + ] + } + ] + }, + { + "name": "value1", + "type": "float?", + "desc": "参数1(优先使用)" + }, + { + "name": "value2", + "type": "float?", + "desc": "参数2(优先使用)" + } + ] + }, + { + "name": "NotNull", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断变量是否存在", + "input": [ + "判断的变量" + ] + }, + { + "name": "Now", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "获取当前时间", + "output": [ + "当前时间" + ] + }, + { + "name": "Once", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "failure", + "|running" + ], + "desc": "只执行一次", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 第一次执行完全部子节点时返回 `success`,之后永远返回 `failure`" + }, + { + "name": "Parallel", + "type": "Composite", + "status": [ + "success", + "|running" + ], + "children": -1, + "desc": "并行执行", + "doc": "+ 并行执行所有子节点\n+ 当有子节点返回 `running` 时,返回 `running` 状态\n+ 执行完所有子节点后,返回 `success`" + }, + { + "name": "Push", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "向数组中添加元素", + "input": [ + "数组", + "元素" + ], + "doc": "+ 当变量`数组`不是数组类型时返回 `failure`\n+ 其余返回 `success`\n" + }, + { + "name": "Race", + "type": "Composite", + "status": [ + "|success", + "&failure", + "|running" + ], + "children": -1, + "desc": "竞争执行", + "doc": "+ 并行执行所有子节点\n+ 当有子节点返回 `success` 时,立即返回 `success` 状态,并中断其他子节点\n+ 如果所有子节点返回 `failure`或 `error` 则返回 `failure`" + }, + { + "name": "RandomIndex", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "随机返回输入的其中一个!", + "input": [ + "输入目标" + ], + "output": [ + "随机目标", + "索引?" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 在输入数组中,随机返回其中一个\n+ 当输入数组为空时,或者没有合法元素,返回 `failure`\n" + }, + { + "name": "Repeat", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running", + "|failure" + ], + "desc": "循环执行", + "input": [ + "循环次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "循环次数", + "oneof": "循环次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `failure` 时,退出遍历并返回 `failure` 状态\n+ 执行完所有子节点后,返回 `success`\n" + }, + { + "name": "RetryUntilFailure", + "type": "Decorator", + "children": 1, + "status": [ + "!success", + "failure", + "running" + ], + "desc": "一直尝试直到子节点返回失败", + "input": [ + "最大尝试次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "最大尝试次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 只有当子节点返回 `failure` 时,才返回 `success`,其它情况返回 `running` 状态\n+ 如果设定了尝试次数,超过指定次数则返回 `failure`" + }, + { + "name": "RetryUntilSuccess", + "type": "Decorator", + "children": 1, + "status": [ + "|success", + "failure", + "running" + ], + "desc": "一直尝试直到子节点返回成功", + "input": [ + "最大尝试次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "最大尝试次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 只有当子节点返回 `success` 时,才返回 `success`,其它情况返回 `running` 状态\n+ 如果设定了尝试次数,超过指定次数则返回 `failure`" + }, + { + "name": "Selector", + "type": "Composite", + "children": -1, + "desc": "选择执行", + "status": [ + "|success", + "&failure", + "|running" + ], + "doc": "+ 一直往下执行,直到有子节点返回 `success` 则返回 `success`\n+ 若全部节点返回 `failure`或 `error` 则返回 `failure`" + }, + { + "name": "Sequence", + "type": "Composite", + "children": -1, + "status": [ + "&success", + "|failure", + "|running" + ], + "desc": "顺序执行", + "doc": "+ 一直往下执行,只有当所有子节点都返回 `success`, 才返回 `success`\n+ 若子节点返回 `failure`,则直接返回 `failure` 状态\n+ 其余情况返回 `running` 状态\n" + }, + { + "name": "SetField", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "设置对象字段值", + "input": [ + "输入对象", + "字段(field)?", + "值(value)?" + ], + "args": [ + { + "name": "field", + "type": "string?", + "desc": "字段(field)", + "oneof": "字段(field)" + }, + { + "name": "value", + "type": "json?", + "desc": "值(value)", + "oneof": "值(value)" + } + ], + "doc": "+ 对输入对象设置 `field` 和 `value`\n+ 输入参数1必须为对象,否则返回 `failure`\n+ 如果 `field` 不为 `string`, 也返回 `failure`\n+ 如果 `value` 为 `undefined` 或 `null`, 则删除 `field` 的值\n" + }, + { + "name": "Switch", + "type": "Composite", + "children": -1, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "分支执行", + "doc": "+ 按顺序测试 `Case` 节点的判断条件(第一个子节点)\n+ 若测试返回 `success` 则执行 `Case` 第二个子节点,并返回子节点的执行状态\n+ 若没有判断为 `success` 的 `Case` 节点,则返回 `failure`\n" + }, + { + "name": "Timeout", + "type": "Decorator", + "children": 1, + "status": [ + "|success", + "|running", + "failure" + ], + "desc": "超时", + "input": [ + "超时时间?" + ], + "args": [ + { + "name": "time", + "type": "float?", + "desc": "超时时间", + "oneof": "超时时间" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点执行超时或返回 `failure` 时,返回 `failure`\n+ 其余情况返回子节点的执行状态\n" + }, + { + "name": "PlayScript", + "type": "Action", + "children": 0, + "status": [ + "success", + "running", + "failure" + ], + "desc": "播放脚本(GIF/音频/LED)", + "args": [ + { + "name": "script", + "type": "string", + "desc": "脚本路径,如 baby/interaction/curious" + } + ], + "doc": "+ 根据脚本路径驱动 display / audio / led 执行\n+ 运行期间返回 `running`,完成后返回 `success`" + }, + { + "name": "Wait", + "type": "Action", + "children": 0, + "status": [ + "success", + "running" + ], + "desc": "等待", + "input": [ + "等待时间?" + ], + "args": [ + { + "name": "time", + "type": "float?", + "desc": "等待时间", + "oneof": "等待时间" + }, + { + "name": "random", + "type": "float?", + "desc": "随机范围" + } + ] + }, + { + "name": "WaitForEvent", + "type": "Action", + "children": 0, + "status": [ + "success", + "running" + ], + "desc": "等待事件触发", + "args": [ + { + "name": "event", + "type": "string", + "desc": "事件名称" + } + ] + }, + { + "name": "CheckPhysio", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "检查宠物生理数值", + "args": [ + { + "name": "attr", + "type": "string", + "desc": "数值类型", + "options": [ + { + "source": [ + { "name": "饱食度(fullness)", "value": "fullness" }, + { "name": "清洁度(cleanliness)", "value": "cleanliness" }, + { "name": "精力值(energy)", "value": "energy" }, + { "name": "开心值(happiness)", "value": "happiness" } + ] + } + ] + }, + { + "name": "op", + "type": "string", + "desc": "比较操作", + "default": "<=", + "options": [ + { + "source": [ + { "name": "<=", "value": "<=" }, + { "name": "<", "value": "<" }, + { "name": ">=", "value": ">=" }, + { "name": ">", "value": ">" }, + { "name": "==", "value": "==" }, + { "name": "!=", "value": "!=" } + ] + } + ] + }, + { + "name": "value", + "type": "int", + "desc": "比较阈值(0-100)" + } + ], + "doc": "+ 从 demo7 DataCenter 读取指定数值并比较\n+ 例如 fullness <= 30 表示饱食度过低,需要播放饿了的剧本\n" + }, + { + "name": "AddPhysio", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "增加或减少宠物生理数值", + "args": [ + { + "name": "attr", + "type": "string", + "desc": "数值类型", + "options": [ + { + "source": [ + { "name": "饱食度(fullness)", "value": "fullness" }, + { "name": "清洁度(cleanliness)", "value": "cleanliness" }, + { "name": "精力值(energy)", "value": "energy" }, + { "name": "开心值(happiness)", "value": "happiness" } + ] + } + ] + }, + { + "name": "amount", + "type": "int", + "desc": "变化量,可为负数" + } + ], + "doc": "+ 调用 demo7 IPetContext 修改 DataCenter 中的数值\n+ 例如 happiness = -3 表示心情下降 3 点\n" + }, + { + "name": "SetPhysio", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "直接设定宠物生理数值为指定绝对值", + "args": [ + { + "name": "attr", + "type": "string", + "desc": "数值类型", + "options": [ + { + "source": [ + { "name": "饱食度(fullness)", "value": "fullness" }, + { "name": "清洁度(cleanliness)", "value": "cleanliness" }, + { "name": "精力值(energy)", "value": "energy" }, + { "name": "开心值(happiness)", "value": "happiness" } + ] + } + ] + }, + { + "name": "value", + "type": "int", + "desc": "目标数值(0-100)" + } + ], + "doc": "+ 直接将 DataCenter 中的指定数值设置为 value(绝对值,非增量)\n+ 例如喂食后 SetPhysio { fullness: 80 } 将饱食度重置为 80\n" + }, + { + "name": "CheckUtility", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "检查宠物行为效用值(由 PetBrain 计算的 0.0–1.0 驱动强度)", + "args": [ + { + "name": "attr", + "type": "string", + "desc": "效用属性", + "options": [ + { + "source": [ + { "name": "饥饿(hungry)", "value": "hungry" }, + { "name": "困倦(sleepy)", "value": "sleepy" }, + { "name": "脏了(dirty)", "value": "dirty" }, + { "name": "开心(laugh)", "value": "laugh" }, + { "name": "好奇(curious)", "value": "curious" }, + { "name": "悲伤(sad)", "value": "sad" } + ] + } + ] + }, + { + "name": "op", + "type": "string", + "desc": "比较操作", + "default": ">=", + "options": [ + { + "source": [ + { "name": ">=", "value": ">=" }, + { "name": ">", "value": ">" }, + { "name": "<=", "value": "<=" }, + { "name": "<", "value": "<" }, + { "name": "==", "value": "==" }, + { "name": "!=", "value": "!=" } + ] + } + ] + }, + { + "name": "value", + "type": "float", + "desc": "比较阈值(0.0 – 1.0)" + } + ], + "doc": "+ 从 PetBrain::GetBehaviorUtilities() 读取效用分数,与阈值比较\n+ attr 可选值:hungry / sleepy / dirty / laugh / curious / sad\n+ 例如:{ attr: \"hungry\", op: \">=\", value: 0.6 } 表示饥饿驱动力 ≥ 60%,应播放饿了剧本\n+ 与 CheckPhysio 的区别:CheckPhysio 读取的是原始整数值(0-100),CheckUtility 读取的是经过曲线映射后的标准化驱动强度\n" + }, + { + "name": "RequestModeSwitch", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "请求切换宠物模式", + "args": [ + { + "name": "mode", + "type": "string", + "desc": "目标模式", + "options": [ + { + "source": [ + { "name": "待机模式", "value": "MODE_IDLE" }, + { "name": "菜单模式", "value": "MODE_MENU" }, + { "name": "睡眠模式", "value": "MODE_SLEEPING" } + ] + } + ] + } + ], + "doc": "+ 请求切换到指定的宠物模式\n+ MODE_MENU: 打开菜单(等同于 Log 中的 OPEN_MENU)\n+ MODE_IDLE: 返回待机\n+ MODE_SLEEPING: 进入睡眠\n" + }, + { + "name": "Watchdog", + "type": "Composite", + "children": 3, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "测试执行", + "doc": "+ 必须有3个子节点\n+ 第一个子节点为条件节点,返回 `success` 或 `failure` 状态\n+ 第二个子节点为条件为 `success` 时执行的节点\n+ 第三个子节点为条件为 `failure` 时执行的节点,不管子节点返回什么状态,都直接返回 `failure`\n+ 当第二个子节点返回 `running` 时,由本节点维护其运行状态\n+ 每一次 tick 都会先执行测试节点,只有当测试节点返回 `success`,才执行第二个子节点\n" + } +] \ No newline at end of file diff --git a/baby/workspace.b3-workspace b/baby/workspace.b3-workspace new file mode 100644 index 0000000..7974305 --- /dev/null +++ b/baby/workspace.b3-workspace @@ -0,0 +1,13 @@ +{ + "nodeConf": "node-config.b3-setting", + "metadata": [], + "files": [ + { + "path": "example.json", + "desc": "最小宠物养成行为树" + } + ], + "settings": { + "checkExpr": true + } +} \ No newline at end of file diff --git a/package-lock.json b/package-lock.json index 1d8c9e4..c412440 100644 --- a/package-lock.json +++ b/package-lock.json @@ -565,7 +565,6 @@ "integrity": "sha512-lWBYIrF7qK5+GjY5Uy+/hEgp8OJWOD/rpy74GplYRhEauvbHDeFB8t5hPOZxCZ0Oxf4Cc36tK51/l3ymJysrKw==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.26.2", @@ -1765,6 +1764,7 @@ "version": "0.3.5", "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.5.tgz", "integrity": "sha512-IzL8ZoEDIBRWEzlCcRhOaCupYyN5gdIK+Q6fbFdPDg6HqX6jpkItn7DFIpW9LQzXG6Df9sA7+OKnq0qlz/GaQg==", + "dev": true, "dependencies": { "@jridgewell/set-array": "^1.2.1", "@jridgewell/sourcemap-codec": "^1.4.10", @@ -1778,6 +1778,7 @@ "version": "3.1.2", "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", + "dev": true, "engines": { "node": ">=6.0.0" } @@ -1786,29 +1787,23 @@ "version": "1.2.1", "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.2.1.tgz", "integrity": "sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==", + "dev": true, "engines": { "node": ">=6.0.0" } }, - "node_modules/@jridgewell/source-map": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.5.tgz", - "integrity": "sha512-UTYAUj/wviwdsMfzoSJspJxbkH5o1snzwX0//0ENX1u/55kkZZkcTZP6u9bwKGkv+dkk9at4m1Cpt0uY80kcpQ==", - "dependencies": { - "@jridgewell/gen-mapping": "^0.3.0", - "@jridgewell/trace-mapping": "^0.3.9" - } - }, "node_modules/@jridgewell/sourcemap-codec": { "version": "1.5.0", "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.0.tgz", "integrity": "sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==", + "dev": true, "license": "MIT" }, "node_modules/@jridgewell/trace-mapping": { "version": "0.3.25", "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.25.tgz", "integrity": "sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==", + "dev": true, "dependencies": { "@jridgewell/resolve-uri": "^3.1.0", "@jridgewell/sourcemap-codec": "^1.4.14" @@ -2626,21 +2621,12 @@ "version": "8.56.11", "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.56.11.tgz", "integrity": "sha512-sVBpJMf7UPo/wGecYOpk2aQya2VUGeHhe38WG7/mN5FufNSubf5VT9Uh9Uyp8/eLJpu1/tuhJ/qTo4mhSB4V4Q==", + "dev": true, "dependencies": { "@types/estree": "*", "@types/json-schema": "*" } }, - "node_modules/@types/eslint-scope": { - "version": "3.7.7", - "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.7.tgz", - "integrity": "sha512-MzMFlSLBqNF2gcHWO0G1vP/YQyfvrxZ0bF+u7mzUdZ1/xK4A4sru+nraZz5i3iEIk1l1uyicaDVTB4QbbEkAYg==", - "license": "MIT", - "dependencies": { - "@types/eslint": "*", - "@types/estree": "*" - } - }, "node_modules/@types/estree": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.7.tgz", @@ -2686,7 +2672,8 @@ "node_modules/@types/json-schema": { "version": "7.0.15", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", - "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==" + "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", + "dev": true }, "node_modules/@types/keyv": { "version": "3.1.4", @@ -2731,14 +2718,15 @@ "node_modules/@types/prop-types": { "version": "15.7.5", "resolved": "https://registry.npmmirror.com/@types/prop-types/-/prop-types-15.7.5.tgz", - "integrity": "sha512-JCB8C6SnDoQf0cNycqd/35A7MjcnK+ZTqE7judS6o7utxUCg6imJg3QK2qzHKszlTjcj2cn+NwMB2i96ubpj7w==" + "integrity": "sha512-JCB8C6SnDoQf0cNycqd/35A7MjcnK+ZTqE7judS6o7utxUCg6imJg3QK2qzHKszlTjcj2cn+NwMB2i96ubpj7w==", + "dev": true }, "node_modules/@types/react": { "version": "18.3.18", "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.18.tgz", "integrity": "sha512-t4yC+vtgnkYjNSKlFx1jkAhH8LgTo2N/7Qvi83kdEaUtMDiwpbLAktKDaAMlRcJ5eSxZkH74eEGt1ky31d7kfQ==", + "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@types/prop-types": "*", "csstype": "^3.0.2" @@ -2821,7 +2809,6 @@ "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-7.18.0.tgz", "integrity": "sha512-4Z+L8I2OqhZV8qA132M4wNL30ypZGYOQVBfMgxDH/K5UX0PNqTu1c6za9ST5r9+tavvHiTWmBnKzpCJ/GlVFtg==", "dev": true, - "peer": true, "dependencies": { "@typescript-eslint/scope-manager": "7.18.0", "@typescript-eslint/types": "7.18.0", @@ -3131,152 +3118,6 @@ "url": "https://opencollective.com/vitest" } }, - "node_modules/@webassemblyjs/ast": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.14.1.tgz", - "integrity": "sha512-nuBEDgQfm1ccRp/8bCQrx1frohyufl4JlbMMZ4P1wpeOfDhF6FQkxZJ1b/e+PLwr6X1Nhw6OLme5usuBWYBvuQ==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/helper-numbers": "1.13.2", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2" - } - }, - "node_modules/@webassemblyjs/floating-point-hex-parser": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.13.2.tgz", - "integrity": "sha512-6oXyTOzbKxGH4steLbLNOu71Oj+C8Lg34n6CqRvqfS2O71BxY6ByfMDRhBytzknj9yGUPVJ1qIKhRlAwO1AovA==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/helper-api-error": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.13.2.tgz", - "integrity": "sha512-U56GMYxy4ZQCbDZd6JuvvNV/WFildOjsaWD3Tzzvmw/mas3cXzRJPMjP83JqEsgSbyrmaGjBfDtV7KDXV9UzFQ==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/helper-buffer": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.14.1.tgz", - "integrity": "sha512-jyH7wtcHiKssDtFPRB+iQdxlDf96m0E39yb0k5uJVhFGleZFoNw1c4aeIcVUPPbXUVJ94wwnMOAqUHyzoEPVMA==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/helper-numbers": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.13.2.tgz", - "integrity": "sha512-FE8aCmS5Q6eQYcV3gI35O4J789wlQA+7JrqTTpJqn5emA4U2hvwJmvFRC0HODS+3Ye6WioDklgd6scJ3+PLnEA==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/floating-point-hex-parser": "1.13.2", - "@webassemblyjs/helper-api-error": "1.13.2", - "@xtuc/long": "4.2.2" - } - }, - "node_modules/@webassemblyjs/helper-wasm-bytecode": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.13.2.tgz", - "integrity": "sha512-3QbLKy93F0EAIXLh0ogEVR6rOubA9AoZ+WRYhNbFyuB70j3dRdwH9g+qXhLAO0kiYGlg3TxDV+I4rQTr/YNXkA==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/helper-wasm-section": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.14.1.tgz", - "integrity": "sha512-ds5mXEqTJ6oxRoqjhWDU83OgzAYjwsCV8Lo/N+oRsNDmx/ZDpqalmrtgOMkHwxsG0iI//3BwWAErYRHtgn0dZw==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-buffer": "1.14.1", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2", - "@webassemblyjs/wasm-gen": "1.14.1" - } - }, - "node_modules/@webassemblyjs/ieee754": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.13.2.tgz", - "integrity": "sha512-4LtOzh58S/5lX4ITKxnAK2USuNEvpdVV9AlgGQb8rJDHaLeHciwG4zlGr0j/SNWlr7x3vO1lDEsuePvtcDNCkw==", - "license": "MIT", - "dependencies": { - "@xtuc/ieee754": "^1.2.0" - } - }, - "node_modules/@webassemblyjs/leb128": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.13.2.tgz", - "integrity": "sha512-Lde1oNoIdzVzdkNEAWZ1dZ5orIbff80YPdHx20mrHwHrVNNTjNr8E3xz9BdpcGqRQbAEa+fkrCb+fRFTl/6sQw==", - "license": "Apache-2.0", - "dependencies": { - "@xtuc/long": "4.2.2" - } - }, - "node_modules/@webassemblyjs/utf8": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.13.2.tgz", - "integrity": "sha512-3NQWGjKTASY1xV5m7Hr0iPeXD9+RDobLll3T9d2AO+g3my8xy5peVyjSag4I50mR1bBSN/Ct12lo+R9tJk0NZQ==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/wasm-edit": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.14.1.tgz", - "integrity": "sha512-RNJUIQH/J8iA/1NzlE4N7KtyZNHi3w7at7hDjvRNm5rcUXa00z1vRz3glZoULfJ5mpvYhLybmVcwcjGrC1pRrQ==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-buffer": "1.14.1", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2", - "@webassemblyjs/helper-wasm-section": "1.14.1", - "@webassemblyjs/wasm-gen": "1.14.1", - "@webassemblyjs/wasm-opt": "1.14.1", - "@webassemblyjs/wasm-parser": "1.14.1", - "@webassemblyjs/wast-printer": "1.14.1" - } - }, - "node_modules/@webassemblyjs/wasm-gen": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.14.1.tgz", - "integrity": "sha512-AmomSIjP8ZbfGQhumkNvgC33AY7qtMCXnN6bL2u2Js4gVCg8fp735aEiMSBbDR7UQIj90n4wKAFUSEd0QN2Ukg==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2", - "@webassemblyjs/ieee754": "1.13.2", - "@webassemblyjs/leb128": "1.13.2", - "@webassemblyjs/utf8": "1.13.2" - } - }, - "node_modules/@webassemblyjs/wasm-opt": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.14.1.tgz", - "integrity": "sha512-PTcKLUNvBqnY2U6E5bdOQcSM+oVP/PmrDY9NzowJjislEjwP/C4an2303MCVS2Mg9d3AJpIGdUFIQQWbPds0Sw==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-buffer": "1.14.1", - "@webassemblyjs/wasm-gen": "1.14.1", - "@webassemblyjs/wasm-parser": "1.14.1" - } - }, - "node_modules/@webassemblyjs/wasm-parser": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.14.1.tgz", - "integrity": "sha512-JLBl+KZ0R5qB7mCnud/yyX08jWFw5MsoalJ1pQ4EdFlgj9VdXKGuENGsiCIjegI1W7p91rUlcB/LB5yRJKNTcQ==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-api-error": "1.13.2", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2", - "@webassemblyjs/ieee754": "1.13.2", - "@webassemblyjs/leb128": "1.13.2", - "@webassemblyjs/utf8": "1.13.2" - } - }, - "node_modules/@webassemblyjs/wast-printer": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.14.1.tgz", - "integrity": "sha512-kPSSXE6De1XOR820C90RIo2ogvZG+c3KiHzqUoO/F34Y2shGzesfqv7o57xrxovZJH/MetF5UjroJ/R/3isoiw==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.14.1", - "@xtuc/long": "4.2.2" - } - }, "node_modules/@xmldom/xmldom": { "version": "0.8.10", "resolved": "https://registry.npmjs.org/@xmldom/xmldom/-/xmldom-0.8.10.tgz", @@ -3286,18 +3127,6 @@ "node": ">=10.0.0" } }, - "node_modules/@xtuc/ieee754": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz", - "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==", - "license": "BSD-3-Clause" - }, - "node_modules/@xtuc/long": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/@xtuc/long/-/long-4.2.2.tgz", - "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==", - "license": "Apache-2.0" - }, "node_modules/7zip-bin": { "version": "5.2.0", "resolved": "https://registry.npmjs.org/7zip-bin/-/7zip-bin-5.2.0.tgz", @@ -3308,8 +3137,8 @@ "version": "8.14.1", "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.14.1.tgz", "integrity": "sha512-OvQ/2pUDKmgfCg++xsTX1wGxfTaszcHVcTctW4UJB4hibJx2HXxxO5UmVgyjMa+ZDsiaf5wWLXYpRWMmBI0QHg==", + "dev": true, "license": "MIT", - "peer": true, "bin": { "acorn": "bin/acorn" }, @@ -3365,7 +3194,6 @@ "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", "dev": true, - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", @@ -3377,45 +3205,6 @@ "url": "https://github.com/sponsors/epoberezkin" } }, - "node_modules/ajv-formats": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-2.1.1.tgz", - "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", - "license": "MIT", - "dependencies": { - "ajv": "^8.0.0" - }, - "peerDependencies": { - "ajv": "^8.0.0" - }, - "peerDependenciesMeta": { - "ajv": { - "optional": true - } - } - }, - "node_modules/ajv-formats/node_modules/ajv": { - "version": "8.17.1", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz", - "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.3", - "fast-uri": "^3.0.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/ajv-formats/node_modules/json-schema-traverse": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", - "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", - "license": "MIT" - }, "node_modules/ajv-keywords": { "version": "3.5.2", "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", @@ -3662,75 +3451,6 @@ "node": ">= 10.0.0" } }, - "node_modules/archiver": { - "version": "5.3.2", - "resolved": "https://registry.npmjs.org/archiver/-/archiver-5.3.2.tgz", - "integrity": "sha512-+25nxyyznAXF7Nef3y0EbBeqmGZgeN/BxHX29Rs39djAfaFalmQ89SE6CWyDCHzGL0yt/ycBtNOmGTW0FyGWNw==", - "dev": true, - "dependencies": { - "archiver-utils": "^2.1.0", - "async": "^3.2.4", - "buffer-crc32": "^0.2.1", - "readable-stream": "^3.6.0", - "readdir-glob": "^1.1.2", - "tar-stream": "^2.2.0", - "zip-stream": "^4.1.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/archiver-utils": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/archiver-utils/-/archiver-utils-2.1.0.tgz", - "integrity": "sha512-bEL/yUb/fNNiNTuUz979Z0Yg5L+LzLxGJz8x79lYmR54fmTIb6ob/hNQgkQnIUDWIFjZVQwl9Xs356I6BAMHfw==", - "dev": true, - "dependencies": { - "glob": "^7.1.4", - "graceful-fs": "^4.2.0", - "lazystream": "^1.0.0", - "lodash.defaults": "^4.2.0", - "lodash.difference": "^4.5.0", - "lodash.flatten": "^4.4.0", - "lodash.isplainobject": "^4.0.6", - "lodash.union": "^4.6.0", - "normalize-path": "^3.0.0", - "readable-stream": "^2.0.0" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/archiver-utils/node_modules/readable-stream": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", - "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", - "dev": true, - "dependencies": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "node_modules/archiver-utils/node_modules/safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true - }, - "node_modules/archiver-utils/node_modules/string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "dev": true, - "dependencies": { - "safe-buffer": "~5.1.0" - } - }, "node_modules/arg": { "version": "5.0.2", "resolved": "https://registry.npmjs.org/arg/-/arg-5.0.2.tgz", @@ -3890,15 +3610,6 @@ } ] }, - "node_modules/big.js": { - "version": "5.2.2", - "resolved": "https://registry.npmjs.org/big.js/-/big.js-5.2.2.tgz", - "integrity": "sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==", - "license": "MIT", - "engines": { - "node": "*" - } - }, "node_modules/binary-extensions": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.3.0.tgz", @@ -3911,17 +3622,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/bl": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", - "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", - "dev": true, - "dependencies": { - "buffer": "^5.5.0", - "inherits": "^2.0.4", - "readable-stream": "^3.4.0" - } - }, "node_modules/bluebird": { "version": "3.7.2", "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.7.2.tgz", @@ -3969,6 +3669,7 @@ "version": "4.24.4", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.24.4.tgz", "integrity": "sha512-KDi1Ny1gSePi1vm0q4oxSF8b4DR44GF4BbmS2YdhPLOEqd8pDviZOGH/GsmRwoWJ2+5Lr085X7naowMwKHDG1A==", + "dev": true, "funding": [ { "type": "opencollective", @@ -3984,7 +3685,6 @@ } ], "license": "MIT", - "peer": true, "dependencies": { "caniuse-lite": "^1.0.30001688", "electron-to-chromium": "^1.5.73", @@ -4023,6 +3723,7 @@ "url": "https://feross.org/support" } ], + "optional": true, "dependencies": { "base64-js": "^1.3.1", "ieee754": "^1.1.13" @@ -4051,7 +3752,8 @@ "node_modules/buffer-from": { "version": "1.1.2", "resolved": "https://registry.npmmirror.com/buffer-from/-/buffer-from-1.1.2.tgz", - "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==" + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", + "dev": true }, "node_modules/builder-util": { "version": "24.13.1", @@ -4209,6 +3911,7 @@ "version": "1.0.30001701", "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001701.tgz", "integrity": "sha512-faRs/AW3jA9nTwmJBSO1PQ6L/EOgsB5HMQQq4iCu5zhPgVVgO/pZRHlmatwijZKetFw8/Pr4q6dEN8sJuq8qTw==", + "dev": true, "funding": [ { "type": "opencollective", @@ -4370,15 +4073,6 @@ "node": ">=10" } }, - "node_modules/chrome-trace-event": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.4.tgz", - "integrity": "sha512-rNjApaLzuwaOTjCiT8lSDdGN1APCiqkChLMJxJPWLunPAt5fy8xgU9/jNOchV84wfIxrA0lRQB7oCT8jrn/wrQ==", - "license": "MIT", - "engines": { - "node": ">=6.0" - } - }, "node_modules/chromium-pickle-js": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/chromium-pickle-js/-/chromium-pickle-js-0.2.0.tgz", @@ -4490,11 +4184,6 @@ "url": "https://github.com/sponsors/wooorm" } }, - "node_modules/commander": { - "version": "2.20.3", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", - "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==" - }, "node_modules/compare-version": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/compare-version/-/compare-version-0.1.2.tgz", @@ -4504,21 +4193,6 @@ "node": ">=0.10.0" } }, - "node_modules/compress-commons": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/compress-commons/-/compress-commons-4.1.2.tgz", - "integrity": "sha512-D3uMHtGc/fcO1Gt1/L7i1e33VOvD4A9hfQLP+6ewd+BvG/gQ84Yh4oftEhAdjSMgBgwGL+jsppT7JYNpo6MHHg==", - "dev": true, - "dependencies": { - "buffer-crc32": "^0.2.13", - "crc32-stream": "^4.0.2", - "normalize-path": "^3.0.0", - "readable-stream": "^3.6.0" - }, - "engines": { - "node": ">= 10" - } - }, "node_modules/compute-scroll-into-view": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/compute-scroll-into-view/-/compute-scroll-into-view-3.1.0.tgz", @@ -4614,7 +4288,8 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", "integrity": "sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ==", - "dev": true + "dev": true, + "optional": true }, "node_modules/crc": { "version": "3.8.0", @@ -4626,31 +4301,6 @@ "buffer": "^5.1.0" } }, - "node_modules/crc-32": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/crc-32/-/crc-32-1.2.2.tgz", - "integrity": "sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ==", - "dev": true, - "bin": { - "crc32": "bin/crc32.njs" - }, - "engines": { - "node": ">=0.8" - } - }, - "node_modules/crc32-stream": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/crc32-stream/-/crc32-stream-4.0.3.tgz", - "integrity": "sha512-NT7w2JVU7DFroFdYkeq8cywxrgjPHWkdX1wjpRQXPX5Asews3tA+Ght6lddQO5Mkumffp3X7GEqku3epj2toIw==", - "dev": true, - "dependencies": { - "crc-32": "^1.2.0", - "readable-stream": "^3.4.0" - }, - "engines": { - "node": ">= 10" - } - }, "node_modules/cross-fetch": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/cross-fetch/-/cross-fetch-4.0.0.tgz", @@ -5210,7 +4860,6 @@ "resolved": "https://registry.npmjs.org/dmg-builder/-/dmg-builder-24.13.3.tgz", "integrity": "sha512-rcJUkMfnJpfCboZoOOPf4L29TRtEieHNOeAbYPWPxlaBw/Z1RKrRA86dOI9rwaI4tQSc/RD82zTNHprfUHXsoQ==", "dev": true, - "peer": true, "dependencies": { "app-builder-lib": "24.13.3", "builder-util": "24.13.1", @@ -5365,7 +5014,6 @@ "integrity": "sha512-kBoY1jlOCgQQJsVhaO4rYjKXL4FAsh6v42IzV5devYFFeMnciAPl02klrK5gD0VT8A2MeE4nulH32uYafca/VQ==", "hasInstallScript": true, "license": "MIT", - "peer": true, "dependencies": { "@electron/get": "^2.0.0", "@types/node": "^20.9.0", @@ -5404,53 +5052,6 @@ "node": ">=14.0.0" } }, - "node_modules/electron-builder-squirrel-windows": { - "version": "24.13.3", - "resolved": "https://registry.npmjs.org/electron-builder-squirrel-windows/-/electron-builder-squirrel-windows-24.13.3.tgz", - "integrity": "sha512-oHkV0iogWfyK+ah9ZIvMDpei1m9ZRpdXcvde1wTpra2U8AFDNNpqJdnin5z+PM1GbQ5BoaKCWas2HSjtR0HwMg==", - "dev": true, - "dependencies": { - "app-builder-lib": "24.13.3", - "archiver": "^5.3.1", - "builder-util": "24.13.1", - "fs-extra": "^10.1.0" - } - }, - "node_modules/electron-builder-squirrel-windows/node_modules/fs-extra": { - "version": "10.1.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-10.1.0.tgz", - "integrity": "sha512-oRXApq54ETRj4eMiFzGnHWGy+zo5raudjuxN0b8H7s/RU2oW0Wvsx9O0ACRN/kRq9E8Vu/ReskGB5o3ji+FzHQ==", - "dev": true, - "dependencies": { - "graceful-fs": "^4.2.0", - "jsonfile": "^6.0.1", - "universalify": "^2.0.0" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/electron-builder-squirrel-windows/node_modules/jsonfile": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz", - "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==", - "dev": true, - "dependencies": { - "universalify": "^2.0.0" - }, - "optionalDependencies": { - "graceful-fs": "^4.1.6" - } - }, - "node_modules/electron-builder-squirrel-windows/node_modules/universalify": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz", - "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==", - "dev": true, - "engines": { - "node": ">= 10.0.0" - } - }, "node_modules/electron-builder/node_modules/builder-util-runtime": { "version": "9.2.4", "resolved": "https://registry.npmjs.org/builder-util-runtime/-/builder-util-runtime-9.2.4.tgz", @@ -5582,6 +5183,7 @@ "version": "1.5.109", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.109.tgz", "integrity": "sha512-AidaH9JETVRr9DIPGfp1kAarm/W6hRJTPuCnkF+2MqhF4KaAgRIcBc8nvjk+YMXZhwfISof/7WG29eS4iGxQLQ==", + "dev": true, "license": "ISC" }, "node_modules/electron-updater": { @@ -5638,15 +5240,6 @@ "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", "dev": true }, - "node_modules/emojis-list": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", - "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, "node_modules/end-of-stream": { "version": "1.4.4", "resolved": "https://registry.npmmirror.com/end-of-stream/-/end-of-stream-1.4.4.tgz", @@ -5655,19 +5248,6 @@ "once": "^1.4.0" } }, - "node_modules/enhanced-resolve": { - "version": "5.18.1", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.18.1.tgz", - "integrity": "sha512-ZSW3ma5GkcQBIpwZTSRAI8N71Uuwgs93IezB7mf7R60tC8ZbJideoDNKjHn2O9KIlx6rkGTTEk1xUCK2E1Y2Yg==", - "license": "MIT", - "dependencies": { - "graceful-fs": "^4.2.4", - "tapable": "^2.2.0" - }, - "engines": { - "node": ">=10.13.0" - } - }, "node_modules/env-paths": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/env-paths/-/env-paths-2.2.1.tgz", @@ -5704,6 +5284,7 @@ "version": "1.6.0", "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-1.6.0.tgz", "integrity": "sha512-qqnD1yMU6tk/jnaMosogGySTZP8YtUgAffA9nMN+E/rjxcfRQ6IEk7IiozUjgxKoFHBGjTLnrHB/YC45r/59EQ==", + "dev": true, "license": "MIT" }, "node_modules/es-object-atoms": { @@ -5746,7 +5327,6 @@ "dev": true, "hasInstallScript": true, "license": "MIT", - "peer": true, "bin": { "esbuild": "bin/esbuild" }, @@ -5785,6 +5365,7 @@ "version": "3.2.0", "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.2.0.tgz", "integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==", + "dev": true, "license": "MIT", "engines": { "node": ">=6" @@ -5807,7 +5388,6 @@ "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.57.0.tgz", "integrity": "sha512-dZ6+mexnaTIbSBZWgou51U6OmzIhYM2VcNdtiTtI7qPNZm35Akpr0f6vtw3w1Kmn5PYo+tZVfh13WrhpS6oLqQ==", "dev": true, - "peer": true, "dependencies": { "@eslint-community/eslint-utils": "^4.2.0", "@eslint-community/regexpp": "^4.6.1", @@ -5867,19 +5447,6 @@ "eslint": ">=7" } }, - "node_modules/eslint-scope": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", - "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", - "license": "BSD-2-Clause", - "dependencies": { - "esrecurse": "^4.3.0", - "estraverse": "^4.1.1" - }, - "engines": { - "node": ">=8.0.0" - } - }, "node_modules/eslint-visitor-keys": { "version": "3.4.3", "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz", @@ -6056,6 +5623,7 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, "dependencies": { "estraverse": "^5.2.0" }, @@ -6067,15 +5635,7 @@ "version": "5.3.0", "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", - "engines": { - "node": ">=4.0" - } - }, - "node_modules/estraverse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", - "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", - "license": "BSD-2-Clause", + "dev": true, "engines": { "node": ">=4.0" } @@ -6114,15 +5674,6 @@ "integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==", "license": "MIT" }, - "node_modules/events": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", - "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==", - "license": "MIT", - "engines": { - "node": ">=0.8.x" - } - }, "node_modules/expect-type": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/expect-type/-/expect-type-1.2.0.tgz", @@ -6212,22 +5763,6 @@ "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", "dev": true }, - "node_modules/fast-uri": { - "version": "3.0.6", - "resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.0.6.tgz", - "integrity": "sha512-Atfo14OibSv5wAp4VWNsFYE1AchQRTv9cBGWET4pZWHzYshFSS9NQI6I57rdKn9croWVMbYFbLhJ+yJvmZIIHw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/fastify" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/fastify" - } - ], - "license": "BSD-3-Clause" - }, "node_modules/fastq": { "version": "1.17.1", "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.17.1.tgz", @@ -6371,12 +5906,6 @@ "url": "https://github.com/sponsors/rawify" } }, - "node_modules/fs-constants": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", - "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", - "dev": true - }, "node_modules/fs-extra": { "version": "8.1.0", "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-8.1.0.tgz", @@ -6558,12 +6087,6 @@ "node": ">=10.13.0" } }, - "node_modules/glob-to-regexp": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz", - "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==", - "license": "BSD-2-Clause" - }, "node_modules/global-agent": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/global-agent/-/global-agent-3.0.0.tgz", @@ -6687,6 +6210,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, "engines": { "node": ">=8" } @@ -6872,7 +6396,6 @@ "url": "https://www.i18next.com/how-to/faq#i18next-is-awesome.-how-can-i-support-the-project" } ], - "peer": true, "dependencies": { "@babel/runtime": "^7.23.2" } @@ -6939,7 +6462,8 @@ "type": "consulting", "url": "https://feross.org/support" } - ] + ], + "optional": true }, "node_modules/ignore": { "version": "5.3.1", @@ -7176,12 +6700,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", - "dev": true - }, "node_modules/isbinaryfile": { "version": "5.0.2", "resolved": "https://registry.npmjs.org/isbinaryfile/-/isbinaryfile-5.0.2.tgz", @@ -7236,20 +6754,6 @@ "node": ">=10" } }, - "node_modules/jest-worker": { - "version": "27.5.1", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", - "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", - "license": "MIT", - "dependencies": { - "@types/node": "*", - "merge-stream": "^2.0.0", - "supports-color": "^8.0.0" - }, - "engines": { - "node": ">= 10.13.0" - } - }, "node_modules/jiti": { "version": "1.21.7", "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.21.7.tgz", @@ -7268,7 +6772,8 @@ "node_modules/js-tokens": { "version": "4.0.0", "resolved": "https://registry.npmmirror.com/js-tokens/-/js-tokens-4.0.0.tgz", - "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==" + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true }, "node_modules/js-yaml": { "version": "4.1.0", @@ -7299,12 +6804,6 @@ "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==" }, - "node_modules/json-parse-even-better-errors": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", - "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", - "license": "MIT" - }, "node_modules/json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", @@ -7335,6 +6834,7 @@ "version": "2.2.3", "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", + "dev": true, "bin": { "json5": "lib/cli.js" }, @@ -7373,48 +6873,6 @@ "resolved": "https://registry.npmjs.org/lazy-val/-/lazy-val-1.0.5.tgz", "integrity": "sha512-0/BnGCCfyUMkBpeDgWihanIAF9JmZhHBgUhEqzvf+adhNGLoP6TaiI5oF8oyb3I45P+PcnrqihSf01M0l0G5+Q==" }, - "node_modules/lazystream": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/lazystream/-/lazystream-1.0.1.tgz", - "integrity": "sha512-b94GiNHQNy6JNTrt5w6zNyffMrNkXZb3KTkCZJb2V1xaEGCk093vkZ2jk3tpaeP33/OiXC+WvK9AxUebnf5nbw==", - "dev": true, - "dependencies": { - "readable-stream": "^2.0.5" - }, - "engines": { - "node": ">= 0.6.3" - } - }, - "node_modules/lazystream/node_modules/readable-stream": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", - "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", - "dev": true, - "dependencies": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "node_modules/lazystream/node_modules/safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true - }, - "node_modules/lazystream/node_modules/string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "dev": true, - "dependencies": { - "safe-buffer": "~5.1.0" - } - }, "node_modules/levn": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", @@ -7448,29 +6906,6 @@ "dev": true, "license": "MIT" }, - "node_modules/loader-runner": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.0.tgz", - "integrity": "sha512-3R/1M+yS3j5ou80Me59j7F9IMs4PXs3VqRrm0TU3AbKPxlmpoY1TNscJV/oGJXo8qCatFGTfDbY6W6ipGOYXfg==", - "license": "MIT", - "engines": { - "node": ">=6.11.5" - } - }, - "node_modules/loader-utils": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.4.tgz", - "integrity": "sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw==", - "license": "MIT", - "dependencies": { - "big.js": "^5.2.2", - "emojis-list": "^3.0.0", - "json5": "^2.1.2" - }, - "engines": { - "node": ">=8.9.0" - } - }, "node_modules/lodash": { "version": "4.17.21", "resolved": "https://registry.npmmirror.com/lodash/-/lodash-4.17.21.tgz", @@ -7481,52 +6916,22 @@ "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==" }, - "node_modules/lodash.defaults": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/lodash.defaults/-/lodash.defaults-4.2.0.tgz", - "integrity": "sha512-qjxPLHd3r5DnsdGacqOMU6pb/avJzdh9tFX2ymgoZE27BmjXrNy/y4LoaiTeAb+O3gL8AfpJGtqfX/ae2leYYQ==", - "dev": true - }, - "node_modules/lodash.difference": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.difference/-/lodash.difference-4.5.0.tgz", - "integrity": "sha512-dS2j+W26TQ7taQBGN8Lbbq04ssV3emRw4NY58WErlTO29pIqS0HmoT5aJ9+TUQ1N3G+JOZSji4eugsWwGp9yPA==", - "dev": true - }, "node_modules/lodash.escaperegexp": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/lodash.escaperegexp/-/lodash.escaperegexp-4.1.2.tgz", "integrity": "sha512-TM9YBvyC84ZxE3rgfefxUWiQKLilstD6k7PTGt6wfbtXF8ixIJLOL3VYyV/z+ZiPLsVxAsKAFVwWlWeb2Y8Yyw==" }, - "node_modules/lodash.flatten": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/lodash.flatten/-/lodash.flatten-4.4.0.tgz", - "integrity": "sha512-C5N2Z3DgnnKr0LOpv/hKCgKdb7ZZwafIrsesve6lmzvZIRZRGaZ/l6Q8+2W7NaT+ZwO3fFlSCzCzrDCFdJfZ4g==", - "dev": true - }, "node_modules/lodash.isequal": { "version": "4.5.0", "resolved": "https://registry.npmjs.org/lodash.isequal/-/lodash.isequal-4.5.0.tgz", "integrity": "sha512-pDo3lu8Jhfjqls6GkMgpahsF9kCyayhgykjyLMNFTKWrpVdAQtYyB4muAMWozBB4ig/dtWAmsMxLEI8wuz+DYQ==" }, - "node_modules/lodash.isplainobject": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", - "integrity": "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==", - "dev": true - }, "node_modules/lodash.merge": { "version": "4.6.2", "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", "dev": true }, - "node_modules/lodash.union": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/lodash.union/-/lodash.union-4.6.0.tgz", - "integrity": "sha512-c4pB2CdGrGdjMKYLA+XiRDO7Y0PRQbm/Gzg8qMj+QH+pFVAoTp5sBpO0odL3FjoPCGjK96p6qsP+yQoiLoOBcw==", - "dev": true - }, "node_modules/longest-streak": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz", @@ -7540,6 +6945,7 @@ "version": "1.4.0", "resolved": "https://registry.npmmirror.com/loose-envify/-/loose-envify-1.4.0.tgz", "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", + "dev": true, "dependencies": { "js-tokens": "^3.0.0 || ^4.0.0" }, @@ -7750,12 +7156,6 @@ "url": "https://opencollective.com/unified" } }, - "node_modules/merge-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", - "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", - "license": "MIT" - }, "node_modules/merge2": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", @@ -8216,6 +7616,7 @@ "version": "1.52.0", "resolved": "https://registry.npmmirror.com/mime-db/-/mime-db-1.52.0.tgz", "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "dev": true, "engines": { "node": ">= 0.6" } @@ -8224,6 +7625,7 @@ "version": "2.1.35", "resolved": "https://registry.npmmirror.com/mime-types/-/mime-types-2.1.35.tgz", "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dev": true, "dependencies": { "mime-db": "1.52.0" }, @@ -8375,12 +7777,6 @@ "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", "dev": true }, - "node_modules/neo-async": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", - "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", - "license": "MIT" - }, "node_modules/node-addon-api": { "version": "1.7.2", "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-1.7.2.tgz", @@ -8392,6 +7788,7 @@ "version": "2.0.19", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.19.tgz", "integrity": "sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw==", + "dev": true, "license": "MIT" }, "node_modules/normalize-path": { @@ -8633,6 +8030,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", + "dev": true, "license": "ISC" }, "node_modules/picomatch": { @@ -8738,7 +8136,6 @@ } ], "license": "MIT", - "peer": true, "dependencies": { "nanoid": "^3.3.8", "picocolors": "^1.1.1", @@ -8897,12 +8294,6 @@ "node": ">= 0.8.0" } }, - "node_modules/process-nextick-args": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", - "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", - "dev": true - }, "node_modules/progress": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", @@ -8988,15 +8379,6 @@ "integrity": "sha512-RKJ22hX8mHe3Y6wH/N3wCM6BWtjaxIyyUIkpHOvfFnxdI4yD4tBXEBKSbriGujF6jnSVkJrffuo6vxACiSSxIw==", "license": "ISC" }, - "node_modules/randombytes": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", - "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", - "license": "MIT", - "dependencies": { - "safe-buffer": "^5.1.0" - } - }, "node_modules/rbush": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/rbush/-/rbush-3.0.1.tgz", @@ -9587,7 +8969,7 @@ "version": "18.3.1", "resolved": "https://registry.npmjs.org/react/-/react-18.3.1.tgz", "integrity": "sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==", - "peer": true, + "dev": true, "dependencies": { "loose-envify": "^1.1.0" }, @@ -9599,7 +8981,7 @@ "version": "18.3.1", "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.3.1.tgz", "integrity": "sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw==", - "peer": true, + "dev": true, "dependencies": { "loose-envify": "^1.1.0", "scheduler": "^0.23.2" @@ -9723,50 +9105,6 @@ "node": ">=12.0.0" } }, - "node_modules/readable-stream": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", - "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", - "dev": true, - "dependencies": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/readdir-glob": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/readdir-glob/-/readdir-glob-1.1.3.tgz", - "integrity": "sha512-v05I2k7xN8zXvPD9N+z/uhXPaj0sUFCe2rcWZIpBsqxfP7xXFQ0tipAd/wjj1YxWyWtUS5IDJpOG82JKt2EAVA==", - "dev": true, - "dependencies": { - "minimatch": "^5.1.0" - } - }, - "node_modules/readdir-glob/node_modules/brace-expansion": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", - "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", - "dev": true, - "dependencies": { - "balanced-match": "^1.0.0" - } - }, - "node_modules/readdir-glob/node_modules/minimatch": { - "version": "5.1.6", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.6.tgz", - "integrity": "sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g==", - "dev": true, - "dependencies": { - "brace-expansion": "^2.0.1" - }, - "engines": { - "node": ">=10" - } - }, "node_modules/readdirp": { "version": "3.6.0", "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", @@ -9824,15 +9162,6 @@ "node": ">=0.10.0" } }, - "node_modules/require-from-string": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", - "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/resize-observer-polyfill": { "version": "1.5.1", "resolved": "https://registry.npmmirror.com/resize-observer-polyfill/-/resize-observer-polyfill-1.5.1.tgz", @@ -10002,25 +9331,6 @@ "integrity": "sha512-PdhdWy89SiZogBLaw42zdeqtRJ//zFd2PgQavcICDUgJT5oW10QCRKbJ6bg4r0/UY2M6BWd5tkxuGFRvCkgfHQ==", "license": "BSD-3-Clause" }, - "node_modules/safe-buffer": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", - "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ] - }, "node_modules/safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", @@ -10040,7 +9350,6 @@ "resolved": "https://registry.npmjs.org/sass/-/sass-1.77.8.tgz", "integrity": "sha512-4UHg6prsrycW20fqLGPShtEvo/WyHRVRHwOP4DzkUrObWoWI05QBSfzU71TVB7PFaL104TwNaHpjlWXAZbQiNQ==", "dev": true, - "peer": true, "dependencies": { "chokidar": ">=3.0.0 <4.0.0", "immutable": "^4.0.0", @@ -10062,64 +9371,11 @@ "version": "0.23.2", "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz", "integrity": "sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ==", + "dev": true, "dependencies": { "loose-envify": "^1.1.0" } }, - "node_modules/schema-utils": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-4.3.0.tgz", - "integrity": "sha512-Gf9qqc58SpCA/xdziiHz35F4GNIWYWZrEshUc/G/r5BnLph6xpKuLeoJoQuj5WfBIx/eQLf+hmVPYHaxJu7V2g==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.9", - "ajv": "^8.9.0", - "ajv-formats": "^2.1.1", - "ajv-keywords": "^5.1.0" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/schema-utils/node_modules/ajv": { - "version": "8.17.1", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz", - "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", - "license": "MIT", - "peer": true, - "dependencies": { - "fast-deep-equal": "^3.1.3", - "fast-uri": "^3.0.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/schema-utils/node_modules/ajv-keywords": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-5.1.0.tgz", - "integrity": "sha512-YCS/JNFAUyr5vAuhk1DWm1CBxRHW9LbJ2ozWeemrIqpbsqKjHVxYPyi5GC0rjZIT5JxJ3virVTS8wk4i/Z+krw==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.3" - }, - "peerDependencies": { - "ajv": "^8.8.2" - } - }, - "node_modules/schema-utils/node_modules/json-schema-traverse": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", - "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", - "license": "MIT" - }, "node_modules/screenfull": { "version": "5.2.0", "resolved": "https://registry.npmjs.org/screenfull/-/screenfull-5.2.0.tgz", @@ -10172,15 +9428,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/serialize-javascript": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.2.tgz", - "integrity": "sha512-Saa1xPByTTq2gdeFZYLLo+RFE35NHZkAbqZeWNd3BpzppeVisAqpDjcp8dyf6uIvEqJRd46jemmyA4iFIeVk8g==", - "license": "BSD-3-Clause", - "dependencies": { - "randombytes": "^2.1.0" - } - }, "node_modules/shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -10281,6 +9528,7 @@ "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, "engines": { "node": ">=0.10.0" } @@ -10299,6 +9547,7 @@ "version": "0.5.21", "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz", "integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==", + "dev": true, "dependencies": { "buffer-from": "^1.0.0", "source-map": "^0.6.0" @@ -10342,15 +9591,6 @@ "dev": true, "license": "MIT" }, - "node_modules/string_decoder": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", - "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", - "dev": true, - "dependencies": { - "safe-buffer": "~5.2.0" - } - }, "node_modules/string-convert": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/string-convert/-/string-convert-0.2.1.tgz", @@ -10565,21 +9805,6 @@ "node": ">= 8.0" } }, - "node_modules/supports-color": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "license": "MIT", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/supports-color?sponsor=1" - } - }, "node_modules/supports-preserve-symlinks-flag": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", @@ -10655,15 +9880,6 @@ "postcss": "^8.0.0" } }, - "node_modules/tapable": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", - "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, "node_modules/tar": { "version": "6.2.1", "resolved": "https://registry.npmjs.org/tar/-/tar-6.2.1.tgz", @@ -10681,22 +9897,6 @@ "node": ">=10" } }, - "node_modules/tar-stream": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", - "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", - "dev": true, - "dependencies": { - "bl": "^4.0.3", - "end-of-stream": "^1.4.1", - "fs-constants": "^1.0.0", - "inherits": "^2.0.3", - "readable-stream": "^3.1.1" - }, - "engines": { - "node": ">=6" - } - }, "node_modules/tar/node_modules/mkdirp": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz", @@ -10754,57 +9954,6 @@ "node": ">= 10.0.0" } }, - "node_modules/terser": { - "version": "5.31.5", - "resolved": "https://registry.npmjs.org/terser/-/terser-5.31.5.tgz", - "integrity": "sha512-YPmas0L0rE1UyLL/llTWA0SiDOqIcAQYLeUj7cJYzXHlRTAnMSg9pPe4VJ5PlKvTrPQsdVFuiRiwyeNlYgwh2Q==", - "dependencies": { - "@jridgewell/source-map": "^0.3.3", - "acorn": "^8.8.2", - "commander": "^2.20.0", - "source-map-support": "~0.5.20" - }, - "bin": { - "terser": "bin/terser" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/terser-webpack-plugin": { - "version": "5.3.14", - "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.14.tgz", - "integrity": "sha512-vkZjpUjb6OMS7dhV+tILUW6BhpDR7P2L/aQSAv+Uwk+m8KATX9EccViHTJR2qDtACKPIYndLGCyl3FMo+r2LMw==", - "license": "MIT", - "dependencies": { - "@jridgewell/trace-mapping": "^0.3.25", - "jest-worker": "^27.4.5", - "schema-utils": "^4.3.0", - "serialize-javascript": "^6.0.2", - "terser": "^5.31.1" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^5.1.0" - }, - "peerDependenciesMeta": { - "@swc/core": { - "optional": true - }, - "esbuild": { - "optional": true - }, - "uglify-js": { - "optional": true - } - } - }, "node_modules/text-table": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", @@ -10899,7 +10048,6 @@ "integrity": "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==", "dev": true, "license": "MIT", - "peer": true, "engines": { "node": ">=12" }, @@ -11039,7 +10187,6 @@ "integrity": "sha512-4H8vUNGNjQ4V2EOoGw005+c+dGuPSnhpPBPHBtsZdGZBk/iJb4kguGlPWaZTZ3q5nMtFOEsY0nRDlh9PJyd6SQ==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "esbuild": "~0.25.0", "get-tsconfig": "^4.7.5" @@ -11084,7 +10231,6 @@ "integrity": "sha512-aJn6wq13/afZp/jT9QZmwEjDqqvSGp1VT5GVg+f/t6/oVyrgXM6BY1h9BRh/O5p3PlUPAe+WuiEZOmb/49RqoQ==", "dev": true, "license": "Apache-2.0", - "peer": true, "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" @@ -11204,6 +10350,7 @@ "version": "1.1.3", "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.1.3.tgz", "integrity": "sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==", + "dev": true, "funding": [ { "type": "opencollective", @@ -11325,7 +10472,6 @@ "integrity": "sha512-cZn6NDFE7wdTpINgs++ZJ4N49W2vRp8LCKrn3Ob1kYNtOo21vfDoaV5GzBfLU4MovSAB8uNRm4jgzVQZ+mBzPQ==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "esbuild": "^0.25.0", "fdir": "^6.4.4", @@ -11475,8 +10621,7 @@ "resolved": "https://registry.npmjs.org/vite-plugin-electron-renderer/-/vite-plugin-electron-renderer-0.14.6.tgz", "integrity": "sha512-oqkWFa7kQIkvHXG7+Mnl1RTroA4sP0yesKatmAy0gjZC4VwUqlvF9IvOpHd1fpLWsqYX/eZlVxlhULNtaQ78Jw==", "dev": true, - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/vite/node_modules/fdir": { "version": "6.4.4", @@ -11499,7 +10644,6 @@ "integrity": "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==", "dev": true, "license": "MIT", - "peer": true, "engines": { "node": ">=12" }, @@ -11585,80 +10729,11 @@ "node": ">=0.10.0" } }, - "node_modules/watchpack": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.2.tgz", - "integrity": "sha512-TnbFSbcOCcDgjZ4piURLCbJ3nJhznVh9kw6F6iokjiFPl8ONxe9A6nMDVXDiNbrSfLILs6vB07F7wLBrwPYzJw==", - "license": "MIT", - "dependencies": { - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.1.2" - }, - "engines": { - "node": ">=10.13.0" - } - }, "node_modules/webidl-conversions": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==" }, - "node_modules/webpack": { - "version": "5.98.0", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.98.0.tgz", - "integrity": "sha512-UFynvx+gM44Gv9qFgj0acCQK2VE1CtdfwFdimkapco3hlPCJ/zeq73n2yVKimVbtm+TnApIugGhLJnkU6gjYXA==", - "license": "MIT", - "peer": true, - "dependencies": { - "@types/eslint-scope": "^3.7.7", - "@types/estree": "^1.0.6", - "@webassemblyjs/ast": "^1.14.1", - "@webassemblyjs/wasm-edit": "^1.14.1", - "@webassemblyjs/wasm-parser": "^1.14.1", - "acorn": "^8.14.0", - "browserslist": "^4.24.0", - "chrome-trace-event": "^1.0.2", - "enhanced-resolve": "^5.17.1", - "es-module-lexer": "^1.2.1", - "eslint-scope": "5.1.1", - "events": "^3.2.0", - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.2.11", - "json-parse-even-better-errors": "^2.3.1", - "loader-runner": "^4.2.0", - "mime-types": "^2.1.27", - "neo-async": "^2.6.2", - "schema-utils": "^4.3.0", - "tapable": "^2.1.1", - "terser-webpack-plugin": "^5.3.11", - "watchpack": "^2.4.1", - "webpack-sources": "^3.2.3" - }, - "bin": { - "webpack": "bin/webpack.js" - }, - "engines": { - "node": ">=10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependenciesMeta": { - "webpack-cli": { - "optional": true - } - } - }, - "node_modules/webpack-sources": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.3.tgz", - "integrity": "sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==", - "license": "MIT", - "engines": { - "node": ">=10.13.0" - } - }, "node_modules/whatwg-url": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", @@ -11700,19 +10775,6 @@ "node": ">=8" } }, - "node_modules/workerize-loader": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/workerize-loader/-/workerize-loader-2.0.2.tgz", - "integrity": "sha512-HoZ6XY4sHWxA2w0WpzgBwUiR3dv1oo7bS+oCwIpb6n54MclQ/7KXdXsVIChTCygyuHtVuGBO1+i3HzTt699UJQ==", - "license": "MIT", - "peer": true, - "dependencies": { - "loader-utils": "^2.0.0" - }, - "peerDependencies": { - "webpack": "*" - } - }, "node_modules/wrap-ansi": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", @@ -11838,41 +10900,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/zip-stream": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/zip-stream/-/zip-stream-4.1.1.tgz", - "integrity": "sha512-9qv4rlDiopXg4E69k+vMHjNN63YFMe9sZMrdlvKnCjlCRWeCBswPPMPUfx+ipsAWq1LXHe70RcbaHdJJpS6hyQ==", - "dev": true, - "dependencies": { - "archiver-utils": "^3.0.4", - "compress-commons": "^4.1.2", - "readable-stream": "^3.6.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/zip-stream/node_modules/archiver-utils": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/archiver-utils/-/archiver-utils-3.0.4.tgz", - "integrity": "sha512-KVgf4XQVrTjhyWmx6cte4RxonPLR9onExufI1jhvw/MQ4BB6IsZD5gT8Lq+u/+pRkWna/6JoHpiQioaqFP5Rzw==", - "dev": true, - "dependencies": { - "glob": "^7.2.3", - "graceful-fs": "^4.2.0", - "lazystream": "^1.0.0", - "lodash.defaults": "^4.2.0", - "lodash.difference": "^4.5.0", - "lodash.flatten": "^4.4.0", - "lodash.isplainobject": "^4.0.6", - "lodash.union": "^4.6.0", - "normalize-path": "^3.0.0", - "readable-stream": "^3.6.0" - }, - "engines": { - "node": ">= 10" - } - }, "node_modules/zustand": { "version": "5.0.3", "resolved": "https://registry.npmjs.org/zustand/-/zustand-5.0.3.tgz", @@ -12351,7 +11378,6 @@ "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.26.9.tgz", "integrity": "sha512-lWBYIrF7qK5+GjY5Uy+/hEgp8OJWOD/rpy74GplYRhEauvbHDeFB8t5hPOZxCZ0Oxf4Cc36tK51/l3ymJysrKw==", "dev": true, - "peer": true, "requires": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.26.2", @@ -12701,8 +11727,7 @@ }, "@electron/remote": { "version": "git+ssh://git@github.com/electron/remote.git#5d7d09a22e99ea3f8c6e0085804f38c8ed69a919", - "from": "@electron/remote@github:electron/remote", - "requires": {} + "from": "@electron/remote@github:electron/remote" }, "@electron/universal": { "version": "1.5.1", @@ -13081,6 +12106,7 @@ "version": "0.3.5", "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.5.tgz", "integrity": "sha512-IzL8ZoEDIBRWEzlCcRhOaCupYyN5gdIK+Q6fbFdPDg6HqX6jpkItn7DFIpW9LQzXG6Df9sA7+OKnq0qlz/GaQg==", + "dev": true, "requires": { "@jridgewell/set-array": "^1.2.1", "@jridgewell/sourcemap-codec": "^1.4.10", @@ -13090,31 +12116,26 @@ "@jridgewell/resolve-uri": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", - "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==" + "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", + "dev": true }, "@jridgewell/set-array": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.2.1.tgz", - "integrity": "sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==" - }, - "@jridgewell/source-map": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.5.tgz", - "integrity": "sha512-UTYAUj/wviwdsMfzoSJspJxbkH5o1snzwX0//0ENX1u/55kkZZkcTZP6u9bwKGkv+dkk9at4m1Cpt0uY80kcpQ==", - "requires": { - "@jridgewell/gen-mapping": "^0.3.0", - "@jridgewell/trace-mapping": "^0.3.9" - } + "integrity": "sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==", + "dev": true }, "@jridgewell/sourcemap-codec": { "version": "1.5.0", "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.0.tgz", - "integrity": "sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==" + "integrity": "sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==", + "dev": true }, "@jridgewell/trace-mapping": { "version": "0.3.25", "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.25.tgz", "integrity": "sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==", + "dev": true, "requires": { "@jridgewell/resolve-uri": "^3.1.0", "@jridgewell/sourcemap-codec": "^1.4.14" @@ -13174,8 +12195,7 @@ "@naoak/workerize-transferable": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/@naoak/workerize-transferable/-/workerize-transferable-0.1.0.tgz", - "integrity": "sha512-fDLfuP71IPNP5+zSfxFb52OHgtjZvauRJWbVnpzQ7G7BjcbLjTny0OW1d3ZO806XKpLWNKmeeW3MhE0sy8iwYQ==", - "requires": {} + "integrity": "sha512-fDLfuP71IPNP5+zSfxFb52OHgtjZvauRJWbVnpzQ7G7BjcbLjTny0OW1d3ZO806XKpLWNKmeeW3MhE0sy8iwYQ==" }, "@nodelib/fs.scandir": { "version": "2.1.5", @@ -13659,20 +12679,12 @@ "version": "8.56.11", "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.56.11.tgz", "integrity": "sha512-sVBpJMf7UPo/wGecYOpk2aQya2VUGeHhe38WG7/mN5FufNSubf5VT9Uh9Uyp8/eLJpu1/tuhJ/qTo4mhSB4V4Q==", + "dev": true, "requires": { "@types/estree": "*", "@types/json-schema": "*" } }, - "@types/eslint-scope": { - "version": "3.7.7", - "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.7.tgz", - "integrity": "sha512-MzMFlSLBqNF2gcHWO0G1vP/YQyfvrxZ0bF+u7mzUdZ1/xK4A4sru+nraZz5i3iEIk1l1uyicaDVTB4QbbEkAYg==", - "requires": { - "@types/eslint": "*", - "@types/estree": "*" - } - }, "@types/estree": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.7.tgz", @@ -13716,7 +12728,8 @@ "@types/json-schema": { "version": "7.0.15", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", - "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==" + "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", + "dev": true }, "@types/keyv": { "version": "3.1.4", @@ -13761,13 +12774,14 @@ "@types/prop-types": { "version": "15.7.5", "resolved": "https://registry.npmmirror.com/@types/prop-types/-/prop-types-15.7.5.tgz", - "integrity": "sha512-JCB8C6SnDoQf0cNycqd/35A7MjcnK+ZTqE7judS6o7utxUCg6imJg3QK2qzHKszlTjcj2cn+NwMB2i96ubpj7w==" + "integrity": "sha512-JCB8C6SnDoQf0cNycqd/35A7MjcnK+ZTqE7judS6o7utxUCg6imJg3QK2qzHKszlTjcj2cn+NwMB2i96ubpj7w==", + "dev": true }, "@types/react": { "version": "18.3.18", "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.18.tgz", "integrity": "sha512-t4yC+vtgnkYjNSKlFx1jkAhH8LgTo2N/7Qvi83kdEaUtMDiwpbLAktKDaAMlRcJ5eSxZkH74eEGt1ky31d7kfQ==", - "peer": true, + "dev": true, "requires": { "@types/prop-types": "*", "csstype": "^3.0.2" @@ -13777,8 +12791,7 @@ "version": "18.3.5", "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-18.3.5.tgz", "integrity": "sha512-P4t6saawp+b/dFrUr2cvkVsfvPguwsxtH6dNIYRllMsefqFzkZk5UIjzyDOv5g1dXIPdG4Sp1yCR4Z6RCUsG/Q==", - "dev": true, - "requires": {} + "dev": true }, "@types/responselike": { "version": "1.0.3", @@ -13831,7 +12844,6 @@ "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-7.18.0.tgz", "integrity": "sha512-4Z+L8I2OqhZV8qA132M4wNL30ypZGYOQVBfMgxDH/K5UX0PNqTu1c6za9ST5r9+tavvHiTWmBnKzpCJ/GlVFtg==", "dev": true, - "peer": true, "requires": { "@typescript-eslint/scope-manager": "7.18.0", "@typescript-eslint/types": "7.18.0", @@ -14017,153 +13029,12 @@ "tinyrainbow": "^2.0.0" } }, - "@webassemblyjs/ast": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.14.1.tgz", - "integrity": "sha512-nuBEDgQfm1ccRp/8bCQrx1frohyufl4JlbMMZ4P1wpeOfDhF6FQkxZJ1b/e+PLwr6X1Nhw6OLme5usuBWYBvuQ==", - "requires": { - "@webassemblyjs/helper-numbers": "1.13.2", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2" - } - }, - "@webassemblyjs/floating-point-hex-parser": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.13.2.tgz", - "integrity": "sha512-6oXyTOzbKxGH4steLbLNOu71Oj+C8Lg34n6CqRvqfS2O71BxY6ByfMDRhBytzknj9yGUPVJ1qIKhRlAwO1AovA==" - }, - "@webassemblyjs/helper-api-error": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.13.2.tgz", - "integrity": "sha512-U56GMYxy4ZQCbDZd6JuvvNV/WFildOjsaWD3Tzzvmw/mas3cXzRJPMjP83JqEsgSbyrmaGjBfDtV7KDXV9UzFQ==" - }, - "@webassemblyjs/helper-buffer": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.14.1.tgz", - "integrity": "sha512-jyH7wtcHiKssDtFPRB+iQdxlDf96m0E39yb0k5uJVhFGleZFoNw1c4aeIcVUPPbXUVJ94wwnMOAqUHyzoEPVMA==" - }, - "@webassemblyjs/helper-numbers": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.13.2.tgz", - "integrity": "sha512-FE8aCmS5Q6eQYcV3gI35O4J789wlQA+7JrqTTpJqn5emA4U2hvwJmvFRC0HODS+3Ye6WioDklgd6scJ3+PLnEA==", - "requires": { - "@webassemblyjs/floating-point-hex-parser": "1.13.2", - "@webassemblyjs/helper-api-error": "1.13.2", - "@xtuc/long": "4.2.2" - } - }, - "@webassemblyjs/helper-wasm-bytecode": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.13.2.tgz", - "integrity": "sha512-3QbLKy93F0EAIXLh0ogEVR6rOubA9AoZ+WRYhNbFyuB70j3dRdwH9g+qXhLAO0kiYGlg3TxDV+I4rQTr/YNXkA==" - }, - "@webassemblyjs/helper-wasm-section": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.14.1.tgz", - "integrity": "sha512-ds5mXEqTJ6oxRoqjhWDU83OgzAYjwsCV8Lo/N+oRsNDmx/ZDpqalmrtgOMkHwxsG0iI//3BwWAErYRHtgn0dZw==", - "requires": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-buffer": "1.14.1", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2", - "@webassemblyjs/wasm-gen": "1.14.1" - } - }, - "@webassemblyjs/ieee754": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.13.2.tgz", - "integrity": "sha512-4LtOzh58S/5lX4ITKxnAK2USuNEvpdVV9AlgGQb8rJDHaLeHciwG4zlGr0j/SNWlr7x3vO1lDEsuePvtcDNCkw==", - "requires": { - "@xtuc/ieee754": "^1.2.0" - } - }, - "@webassemblyjs/leb128": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.13.2.tgz", - "integrity": "sha512-Lde1oNoIdzVzdkNEAWZ1dZ5orIbff80YPdHx20mrHwHrVNNTjNr8E3xz9BdpcGqRQbAEa+fkrCb+fRFTl/6sQw==", - "requires": { - "@xtuc/long": "4.2.2" - } - }, - "@webassemblyjs/utf8": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.13.2.tgz", - "integrity": "sha512-3NQWGjKTASY1xV5m7Hr0iPeXD9+RDobLll3T9d2AO+g3my8xy5peVyjSag4I50mR1bBSN/Ct12lo+R9tJk0NZQ==" - }, - "@webassemblyjs/wasm-edit": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.14.1.tgz", - "integrity": "sha512-RNJUIQH/J8iA/1NzlE4N7KtyZNHi3w7at7hDjvRNm5rcUXa00z1vRz3glZoULfJ5mpvYhLybmVcwcjGrC1pRrQ==", - "requires": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-buffer": "1.14.1", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2", - "@webassemblyjs/helper-wasm-section": "1.14.1", - "@webassemblyjs/wasm-gen": "1.14.1", - "@webassemblyjs/wasm-opt": "1.14.1", - "@webassemblyjs/wasm-parser": "1.14.1", - "@webassemblyjs/wast-printer": "1.14.1" - } - }, - "@webassemblyjs/wasm-gen": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.14.1.tgz", - "integrity": "sha512-AmomSIjP8ZbfGQhumkNvgC33AY7qtMCXnN6bL2u2Js4gVCg8fp735aEiMSBbDR7UQIj90n4wKAFUSEd0QN2Ukg==", - "requires": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2", - "@webassemblyjs/ieee754": "1.13.2", - "@webassemblyjs/leb128": "1.13.2", - "@webassemblyjs/utf8": "1.13.2" - } - }, - "@webassemblyjs/wasm-opt": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.14.1.tgz", - "integrity": "sha512-PTcKLUNvBqnY2U6E5bdOQcSM+oVP/PmrDY9NzowJjislEjwP/C4an2303MCVS2Mg9d3AJpIGdUFIQQWbPds0Sw==", - "requires": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-buffer": "1.14.1", - "@webassemblyjs/wasm-gen": "1.14.1", - "@webassemblyjs/wasm-parser": "1.14.1" - } - }, - "@webassemblyjs/wasm-parser": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.14.1.tgz", - "integrity": "sha512-JLBl+KZ0R5qB7mCnud/yyX08jWFw5MsoalJ1pQ4EdFlgj9VdXKGuENGsiCIjegI1W7p91rUlcB/LB5yRJKNTcQ==", - "requires": { - "@webassemblyjs/ast": "1.14.1", - "@webassemblyjs/helper-api-error": "1.13.2", - "@webassemblyjs/helper-wasm-bytecode": "1.13.2", - "@webassemblyjs/ieee754": "1.13.2", - "@webassemblyjs/leb128": "1.13.2", - "@webassemblyjs/utf8": "1.13.2" - } - }, - "@webassemblyjs/wast-printer": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.14.1.tgz", - "integrity": "sha512-kPSSXE6De1XOR820C90RIo2ogvZG+c3KiHzqUoO/F34Y2shGzesfqv7o57xrxovZJH/MetF5UjroJ/R/3isoiw==", - "requires": { - "@webassemblyjs/ast": "1.14.1", - "@xtuc/long": "4.2.2" - } - }, "@xmldom/xmldom": { "version": "0.8.10", "resolved": "https://registry.npmjs.org/@xmldom/xmldom/-/xmldom-0.8.10.tgz", "integrity": "sha512-2WALfTl4xo2SkGCYRt6rDTFfk9R1czmBvUQy12gK2KuRKIpWEhcbbzy8EZXtz/jkRqHX8bFEc6FC1HjX4TUWYw==", "dev": true }, - "@xtuc/ieee754": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz", - "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==" - }, - "@xtuc/long": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/@xtuc/long/-/long-4.2.2.tgz", - "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==" - }, "7zip-bin": { "version": "5.2.0", "resolved": "https://registry.npmjs.org/7zip-bin/-/7zip-bin-5.2.0.tgz", @@ -14174,14 +13045,13 @@ "version": "8.14.1", "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.14.1.tgz", "integrity": "sha512-OvQ/2pUDKmgfCg++xsTX1wGxfTaszcHVcTctW4UJB4hibJx2HXxxO5UmVgyjMa+ZDsiaf5wWLXYpRWMmBI0QHg==", - "peer": true + "dev": true }, "acorn-jsx": { "version": "5.3.2", "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", - "dev": true, - "requires": {} + "dev": true }, "agent-base": { "version": "6.0.2", @@ -14213,7 +13083,6 @@ "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", "dev": true, - "peer": true, "requires": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", @@ -14221,38 +13090,11 @@ "uri-js": "^4.2.2" } }, - "ajv-formats": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-2.1.1.tgz", - "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", - "requires": { - "ajv": "^8.0.0" - }, - "dependencies": { - "ajv": { - "version": "8.17.1", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz", - "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", - "requires": { - "fast-deep-equal": "^3.1.3", - "fast-uri": "^3.0.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2" - } - }, - "json-schema-traverse": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", - "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==" - } - } - }, "ajv-keywords": { "version": "3.5.2", "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "dev": true, - "requires": {} + "dev": true }, "ansi-regex": { "version": "5.0.1", @@ -14450,71 +13292,6 @@ } } }, - "archiver": { - "version": "5.3.2", - "resolved": "https://registry.npmjs.org/archiver/-/archiver-5.3.2.tgz", - "integrity": "sha512-+25nxyyznAXF7Nef3y0EbBeqmGZgeN/BxHX29Rs39djAfaFalmQ89SE6CWyDCHzGL0yt/ycBtNOmGTW0FyGWNw==", - "dev": true, - "requires": { - "archiver-utils": "^2.1.0", - "async": "^3.2.4", - "buffer-crc32": "^0.2.1", - "readable-stream": "^3.6.0", - "readdir-glob": "^1.1.2", - "tar-stream": "^2.2.0", - "zip-stream": "^4.1.0" - } - }, - "archiver-utils": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/archiver-utils/-/archiver-utils-2.1.0.tgz", - "integrity": "sha512-bEL/yUb/fNNiNTuUz979Z0Yg5L+LzLxGJz8x79lYmR54fmTIb6ob/hNQgkQnIUDWIFjZVQwl9Xs356I6BAMHfw==", - "dev": true, - "requires": { - "glob": "^7.1.4", - "graceful-fs": "^4.2.0", - "lazystream": "^1.0.0", - "lodash.defaults": "^4.2.0", - "lodash.difference": "^4.5.0", - "lodash.flatten": "^4.4.0", - "lodash.isplainobject": "^4.0.6", - "lodash.union": "^4.6.0", - "normalize-path": "^3.0.0", - "readable-stream": "^2.0.0" - }, - "dependencies": { - "readable-stream": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", - "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", - "dev": true, - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true - }, - "string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "dev": true, - "requires": { - "safe-buffer": "~5.1.0" - } - } - } - }, "arg": { "version": "5.0.2", "resolved": "https://registry.npmjs.org/arg/-/arg-5.0.2.tgz", @@ -14612,28 +13389,12 @@ "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", "dev": true }, - "big.js": { - "version": "5.2.2", - "resolved": "https://registry.npmjs.org/big.js/-/big.js-5.2.2.tgz", - "integrity": "sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==" - }, "binary-extensions": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.3.0.tgz", "integrity": "sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==", "dev": true }, - "bl": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", - "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", - "dev": true, - "requires": { - "buffer": "^5.5.0", - "inherits": "^2.0.4", - "readable-stream": "^3.4.0" - } - }, "bluebird": { "version": "3.7.2", "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.7.2.tgz", @@ -14678,7 +13439,7 @@ "version": "4.24.4", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.24.4.tgz", "integrity": "sha512-KDi1Ny1gSePi1vm0q4oxSF8b4DR44GF4BbmS2YdhPLOEqd8pDviZOGH/GsmRwoWJ2+5Lr085X7naowMwKHDG1A==", - "peer": true, + "dev": true, "requires": { "caniuse-lite": "^1.0.30001688", "electron-to-chromium": "^1.5.73", @@ -14696,6 +13457,7 @@ "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", "dev": true, + "optional": true, "requires": { "base64-js": "^1.3.1", "ieee754": "^1.1.13" @@ -14715,7 +13477,8 @@ "buffer-from": { "version": "1.1.2", "resolved": "https://registry.npmmirror.com/buffer-from/-/buffer-from-1.1.2.tgz", - "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==" + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", + "dev": true }, "builder-util": { "version": "24.13.1", @@ -14839,7 +13602,8 @@ "caniuse-lite": { "version": "1.0.30001701", "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001701.tgz", - "integrity": "sha512-faRs/AW3jA9nTwmJBSO1PQ6L/EOgsB5HMQQq4iCu5zhPgVVgO/pZRHlmatwijZKetFw8/Pr4q6dEN8sJuq8qTw==" + "integrity": "sha512-faRs/AW3jA9nTwmJBSO1PQ6L/EOgsB5HMQQq4iCu5zhPgVVgO/pZRHlmatwijZKetFw8/Pr4q6dEN8sJuq8qTw==", + "dev": true }, "ccount": { "version": "2.0.1", @@ -14939,11 +13703,6 @@ "integrity": "sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==", "dev": true }, - "chrome-trace-event": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.4.tgz", - "integrity": "sha512-rNjApaLzuwaOTjCiT8lSDdGN1APCiqkChLMJxJPWLunPAt5fy8xgU9/jNOchV84wfIxrA0lRQB7oCT8jrn/wrQ==" - }, "chromium-pickle-js": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/chromium-pickle-js/-/chromium-pickle-js-0.2.0.tgz", @@ -15024,29 +13783,12 @@ "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz", "integrity": "sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==" }, - "commander": { - "version": "2.20.3", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", - "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==" - }, "compare-version": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/compare-version/-/compare-version-0.1.2.tgz", "integrity": "sha512-pJDh5/4wrEnXX/VWRZvruAGHkzKdr46z11OlTPN+VrATlWWhSKewNCJ1futCO5C7eJB3nPMFZA1LeYtcFboZ2A==", "dev": true }, - "compress-commons": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/compress-commons/-/compress-commons-4.1.2.tgz", - "integrity": "sha512-D3uMHtGc/fcO1Gt1/L7i1e33VOvD4A9hfQLP+6ewd+BvG/gQ84Yh4oftEhAdjSMgBgwGL+jsppT7JYNpo6MHHg==", - "dev": true, - "requires": { - "buffer-crc32": "^0.2.13", - "crc32-stream": "^4.0.2", - "normalize-path": "^3.0.0", - "readable-stream": "^3.6.0" - } - }, "compute-scroll-into-view": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/compute-scroll-into-view/-/compute-scroll-into-view-3.1.0.tgz", @@ -15125,7 +13867,8 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", "integrity": "sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ==", - "dev": true + "dev": true, + "optional": true }, "crc": { "version": "3.8.0", @@ -15137,22 +13880,6 @@ "buffer": "^5.1.0" } }, - "crc-32": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/crc-32/-/crc-32-1.2.2.tgz", - "integrity": "sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ==", - "dev": true - }, - "crc32-stream": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/crc32-stream/-/crc32-stream-4.0.3.tgz", - "integrity": "sha512-NT7w2JVU7DFroFdYkeq8cywxrgjPHWkdX1wjpRQXPX5Asews3tA+Ght6lddQO5Mkumffp3X7GEqku3epj2toIw==", - "dev": true, - "requires": { - "crc-32": "^1.2.0", - "readable-stream": "^3.4.0" - } - }, "cross-fetch": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/cross-fetch/-/cross-fetch-4.0.0.tgz", @@ -15526,7 +14253,6 @@ "resolved": "https://registry.npmjs.org/dmg-builder/-/dmg-builder-24.13.3.tgz", "integrity": "sha512-rcJUkMfnJpfCboZoOOPf4L29TRtEieHNOeAbYPWPxlaBw/Z1RKrRA86dOI9rwaI4tQSc/RD82zTNHprfUHXsoQ==", "dev": true, - "peer": true, "requires": { "app-builder-lib": "24.13.3", "builder-util": "24.13.1", @@ -15644,7 +14370,6 @@ "version": "33.4.2", "resolved": "https://registry.npmjs.org/electron/-/electron-33.4.2.tgz", "integrity": "sha512-kBoY1jlOCgQQJsVhaO4rYjKXL4FAsh6v42IzV5devYFFeMnciAPl02klrK5gD0VT8A2MeE4nulH32uYafca/VQ==", - "peer": true, "requires": { "@electron/get": "^2.0.0", "@types/node": "^20.9.0", @@ -15709,47 +14434,6 @@ } } }, - "electron-builder-squirrel-windows": { - "version": "24.13.3", - "resolved": "https://registry.npmjs.org/electron-builder-squirrel-windows/-/electron-builder-squirrel-windows-24.13.3.tgz", - "integrity": "sha512-oHkV0iogWfyK+ah9ZIvMDpei1m9ZRpdXcvde1wTpra2U8AFDNNpqJdnin5z+PM1GbQ5BoaKCWas2HSjtR0HwMg==", - "dev": true, - "requires": { - "app-builder-lib": "24.13.3", - "archiver": "^5.3.1", - "builder-util": "24.13.1", - "fs-extra": "^10.1.0" - }, - "dependencies": { - "fs-extra": { - "version": "10.1.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-10.1.0.tgz", - "integrity": "sha512-oRXApq54ETRj4eMiFzGnHWGy+zo5raudjuxN0b8H7s/RU2oW0Wvsx9O0ACRN/kRq9E8Vu/ReskGB5o3ji+FzHQ==", - "dev": true, - "requires": { - "graceful-fs": "^4.2.0", - "jsonfile": "^6.0.1", - "universalify": "^2.0.0" - } - }, - "jsonfile": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz", - "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==", - "dev": true, - "requires": { - "graceful-fs": "^4.1.6", - "universalify": "^2.0.0" - } - }, - "universalify": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz", - "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==", - "dev": true - } - } - }, "electron-is-accelerator": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/electron-is-accelerator/-/electron-is-accelerator-0.1.2.tgz", @@ -15823,7 +14507,8 @@ "electron-to-chromium": { "version": "1.5.109", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.109.tgz", - "integrity": "sha512-AidaH9JETVRr9DIPGfp1kAarm/W6hRJTPuCnkF+2MqhF4KaAgRIcBc8nvjk+YMXZhwfISof/7WG29eS4iGxQLQ==" + "integrity": "sha512-AidaH9JETVRr9DIPGfp1kAarm/W6hRJTPuCnkF+2MqhF4KaAgRIcBc8nvjk+YMXZhwfISof/7WG29eS4iGxQLQ==", + "dev": true }, "electron-updater": { "version": "6.3.9", @@ -15872,11 +14557,6 @@ "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", "dev": true }, - "emojis-list": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", - "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==" - }, "end-of-stream": { "version": "1.4.4", "resolved": "https://registry.npmmirror.com/end-of-stream/-/end-of-stream-1.4.4.tgz", @@ -15885,15 +14565,6 @@ "once": "^1.4.0" } }, - "enhanced-resolve": { - "version": "5.18.1", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.18.1.tgz", - "integrity": "sha512-ZSW3ma5GkcQBIpwZTSRAI8N71Uuwgs93IezB7mf7R60tC8ZbJideoDNKjHn2O9KIlx6rkGTTEk1xUCK2E1Y2Yg==", - "requires": { - "graceful-fs": "^4.2.4", - "tapable": "^2.2.0" - } - }, "env-paths": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/env-paths/-/env-paths-2.2.1.tgz", @@ -15920,7 +14591,8 @@ "es-module-lexer": { "version": "1.6.0", "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-1.6.0.tgz", - "integrity": "sha512-qqnD1yMU6tk/jnaMosogGySTZP8YtUgAffA9nMN+E/rjxcfRQ6IEk7IiozUjgxKoFHBGjTLnrHB/YC45r/59EQ==" + "integrity": "sha512-qqnD1yMU6tk/jnaMosogGySTZP8YtUgAffA9nMN+E/rjxcfRQ6IEk7IiozUjgxKoFHBGjTLnrHB/YC45r/59EQ==", + "dev": true }, "es-object-atoms": { "version": "1.1.1", @@ -15954,7 +14626,6 @@ "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.25.0.tgz", "integrity": "sha512-BXq5mqc8ltbaN34cDqWuYKyNhX8D/Z0J1xdtdQ8UcIIIyJyz+ZMKUt58tF3SrZ85jcfN/PZYhjR5uDQAYNVbuw==", "dev": true, - "peer": true, "requires": { "@esbuild/aix-ppc64": "0.25.0", "@esbuild/android-arm": "0.25.0", @@ -15986,7 +14657,8 @@ "escalade": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.2.0.tgz", - "integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==" + "integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==", + "dev": true }, "escape-string-regexp": { "version": "4.0.0", @@ -15999,7 +14671,6 @@ "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.57.0.tgz", "integrity": "sha512-dZ6+mexnaTIbSBZWgou51U6OmzIhYM2VcNdtiTtI7qPNZm35Akpr0f6vtw3w1Kmn5PYo+tZVfh13WrhpS6oLqQ==", "dev": true, - "peer": true, "requires": { "@eslint-community/eslint-utils": "^4.2.0", "@eslint-community/regexpp": "^4.6.1", @@ -16121,17 +14792,7 @@ "version": "0.4.9", "resolved": "https://registry.npmjs.org/eslint-plugin-react-refresh/-/eslint-plugin-react-refresh-0.4.9.tgz", "integrity": "sha512-QK49YrBAo5CLNLseZ7sZgvgTy21E6NEw22eZqc4teZfH8pxV3yXc9XXOYfUI6JNpw7mfHNkAeWtBxrTyykB6HA==", - "dev": true, - "requires": {} - }, - "eslint-scope": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", - "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", - "requires": { - "esrecurse": "^4.3.0", - "estraverse": "^4.1.1" - } + "dev": true }, "eslint-visitor-keys": { "version": "3.4.3", @@ -16171,6 +14832,7 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, "requires": { "estraverse": "^5.2.0" }, @@ -16178,15 +14840,11 @@ "estraverse": { "version": "5.3.0", "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", - "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==" + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true } } }, - "estraverse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", - "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==" - }, "estree-util-is-identifier-name": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/estree-util-is-identifier-name/-/estree-util-is-identifier-name-3.0.0.tgz", @@ -16212,11 +14870,6 @@ "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-5.0.1.tgz", "integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==" }, - "events": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", - "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==" - }, "expect-type": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/expect-type/-/expect-type-1.2.0.tgz", @@ -16287,11 +14940,6 @@ "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", "dev": true }, - "fast-uri": { - "version": "3.0.6", - "resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.0.6.tgz", - "integrity": "sha512-Atfo14OibSv5wAp4VWNsFYE1AchQRTv9cBGWET4pZWHzYshFSS9NQI6I57rdKn9croWVMbYFbLhJ+yJvmZIIHw==" - }, "fastq": { "version": "1.17.1", "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.17.1.tgz", @@ -16407,12 +15055,6 @@ "integrity": "sha512-ZsDfxO51wGAXREY55a7la9LScWpwv9RxIrYABrlvOFBlH/ShPnrtsXeuUIfXKKOVicNxQ+o8JTbJvjS4M89yew==", "dev": true }, - "fs-constants": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", - "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", - "dev": true - }, "fs-extra": { "version": "8.1.0", "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-8.1.0.tgz", @@ -16547,11 +15189,6 @@ "is-glob": "^4.0.3" } }, - "glob-to-regexp": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz", - "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==" - }, "global-agent": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/global-agent/-/global-agent-3.0.0.tgz", @@ -16641,7 +15278,8 @@ "has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true }, "has-property-descriptors": { "version": "1.0.2", @@ -16767,7 +15405,6 @@ "version": "23.12.2", "resolved": "https://registry.npmjs.org/i18next/-/i18next-23.12.2.tgz", "integrity": "sha512-XIeh5V+bi8SJSWGL3jqbTEBW5oD6rbP5L+E7dVQh1MNTxxYef0x15rhJVcRb7oiuq4jLtgy2SD8eFlf6P2cmqg==", - "peer": true, "requires": { "@babel/runtime": "^7.23.2" } @@ -16811,7 +15448,8 @@ "version": "1.2.1", "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", - "dev": true + "dev": true, + "optional": true }, "ignore": { "version": "5.3.1", @@ -16979,12 +15617,6 @@ "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz", "integrity": "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==" }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", - "dev": true - }, "isbinaryfile": { "version": "5.0.2", "resolved": "https://registry.npmjs.org/isbinaryfile/-/isbinaryfile-5.0.2.tgz", @@ -17019,16 +15651,6 @@ "minimatch": "^3.1.2" } }, - "jest-worker": { - "version": "27.5.1", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", - "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", - "requires": { - "@types/node": "*", - "merge-stream": "^2.0.0", - "supports-color": "^8.0.0" - } - }, "jiti": { "version": "1.21.7", "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.21.7.tgz", @@ -17043,7 +15665,8 @@ "js-tokens": { "version": "4.0.0", "resolved": "https://registry.npmmirror.com/js-tokens/-/js-tokens-4.0.0.tgz", - "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==" + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true }, "js-yaml": { "version": "4.1.0", @@ -17064,11 +15687,6 @@ "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==" }, - "json-parse-even-better-errors": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", - "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==" - }, "json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", @@ -17098,7 +15716,8 @@ "json5": { "version": "2.2.3", "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", - "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==" + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", + "dev": true }, "jsonfile": { "version": "4.0.0", @@ -17131,47 +15750,6 @@ "resolved": "https://registry.npmjs.org/lazy-val/-/lazy-val-1.0.5.tgz", "integrity": "sha512-0/BnGCCfyUMkBpeDgWihanIAF9JmZhHBgUhEqzvf+adhNGLoP6TaiI5oF8oyb3I45P+PcnrqihSf01M0l0G5+Q==" }, - "lazystream": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/lazystream/-/lazystream-1.0.1.tgz", - "integrity": "sha512-b94GiNHQNy6JNTrt5w6zNyffMrNkXZb3KTkCZJb2V1xaEGCk093vkZ2jk3tpaeP33/OiXC+WvK9AxUebnf5nbw==", - "dev": true, - "requires": { - "readable-stream": "^2.0.5" - }, - "dependencies": { - "readable-stream": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", - "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", - "dev": true, - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true - }, - "string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "dev": true, - "requires": { - "safe-buffer": "~5.1.0" - } - } - } - }, "levn": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", @@ -17194,21 +15772,6 @@ "integrity": "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==", "dev": true }, - "loader-runner": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.0.tgz", - "integrity": "sha512-3R/1M+yS3j5ou80Me59j7F9IMs4PXs3VqRrm0TU3AbKPxlmpoY1TNscJV/oGJXo8qCatFGTfDbY6W6ipGOYXfg==" - }, - "loader-utils": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.4.tgz", - "integrity": "sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw==", - "requires": { - "big.js": "^5.2.2", - "emojis-list": "^3.0.0", - "json5": "^2.1.2" - } - }, "lodash": { "version": "4.17.21", "resolved": "https://registry.npmmirror.com/lodash/-/lodash-4.17.21.tgz", @@ -17219,52 +15782,22 @@ "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==" }, - "lodash.defaults": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/lodash.defaults/-/lodash.defaults-4.2.0.tgz", - "integrity": "sha512-qjxPLHd3r5DnsdGacqOMU6pb/avJzdh9tFX2ymgoZE27BmjXrNy/y4LoaiTeAb+O3gL8AfpJGtqfX/ae2leYYQ==", - "dev": true - }, - "lodash.difference": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.difference/-/lodash.difference-4.5.0.tgz", - "integrity": "sha512-dS2j+W26TQ7taQBGN8Lbbq04ssV3emRw4NY58WErlTO29pIqS0HmoT5aJ9+TUQ1N3G+JOZSji4eugsWwGp9yPA==", - "dev": true - }, "lodash.escaperegexp": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/lodash.escaperegexp/-/lodash.escaperegexp-4.1.2.tgz", "integrity": "sha512-TM9YBvyC84ZxE3rgfefxUWiQKLilstD6k7PTGt6wfbtXF8ixIJLOL3VYyV/z+ZiPLsVxAsKAFVwWlWeb2Y8Yyw==" }, - "lodash.flatten": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/lodash.flatten/-/lodash.flatten-4.4.0.tgz", - "integrity": "sha512-C5N2Z3DgnnKr0LOpv/hKCgKdb7ZZwafIrsesve6lmzvZIRZRGaZ/l6Q8+2W7NaT+ZwO3fFlSCzCzrDCFdJfZ4g==", - "dev": true - }, "lodash.isequal": { "version": "4.5.0", "resolved": "https://registry.npmjs.org/lodash.isequal/-/lodash.isequal-4.5.0.tgz", "integrity": "sha512-pDo3lu8Jhfjqls6GkMgpahsF9kCyayhgykjyLMNFTKWrpVdAQtYyB4muAMWozBB4ig/dtWAmsMxLEI8wuz+DYQ==" }, - "lodash.isplainobject": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", - "integrity": "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==", - "dev": true - }, "lodash.merge": { "version": "4.6.2", "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", "dev": true }, - "lodash.union": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/lodash.union/-/lodash.union-4.6.0.tgz", - "integrity": "sha512-c4pB2CdGrGdjMKYLA+XiRDO7Y0PRQbm/Gzg8qMj+QH+pFVAoTp5sBpO0odL3FjoPCGjK96p6qsP+yQoiLoOBcw==", - "dev": true - }, "longest-streak": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz", @@ -17274,6 +15807,7 @@ "version": "1.4.0", "resolved": "https://registry.npmmirror.com/loose-envify/-/loose-envify-1.4.0.tgz", "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", + "dev": true, "requires": { "js-tokens": "^3.0.0 || ^4.0.0" } @@ -17435,11 +15969,6 @@ "@types/mdast": "^4.0.0" } }, - "merge-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", - "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==" - }, "merge2": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", @@ -17676,12 +16205,14 @@ "mime-db": { "version": "1.52.0", "resolved": "https://registry.npmmirror.com/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==" + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "dev": true }, "mime-types": { "version": "2.1.35", "resolved": "https://registry.npmmirror.com/mime-types/-/mime-types-2.1.35.tgz", "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dev": true, "requires": { "mime-db": "1.52.0" } @@ -17795,11 +16326,6 @@ "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", "dev": true }, - "neo-async": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", - "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==" - }, "node-addon-api": { "version": "1.7.2", "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-1.7.2.tgz", @@ -17810,7 +16336,8 @@ "node-releases": { "version": "2.0.19", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.19.tgz", - "integrity": "sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw==" + "integrity": "sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw==", + "dev": true }, "normalize-path": { "version": "3.0.0", @@ -17983,7 +16510,8 @@ "picocolors": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", - "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==" + "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", + "dev": true }, "picomatch": { "version": "2.3.1", @@ -18038,7 +16566,6 @@ "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.3.tgz", "integrity": "sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==", "dev": true, - "peer": true, "requires": { "nanoid": "^3.3.8", "picocolors": "^1.1.1", @@ -18114,12 +16641,6 @@ "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", "dev": true }, - "process-nextick-args": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", - "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", - "dev": true - }, "progress": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", @@ -18171,14 +16692,6 @@ "resolved": "https://registry.npmjs.org/quickselect/-/quickselect-2.0.0.tgz", "integrity": "sha512-RKJ22hX8mHe3Y6wH/N3wCM6BWtjaxIyyUIkpHOvfFnxdI4yD4tBXEBKSbriGujF6jnSVkJrffuo6vxACiSSxIw==" }, - "randombytes": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", - "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", - "requires": { - "safe-buffer": "^5.1.0" - } - }, "rbush": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/rbush/-/rbush-3.0.1.tgz", @@ -18583,7 +17096,7 @@ "version": "18.3.1", "resolved": "https://registry.npmjs.org/react/-/react-18.3.1.tgz", "integrity": "sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==", - "peer": true, + "dev": true, "requires": { "loose-envify": "^1.1.0" } @@ -18592,7 +17105,7 @@ "version": "18.3.1", "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.3.1.tgz", "integrity": "sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw==", - "peer": true, + "dev": true, "requires": { "loose-envify": "^1.1.0", "scheduler": "^0.23.2" @@ -18615,8 +17128,7 @@ "react-icons": { "version": "5.2.1", "resolved": "https://registry.npmjs.org/react-icons/-/react-icons-5.2.1.tgz", - "integrity": "sha512-zdbW5GstTzXaVKvGSyTaBalt7HSfuK5ovrzlpyiWHAFXndXTdd/1hdDHI4xBM1Mn7YriT6aqESucFl9kEXzrdw==", - "requires": {} + "integrity": "sha512-zdbW5GstTzXaVKvGSyTaBalt7HSfuK5ovrzlpyiWHAFXndXTdd/1hdDHI4xBM1Mn7YriT6aqESucFl9kEXzrdw==" }, "react-markdown": { "version": "9.0.1", @@ -18677,46 +17189,6 @@ "lazy-val": "^1.0.4" } }, - "readable-stream": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", - "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", - "dev": true, - "requires": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - } - }, - "readdir-glob": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/readdir-glob/-/readdir-glob-1.1.3.tgz", - "integrity": "sha512-v05I2k7xN8zXvPD9N+z/uhXPaj0sUFCe2rcWZIpBsqxfP7xXFQ0tipAd/wjj1YxWyWtUS5IDJpOG82JKt2EAVA==", - "dev": true, - "requires": { - "minimatch": "^5.1.0" - }, - "dependencies": { - "brace-expansion": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", - "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", - "dev": true, - "requires": { - "balanced-match": "^1.0.0" - } - }, - "minimatch": { - "version": "5.1.6", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.6.tgz", - "integrity": "sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g==", - "dev": true, - "requires": { - "brace-expansion": "^2.0.1" - } - } - } - }, "readdirp": { "version": "3.6.0", "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", @@ -18760,11 +17232,6 @@ "integrity": "sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==", "dev": true }, - "require-from-string": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", - "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==" - }, "resize-observer-polyfill": { "version": "1.5.1", "resolved": "https://registry.npmmirror.com/resize-observer-polyfill/-/resize-observer-polyfill-1.5.1.tgz", @@ -18879,11 +17346,6 @@ "resolved": "https://registry.npmjs.org/rw/-/rw-1.3.3.tgz", "integrity": "sha512-PdhdWy89SiZogBLaw42zdeqtRJ//zFd2PgQavcICDUgJT5oW10QCRKbJ6bg4r0/UY2M6BWd5tkxuGFRvCkgfHQ==" }, - "safe-buffer": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", - "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==" - }, "safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", @@ -18903,7 +17365,6 @@ "resolved": "https://registry.npmjs.org/sass/-/sass-1.77.8.tgz", "integrity": "sha512-4UHg6prsrycW20fqLGPShtEvo/WyHRVRHwOP4DzkUrObWoWI05QBSfzU71TVB7PFaL104TwNaHpjlWXAZbQiNQ==", "dev": true, - "peer": true, "requires": { "chokidar": ">=3.0.0 <4.0.0", "immutable": "^4.0.0", @@ -18919,48 +17380,11 @@ "version": "0.23.2", "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz", "integrity": "sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ==", + "dev": true, "requires": { "loose-envify": "^1.1.0" } }, - "schema-utils": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-4.3.0.tgz", - "integrity": "sha512-Gf9qqc58SpCA/xdziiHz35F4GNIWYWZrEshUc/G/r5BnLph6xpKuLeoJoQuj5WfBIx/eQLf+hmVPYHaxJu7V2g==", - "requires": { - "@types/json-schema": "^7.0.9", - "ajv": "^8.9.0", - "ajv-formats": "^2.1.1", - "ajv-keywords": "^5.1.0" - }, - "dependencies": { - "ajv": { - "version": "8.17.1", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz", - "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", - "peer": true, - "requires": { - "fast-deep-equal": "^3.1.3", - "fast-uri": "^3.0.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2" - } - }, - "ajv-keywords": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-5.1.0.tgz", - "integrity": "sha512-YCS/JNFAUyr5vAuhk1DWm1CBxRHW9LbJ2ozWeemrIqpbsqKjHVxYPyi5GC0rjZIT5JxJ3virVTS8wk4i/Z+krw==", - "requires": { - "fast-deep-equal": "^3.1.3" - } - }, - "json-schema-traverse": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", - "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==" - } - } - }, "screenfull": { "version": "5.2.0", "resolved": "https://registry.npmjs.org/screenfull/-/screenfull-5.2.0.tgz", @@ -18994,14 +17418,6 @@ "type-fest": "^0.13.1" } }, - "serialize-javascript": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.2.tgz", - "integrity": "sha512-Saa1xPByTTq2gdeFZYLLo+RFE35NHZkAbqZeWNd3BpzppeVisAqpDjcp8dyf6uIvEqJRd46jemmyA4iFIeVk8g==", - "requires": { - "randombytes": "^2.1.0" - } - }, "shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -19074,7 +17490,8 @@ "source-map": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true }, "source-map-js": { "version": "1.2.1", @@ -19086,6 +17503,7 @@ "version": "0.5.21", "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz", "integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==", + "dev": true, "requires": { "buffer-from": "^1.0.0", "source-map": "^0.6.0" @@ -19120,15 +17538,6 @@ "integrity": "sha512-Bc3YwwCB+OzldMxOXJIIvC6cPRWr/LxOp48CdQTOkPyk/t4JWWJbrilwBd7RJzKV8QW7tJkcgAmeuLLJugl5/w==", "dev": true }, - "string_decoder": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", - "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", - "dev": true, - "requires": { - "safe-buffer": "~5.2.0" - } - }, "string-convert": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/string-convert/-/string-convert-0.2.1.tgz", @@ -19281,14 +17690,6 @@ "debug": "^4.1.0" } }, - "supports-color": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "requires": { - "has-flag": "^4.0.0" - } - }, "supports-preserve-symlinks-flag": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", @@ -19343,11 +17744,6 @@ } } }, - "tapable": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", - "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==" - }, "tar": { "version": "6.2.1", "resolved": "https://registry.npmjs.org/tar/-/tar-6.2.1.tgz", @@ -19370,19 +17766,6 @@ } } }, - "tar-stream": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", - "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", - "dev": true, - "requires": { - "bl": "^4.0.3", - "end-of-stream": "^1.4.1", - "fs-constants": "^1.0.0", - "inherits": "^2.0.3", - "readable-stream": "^3.1.1" - } - }, "temp-file": { "version": "3.4.0", "resolved": "https://registry.npmjs.org/temp-file/-/temp-file-3.4.0.tgz", @@ -19422,29 +17805,6 @@ } } }, - "terser": { - "version": "5.31.5", - "resolved": "https://registry.npmjs.org/terser/-/terser-5.31.5.tgz", - "integrity": "sha512-YPmas0L0rE1UyLL/llTWA0SiDOqIcAQYLeUj7cJYzXHlRTAnMSg9pPe4VJ5PlKvTrPQsdVFuiRiwyeNlYgwh2Q==", - "requires": { - "@jridgewell/source-map": "^0.3.3", - "acorn": "^8.8.2", - "commander": "^2.20.0", - "source-map-support": "~0.5.20" - } - }, - "terser-webpack-plugin": { - "version": "5.3.14", - "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.14.tgz", - "integrity": "sha512-vkZjpUjb6OMS7dhV+tILUW6BhpDR7P2L/aQSAv+Uwk+m8KATX9EccViHTJR2qDtACKPIYndLGCyl3FMo+r2LMw==", - "requires": { - "@jridgewell/trace-mapping": "^0.3.25", - "jest-worker": "^27.4.5", - "schema-utils": "^4.3.0", - "serialize-javascript": "^6.0.2", - "terser": "^5.31.1" - } - }, "text-table": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", @@ -19505,15 +17865,13 @@ "version": "6.4.4", "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.4.4.tgz", "integrity": "sha512-1NZP+GK4GfuAv3PqKvxQRDMjdSRZjnkq7KfhlNrCNNlZ0ygQFpebfrnfnq/W7fpUnAv9aGWmY1zKx7FYL3gwhg==", - "dev": true, - "requires": {} + "dev": true }, "picomatch": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.2.tgz", "integrity": "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==", - "dev": true, - "peer": true + "dev": true } } }, @@ -19592,8 +17950,7 @@ "version": "1.3.0", "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-1.3.0.tgz", "integrity": "sha512-UQMIo7pb8WRomKR1/+MFVLTroIvDVtMX3K6OUir8ynLyzB8Jeriont2bTAtmNPa1ekAgN7YPDyf6V+ygrdU+eQ==", - "dev": true, - "requires": {} + "dev": true }, "ts-interface-checker": { "version": "0.1.13", @@ -19616,7 +17973,6 @@ "resolved": "https://registry.npmjs.org/tsx/-/tsx-4.19.3.tgz", "integrity": "sha512-4H8vUNGNjQ4V2EOoGw005+c+dGuPSnhpPBPHBtsZdGZBk/iJb4kguGlPWaZTZ3q5nMtFOEsY0nRDlh9PJyd6SQ==", "dev": true, - "peer": true, "requires": { "esbuild": "~0.25.0", "fsevents": "~2.3.3", @@ -19642,8 +17998,7 @@ "version": "5.8.2", "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.8.2.tgz", "integrity": "sha512-aJn6wq13/afZp/jT9QZmwEjDqqvSGp1VT5GVg+f/t6/oVyrgXM6BY1h9BRh/O5p3PlUPAe+WuiEZOmb/49RqoQ==", - "dev": true, - "peer": true + "dev": true }, "undici-types": { "version": "5.26.5", @@ -19725,6 +18080,7 @@ "version": "1.1.3", "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.1.3.tgz", "integrity": "sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==", + "dev": true, "requires": { "escalade": "^3.2.0", "picocolors": "^1.1.1" @@ -19742,8 +18098,7 @@ "use-force-update": { "version": "1.0.11", "resolved": "https://registry.npmjs.org/use-force-update/-/use-force-update-1.0.11.tgz", - "integrity": "sha512-h4SICYgTJHon8w9dFIqdqR1Vrzdgl4YaRfRwhmAh01kBGljzTICanyfaFU8C4etuEfRdYpE+04XX2ZrEhOWKXQ==", - "requires": {} + "integrity": "sha512-h4SICYgTJHon8w9dFIqdqR1Vrzdgl4YaRfRwhmAh01kBGljzTICanyfaFU8C4etuEfRdYpE+04XX2ZrEhOWKXQ==" }, "usehooks-ts": { "version": "3.1.0", @@ -19801,7 +18156,6 @@ "resolved": "https://registry.npmjs.org/vite/-/vite-6.3.5.tgz", "integrity": "sha512-cZn6NDFE7wdTpINgs++ZJ4N49W2vRp8LCKrn3Ob1kYNtOo21vfDoaV5GzBfLU4MovSAB8uNRm4jgzVQZ+mBzPQ==", "dev": true, - "peer": true, "requires": { "esbuild": "^0.25.0", "fdir": "^6.4.4", @@ -19816,15 +18170,13 @@ "version": "6.4.4", "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.4.4.tgz", "integrity": "sha512-1NZP+GK4GfuAv3PqKvxQRDMjdSRZjnkq7KfhlNrCNNlZ0ygQFpebfrnfnq/W7fpUnAv9aGWmY1zKx7FYL3gwhg==", - "dev": true, - "requires": {} + "dev": true }, "picomatch": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.2.tgz", "integrity": "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==", - "dev": true, - "peer": true + "dev": true } } }, @@ -19843,8 +18195,7 @@ "version": "0.14.1", "resolved": "https://registry.npmjs.org/vite-plugin-electron/-/vite-plugin-electron-0.14.1.tgz", "integrity": "sha512-QGQ2nJ4wjMf1FaDSkdoC/UskQGiYGcAToATJqJXvqrL4Jmt0CFaZqoDjh1xLicUWEo/X7urHYjhKTqwEeP7F7g==", - "dev": true, - "requires": {} + "dev": true } } }, @@ -19865,15 +18216,13 @@ "version": "0.29.0", "resolved": "https://registry.npmjs.org/vite-plugin-electron/-/vite-plugin-electron-0.29.0.tgz", "integrity": "sha512-HP0DI9Shg41hzt55IKYVnbrChWXHX95QtsEQfM+szQBpWjVhVGMlqRjVco6ebfQjWNr+Ga+PeoBjMIl8zMaufw==", - "dev": true, - "requires": {} + "dev": true }, "vite-plugin-electron-renderer": { "version": "0.14.6", "resolved": "https://registry.npmjs.org/vite-plugin-electron-renderer/-/vite-plugin-electron-renderer-0.14.6.tgz", "integrity": "sha512-oqkWFa7kQIkvHXG7+Mnl1RTroA4sP0yesKatmAy0gjZC4VwUqlvF9IvOpHd1fpLWsqYX/eZlVxlhULNtaQ78Jw==", - "dev": true, - "peer": true + "dev": true }, "vitest": { "version": "3.0.7", @@ -19908,56 +18257,11 @@ "resolved": "https://registry.npmjs.org/void-elements/-/void-elements-3.1.0.tgz", "integrity": "sha512-Dhxzh5HZuiHQhbvTW9AMetFfBHDMYpo23Uo9btPXgdYP+3T5S+p+jgNy7spra+veYhBP2dCSgxR/i2Y02h5/6w==" }, - "watchpack": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.2.tgz", - "integrity": "sha512-TnbFSbcOCcDgjZ4piURLCbJ3nJhznVh9kw6F6iokjiFPl8ONxe9A6nMDVXDiNbrSfLILs6vB07F7wLBrwPYzJw==", - "requires": { - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.1.2" - } - }, "webidl-conversions": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==" }, - "webpack": { - "version": "5.98.0", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.98.0.tgz", - "integrity": "sha512-UFynvx+gM44Gv9qFgj0acCQK2VE1CtdfwFdimkapco3hlPCJ/zeq73n2yVKimVbtm+TnApIugGhLJnkU6gjYXA==", - "peer": true, - "requires": { - "@types/eslint-scope": "^3.7.7", - "@types/estree": "^1.0.6", - "@webassemblyjs/ast": "^1.14.1", - "@webassemblyjs/wasm-edit": "^1.14.1", - "@webassemblyjs/wasm-parser": "^1.14.1", - "acorn": "^8.14.0", - "browserslist": "^4.24.0", - "chrome-trace-event": "^1.0.2", - "enhanced-resolve": "^5.17.1", - "es-module-lexer": "^1.2.1", - "eslint-scope": "5.1.1", - "events": "^3.2.0", - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.2.11", - "json-parse-even-better-errors": "^2.3.1", - "loader-runner": "^4.2.0", - "mime-types": "^2.1.27", - "neo-async": "^2.6.2", - "schema-utils": "^4.3.0", - "tapable": "^2.1.1", - "terser-webpack-plugin": "^5.3.11", - "watchpack": "^2.4.1", - "webpack-sources": "^3.2.3" - } - }, - "webpack-sources": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.3.tgz", - "integrity": "sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==" - }, "whatwg-url": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", @@ -19986,15 +18290,6 @@ "stackback": "0.0.2" } }, - "workerize-loader": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/workerize-loader/-/workerize-loader-2.0.2.tgz", - "integrity": "sha512-HoZ6XY4sHWxA2w0WpzgBwUiR3dv1oo7bS+oCwIpb6n54MclQ/7KXdXsVIChTCygyuHtVuGBO1+i3HzTt699UJQ==", - "peer": true, - "requires": { - "loader-utils": "^2.0.0" - } - }, "wrap-ansi": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", @@ -20082,42 +18377,10 @@ "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", "dev": true }, - "zip-stream": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/zip-stream/-/zip-stream-4.1.1.tgz", - "integrity": "sha512-9qv4rlDiopXg4E69k+vMHjNN63YFMe9sZMrdlvKnCjlCRWeCBswPPMPUfx+ipsAWq1LXHe70RcbaHdJJpS6hyQ==", - "dev": true, - "requires": { - "archiver-utils": "^3.0.4", - "compress-commons": "^4.1.2", - "readable-stream": "^3.6.0" - }, - "dependencies": { - "archiver-utils": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/archiver-utils/-/archiver-utils-3.0.4.tgz", - "integrity": "sha512-KVgf4XQVrTjhyWmx6cte4RxonPLR9onExufI1jhvw/MQ4BB6IsZD5gT8Lq+u/+pRkWna/6JoHpiQioaqFP5Rzw==", - "dev": true, - "requires": { - "glob": "^7.2.3", - "graceful-fs": "^4.2.0", - "lazystream": "^1.0.0", - "lodash.defaults": "^4.2.0", - "lodash.difference": "^4.5.0", - "lodash.flatten": "^4.4.0", - "lodash.isplainobject": "^4.0.6", - "lodash.union": "^4.6.0", - "normalize-path": "^3.0.0", - "readable-stream": "^3.6.0" - } - } - } - }, "zustand": { "version": "5.0.3", "resolved": "https://registry.npmjs.org/zustand/-/zustand-5.0.3.tgz", - "integrity": "sha512-14fwWQtU3pH4dE0dOpdMiWjddcH+QzKIgk1cl8epwSE7yag43k/AD/m4L6+K7DytAOr9gGBe3/EXj9g7cdostg==", - "requires": {} + "integrity": "sha512-14fwWQtU3pH4dE0dOpdMiWjddcH+QzKIgk1cl8epwSE7yag43k/AD/m4L6+K7DytAOr9gGBe3/EXj9g7cdostg==" }, "zwitch": { "version": "2.0.4", diff --git a/sample/workdir/monster.json b/sample/workdir/monster.json index 5460003..11abf40 100644 --- a/sample/workdir/monster.json +++ b/sample/workdir/monster.json @@ -1,72 +1,92 @@ { - "version": "1.8.0", - "name": "monster", + "$override": { + }, + "custom": { + }, "desc": "怪物测试AI", - "firstid": 1, "export": true, - "group": ["Test"], - "import": [], - "vars": [], + "group": [ + "Test" + ], + "import": [ + ], + "name": "monster", + "prefix": "", "root": { - "id": 1, - "name": "Sequence", - "desc": "怪物测试AI", + "$id": "UzMJ4RCPJi", "children": [ { - "id": 2, - "name": "Sequence", - "desc": "攻击", + "$id": "22VgEJ8qBb", "children": [ { - "id": 3, - "name": "GetHp", - "output": ["hp"], + "$id": "sPc1hCO5Y0", "children": [ { - "id": 4, - "name": "Sequence", + "$id": "IliI30nEez", "desc": "新建行为树", + "id": "4", + "name": "Sequence", "path": "workdir/subtree2.json" } + ], + "id": "3", + "name": "GetHp", + "output": [ + "hp" ] }, { - "id": 6, - "name": "Cmp", + "$id": "UflkVPzbM2", "args": { - "value": "hp", - "gt": 50 + "gt": 50, + "value": "hp" }, - "input": ["hp"] + "id": "6", + "input": [ + "hp" + ], + "name": "Cmp" }, { - "id": 7, - "name": "TestB3", - "desc": "攻击", + "$id": "vGBhrKx6OT", "args": { - "time": 1, - "open": true, "check": "1", "name": "1", - "status": "FAILURE" - } + "open": true, + "status": "FAILURE", + "time": 1 + }, + "desc": "攻击", + "id": "7", + "name": "TestB3" }, { - "id": 8, - "name": "Sequence", + "$id": "0XPfo7WtaM", "desc": "新建行为树", + "id": "8", + "name": "Sequence", "path": "workdir/subtree1.json" } - ] + ], + "desc": "攻击", + "id": "2", + "name": "Sequence" }, { - "id": 11, - "name": "Log", - "desc": "逃跑", + "$id": "k3OVVSX9ih", "args": { "message": "Run!" - } + }, + "desc": "逃跑", + "id": "11", + "name": "Log" } - ] - } -} + ], + "desc": "怪物测试AI", + "id": "1", + "name": "Sequence" + }, + "vars": [ + ], + "version": "2.0.0" +} \ No newline at end of file diff --git a/sample/workdir/sub/subtree1.json b/sample/workdir/sub/subtree1.json index f925b66..5f6c2c2 100644 --- a/sample/workdir/sub/subtree1.json +++ b/sample/workdir/sub/subtree1.json @@ -1,30 +1,40 @@ { - "version": "1.8.0", - "name": "subtree1", + "$override": { + }, + "custom": { + }, "desc": "子树1", - "firstid": 1, - "group": [], - "import": [], - "vars": [], + "group": [ + ], + "import": [ + ], + "name": "subtree1", + "prefix": "", "root": { - "id": 1, - "name": "Sequence", - "desc": "新建行为树", + "$id": "IP1AisFtFv", "children": [ { - "id": 2, - "name": "Log", + "$id": "yZbdLrFj5E", "args": { "message": "d" - } + }, + "id": "2", + "name": "Log" }, { - "id": 3, - "name": "Wait", + "$id": "xkChWKGQn1", "args": { "time": 1 - } + }, + "id": "3", + "name": "Wait" } - ] - } -} + ], + "desc": "新建行为树", + "id": "1", + "name": "Sequence" + }, + "vars": [ + ], + "version": "2.0.0" +} \ No newline at end of file diff --git a/sample/workdir/subtree1.json b/sample/workdir/subtree1.json index 3a6b866..29527f8 100644 --- a/sample/workdir/subtree1.json +++ b/sample/workdir/subtree1.json @@ -1,30 +1,39 @@ { - "version": "1.8.0", - "name": "subtree1", + "$override": { + }, + "custom": { + }, "desc": "子树1", - "firstid": 1, - "group": [], - "import": [], - "vars": [], + "group": [ + ], + "import": [ + ], + "name": "subtree1", + "prefix": "", "root": { - "id": 1, - "name": "Sequence", - "desc": "新建行为树", + "$id": "GosdwkpHRi", "children": [ { - "id": 2, - "name": "Log", - "args": { - "message": "hello" - } + "$id": "VJjl0tZcRq", + "desc": "新建行为树", + "id": "2", + "name": "Sequence", + "path": "workdir/sub/subtree1.json" }, { - "id": 3, - "name": "Wait", + "$id": "6OKeNNuNW9", "args": { "time": 1 - } + }, + "id": "5", + "name": "Wait" } - ] - } -} + ], + "desc": "新建行为树", + "id": "1", + "name": "Sequence" + }, + "vars": [ + ], + "version": "2.0.0" +} \ No newline at end of file diff --git a/sample/workdir/subtree2.json b/sample/workdir/subtree2.json index b86b161..57e2864 100644 --- a/sample/workdir/subtree2.json +++ b/sample/workdir/subtree2.json @@ -1,22 +1,34 @@ { - "version": "1.8.0", - "name": "subtree2", + "$override": { + }, + "custom": { + }, "desc": "子树2", - "firstid": 1, - "group": [], - "import": [], - "vars": [], + "group": [ + ], + "import": [ + ], + "name": "subtree2", + "prefix": "", "root": { - "id": 1, - "name": "Sequence", - "desc": "新建行为树", + "$id": "TZZbFRZLIC", "children": [ { - "id": 2, - "name": "Cmp", - "args": {}, - "input": ["x"] + "$id": "iF9KMbqNoB", + "args": { + }, + "id": "2", + "input": [ + "x" + ], + "name": "Cmp" } - ] - } -} + ], + "desc": "新建行为树", + "id": "1", + "name": "Sequence" + }, + "vars": [ + ], + "version": "2.0.0" +} \ No newline at end of file diff --git a/teen/example.json b/teen/example.json new file mode 100644 index 0000000..e45fa51 --- /dev/null +++ b/teen/example.json @@ -0,0 +1,44 @@ +{ + "$override": { + }, + "custom": { + }, + "group": [ + ], + "import": [ + ], + "name": "example", + "prefix": "", + "root": { + "$id": "WlN4KrHMeI", + "children": [ + { + "$id": "VewHwrsZoK", + "args": { + "level": "log", + "message": "hello" + }, + "id": "2", + "name": "Log" + }, + { + "$id": "w2qpYhd3fi", + "args": { + "time": 1 + }, + "id": "3", + "name": "Wait" + }, + { + "$id": "bro2CDGyFh", + "id": "4", + "name": "unknow" + } + ], + "id": "1", + "name": "Sequence" + }, + "vars": [ + ], + "version": "2.0.0" +} \ No newline at end of file diff --git a/teen/node-config.b3-setting b/teen/node-config.b3-setting new file mode 100644 index 0000000..df30ecf --- /dev/null +++ b/teen/node-config.b3-setting @@ -0,0 +1,856 @@ +[ + { + "name": "AlwaysFailure", + "type": "Decorator", + "children": 1, + "status": [ + "failure", + "|running" + ], + "desc": "始终返回失败", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `running` 时,返回 `running`\n+ 其它情况,不管子节点是否成功都返回 `failure`\n" + }, + { + "name": "AlwaysRunning", + "type": "Decorator", + "children": 1, + "status": [ + "running" + ], + "desc": "始终返回运行中状态", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 始终返回 `running`\n" + }, + { + "name": "AlwaysSuccess", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running" + ], + "desc": "始终返回成功", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `running` 时,返回 `running`\n+ 其它情况,不管子节点是否成功都返回 `success`\n" + }, + { + "name": "Assert", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "断言", + "args": [ + { + "name": "message", + "type": "string", + "desc": "消息" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `failure` 时,抛出异常\n+ 其余情况返回子节点的执行状态\n" + }, + { + "name": "Calculate", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "简单的数值公式计算", + "args": [ + { + "name": "value", + "type": "expr", + "desc": "计算公式" + } + ], + "output": [ + "计算结果" + ], + "doc": "+ 做简单的数值公式计算,返回结果到输出\n" + }, + { + "name": "Case", + "type": "Composite", + "children": 2, + "status": [ + "&success", + "|failure", + "|running" + ], + "desc": "分支选择", + "doc": "+ 必须有两个子节点\n+ 第一个子节点为判断条件\n+ 第二个子节点为判断为 `success` 时执行的节点\n+ 此节点不会真正意义的执行,而是交由 `Switch` 节点来执行\n" + }, + { + "name": "Check", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "检查True或False", + "args": [ + { + "name": "value", + "type": "expr", + "desc": "值" + } + ], + "doc": "+ 做简单数值公式判定,返回 `success` 或 `failure`\n" + }, + { + "name": "Concat", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "将两个输入合并为一个数组,并返回新数组", + "input": [ + "数组1", + "数组2" + ], + "output": [ + "新数组" + ], + "doc": "+ 如果输入不是数组,则返回 `failure`\n" + }, + { + "name": "Delay", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "延时执行子节点", + "input": [ + "延时时间?" + ], + "args": [ + { + "name": "delay", + "type": "float?", + "desc": "延时时间", + "oneof": "延时时间" + }, + { + "name": "cacheVars", + "type": "string[]?", + "desc": "暂存环境变量" + } + ], + "doc": "+ 当延时触发时,执行第一个子节点,多个仅执行第一个\n+ 如果子节点返回 `running`,会中断执行并清理执行栈" + }, + { + "name": "Filter", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "failure", + "|running" + ], + "desc": "返回满足条件的元素", + "input": [ + "输入数组" + ], + "output": [ + "变量", + "新数组" + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 遍历输入数组,将当前元素写入`变量`,满足条件的元素放入新数组\n+ 只有当新数组不为空时,才返回 `success`\n" + }, + { + "name": "ForEach", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running", + "|failure" + ], + "desc": "遍历数组", + "input": [ + "数组" + ], + "output": [ + "变量", + "索引?" + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 遍历输入数组,将当前元素写入`变量`\n+ 当子节点返回 `failure` 时,退出遍历并返回 `failure` 状态\n+ 执行完所有子节点后,返回 `success`" + }, + { + "name": "GetField", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "获取对象的字段值", + "args": [ + { + "name": "field", + "type": "string?", + "desc": "字段(field)", + "oneof": "字段(field)" + } + ], + "input": [ + "对象", + "字段(field)?" + ], + "output": [ + "字段值(value)" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 只有获取到合法元素时候才会返回 `success`,否则返回 `failure`\n" + }, + { + "name": "IfElse", + "type": "Composite", + "children": 3, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "条件执行", + "doc": "+ 必须有三个子节点\n+ 第一个子节点为条件节点\n+ 第二个子节点为条件为 `success` 时执行的节点\n+ 第三个子节点为条件为 `failure` 时执行的节点,\n" + }, + { + "name": "Includes", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断元素是否在数组中", + "input": [ + "数组", + "元素" + ], + "doc": "+ 若输入的元素不合法,返回 `failure`\n+ 只有数组包含元素时返回 `success`,否则返回 `failure`\n" + }, + { + "name": "Index", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "索引输入的数组", + "args": [ + { + "name": "index", + "type": "int?", + "desc": "索引", + "oneof": "索引" + } + ], + "input": [ + "数组", + "索引?" + ], + "output": [ + "值" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 索引数组的时候,第一个元素的索引为 0\n+ 只有索引到有合法元素时候才会返回 `success`,否则返回 `failure`\n" + }, + { + "name": "Invert", + "type": "Decorator", + "children": 1, + "status": [ + "!success", + "!failure", + "|running" + ], + "desc": "反转子节点运行结果", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `success` 时返回 `failure`\n+ 当子节点返回 `failure` 时返回 `success`\n+ 当子节点返回 `error` 时返回 `error`\n" + }, + { + "name": "IsNull", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断变量是否不存在", + "input": [ + "判断的变量" + ] + }, + { + "name": "JustFailure", + "type": "Action", + "children": 0, + "status": [ + "failure" + ], + "desc": "什么都不干,只返回失败" + }, + { + "name": "JustSuccess", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "什么都不干,只返回成功" + }, + { + "name": "Let", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "定义新的变量名", + "input": [ + "已存在变量名?" + ], + "args": [ + { + "name": "value", + "type": "json?", + "desc": "值(value)", + "oneof": "已存在变量名" + } + ], + "output": [ + "新变量名" + ], + "doc": "+ 如果有输入变量,则给已有变量重新定义一个名字\n+ 如果`值(value)`为 `null`,则清除变量\n" + }, + { + "name": "Listen", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "侦听事件", + "input": [ + "目标对象?" + ], + "output": [ + "事件目标?", + "事件参数..." + ], + "args": [ + { + "name": "event", + "type": "string", + "desc": "事件", + "options": [ + { + "source": [ + { + "name": "行为树被中断", + "value": "treeInterrupted" + }, + { + "name": "行为树开始执行前", + "value": "treeBeforeTicked" + }, + { + "name": "行为树执行完成后", + "value": "treeAfterTicked" + }, + { + "name": "行为树执行成功后", + "value": "treeTickedSuccess" + }, + { + "name": "行为树执行失败后", + "value": "treeTickedFailure" + }, + { + "name": "行为树被清理", + "value": "treeCleaned" + } + ] + } + ] + } + ], + "doc": "+ 当事件触发时,执行第一个子节点,多个仅执行第一个\n+ 如果子节点返回 `running`,会中断执行并清理执行栈" + }, + { + "name": "Log", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "打印日志", + "input": [ + "日志?" + ], + "args": [ + { + "name": "message", + "type": "string", + "desc": "日志" + }, + { + "name": "level", + "type": "string", + "desc": "日志级别", + "default": "log", + "options": [ + { + "source": [ + { + "name": "LOG", + "value": "log" + }, + { + "name": "INFO", + "value": "info" + }, + { + "name": "DEBUG", + "value": "debug" + }, + { + "name": "WARN", + "value": "warn" + }, + { + "name": "ERROR", + "value": "error" + } + ] + } + ] + } + ] + }, + { + "name": "Math", + "type": "Action", + "desc": "执行数学运算", + "input": [ + "参数..." + ], + "output": [ + "结果" + ], + "status": [ + "success", + "failure" + ], + "args": [ + { + "name": "op", + "type": "string", + "desc": "数学运算类型", + "options": [ + { + "source": [ + { + "name": "绝对值", + "value": "abs" + }, + { + "name": "向上取整", + "value": "ceil" + }, + { + "name": "向下取整", + "value": "floor" + }, + { + "name": "四舍五入", + "value": "round" + }, + { + "name": "符号", + "value": "sign" + }, + { + "name": "正弦", + "value": "sin" + }, + { + "name": "余弦", + "value": "cos" + }, + { + "name": "正切", + "value": "tan" + }, + { + "name": "反正切2", + "value": "atan2" + }, + { + "name": "幂运算", + "value": "pow" + }, + { + "name": "平方根", + "value": "sqrt" + }, + { + "name": "自然对数", + "value": "log" + }, + { + "name": "最小值", + "value": "min" + }, + { + "name": "最大值", + "value": "max" + }, + { + "name": "随机数", + "value": "random" + }, + { + "name": "随机整数", + "value": "randInt" + }, + { + "name": "随机浮点数", + "value": "randFloat" + }, + { + "name": "求和", + "value": "sum" + }, + { + "name": "平均值", + "value": "average" + }, + { + "name": "乘积", + "value": "product" + } + ] + } + ] + }, + { + "name": "value1", + "type": "float?", + "desc": "参数1(优先使用)" + }, + { + "name": "value2", + "type": "float?", + "desc": "参数2(优先使用)" + } + ] + }, + { + "name": "NotNull", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断变量是否存在", + "input": [ + "判断的变量" + ] + }, + { + "name": "Now", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "获取当前时间", + "output": [ + "当前时间" + ] + }, + { + "name": "Once", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "failure", + "|running" + ], + "desc": "只执行一次", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 第一次执行完全部子节点时返回 `success`,之后永远返回 `failure`" + }, + { + "name": "Parallel", + "type": "Composite", + "status": [ + "success", + "|running" + ], + "children": -1, + "desc": "并行执行", + "doc": "+ 并行执行所有子节点\n+ 当有子节点返回 `running` 时,返回 `running` 状态\n+ 执行完所有子节点后,返回 `success`" + }, + { + "name": "Push", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "向数组中添加元素", + "input": [ + "数组", + "元素" + ], + "doc": "+ 当变量`数组`不是数组类型时返回 `failure`\n+ 其余返回 `success`\n" + }, + { + "name": "Race", + "type": "Composite", + "status": [ + "|success", + "&failure", + "|running" + ], + "children": -1, + "desc": "竞争执行", + "doc": "+ 并行执行所有子节点\n+ 当有子节点返回 `success` 时,立即返回 `success` 状态,并中断其他子节点\n+ 如果所有子节点返回 `failure`或 `error` 则返回 `failure`" + }, + { + "name": "RandomIndex", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "随机返回输入的其中一个!", + "input": [ + "输入目标" + ], + "output": [ + "随机目标", + "索引?" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 在输入数组中,随机返回其中一个\n+ 当输入数组为空时,或者没有合法元素,返回 `failure`\n" + }, + { + "name": "Repeat", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running", + "|failure" + ], + "desc": "循环执行", + "input": [ + "循环次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "循环次数", + "oneof": "循环次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `failure` 时,退出遍历并返回 `failure` 状态\n+ 执行完所有子节点后,返回 `success`\n" + }, + { + "name": "RetryUntilFailure", + "type": "Decorator", + "children": 1, + "status": [ + "!success", + "failure", + "running" + ], + "desc": "一直尝试直到子节点返回失败", + "input": [ + "最大尝试次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "最大尝试次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 只有当子节点返回 `failure` 时,才返回 `success`,其它情况返回 `running` 状态\n+ 如果设定了尝试次数,超过指定次数则返回 `failure`" + }, + { + "name": "RetryUntilSuccess", + "type": "Decorator", + "children": 1, + "status": [ + "|success", + "failure", + "running" + ], + "desc": "一直尝试直到子节点返回成功", + "input": [ + "最大尝试次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "最大尝试次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 只有当子节点返回 `success` 时,才返回 `success`,其它情况返回 `running` 状态\n+ 如果设定了尝试次数,超过指定次数则返回 `failure`" + }, + { + "name": "Selector", + "type": "Composite", + "children": -1, + "desc": "选择执行", + "status": [ + "|success", + "&failure", + "|running" + ], + "doc": "+ 一直往下执行,直到有子节点返回 `success` 则返回 `success`\n+ 若全部节点返回 `failure`或 `error` 则返回 `failure`" + }, + { + "name": "Sequence", + "type": "Composite", + "children": -1, + "status": [ + "&success", + "|failure", + "|running" + ], + "desc": "顺序执行", + "doc": "+ 一直往下执行,只有当所有子节点都返回 `success`, 才返回 `success`\n+ 若子节点返回 `failure`,则直接返回 `failure` 状态\n+ 其余情况返回 `running` 状态\n" + }, + { + "name": "SetField", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "设置对象字段值", + "input": [ + "输入对象", + "字段(field)?", + "值(value)?" + ], + "args": [ + { + "name": "field", + "type": "string?", + "desc": "字段(field)", + "oneof": "字段(field)" + }, + { + "name": "value", + "type": "json?", + "desc": "值(value)", + "oneof": "值(value)" + } + ], + "doc": "+ 对输入对象设置 `field` 和 `value`\n+ 输入参数1必须为对象,否则返回 `failure`\n+ 如果 `field` 不为 `string`, 也返回 `failure`\n+ 如果 `value` 为 `undefined` 或 `null`, 则删除 `field` 的值\n" + }, + { + "name": "Switch", + "type": "Composite", + "children": -1, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "分支执行", + "doc": "+ 按顺序测试 `Case` 节点的判断条件(第一个子节点)\n+ 若测试返回 `success` 则执行 `Case` 第二个子节点,并返回子节点的执行状态\n+ 若没有判断为 `success` 的 `Case` 节点,则返回 `failure`\n" + }, + { + "name": "Timeout", + "type": "Decorator", + "children": 1, + "status": [ + "|success", + "|running", + "failure" + ], + "desc": "超时", + "input": [ + "超时时间?" + ], + "args": [ + { + "name": "time", + "type": "float?", + "desc": "超时时间", + "oneof": "超时时间" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点执行超时或返回 `failure` 时,返回 `failure`\n+ 其余情况返回子节点的执行状态\n" + }, + { + "name": "Wait", + "type": "Action", + "children": 0, + "status": [ + "success", + "running" + ], + "desc": "等待", + "input": [ + "等待时间?" + ], + "args": [ + { + "name": "time", + "type": "float?", + "desc": "等待时间", + "oneof": "等待时间" + }, + { + "name": "random", + "type": "float?", + "desc": "随机范围" + } + ] + }, + { + "name": "WaitForEvent", + "type": "Action", + "children": 0, + "status": [ + "success", + "running" + ], + "desc": "等待事件触发", + "args": [ + { + "name": "event", + "type": "string", + "desc": "事件名称" + } + ] + }, + { + "name": "Watchdog", + "type": "Composite", + "children": 3, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "测试执行", + "doc": "+ 必须有3个子节点\n+ 第一个子节点为条件节点,返回 `success` 或 `failure` 状态\n+ 第二个子节点为条件为 `success` 时执行的节点\n+ 第三个子节点为条件为 `failure` 时执行的节点,不管子节点返回什么状态,都直接返回 `failure`\n+ 当第二个子节点返回 `running` 时,由本节点维护其运行状态\n+ 每一次 tick 都会先执行测试节点,只有当测试节点返回 `success`,才执行第二个子节点\n" + } +] \ No newline at end of file diff --git a/teen/workspace.b3-workspace b/teen/workspace.b3-workspace new file mode 100644 index 0000000..9a0c33c --- /dev/null +++ b/teen/workspace.b3-workspace @@ -0,0 +1,4 @@ +{ + "nodeConf": "node-config.b3-setting", + "metadata": [] +} \ No newline at end of file diff --git a/test1/example.json b/test1/example.json new file mode 100644 index 0000000..0b8c697 --- /dev/null +++ b/test1/example.json @@ -0,0 +1,429 @@ +{ + "$override": {}, + "custom": {}, + "desc": "幼年期待机状态树(依据 xlsx:幼年期行为树)", + "export": true, + "group": [], + "import": [], + "name": "idle_state", + "prefix": "", + "root": { + "$id": "rootIdle001", + "id": "1", + "name": "Parallel", + "children": [ + { + "$id": "idleLoop001", + "id": "10", + "name": "Repeat", + "children": [ + { + "$id": "idleSeq001", + "id": "11", + "name": "Sequence", + "children": [ + { + "$id": "idleLog001", + "id": "12", + "name": "Log", + "args": { + "level": "info", + "message": "待机: 基础表情 BABY_EMOMID_BASIC_NORMAL" + } + }, + { + "$id": "idleWait001", + "id": "13", + "name": "Wait", + "args": { + "time": 10 + } + }, + { + "$id": "idleCur001", + "id": "14", + "name": "Log", + "args": { + "level": "info", + "message": "待机触发: 好奇 BABY_EMOCHAT_CURIOUS_NORMAL" + } + } + ] + } + ] + }, + { + "$id": "evSwipe001", + "id": "20", + "name": "Repeat", + "children": [ + { + "$id": "evSwipeSeq", + "id": "21", + "name": "Sequence", + "children": [ + { + "$id": "evSwipeWait", + "id": "22", + "name": "WaitForEvent", + "args": { + "event": "touch_strip_swipe" + } + }, + { + "$id": "evSwipeIf", + "id": "23", + "name": "IfElse", + "children": [ + { + "$id": "evSwipeCheck", + "id": "24", + "name": "Check", + "args": { + "value": "emotionHigh" + } + }, + { + "$id": "evSwipeHigh", + "id": "25", + "name": "Log", + "args": { + "level": "info", + "message": "触摸条左/右滑(高情绪): 撒娇 BABY_EMOLOW_CLINGY_NORMAL" + } + }, + { + "$id": "evSwipeLow", + "id": "26", + "name": "Log", + "args": { + "level": "info", + "message": "触摸条左/右滑(低情绪): 委屈 BABY_EMOCHAT_HURT_NORMAL" + } + } + ] + } + ] + } + ] + }, + { + "$id": "evLong001", + "id": "30", + "name": "Repeat", + "children": [ + { + "$id": "evLongSeq", + "id": "31", + "name": "Sequence", + "children": [ + { + "$id": "evLongWait", + "id": "32", + "name": "WaitForEvent", + "args": { + "event": "touch_strip_long" + } + }, + { + "$id": "evLongLog", + "id": "33", + "name": "Log", + "args": { + "level": "info", + "message": "长时间抚摸: 害羞 BABY_EMOCHAT_SHY_NORMAL" + } + } + ] + } + ] + }, + { + "$id": "evTap001", + "id": "40", + "name": "Repeat", + "children": [ + { + "$id": "evTapSeq", + "id": "41", + "name": "Sequence", + "children": [ + { + "$id": "evTapWait", + "id": "42", + "name": "WaitForEvent", + "args": { + "event": "touch_strip_tap_once" + } + }, + { + "$id": "evTapLog", + "id": "43", + "name": "Log", + "args": { + "level": "info", + "message": "敲击1下: 疑惑 BABY_EMOCHAT_CONFUSE_NORMAL" + } + } + ] + } + ] + }, + { + "$id": "evLeft001", + "id": "50", + "name": "Repeat", + "children": [ + { + "$id": "evLeftSeq", + "id": "51", + "name": "Sequence", + "children": [ + { + "$id": "evLeftWait", + "id": "52", + "name": "WaitForEvent", + "args": { + "event": "left_ear_press" + } + }, + { + "$id": "evLeftLog", + "id": "53", + "name": "Log", + "args": { + "level": "info", + "message": "左耳按一下: 菜单呼出" + } + } + ] + } + ] + }, + { + "$id": "evRight001", + "id": "60", + "name": "Repeat", + "children": [ + { + "$id": "evRightSeq", + "id": "61", + "name": "Sequence", + "children": [ + { + "$id": "evRightWait", + "id": "62", + "name": "WaitForEvent", + "args": { + "event": "right_ear_press" + } + }, + { + "$id": "evRightLog", + "id": "63", + "name": "Log", + "args": { + "level": "info", + "message": "右耳按一下: 学说话 BABY_EMORAISING_LEARNTOTALK_NORMAL (音频缺失)" + } + } + ] + } + ] + }, + { + "$id": "evRadarIn01", + "id": "70", + "name": "Repeat", + "children": [ + { + "$id": "evRadarInSq", + "id": "71", + "name": "Sequence", + "children": [ + { + "$id": "evRadarInWt", + "id": "72", + "name": "WaitForEvent", + "args": { + "event": "radar_person_enter_front_2_3m" + } + }, + { + "$id": "evRadarInLg", + "id": "73", + "name": "Log", + "args": { + "level": "info", + "message": "雷达2-3m正面走来: 撒娇 BABY_EMOLOW_CLINGY_NORMAL" + } + } + ] + } + ] + }, + { + "$id": "evRadarOut1", + "id": "80", + "name": "Repeat", + "children": [ + { + "$id": "evRadarOutS", + "id": "81", + "name": "Sequence", + "children": [ + { + "$id": "evRadarOutW", + "id": "82", + "name": "WaitForEvent", + "args": { + "event": "radar_person_leave_2_3m" + } + }, + { + "$id": "evRadarOutL", + "id": "83", + "name": "Log", + "args": { + "level": "info", + "message": "走出雷达范围: 好奇 BABY_EMOCHAT_CURIOUS_NORMAL" + } + } + ] + } + ] + }, + { + "$id": "evSound001", + "id": "90", + "name": "Repeat", + "children": [ + { + "$id": "evSoundSeq", + "id": "91", + "name": "Sequence", + "children": [ + { + "$id": "evSoundWait", + "id": "92", + "name": "WaitForEvent", + "args": { + "event": "sound_localized" + } + }, + { + "$id": "evSoundLog", + "id": "93", + "name": "Log", + "args": { + "level": "info", + "message": "听到声音并定位: 学说话 BABY_EMORAISING_LEARNTOTALK_NORMAL" + } + } + ] + } + ] + }, + { + "$id": "evPickup001", + "id": "100", + "name": "Repeat", + "children": [ + { + "$id": "evPickupSeq", + "id": "101", + "name": "Sequence", + "children": [ + { + "$id": "evPickupW", + "id": "102", + "name": "WaitForEvent", + "args": { + "event": "posture_pickup" + } + }, + { + "$id": "evPickupL", + "id": "103", + "name": "Log", + "args": { + "level": "info", + "message": "识别拿起: 好奇 BABY_EMOCHAT_CURIOUS_NORMAL" + } + } + ] + } + ] + }, + { + "$id": "evShake001", + "id": "110", + "name": "Repeat", + "children": [ + { + "$id": "evShakeSeq", + "id": "111", + "name": "Sequence", + "children": [ + { + "$id": "evShakeWait", + "id": "112", + "name": "WaitForEvent", + "args": { + "event": "posture_shake" + } + }, + { + "$id": "evShakeLog", + "id": "113", + "name": "Log", + "args": { + "level": "warn", + "message": "识别摇晃: 晕了的表情(表情缺失)" + } + } + ] + } + ] + }, + { + "$id": "evUpside001", + "id": "120", + "name": "Repeat", + "children": [ + { + "$id": "evUpsideSeq", + "id": "121", + "name": "Sequence", + "children": [ + { + "$id": "evUpsideWt", + "id": "122", + "name": "WaitForEvent", + "args": { + "event": "posture_upside_down" + } + }, + { + "$id": "evUpsideLog", + "id": "123", + "name": "Log", + "args": { + "level": "warn", + "message": "识别倒立: 晕了的表情(表情缺失)" + } + } + ] + } + ] + } + ] + }, + "vars": [ + { + "name": "emotionHigh", + "desc": "当前是否高情绪值,供触摸条左/右滑分支判断" + } + ], + "version": "2.0.0" +} diff --git a/test1/node-config.b3-setting b/test1/node-config.b3-setting new file mode 100644 index 0000000..df30ecf --- /dev/null +++ b/test1/node-config.b3-setting @@ -0,0 +1,856 @@ +[ + { + "name": "AlwaysFailure", + "type": "Decorator", + "children": 1, + "status": [ + "failure", + "|running" + ], + "desc": "始终返回失败", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `running` 时,返回 `running`\n+ 其它情况,不管子节点是否成功都返回 `failure`\n" + }, + { + "name": "AlwaysRunning", + "type": "Decorator", + "children": 1, + "status": [ + "running" + ], + "desc": "始终返回运行中状态", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 始终返回 `running`\n" + }, + { + "name": "AlwaysSuccess", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running" + ], + "desc": "始终返回成功", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `running` 时,返回 `running`\n+ 其它情况,不管子节点是否成功都返回 `success`\n" + }, + { + "name": "Assert", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "断言", + "args": [ + { + "name": "message", + "type": "string", + "desc": "消息" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `failure` 时,抛出异常\n+ 其余情况返回子节点的执行状态\n" + }, + { + "name": "Calculate", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "简单的数值公式计算", + "args": [ + { + "name": "value", + "type": "expr", + "desc": "计算公式" + } + ], + "output": [ + "计算结果" + ], + "doc": "+ 做简单的数值公式计算,返回结果到输出\n" + }, + { + "name": "Case", + "type": "Composite", + "children": 2, + "status": [ + "&success", + "|failure", + "|running" + ], + "desc": "分支选择", + "doc": "+ 必须有两个子节点\n+ 第一个子节点为判断条件\n+ 第二个子节点为判断为 `success` 时执行的节点\n+ 此节点不会真正意义的执行,而是交由 `Switch` 节点来执行\n" + }, + { + "name": "Check", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "检查True或False", + "args": [ + { + "name": "value", + "type": "expr", + "desc": "值" + } + ], + "doc": "+ 做简单数值公式判定,返回 `success` 或 `failure`\n" + }, + { + "name": "Concat", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "将两个输入合并为一个数组,并返回新数组", + "input": [ + "数组1", + "数组2" + ], + "output": [ + "新数组" + ], + "doc": "+ 如果输入不是数组,则返回 `failure`\n" + }, + { + "name": "Delay", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "延时执行子节点", + "input": [ + "延时时间?" + ], + "args": [ + { + "name": "delay", + "type": "float?", + "desc": "延时时间", + "oneof": "延时时间" + }, + { + "name": "cacheVars", + "type": "string[]?", + "desc": "暂存环境变量" + } + ], + "doc": "+ 当延时触发时,执行第一个子节点,多个仅执行第一个\n+ 如果子节点返回 `running`,会中断执行并清理执行栈" + }, + { + "name": "Filter", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "failure", + "|running" + ], + "desc": "返回满足条件的元素", + "input": [ + "输入数组" + ], + "output": [ + "变量", + "新数组" + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 遍历输入数组,将当前元素写入`变量`,满足条件的元素放入新数组\n+ 只有当新数组不为空时,才返回 `success`\n" + }, + { + "name": "ForEach", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running", + "|failure" + ], + "desc": "遍历数组", + "input": [ + "数组" + ], + "output": [ + "变量", + "索引?" + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 遍历输入数组,将当前元素写入`变量`\n+ 当子节点返回 `failure` 时,退出遍历并返回 `failure` 状态\n+ 执行完所有子节点后,返回 `success`" + }, + { + "name": "GetField", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "获取对象的字段值", + "args": [ + { + "name": "field", + "type": "string?", + "desc": "字段(field)", + "oneof": "字段(field)" + } + ], + "input": [ + "对象", + "字段(field)?" + ], + "output": [ + "字段值(value)" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 只有获取到合法元素时候才会返回 `success`,否则返回 `failure`\n" + }, + { + "name": "IfElse", + "type": "Composite", + "children": 3, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "条件执行", + "doc": "+ 必须有三个子节点\n+ 第一个子节点为条件节点\n+ 第二个子节点为条件为 `success` 时执行的节点\n+ 第三个子节点为条件为 `failure` 时执行的节点,\n" + }, + { + "name": "Includes", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断元素是否在数组中", + "input": [ + "数组", + "元素" + ], + "doc": "+ 若输入的元素不合法,返回 `failure`\n+ 只有数组包含元素时返回 `success`,否则返回 `failure`\n" + }, + { + "name": "Index", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "索引输入的数组", + "args": [ + { + "name": "index", + "type": "int?", + "desc": "索引", + "oneof": "索引" + } + ], + "input": [ + "数组", + "索引?" + ], + "output": [ + "值" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 索引数组的时候,第一个元素的索引为 0\n+ 只有索引到有合法元素时候才会返回 `success`,否则返回 `failure`\n" + }, + { + "name": "Invert", + "type": "Decorator", + "children": 1, + "status": [ + "!success", + "!failure", + "|running" + ], + "desc": "反转子节点运行结果", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `success` 时返回 `failure`\n+ 当子节点返回 `failure` 时返回 `success`\n+ 当子节点返回 `error` 时返回 `error`\n" + }, + { + "name": "IsNull", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断变量是否不存在", + "input": [ + "判断的变量" + ] + }, + { + "name": "JustFailure", + "type": "Action", + "children": 0, + "status": [ + "failure" + ], + "desc": "什么都不干,只返回失败" + }, + { + "name": "JustSuccess", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "什么都不干,只返回成功" + }, + { + "name": "Let", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "定义新的变量名", + "input": [ + "已存在变量名?" + ], + "args": [ + { + "name": "value", + "type": "json?", + "desc": "值(value)", + "oneof": "已存在变量名" + } + ], + "output": [ + "新变量名" + ], + "doc": "+ 如果有输入变量,则给已有变量重新定义一个名字\n+ 如果`值(value)`为 `null`,则清除变量\n" + }, + { + "name": "Listen", + "type": "Decorator", + "children": 1, + "status": [ + "success" + ], + "desc": "侦听事件", + "input": [ + "目标对象?" + ], + "output": [ + "事件目标?", + "事件参数..." + ], + "args": [ + { + "name": "event", + "type": "string", + "desc": "事件", + "options": [ + { + "source": [ + { + "name": "行为树被中断", + "value": "treeInterrupted" + }, + { + "name": "行为树开始执行前", + "value": "treeBeforeTicked" + }, + { + "name": "行为树执行完成后", + "value": "treeAfterTicked" + }, + { + "name": "行为树执行成功后", + "value": "treeTickedSuccess" + }, + { + "name": "行为树执行失败后", + "value": "treeTickedFailure" + }, + { + "name": "行为树被清理", + "value": "treeCleaned" + } + ] + } + ] + } + ], + "doc": "+ 当事件触发时,执行第一个子节点,多个仅执行第一个\n+ 如果子节点返回 `running`,会中断执行并清理执行栈" + }, + { + "name": "Log", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "打印日志", + "input": [ + "日志?" + ], + "args": [ + { + "name": "message", + "type": "string", + "desc": "日志" + }, + { + "name": "level", + "type": "string", + "desc": "日志级别", + "default": "log", + "options": [ + { + "source": [ + { + "name": "LOG", + "value": "log" + }, + { + "name": "INFO", + "value": "info" + }, + { + "name": "DEBUG", + "value": "debug" + }, + { + "name": "WARN", + "value": "warn" + }, + { + "name": "ERROR", + "value": "error" + } + ] + } + ] + } + ] + }, + { + "name": "Math", + "type": "Action", + "desc": "执行数学运算", + "input": [ + "参数..." + ], + "output": [ + "结果" + ], + "status": [ + "success", + "failure" + ], + "args": [ + { + "name": "op", + "type": "string", + "desc": "数学运算类型", + "options": [ + { + "source": [ + { + "name": "绝对值", + "value": "abs" + }, + { + "name": "向上取整", + "value": "ceil" + }, + { + "name": "向下取整", + "value": "floor" + }, + { + "name": "四舍五入", + "value": "round" + }, + { + "name": "符号", + "value": "sign" + }, + { + "name": "正弦", + "value": "sin" + }, + { + "name": "余弦", + "value": "cos" + }, + { + "name": "正切", + "value": "tan" + }, + { + "name": "反正切2", + "value": "atan2" + }, + { + "name": "幂运算", + "value": "pow" + }, + { + "name": "平方根", + "value": "sqrt" + }, + { + "name": "自然对数", + "value": "log" + }, + { + "name": "最小值", + "value": "min" + }, + { + "name": "最大值", + "value": "max" + }, + { + "name": "随机数", + "value": "random" + }, + { + "name": "随机整数", + "value": "randInt" + }, + { + "name": "随机浮点数", + "value": "randFloat" + }, + { + "name": "求和", + "value": "sum" + }, + { + "name": "平均值", + "value": "average" + }, + { + "name": "乘积", + "value": "product" + } + ] + } + ] + }, + { + "name": "value1", + "type": "float?", + "desc": "参数1(优先使用)" + }, + { + "name": "value2", + "type": "float?", + "desc": "参数2(优先使用)" + } + ] + }, + { + "name": "NotNull", + "type": "Condition", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "判断变量是否存在", + "input": [ + "判断的变量" + ] + }, + { + "name": "Now", + "type": "Action", + "children": 0, + "status": [ + "success" + ], + "desc": "获取当前时间", + "output": [ + "当前时间" + ] + }, + { + "name": "Once", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "failure", + "|running" + ], + "desc": "只执行一次", + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 第一次执行完全部子节点时返回 `success`,之后永远返回 `failure`" + }, + { + "name": "Parallel", + "type": "Composite", + "status": [ + "success", + "|running" + ], + "children": -1, + "desc": "并行执行", + "doc": "+ 并行执行所有子节点\n+ 当有子节点返回 `running` 时,返回 `running` 状态\n+ 执行完所有子节点后,返回 `success`" + }, + { + "name": "Push", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "向数组中添加元素", + "input": [ + "数组", + "元素" + ], + "doc": "+ 当变量`数组`不是数组类型时返回 `failure`\n+ 其余返回 `success`\n" + }, + { + "name": "Race", + "type": "Composite", + "status": [ + "|success", + "&failure", + "|running" + ], + "children": -1, + "desc": "竞争执行", + "doc": "+ 并行执行所有子节点\n+ 当有子节点返回 `success` 时,立即返回 `success` 状态,并中断其他子节点\n+ 如果所有子节点返回 `failure`或 `error` 则返回 `failure`" + }, + { + "name": "RandomIndex", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "随机返回输入的其中一个!", + "input": [ + "输入目标" + ], + "output": [ + "随机目标", + "索引?" + ], + "doc": "+ 合法元素不包括 `undefined` 和 `null`\n+ 在输入数组中,随机返回其中一个\n+ 当输入数组为空时,或者没有合法元素,返回 `failure`\n" + }, + { + "name": "Repeat", + "type": "Decorator", + "children": 1, + "status": [ + "success", + "|running", + "|failure" + ], + "desc": "循环执行", + "input": [ + "循环次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "循环次数", + "oneof": "循环次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点返回 `failure` 时,退出遍历并返回 `failure` 状态\n+ 执行完所有子节点后,返回 `success`\n" + }, + { + "name": "RetryUntilFailure", + "type": "Decorator", + "children": 1, + "status": [ + "!success", + "failure", + "running" + ], + "desc": "一直尝试直到子节点返回失败", + "input": [ + "最大尝试次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "最大尝试次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 只有当子节点返回 `failure` 时,才返回 `success`,其它情况返回 `running` 状态\n+ 如果设定了尝试次数,超过指定次数则返回 `failure`" + }, + { + "name": "RetryUntilSuccess", + "type": "Decorator", + "children": 1, + "status": [ + "|success", + "failure", + "running" + ], + "desc": "一直尝试直到子节点返回成功", + "input": [ + "最大尝试次数?" + ], + "args": [ + { + "name": "count", + "type": "int?", + "desc": "最大尝试次数" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 只有当子节点返回 `success` 时,才返回 `success`,其它情况返回 `running` 状态\n+ 如果设定了尝试次数,超过指定次数则返回 `failure`" + }, + { + "name": "Selector", + "type": "Composite", + "children": -1, + "desc": "选择执行", + "status": [ + "|success", + "&failure", + "|running" + ], + "doc": "+ 一直往下执行,直到有子节点返回 `success` 则返回 `success`\n+ 若全部节点返回 `failure`或 `error` 则返回 `failure`" + }, + { + "name": "Sequence", + "type": "Composite", + "children": -1, + "status": [ + "&success", + "|failure", + "|running" + ], + "desc": "顺序执行", + "doc": "+ 一直往下执行,只有当所有子节点都返回 `success`, 才返回 `success`\n+ 若子节点返回 `failure`,则直接返回 `failure` 状态\n+ 其余情况返回 `running` 状态\n" + }, + { + "name": "SetField", + "type": "Action", + "children": 0, + "status": [ + "success", + "failure" + ], + "desc": "设置对象字段值", + "input": [ + "输入对象", + "字段(field)?", + "值(value)?" + ], + "args": [ + { + "name": "field", + "type": "string?", + "desc": "字段(field)", + "oneof": "字段(field)" + }, + { + "name": "value", + "type": "json?", + "desc": "值(value)", + "oneof": "值(value)" + } + ], + "doc": "+ 对输入对象设置 `field` 和 `value`\n+ 输入参数1必须为对象,否则返回 `failure`\n+ 如果 `field` 不为 `string`, 也返回 `failure`\n+ 如果 `value` 为 `undefined` 或 `null`, 则删除 `field` 的值\n" + }, + { + "name": "Switch", + "type": "Composite", + "children": -1, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "分支执行", + "doc": "+ 按顺序测试 `Case` 节点的判断条件(第一个子节点)\n+ 若测试返回 `success` 则执行 `Case` 第二个子节点,并返回子节点的执行状态\n+ 若没有判断为 `success` 的 `Case` 节点,则返回 `failure`\n" + }, + { + "name": "Timeout", + "type": "Decorator", + "children": 1, + "status": [ + "|success", + "|running", + "failure" + ], + "desc": "超时", + "input": [ + "超时时间?" + ], + "args": [ + { + "name": "time", + "type": "float?", + "desc": "超时时间", + "oneof": "超时时间" + } + ], + "doc": "+ 只能有一个子节点,多个仅执行第一个\n+ 当子节点执行超时或返回 `failure` 时,返回 `failure`\n+ 其余情况返回子节点的执行状态\n" + }, + { + "name": "Wait", + "type": "Action", + "children": 0, + "status": [ + "success", + "running" + ], + "desc": "等待", + "input": [ + "等待时间?" + ], + "args": [ + { + "name": "time", + "type": "float?", + "desc": "等待时间", + "oneof": "等待时间" + }, + { + "name": "random", + "type": "float?", + "desc": "随机范围" + } + ] + }, + { + "name": "WaitForEvent", + "type": "Action", + "children": 0, + "status": [ + "success", + "running" + ], + "desc": "等待事件触发", + "args": [ + { + "name": "event", + "type": "string", + "desc": "事件名称" + } + ] + }, + { + "name": "Watchdog", + "type": "Composite", + "children": 3, + "status": [ + "|success", + "|failure", + "|running" + ], + "desc": "测试执行", + "doc": "+ 必须有3个子节点\n+ 第一个子节点为条件节点,返回 `success` 或 `failure` 状态\n+ 第二个子节点为条件为 `success` 时执行的节点\n+ 第三个子节点为条件为 `failure` 时执行的节点,不管子节点返回什么状态,都直接返回 `failure`\n+ 当第二个子节点返回 `running` 时,由本节点维护其运行状态\n+ 每一次 tick 都会先执行测试节点,只有当测试节点返回 `success`,才执行第二个子节点\n" + } +] \ No newline at end of file diff --git a/test1/workspace.b3-workspace b/test1/workspace.b3-workspace new file mode 100644 index 0000000..7d7d4b8 --- /dev/null +++ b/test1/workspace.b3-workspace @@ -0,0 +1,13 @@ +{ + "nodeConf": "node-config.b3-setting", + "metadata": [], + "files": [ + { + "path": "example.json", + "desc": "幼年期待机状态树" + } + ], + "settings": { + "checkExpr": true + } +} diff --git a/test1/行为树需求_幼年期行为树 (1).xlsx b/test1/行为树需求_幼年期行为树 (1).xlsx new file mode 100644 index 0000000000000000000000000000000000000000..61efd0876ad4fe9ad42e52db8b442afdc5bbeca4 GIT binary patch literal 7507 zcmaJ`1yEdBv&P-sf;$8c0YY$h*Fdnr-Q9vqa0!y&?jg9_;2HwMAPE{|(BLu;c5C0} z-}nCQTXk>Use8JnzjM0#eBV)1ghwENL3zCXX(W$7c-wP&Il0=oSpxv>Zk&HScsRTr z?2EGORKa>=z_p`Nfm4Os_e)IlG^QzWeSi{c7Ogj)mc}&ZRH4%TGxex7I&9np1is+( z!zSK28{`=k&a6WW_k0H=>ua9+l#V@JJ&+1T_Ek|SmWBrS1iEu}_i0CXN6+>UU6bP- zT3=fcs}GX#camTNaYBaTRIBZsE{b8Uw*(KVhMFfaU2%!9O088teJnv-ji%}I;Q;!x z8$@l%7?z9-E%vjBK=DBaodvFSXA8deByK;`zsh+pmdzif`2lr z=CvDT@hF*-T&#vZPfeq~nf&_@Jch0?pH@s3Aa`jM8k-!&RvOw7lYGj0BA+~$4!5o3 zxSkC1=v~f=R%4mLK-oBXa>dWF{g~PIn)wZC2)GbkJ=Pe~kH~8V%W&_93Y6Iby%2KD+`W^5lCv zDpt6D&`o@67kWY}M@rf;OfJk;7862Xei*Yor7{?$=V`5Ge7+x8F!~9@#WYJ(dcw`mNP>nhQ3Jx+uh628mph{SN%1m(;aW!FeT zF?D_jhf4Bb8Lgn-1r{rAO4_M@G?qOVBRixY=@r+g!cSO5PZJlm0(eCalie=U+VdEB0dCcxbjsC)KY-krU1(RMf^+UnVjz zOo<^4PZ|c91SAWm*neXcp6(ka^DLhnQeFA!4*YP98;A3L1_d9t?_^bCKjZoB zF+dM!<}u;L^F#21oRM5or&8iiDt?Hpx=36ifyGYL)Z*)!qw1Fz#!KYcCPf0LkiM(p zT}6Czbh<%M^h|j9?gz!e5oTHWp6)vk`@_8N#j0=9)|m_^(GHQ!jum6cj@8Jp%Q{Kr z{7`J=Ik^+${K$4bd)35le&hS1=*QL29LG=9U|FUwd%o2-cK5ySJL@;@m*^zl@sX0z zZ$rykFPn5aO+~K?Pu5#IHNQ|DNi)Qucwa7yfK01jMP7`kXsyciZC6qq#82Fe)PB1u zKZ*<3$nVs=_r96#@|yAmodmhw?1#^cM3>igL6X#FQ*4i*^BeNtVxfAq&HW#`1Vnik z=qAFD1uKW^YEIxrdC6pi`UnRIvM#3%j@J0QMfZeHF8gmHKS^TebS`3H{2F#oW}K5} z%xt3X#lL-kR#oHcRj$U3lFDysZ?@`lzdql(JMd2E2$SJk6+xFyFNkKB=I9-|G1Zz$ zCb+2HKO~67_(*TN>|?Rglx}~?QY(sH?2gclov-giNvlXdOYU=#ZP)EvyW1XL-|6M}93iQdIr!VFn)BQK zrCYGN4vq%|1TXSBpx|ye;%->x8di`@GN-*j_G*3H7&_V2X1Eq#v4LAqS06O76bM)o zw(IaAZvDc5ddrMG9DaAK+8-gtDrsWPBeuS}g6?KD_TWOtqm(@Ta1sc)GPwUSe-Y>i ze)SWC)n7<#;m~JFOF``t3qi83UaRbmc|#J_=MBr)2g@h{+YqAr@*DJsBpiwi z0|SMsDI%kY6qgdTJihhPz`&^e*Y1!1*!>M9ogCc(j_z-@e4GJpMo*2uDs`e}jteLJ zQdoNPdCZC*F-ktYSML;FTZ?e8ohq3o*xaXtCcrPXs2ZV>K^ruXJ#sCQEB~ewqnG%# zg)52O3B7JXu=R9XOZDL80_T?B$!tftF*a%$Noayr?0dlgwHPI2@st4s7nH6+3ci$q z4sH4D+|^KD{^j(|pq!<1*MscdR;U0{Dw_qfP z=T)>%v-tA8Q|w8qczetEK!LuMQjxm?c4g1iie4RHG?V(X;SvzkXA*JyLZuscb+K}= z!BMgq^VSt$@5agTbWfe` zRk-8AK{~#LvPc|)-7m3e8+MJQ7PI97f-{xC)Aaa^g+tB6oh^eg7Xn=VYY9i*72Hw8 zdF$LZtxg6k)cWos@dhFnUhQ^1dk@d3s7Wp|M>pMYUqom%=4775YYeL3DBEyJR&Zm; z%{bd6%B02TPN3{fH|fT3@LDtv6IhipA|LNYP@%I4*YZ1HOnudcUhbW{S3#|NGSEG8Fq9)3Xn4ADW@-^LfTe z+e`yKM zA0N~JM=*!g@lISkYscmeC!h7D1=(oSljdV}T6_cLj_*;5ZJ>@-6l!f6pE6cgl@vD8 z4L7L|AV(h|g1%d3Il{KnFe$a)ptn)E1T{em3K0ktQ|1qFwP_dGWdeZ}gEyOh*wpjh7F8yG<)P2g<`Xt5%e&^#1Dhx&fw2 zL+ye#FoYHGzWjK#eQvB-@B721Mk^20ZWlsdi%*n~_3DQ3@u4-~h;SpEhNxLfU_Ti)_ zAuh zp2H-W5oFG?&~XKAcUePzFAN@n?ovaPQG9JO(fS zukc|036Gn*k3GQckCm3`;8fUx-?Ii44IjKE%2A%>gVVWP(=JZCP)YMt-7^G|n9XAk zXXbn^y**^g28Qu@$QK8b9#8RZoW!kMeg1(#5miw}AP;j?2!j&>kdaP82)g%e10#Hz zgAS&N@SM7-Mj`b$Ggif;r&lna&RU=Df|Gjs<_i3}*^cb7AB zfTFE_0sV^Hv4_9D8EBUImO_7dIwh!Zif7YS7`JB*97Pj>PgB=o9(aY4y+Ofv!Zy-H z>mqhfpXQELUZl4WefsQ(O_roODxgQ@-w(#v^0)AgiHtisFL)VSZ2VJ z^L{GexJfgWf9`3F~dSwCxUqRptd8-QFa zF+1`u-{*$-*0BY0a>VqmvyS}VPy0;D8Ym(e&tZjm?6}>4D*$YMA=g?rutFhHP+^(J9LvXFfa91fK;PX2! z9C&s7_I=+JzqI&LZIg}wm4d7p5lA1`*uBU&JX)iUcVlr!tg8xF36*A(+t_<4K%I_& zgJeUY(>+I`$VfQt*C&rBP@Ym$FP6hc6+~CyoiDeTp_4TvxSskfyP1fR9}eu?pMy!1 zi{WV#RU0*vTkt^FVwg502srqvGO9k7{=nU z_59kTUd+uHcmGvZ#`rYlL>WtJ;#14RM+R{MnEmz|c~ZM<%n~2DjpM?@`v;%T(?8=iKvM9NF~ zK&$BVMYSTaS$Ti*r8y3GB=>#}cu%k?iH-@P&Ow7HqgZV9EgjOmoDv8RzmY=+Lm4Y+ z_|oU-mXf7QuPbna&-7=eoHXL4%YIfY?vD@@mIVL1@6LC-NL}^kBOZ%ix#dxWlu2~6 zzi;U6yU)33;iMpZeUXG0m{nJvh-&SjJUoobkfTP)FmBWCI3*wK`sVbMwIfr-Mofk_ zlOb%sFPa{MkMPYPpEik$TvWo*cEnFE{HW&1;zOQf7glnVOkot)d&VSiglzReLRKYB z%1@Ha1XX72!4Vq4c@l0l-{GQ!l{;i7Bd^K$voSoYw%*tura90mZ|0ffvRuE!naw`w z=6w%8FoU{MsyJABTHB(z8w`e2(-uERfc;UdgMa3U^oq`jkoO>VEGw$;p={1pBEBq_ z&>cJ$m_0oS2dT;1IB~A0V6*lL@qM8UX^vcB{A!rjN!WPgn9z35$k&`ex+Tk&w|_3w zpG9k=r;6CFt%%ie*s^BKKpbp-aMVY*pxpjC1Ss(yapC#_R#|ZNELDkyT7(j=5MO?V zGTtm+9qkSCx_L9?{mOgrWKjFHwtnZb_;z&gkCIHfL{V>B0Ik{%Z4w&2@|Ofr)e!Uk zN;*@{m1VUc!MUg1fxPB>{E;2lug!Y!Bel5Z&Pxr+I)%LkJXVQlmNh~(C?ZH3}MP%P13(gL;Nyb;EULhBT+o%)m{%_dOrEb;vE z%nk97-AJ{Flx$FiX_fL;5}5(!N25Lrx!|6%fLD;uJ{k-~C9?cx*kN4JNdja;iACRX zm=lz@c|GV6;N4ZND+Sa8%s%_|G9N28&qyl#0zZ?)wkB9`>an+EbVy*toj)_1ED>Yv z%_;6mR|~XBF|>7B4O(11$hC}*pTMdrEOt<|4Vca#2LUdi{TDAnNxNme?IlG#YZF%X z%`Yp6o0|?jK%lb+zi$P~Y5hZ1Ek!4E%c(q`c{_0j<-!ekaS`UDdVwjD#8i}X-ox~s zr!a)=auR{@MbmH9o>2`X;!!o9q9m~z$)XiYTrUpBcYQ|XSGpW7ULW; zIx>5sSra>B+)d$*ad~Z2qy%exeYjOY8)u@8n@fg!KRGYexa?6*^0jQy8l)vKRKYch zdpry@ZdMD^f{6MBli;U-nn#eC`;w5Ml^%B+*|!WHAyb z&kc~>IFK3VOG0+>4rR1wJd*rrUb{AmMxs&7SwX5{V}B@3nDM^yRK2Q0!$`QGXO?92 zy&2{9(EcpCpbTZ}>{eAy8=gwRiBQ|&*0j#~w7oU;{gCFt{RF({w!Hq;t~8 zTQrOGr3QV+cjS?=k!7BI33caAkJb3kjc;8+u3x}o^#)Mj$L{7uQjj3NS=& zSSN~_gEIVGISWb6H%0*J`7;ZJBT{@5uS{=QkfLz8J9RP}*Xt0>?$n_fC=O>0(uD$b z*TSW0L?F`2yGstR7%QKAq(hG(jVgtP^$VP0wwWw2*wX>nf7*XL4pUS7PcOdQS2~{bp1&>gk;?w2{`_;`?{dMD5c0RRp#5K2EQRp@s#d=8$RhD4t`I5HAO_Erw>pcFOeq_{YTXQ1Bw?w=>Px# literal 0 HcmV?d00001