@lv-x-software-house/x_view 1.2.4-dev.23 → 1.2.4-dev.25
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/dist/index.js +62 -33
- package/dist/index.mjs +62 -33
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
x.view - from ŀv.x - Software Engineering
|
package/dist/index.js
CHANGED
|
@@ -2893,7 +2893,9 @@ var IGNORED_KEYS = [
|
|
|
2893
2893
|
"is_private",
|
|
2894
2894
|
"abstraction_tree",
|
|
2895
2895
|
"selectedAbstractionParentId",
|
|
2896
|
-
"isAddingAbstractionNodes"
|
|
2896
|
+
"isAddingAbstractionNodes",
|
|
2897
|
+
"status",
|
|
2898
|
+
"is_quest"
|
|
2897
2899
|
];
|
|
2898
2900
|
function extractCustomPropsFromNode(node) {
|
|
2899
2901
|
const customPropTypes = node._customPropTypes || {};
|
|
@@ -7969,10 +7971,13 @@ function InSceneQuestForm({
|
|
|
7969
7971
|
availableAncestries = [],
|
|
7970
7972
|
onMentionClick,
|
|
7971
7973
|
onUploadFile,
|
|
7972
|
-
// NOVAS PROPS PARA O GHOST NODE
|
|
7973
7974
|
onNameChange,
|
|
7974
7975
|
onColorChange,
|
|
7975
|
-
onSizeChange
|
|
7976
|
+
onSizeChange,
|
|
7977
|
+
viewName = "Projeto",
|
|
7978
|
+
// NOVA PROP
|
|
7979
|
+
questCounter = 1
|
|
7980
|
+
// NOVA PROP
|
|
7976
7981
|
}) {
|
|
7977
7982
|
const [name, setName] = (0, import_react16.useState)("");
|
|
7978
7983
|
const [types, setTypes] = (0, import_react16.useState)(["quest"]);
|
|
@@ -7985,6 +7990,7 @@ function InSceneQuestForm({
|
|
|
7985
7990
|
const [customProps, setCustomProps] = (0, import_react16.useState)([]);
|
|
7986
7991
|
const [isDescriptionModalOpen, setIsDescriptionModalOpen] = (0, import_react16.useState)(false);
|
|
7987
7992
|
const propsEndRef = (0, import_react16.useRef)(null);
|
|
7993
|
+
const standardizedName = `${viewName} - ${questCounter} - \xBB ${name || "Nova Quest"}`;
|
|
7988
7994
|
const handleAddProp = () => {
|
|
7989
7995
|
const newProp = createNewCustomProperty(customProps);
|
|
7990
7996
|
setCustomProps([...customProps, newProp]);
|
|
@@ -8021,7 +8027,7 @@ function InSceneQuestForm({
|
|
|
8021
8027
|
const handleSubmit = (e) => {
|
|
8022
8028
|
e.preventDefault();
|
|
8023
8029
|
if (!name.trim()) {
|
|
8024
|
-
alert("O campo '
|
|
8030
|
+
alert("O campo 'T\xEDtulo' \xE9 obrigat\xF3rio.");
|
|
8025
8031
|
return;
|
|
8026
8032
|
}
|
|
8027
8033
|
const additionalData = toObjectFromCustomProps(
|
|
@@ -8029,7 +8035,10 @@ function InSceneQuestForm({
|
|
|
8029
8035
|
);
|
|
8030
8036
|
const processedSections = processDescriptionForSave(description, []);
|
|
8031
8037
|
onSave({
|
|
8032
|
-
name:
|
|
8038
|
+
name: standardizedName,
|
|
8039
|
+
// SALVA O NOME FORMATADO
|
|
8040
|
+
raw_title: name.trim(),
|
|
8041
|
+
// Salva o título puro como fallback ou metadado útil
|
|
8033
8042
|
type: types,
|
|
8034
8043
|
color: QUEST_STATUS_COLORS[status],
|
|
8035
8044
|
status,
|
|
@@ -8068,7 +8077,21 @@ function InSceneQuestForm({
|
|
|
8068
8077
|
},
|
|
8069
8078
|
"\xD7"
|
|
8070
8079
|
)),
|
|
8071
|
-
/* @__PURE__ */ import_react16.default.createElement("form", { onSubmit: handleSubmit, className: "flex flex-col max-h-[68vh]" }, /* @__PURE__ */ import_react16.default.createElement("div", { className: "px-6 pb-28 overflow-y-auto overscroll-contain space-y-4 custom-scrollbar" }, /* @__PURE__ */ import_react16.default.createElement("div", { className: "space-y-1.5
|
|
8080
|
+
/* @__PURE__ */ import_react16.default.createElement("form", { onSubmit: handleSubmit, className: "flex flex-col max-h-[68vh]" }, /* @__PURE__ */ import_react16.default.createElement("div", { className: "px-6 pb-28 overflow-y-auto overscroll-contain space-y-4 custom-scrollbar" }, /* @__PURE__ */ import_react16.default.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ import_react16.default.createElement("label", { className: "text-xs text-slate-300" }, "T\xEDtulo da Quest"), /* @__PURE__ */ import_react16.default.createElement(
|
|
8081
|
+
"input",
|
|
8082
|
+
{
|
|
8083
|
+
required: true,
|
|
8084
|
+
type: "text",
|
|
8085
|
+
placeholder: "Ex.: Refatorar M\xF3dulo X",
|
|
8086
|
+
value: name,
|
|
8087
|
+
onChange: (e) => {
|
|
8088
|
+
const val = e.target.value;
|
|
8089
|
+
setName(val);
|
|
8090
|
+
onNameChange == null ? void 0 : onNameChange(`${viewName} - ${questCounter} - \xBB ${val || "Nova Quest"}`);
|
|
8091
|
+
},
|
|
8092
|
+
className: "w-full bg-slate-800/70 p-2.5 text-sm rounded-lg border border-white/10 focus:outline-none focus:ring-2 focus:ring-indigo-400/60"
|
|
8093
|
+
}
|
|
8094
|
+
), /* @__PURE__ */ import_react16.default.createElement("div", { className: "pt-1 flex items-center gap-1.5" }, /* @__PURE__ */ import_react16.default.createElement("span", { className: "text-[10px] uppercase font-bold text-slate-500 tracking-wider" }, "Preview:"), /* @__PURE__ */ import_react16.default.createElement("p", { className: "text-xs text-indigo-300 font-medium truncate", title: standardizedName }, standardizedName))), /* @__PURE__ */ import_react16.default.createElement("div", { className: "space-y-1.5 relative mt-2" }, /* @__PURE__ */ import_react16.default.createElement("label", { className: "text-xs text-slate-300" }, "Status da Quest"), /* @__PURE__ */ import_react16.default.createElement("div", { className: "relative" }, /* @__PURE__ */ import_react16.default.createElement(
|
|
8072
8095
|
"button",
|
|
8073
8096
|
{
|
|
8074
8097
|
type: "button",
|
|
@@ -8090,20 +8113,7 @@ function InSceneQuestForm({
|
|
|
8090
8113
|
},
|
|
8091
8114
|
/* @__PURE__ */ import_react16.default.createElement("span", { className: "w-3 h-3 rounded-full", style: { backgroundColor: QUEST_STATUS_COLORS[s] } }),
|
|
8092
8115
|
s
|
|
8093
|
-
)))))), /* @__PURE__ */ import_react16.default.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ import_react16.default.createElement("label", { className: "text-xs text-slate-300" }, "
|
|
8094
|
-
"input",
|
|
8095
|
-
{
|
|
8096
|
-
required: true,
|
|
8097
|
-
type: "text",
|
|
8098
|
-
placeholder: "Ex.: Refatorar M\xF3dulo X",
|
|
8099
|
-
value: name,
|
|
8100
|
-
onChange: (e) => {
|
|
8101
|
-
setName(e.target.value);
|
|
8102
|
-
onNameChange == null ? void 0 : onNameChange(e.target.value);
|
|
8103
|
-
},
|
|
8104
|
-
className: "w-full bg-slate-800/70 p-2.5 text-sm rounded-lg border border-white/10 focus:outline-none focus:ring-2 focus:ring-indigo-400/60"
|
|
8105
|
-
}
|
|
8106
|
-
)), /* @__PURE__ */ import_react16.default.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ import_react16.default.createElement("label", { className: "text-xs text-slate-300" }, "Tipos Adicionais"), /* @__PURE__ */ import_react16.default.createElement("div", { className: "relative w-full bg-slate-800/70 p-1.5 min-h-[42px] flex flex-wrap gap-1.5 rounded-lg border border-white/10 focus-within:ring-2 focus-within:ring-indigo-400/60 transition-all" }, types.map((t, index) => /* @__PURE__ */ import_react16.default.createElement("span", { key: index, className: `flex items-center gap-1 px-1.5 py-0.5 rounded-md text-xs font-medium border ${t === "quest" ? "bg-sky-500/20 text-sky-200 border-sky-500/30" : "bg-indigo-500/30 text-indigo-100 border-indigo-500/20"}` }, t, t !== "quest" && /* @__PURE__ */ import_react16.default.createElement("button", { type: "button", onClick: () => handleRemoveType(index), className: "hover:text-white transition-colors" }, /* @__PURE__ */ import_react16.default.createElement(import_fi14.FiX, { size: 12 })))), /* @__PURE__ */ import_react16.default.createElement(
|
|
8116
|
+
)))))), /* @__PURE__ */ import_react16.default.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ import_react16.default.createElement("label", { className: "text-xs text-slate-300" }, "Tipos Adicionais"), /* @__PURE__ */ import_react16.default.createElement("div", { className: "relative w-full bg-slate-800/70 p-1.5 min-h-[42px] flex flex-wrap gap-1.5 rounded-lg border border-white/10 focus-within:ring-2 focus-within:ring-indigo-400/60 transition-all" }, types.map((t, index) => /* @__PURE__ */ import_react16.default.createElement("span", { key: index, className: `flex items-center gap-1 px-1.5 py-0.5 rounded-md text-xs font-medium border ${t === "quest" ? "bg-sky-500/20 text-sky-200 border-sky-500/30" : "bg-indigo-500/30 text-indigo-100 border-indigo-500/20"}` }, t, t !== "quest" && /* @__PURE__ */ import_react16.default.createElement("button", { type: "button", onClick: () => handleRemoveType(index), className: "hover:text-white transition-colors" }, /* @__PURE__ */ import_react16.default.createElement(import_fi14.FiX, { size: 12 })))), /* @__PURE__ */ import_react16.default.createElement(
|
|
8107
8117
|
"input",
|
|
8108
8118
|
{
|
|
8109
8119
|
type: "text",
|
|
@@ -8925,15 +8935,28 @@ function QuestDetailsPanel({
|
|
|
8925
8935
|
},
|
|
8926
8936
|
/* @__PURE__ */ import_react18.default.createElement("span", { className: "w-3 h-3 rounded-full", style: { backgroundColor: QUEST_STATUS_COLORS2[s] } }),
|
|
8927
8937
|
s
|
|
8928
|
-
)))))), /* @__PURE__ */ import_react18.default.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ import_react18.default.createElement("label", { className: "text-xs text-slate-300" }, "Nome"), /* @__PURE__ */ import_react18.default.createElement("input", { type: "text", value: name, onChange: handleNameChange, readOnly: !canEdit, className: `w-full bg-slate-800/70 p-2.5 text-sm rounded-lg border border-white/10 focus:outline-none ${canEdit ? "focus:ring-2 focus:ring-indigo-400/60" : "cursor-default text-slate-400"}` })), /* @__PURE__ */ import_react18.default.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ import_react18.default.createElement("label", { className: "text-xs text-slate-300" }, "Tipos Adicionais"), /* @__PURE__ */ import_react18.default.createElement("div", { className: `relative w-full bg-slate-800/70 p-1.5 min-h-[42px] flex flex-wrap gap-1.5 rounded-lg border border-white/10 ${canEdit ? "focus-within:ring-2 focus-within:ring-indigo-400/60" : ""} transition-all` }, types.map((t, index) => /* @__PURE__ */ import_react18.default.createElement("span", { key: index, className: `flex items-center gap-1 px-1.5 py-0.5 rounded-md text-xs font-medium border ${t === "quest" ? "bg-sky-500/20 text-sky-200 border-sky-500/30" : "bg-indigo-500/30 text-indigo-100 border-indigo-500/20"}` }, t, canEdit && t !== "quest" && /* @__PURE__ */ import_react18.default.createElement("button", { type: "button", onClick: () => handleRemoveType(index), className: "hover:text-white transition-colors" }, /* @__PURE__ */ import_react18.default.createElement(import_fi16.FiX, { size: 12 })))), canEdit && /* @__PURE__ */ import_react18.default.createElement(
|
|
8929
|
-
|
|
8930
|
-
|
|
8931
|
-
|
|
8932
|
-
|
|
8933
|
-
|
|
8934
|
-
|
|
8935
|
-
|
|
8936
|
-
|
|
8938
|
+
)))))), /* @__PURE__ */ import_react18.default.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ import_react18.default.createElement("label", { className: "text-xs text-slate-300" }, "Nome"), /* @__PURE__ */ import_react18.default.createElement("input", { type: "text", value: name, onChange: handleNameChange, readOnly: !canEdit, className: `w-full bg-slate-800/70 p-2.5 text-sm rounded-lg border border-white/10 focus:outline-none ${canEdit ? "focus:ring-2 focus:ring-indigo-400/60" : "cursor-default text-slate-400"}` })), /* @__PURE__ */ import_react18.default.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ import_react18.default.createElement("label", { className: "text-xs text-slate-300" }, "Tipos Adicionais"), /* @__PURE__ */ import_react18.default.createElement("div", { className: `relative w-full bg-slate-800/70 p-1.5 min-h-[42px] flex flex-wrap gap-1.5 rounded-lg border border-white/10 ${canEdit ? "focus-within:ring-2 focus-within:ring-indigo-400/60" : ""} transition-all` }, types.map((t, index) => /* @__PURE__ */ import_react18.default.createElement("span", { key: index, className: `flex items-center gap-1 px-1.5 py-0.5 rounded-md text-xs font-medium border ${t === "quest" ? "bg-sky-500/20 text-sky-200 border-sky-500/30" : "bg-indigo-500/30 text-indigo-100 border-indigo-500/20"}` }, t, canEdit && t !== "quest" && /* @__PURE__ */ import_react18.default.createElement("button", { type: "button", onClick: () => handleRemoveType(index), className: "hover:text-white transition-colors" }, /* @__PURE__ */ import_react18.default.createElement(import_fi16.FiX, { size: 12 })))), canEdit && /* @__PURE__ */ import_react18.default.createElement(
|
|
8939
|
+
"input",
|
|
8940
|
+
{
|
|
8941
|
+
type: "text",
|
|
8942
|
+
value: typeInput,
|
|
8943
|
+
onChange: (e) => {
|
|
8944
|
+
setTypeInput(e.target.value);
|
|
8945
|
+
setShowTypeSuggestions(true);
|
|
8946
|
+
},
|
|
8947
|
+
onKeyDown: handleTypeInputKeyDown,
|
|
8948
|
+
onClick: () => setShowTypeSuggestions(true),
|
|
8949
|
+
onBlur: () => {
|
|
8950
|
+
if (typeInput.trim()) {
|
|
8951
|
+
handleAddType(typeInput);
|
|
8952
|
+
}
|
|
8953
|
+
setTimeout(() => setShowTypeSuggestions(false), 150);
|
|
8954
|
+
},
|
|
8955
|
+
className: "flex-1 bg-transparent text-sm min-w-[80px] focus:outline-none text-slate-200",
|
|
8956
|
+
placeholder: "",
|
|
8957
|
+
autoComplete: "off"
|
|
8958
|
+
}
|
|
8959
|
+
), canEdit && showTypeSuggestions && filteredTypes.length > 0 && /* @__PURE__ */ import_react18.default.createElement("ul", { className: "custom-scrollbar absolute top-full left-0 z-10 w-full mt-1 max-h-40 overflow-y-auto rounded-lg bg-slate-800 border border-white/10 shadow-lg" }, filteredTypes.map((suggestedType, index) => /* @__PURE__ */ import_react18.default.createElement("li", { key: index, className: "px-3 py-2 text-sm text-slate-200 cursor-pointer hover:bg-indigo-600/50", onMouseDown: (e) => {
|
|
8937
8960
|
e.preventDefault();
|
|
8938
8961
|
handleAddType(suggestedType);
|
|
8939
8962
|
} }, suggestedType))))), /* @__PURE__ */ import_react18.default.createElement("div", { className: "space-y-1.5 relative" }, /* @__PURE__ */ import_react18.default.createElement("label", { className: "text-xs text-slate-300" }, "Descri\xE7\xE3o"), /* @__PURE__ */ import_react18.default.createElement("div", { className: "relative group min-h-[60px] bg-slate-800/40 rounded-lg border border-white/10 hover:border-white/20 transition-colors" }, /* @__PURE__ */ import_react18.default.createElement(DescriptionDisplay, { description, savedSections: existingSections, availableNodes, availableAncestries, onOpenReference, onMentionClick, onImageClick: handleImageClickFromText, onSaveDescription: handleSaveDescriptionInline }), /* @__PURE__ */ import_react18.default.createElement("div", { className: "absolute top-0 right-0 flex bg-slate-900/50 rounded-bl-lg backdrop-blur-sm opacity-0 group-hover:opacity-100 focus-within:opacity-100 transition-opacity overflow-hidden border-b border-l border-white/5" }, /* @__PURE__ */ import_react18.default.createElement("button", { type: "button", onClick: () => setIsReadMode(true), className: `p-2 text-slate-400 hover:text-white hover:bg-white/10 transition-colors ${canEdit ? "border-r border-white/5" : ""}`, title: "Modo de Leitura" }, /* @__PURE__ */ import_react18.default.createElement(import_fi16.FiBookOpen, { size: 14 })), canEdit && /* @__PURE__ */ import_react18.default.createElement("button", { type: "button", onClick: () => setIsDescriptionModalOpen(true), className: "p-2 text-slate-400 hover:text-white hover:bg-white/10 transition-colors", title: "Editar descri\xE7\xE3o (Modo de Escrita)" }, /* @__PURE__ */ import_react18.default.createElement(import_fi16.FiEdit2, { size: 14 }))), canEdit && !description && /* @__PURE__ */ import_react18.default.createElement("div", { onClick: () => setIsDescriptionModalOpen(true), className: "absolute inset-0 flex items-center justify-center text-xs text-slate-500 cursor-text" }, "Adicionar descri\xE7\xE3o..."))), /* @__PURE__ */ import_react18.default.createElement("div", { className: "space-y-2" }, /* @__PURE__ */ import_react18.default.createElement("label", { className: "text-xs text-slate-300" }, "Tamanho no Node (Size)"), /* @__PURE__ */ import_react18.default.createElement("div", { className: "flex items-center gap-5" }, ["small", "medium", "large"].map((s) => {
|
|
@@ -10288,7 +10311,7 @@ function XViewScene({
|
|
|
10288
10311
|
delete_file_action,
|
|
10289
10312
|
check_user_permission
|
|
10290
10313
|
}) {
|
|
10291
|
-
var _a, _b, _c, _d, _e, _f, _g;
|
|
10314
|
+
var _a, _b, _c, _d, _e, _f, _g, _h;
|
|
10292
10315
|
const { data: session, status } = (0, import_react27.useSession)();
|
|
10293
10316
|
const router = (0, import_navigation.useRouter)();
|
|
10294
10317
|
const searchParams = (0, import_navigation.useSearchParams)();
|
|
@@ -11963,6 +11986,7 @@ function XViewScene({
|
|
|
11963
11986
|
const handleSaveQuestNode = async (context, newQuestData) => {
|
|
11964
11987
|
const { graphDataRef, sceneDataRef: sceneDataRef2, stateRef: stateRef2, setters, actions, sceneSaveUrl: sceneSaveUrl2, viewType, sceneConfigId: sceneConfigId2, ownerId: ownerId2 } = context;
|
|
11965
11988
|
if (!graphDataRef.current || (viewType == null ? void 0 : viewType.toLowerCase()) !== "view") return;
|
|
11989
|
+
const currentCounter = sceneDataRef2.current.quest_counter || 1;
|
|
11966
11990
|
const newNode = {
|
|
11967
11991
|
id: import_short_uuid2.default.generate(),
|
|
11968
11992
|
...newQuestData,
|
|
@@ -11978,10 +12002,13 @@ function XViewScene({
|
|
|
11978
12002
|
nodes: sceneDataRef2.current.nodes,
|
|
11979
12003
|
links: sceneDataRef2.current.links,
|
|
11980
12004
|
quest_nodes: graphDataRef.current[sceneConfigId2].nodes,
|
|
11981
|
-
quest_links: graphDataRef.current[sceneConfigId2].links
|
|
12005
|
+
quest_links: graphDataRef.current[sceneConfigId2].links,
|
|
12006
|
+
quest_counter: currentCounter + 1
|
|
12007
|
+
// NOVO: Incrementa o contador nos metadados
|
|
11982
12008
|
};
|
|
11983
12009
|
try {
|
|
11984
12010
|
await actions.save_view_data(sceneSaveUrl2, sceneFileData);
|
|
12011
|
+
sceneDataRef2.current.quest_counter = currentCounter + 1;
|
|
11985
12012
|
stateRef2.current.nodeIdToParentFileMap.set(String(newNode.id), {
|
|
11986
12013
|
parentFileId: sceneConfigId2,
|
|
11987
12014
|
ownerId: ownerId2,
|
|
@@ -13643,7 +13670,9 @@ function XViewScene({
|
|
|
13643
13670
|
onMentionClick: handleAddExistingNode,
|
|
13644
13671
|
onUploadFile: upload_file_action,
|
|
13645
13672
|
availableNodes: allAvailableNodes,
|
|
13646
|
-
availableAncestries: allAvailableAncestries
|
|
13673
|
+
availableAncestries: allAvailableAncestries,
|
|
13674
|
+
viewName: viewParams == null ? void 0 : viewParams.name,
|
|
13675
|
+
questCounter: ((_g = sceneDataRef.current) == null ? void 0 : _g.quest_counter) || 1
|
|
13647
13676
|
}
|
|
13648
13677
|
),
|
|
13649
13678
|
readingMode.isActive && readingMode.ancestry && /* @__PURE__ */ import_react26.default.createElement(
|
|
@@ -13912,7 +13941,7 @@ function XViewScene({
|
|
|
13912
13941
|
onClose: () => setIsImportModalOpen(false),
|
|
13913
13942
|
onConfirm: handleConfirmImport,
|
|
13914
13943
|
session,
|
|
13915
|
-
parentDbs: ((
|
|
13944
|
+
parentDbs: ((_h = sceneDataRef.current) == null ? void 0 : _h.parent_dbs) || [],
|
|
13916
13945
|
onFetchAvailableFiles: import_parent_file_modal_get,
|
|
13917
13946
|
currentViewName: viewParams == null ? void 0 : viewParams.name,
|
|
13918
13947
|
currentAncestries: ancestryDataRef.current || []
|
package/dist/index.mjs
CHANGED
|
@@ -2849,7 +2849,9 @@ var IGNORED_KEYS = [
|
|
|
2849
2849
|
"is_private",
|
|
2850
2850
|
"abstraction_tree",
|
|
2851
2851
|
"selectedAbstractionParentId",
|
|
2852
|
-
"isAddingAbstractionNodes"
|
|
2852
|
+
"isAddingAbstractionNodes",
|
|
2853
|
+
"status",
|
|
2854
|
+
"is_quest"
|
|
2853
2855
|
];
|
|
2854
2856
|
function extractCustomPropsFromNode(node) {
|
|
2855
2857
|
const customPropTypes = node._customPropTypes || {};
|
|
@@ -7956,10 +7958,13 @@ function InSceneQuestForm({
|
|
|
7956
7958
|
availableAncestries = [],
|
|
7957
7959
|
onMentionClick,
|
|
7958
7960
|
onUploadFile,
|
|
7959
|
-
// NOVAS PROPS PARA O GHOST NODE
|
|
7960
7961
|
onNameChange,
|
|
7961
7962
|
onColorChange,
|
|
7962
|
-
onSizeChange
|
|
7963
|
+
onSizeChange,
|
|
7964
|
+
viewName = "Projeto",
|
|
7965
|
+
// NOVA PROP
|
|
7966
|
+
questCounter = 1
|
|
7967
|
+
// NOVA PROP
|
|
7963
7968
|
}) {
|
|
7964
7969
|
const [name, setName] = useState16("");
|
|
7965
7970
|
const [types, setTypes] = useState16(["quest"]);
|
|
@@ -7972,6 +7977,7 @@ function InSceneQuestForm({
|
|
|
7972
7977
|
const [customProps, setCustomProps] = useState16([]);
|
|
7973
7978
|
const [isDescriptionModalOpen, setIsDescriptionModalOpen] = useState16(false);
|
|
7974
7979
|
const propsEndRef = useRef12(null);
|
|
7980
|
+
const standardizedName = `${viewName} - ${questCounter} - \xBB ${name || "Nova Quest"}`;
|
|
7975
7981
|
const handleAddProp = () => {
|
|
7976
7982
|
const newProp = createNewCustomProperty(customProps);
|
|
7977
7983
|
setCustomProps([...customProps, newProp]);
|
|
@@ -8008,7 +8014,7 @@ function InSceneQuestForm({
|
|
|
8008
8014
|
const handleSubmit = (e) => {
|
|
8009
8015
|
e.preventDefault();
|
|
8010
8016
|
if (!name.trim()) {
|
|
8011
|
-
alert("O campo '
|
|
8017
|
+
alert("O campo 'T\xEDtulo' \xE9 obrigat\xF3rio.");
|
|
8012
8018
|
return;
|
|
8013
8019
|
}
|
|
8014
8020
|
const additionalData = toObjectFromCustomProps(
|
|
@@ -8016,7 +8022,10 @@ function InSceneQuestForm({
|
|
|
8016
8022
|
);
|
|
8017
8023
|
const processedSections = processDescriptionForSave(description, []);
|
|
8018
8024
|
onSave({
|
|
8019
|
-
name:
|
|
8025
|
+
name: standardizedName,
|
|
8026
|
+
// SALVA O NOME FORMATADO
|
|
8027
|
+
raw_title: name.trim(),
|
|
8028
|
+
// Salva o título puro como fallback ou metadado útil
|
|
8020
8029
|
type: types,
|
|
8021
8030
|
color: QUEST_STATUS_COLORS[status],
|
|
8022
8031
|
status,
|
|
@@ -8055,7 +8064,21 @@ function InSceneQuestForm({
|
|
|
8055
8064
|
},
|
|
8056
8065
|
"\xD7"
|
|
8057
8066
|
)),
|
|
8058
|
-
/* @__PURE__ */ React15.createElement("form", { onSubmit: handleSubmit, className: "flex flex-col max-h-[68vh]" }, /* @__PURE__ */ React15.createElement("div", { className: "px-6 pb-28 overflow-y-auto overscroll-contain space-y-4 custom-scrollbar" }, /* @__PURE__ */ React15.createElement("div", { className: "space-y-1.5
|
|
8067
|
+
/* @__PURE__ */ React15.createElement("form", { onSubmit: handleSubmit, className: "flex flex-col max-h-[68vh]" }, /* @__PURE__ */ React15.createElement("div", { className: "px-6 pb-28 overflow-y-auto overscroll-contain space-y-4 custom-scrollbar" }, /* @__PURE__ */ React15.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ React15.createElement("label", { className: "text-xs text-slate-300" }, "T\xEDtulo da Quest"), /* @__PURE__ */ React15.createElement(
|
|
8068
|
+
"input",
|
|
8069
|
+
{
|
|
8070
|
+
required: true,
|
|
8071
|
+
type: "text",
|
|
8072
|
+
placeholder: "Ex.: Refatorar M\xF3dulo X",
|
|
8073
|
+
value: name,
|
|
8074
|
+
onChange: (e) => {
|
|
8075
|
+
const val = e.target.value;
|
|
8076
|
+
setName(val);
|
|
8077
|
+
onNameChange == null ? void 0 : onNameChange(`${viewName} - ${questCounter} - \xBB ${val || "Nova Quest"}`);
|
|
8078
|
+
},
|
|
8079
|
+
className: "w-full bg-slate-800/70 p-2.5 text-sm rounded-lg border border-white/10 focus:outline-none focus:ring-2 focus:ring-indigo-400/60"
|
|
8080
|
+
}
|
|
8081
|
+
), /* @__PURE__ */ React15.createElement("div", { className: "pt-1 flex items-center gap-1.5" }, /* @__PURE__ */ React15.createElement("span", { className: "text-[10px] uppercase font-bold text-slate-500 tracking-wider" }, "Preview:"), /* @__PURE__ */ React15.createElement("p", { className: "text-xs text-indigo-300 font-medium truncate", title: standardizedName }, standardizedName))), /* @__PURE__ */ React15.createElement("div", { className: "space-y-1.5 relative mt-2" }, /* @__PURE__ */ React15.createElement("label", { className: "text-xs text-slate-300" }, "Status da Quest"), /* @__PURE__ */ React15.createElement("div", { className: "relative" }, /* @__PURE__ */ React15.createElement(
|
|
8059
8082
|
"button",
|
|
8060
8083
|
{
|
|
8061
8084
|
type: "button",
|
|
@@ -8077,20 +8100,7 @@ function InSceneQuestForm({
|
|
|
8077
8100
|
},
|
|
8078
8101
|
/* @__PURE__ */ React15.createElement("span", { className: "w-3 h-3 rounded-full", style: { backgroundColor: QUEST_STATUS_COLORS[s] } }),
|
|
8079
8102
|
s
|
|
8080
|
-
)))))), /* @__PURE__ */ React15.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ React15.createElement("label", { className: "text-xs text-slate-300" }, "
|
|
8081
|
-
"input",
|
|
8082
|
-
{
|
|
8083
|
-
required: true,
|
|
8084
|
-
type: "text",
|
|
8085
|
-
placeholder: "Ex.: Refatorar M\xF3dulo X",
|
|
8086
|
-
value: name,
|
|
8087
|
-
onChange: (e) => {
|
|
8088
|
-
setName(e.target.value);
|
|
8089
|
-
onNameChange == null ? void 0 : onNameChange(e.target.value);
|
|
8090
|
-
},
|
|
8091
|
-
className: "w-full bg-slate-800/70 p-2.5 text-sm rounded-lg border border-white/10 focus:outline-none focus:ring-2 focus:ring-indigo-400/60"
|
|
8092
|
-
}
|
|
8093
|
-
)), /* @__PURE__ */ React15.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ React15.createElement("label", { className: "text-xs text-slate-300" }, "Tipos Adicionais"), /* @__PURE__ */ React15.createElement("div", { className: "relative w-full bg-slate-800/70 p-1.5 min-h-[42px] flex flex-wrap gap-1.5 rounded-lg border border-white/10 focus-within:ring-2 focus-within:ring-indigo-400/60 transition-all" }, types.map((t, index) => /* @__PURE__ */ React15.createElement("span", { key: index, className: `flex items-center gap-1 px-1.5 py-0.5 rounded-md text-xs font-medium border ${t === "quest" ? "bg-sky-500/20 text-sky-200 border-sky-500/30" : "bg-indigo-500/30 text-indigo-100 border-indigo-500/20"}` }, t, t !== "quest" && /* @__PURE__ */ React15.createElement("button", { type: "button", onClick: () => handleRemoveType(index), className: "hover:text-white transition-colors" }, /* @__PURE__ */ React15.createElement(FiX4, { size: 12 })))), /* @__PURE__ */ React15.createElement(
|
|
8103
|
+
)))))), /* @__PURE__ */ React15.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ React15.createElement("label", { className: "text-xs text-slate-300" }, "Tipos Adicionais"), /* @__PURE__ */ React15.createElement("div", { className: "relative w-full bg-slate-800/70 p-1.5 min-h-[42px] flex flex-wrap gap-1.5 rounded-lg border border-white/10 focus-within:ring-2 focus-within:ring-indigo-400/60 transition-all" }, types.map((t, index) => /* @__PURE__ */ React15.createElement("span", { key: index, className: `flex items-center gap-1 px-1.5 py-0.5 rounded-md text-xs font-medium border ${t === "quest" ? "bg-sky-500/20 text-sky-200 border-sky-500/30" : "bg-indigo-500/30 text-indigo-100 border-indigo-500/20"}` }, t, t !== "quest" && /* @__PURE__ */ React15.createElement("button", { type: "button", onClick: () => handleRemoveType(index), className: "hover:text-white transition-colors" }, /* @__PURE__ */ React15.createElement(FiX4, { size: 12 })))), /* @__PURE__ */ React15.createElement(
|
|
8094
8104
|
"input",
|
|
8095
8105
|
{
|
|
8096
8106
|
type: "text",
|
|
@@ -8912,15 +8922,28 @@ function QuestDetailsPanel({
|
|
|
8912
8922
|
},
|
|
8913
8923
|
/* @__PURE__ */ React17.createElement("span", { className: "w-3 h-3 rounded-full", style: { backgroundColor: QUEST_STATUS_COLORS2[s] } }),
|
|
8914
8924
|
s
|
|
8915
|
-
)))))), /* @__PURE__ */ React17.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ React17.createElement("label", { className: "text-xs text-slate-300" }, "Nome"), /* @__PURE__ */ React17.createElement("input", { type: "text", value: name, onChange: handleNameChange, readOnly: !canEdit, className: `w-full bg-slate-800/70 p-2.5 text-sm rounded-lg border border-white/10 focus:outline-none ${canEdit ? "focus:ring-2 focus:ring-indigo-400/60" : "cursor-default text-slate-400"}` })), /* @__PURE__ */ React17.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ React17.createElement("label", { className: "text-xs text-slate-300" }, "Tipos Adicionais"), /* @__PURE__ */ React17.createElement("div", { className: `relative w-full bg-slate-800/70 p-1.5 min-h-[42px] flex flex-wrap gap-1.5 rounded-lg border border-white/10 ${canEdit ? "focus-within:ring-2 focus-within:ring-indigo-400/60" : ""} transition-all` }, types.map((t, index) => /* @__PURE__ */ React17.createElement("span", { key: index, className: `flex items-center gap-1 px-1.5 py-0.5 rounded-md text-xs font-medium border ${t === "quest" ? "bg-sky-500/20 text-sky-200 border-sky-500/30" : "bg-indigo-500/30 text-indigo-100 border-indigo-500/20"}` }, t, canEdit && t !== "quest" && /* @__PURE__ */ React17.createElement("button", { type: "button", onClick: () => handleRemoveType(index), className: "hover:text-white transition-colors" }, /* @__PURE__ */ React17.createElement(FiX6, { size: 12 })))), canEdit && /* @__PURE__ */ React17.createElement(
|
|
8916
|
-
|
|
8917
|
-
|
|
8918
|
-
|
|
8919
|
-
|
|
8920
|
-
|
|
8921
|
-
|
|
8922
|
-
|
|
8923
|
-
|
|
8925
|
+
)))))), /* @__PURE__ */ React17.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ React17.createElement("label", { className: "text-xs text-slate-300" }, "Nome"), /* @__PURE__ */ React17.createElement("input", { type: "text", value: name, onChange: handleNameChange, readOnly: !canEdit, className: `w-full bg-slate-800/70 p-2.5 text-sm rounded-lg border border-white/10 focus:outline-none ${canEdit ? "focus:ring-2 focus:ring-indigo-400/60" : "cursor-default text-slate-400"}` })), /* @__PURE__ */ React17.createElement("div", { className: "space-y-1.5" }, /* @__PURE__ */ React17.createElement("label", { className: "text-xs text-slate-300" }, "Tipos Adicionais"), /* @__PURE__ */ React17.createElement("div", { className: `relative w-full bg-slate-800/70 p-1.5 min-h-[42px] flex flex-wrap gap-1.5 rounded-lg border border-white/10 ${canEdit ? "focus-within:ring-2 focus-within:ring-indigo-400/60" : ""} transition-all` }, types.map((t, index) => /* @__PURE__ */ React17.createElement("span", { key: index, className: `flex items-center gap-1 px-1.5 py-0.5 rounded-md text-xs font-medium border ${t === "quest" ? "bg-sky-500/20 text-sky-200 border-sky-500/30" : "bg-indigo-500/30 text-indigo-100 border-indigo-500/20"}` }, t, canEdit && t !== "quest" && /* @__PURE__ */ React17.createElement("button", { type: "button", onClick: () => handleRemoveType(index), className: "hover:text-white transition-colors" }, /* @__PURE__ */ React17.createElement(FiX6, { size: 12 })))), canEdit && /* @__PURE__ */ React17.createElement(
|
|
8926
|
+
"input",
|
|
8927
|
+
{
|
|
8928
|
+
type: "text",
|
|
8929
|
+
value: typeInput,
|
|
8930
|
+
onChange: (e) => {
|
|
8931
|
+
setTypeInput(e.target.value);
|
|
8932
|
+
setShowTypeSuggestions(true);
|
|
8933
|
+
},
|
|
8934
|
+
onKeyDown: handleTypeInputKeyDown,
|
|
8935
|
+
onClick: () => setShowTypeSuggestions(true),
|
|
8936
|
+
onBlur: () => {
|
|
8937
|
+
if (typeInput.trim()) {
|
|
8938
|
+
handleAddType(typeInput);
|
|
8939
|
+
}
|
|
8940
|
+
setTimeout(() => setShowTypeSuggestions(false), 150);
|
|
8941
|
+
},
|
|
8942
|
+
className: "flex-1 bg-transparent text-sm min-w-[80px] focus:outline-none text-slate-200",
|
|
8943
|
+
placeholder: "",
|
|
8944
|
+
autoComplete: "off"
|
|
8945
|
+
}
|
|
8946
|
+
), canEdit && showTypeSuggestions && filteredTypes.length > 0 && /* @__PURE__ */ React17.createElement("ul", { className: "custom-scrollbar absolute top-full left-0 z-10 w-full mt-1 max-h-40 overflow-y-auto rounded-lg bg-slate-800 border border-white/10 shadow-lg" }, filteredTypes.map((suggestedType, index) => /* @__PURE__ */ React17.createElement("li", { key: index, className: "px-3 py-2 text-sm text-slate-200 cursor-pointer hover:bg-indigo-600/50", onMouseDown: (e) => {
|
|
8924
8947
|
e.preventDefault();
|
|
8925
8948
|
handleAddType(suggestedType);
|
|
8926
8949
|
} }, suggestedType))))), /* @__PURE__ */ React17.createElement("div", { className: "space-y-1.5 relative" }, /* @__PURE__ */ React17.createElement("label", { className: "text-xs text-slate-300" }, "Descri\xE7\xE3o"), /* @__PURE__ */ React17.createElement("div", { className: "relative group min-h-[60px] bg-slate-800/40 rounded-lg border border-white/10 hover:border-white/20 transition-colors" }, /* @__PURE__ */ React17.createElement(DescriptionDisplay, { description, savedSections: existingSections, availableNodes, availableAncestries, onOpenReference, onMentionClick, onImageClick: handleImageClickFromText, onSaveDescription: handleSaveDescriptionInline }), /* @__PURE__ */ React17.createElement("div", { className: "absolute top-0 right-0 flex bg-slate-900/50 rounded-bl-lg backdrop-blur-sm opacity-0 group-hover:opacity-100 focus-within:opacity-100 transition-opacity overflow-hidden border-b border-l border-white/5" }, /* @__PURE__ */ React17.createElement("button", { type: "button", onClick: () => setIsReadMode(true), className: `p-2 text-slate-400 hover:text-white hover:bg-white/10 transition-colors ${canEdit ? "border-r border-white/5" : ""}`, title: "Modo de Leitura" }, /* @__PURE__ */ React17.createElement(FiBookOpen4, { size: 14 })), canEdit && /* @__PURE__ */ React17.createElement("button", { type: "button", onClick: () => setIsDescriptionModalOpen(true), className: "p-2 text-slate-400 hover:text-white hover:bg-white/10 transition-colors", title: "Editar descri\xE7\xE3o (Modo de Escrita)" }, /* @__PURE__ */ React17.createElement(FiEdit28, { size: 14 }))), canEdit && !description && /* @__PURE__ */ React17.createElement("div", { onClick: () => setIsDescriptionModalOpen(true), className: "absolute inset-0 flex items-center justify-center text-xs text-slate-500 cursor-text" }, "Adicionar descri\xE7\xE3o..."))), /* @__PURE__ */ React17.createElement("div", { className: "space-y-2" }, /* @__PURE__ */ React17.createElement("label", { className: "text-xs text-slate-300" }, "Tamanho no Node (Size)"), /* @__PURE__ */ React17.createElement("div", { className: "flex items-center gap-5" }, ["small", "medium", "large"].map((s) => {
|
|
@@ -10288,7 +10311,7 @@ function XViewScene({
|
|
|
10288
10311
|
delete_file_action,
|
|
10289
10312
|
check_user_permission
|
|
10290
10313
|
}) {
|
|
10291
|
-
var _a, _b, _c, _d, _e, _f, _g;
|
|
10314
|
+
var _a, _b, _c, _d, _e, _f, _g, _h;
|
|
10292
10315
|
const { data: session, status } = useSession();
|
|
10293
10316
|
const router = useRouter();
|
|
10294
10317
|
const searchParams = useSearchParams();
|
|
@@ -11963,6 +11986,7 @@ function XViewScene({
|
|
|
11963
11986
|
const handleSaveQuestNode = async (context, newQuestData) => {
|
|
11964
11987
|
const { graphDataRef, sceneDataRef: sceneDataRef2, stateRef: stateRef2, setters, actions, sceneSaveUrl: sceneSaveUrl2, viewType, sceneConfigId: sceneConfigId2, ownerId: ownerId2 } = context;
|
|
11965
11988
|
if (!graphDataRef.current || (viewType == null ? void 0 : viewType.toLowerCase()) !== "view") return;
|
|
11989
|
+
const currentCounter = sceneDataRef2.current.quest_counter || 1;
|
|
11966
11990
|
const newNode = {
|
|
11967
11991
|
id: short2.generate(),
|
|
11968
11992
|
...newQuestData,
|
|
@@ -11978,10 +12002,13 @@ function XViewScene({
|
|
|
11978
12002
|
nodes: sceneDataRef2.current.nodes,
|
|
11979
12003
|
links: sceneDataRef2.current.links,
|
|
11980
12004
|
quest_nodes: graphDataRef.current[sceneConfigId2].nodes,
|
|
11981
|
-
quest_links: graphDataRef.current[sceneConfigId2].links
|
|
12005
|
+
quest_links: graphDataRef.current[sceneConfigId2].links,
|
|
12006
|
+
quest_counter: currentCounter + 1
|
|
12007
|
+
// NOVO: Incrementa o contador nos metadados
|
|
11982
12008
|
};
|
|
11983
12009
|
try {
|
|
11984
12010
|
await actions.save_view_data(sceneSaveUrl2, sceneFileData);
|
|
12011
|
+
sceneDataRef2.current.quest_counter = currentCounter + 1;
|
|
11985
12012
|
stateRef2.current.nodeIdToParentFileMap.set(String(newNode.id), {
|
|
11986
12013
|
parentFileId: sceneConfigId2,
|
|
11987
12014
|
ownerId: ownerId2,
|
|
@@ -13643,7 +13670,9 @@ function XViewScene({
|
|
|
13643
13670
|
onMentionClick: handleAddExistingNode,
|
|
13644
13671
|
onUploadFile: upload_file_action,
|
|
13645
13672
|
availableNodes: allAvailableNodes,
|
|
13646
|
-
availableAncestries: allAvailableAncestries
|
|
13673
|
+
availableAncestries: allAvailableAncestries,
|
|
13674
|
+
viewName: viewParams == null ? void 0 : viewParams.name,
|
|
13675
|
+
questCounter: ((_g = sceneDataRef.current) == null ? void 0 : _g.quest_counter) || 1
|
|
13647
13676
|
}
|
|
13648
13677
|
),
|
|
13649
13678
|
readingMode.isActive && readingMode.ancestry && /* @__PURE__ */ React25.createElement(
|
|
@@ -13912,7 +13941,7 @@ function XViewScene({
|
|
|
13912
13941
|
onClose: () => setIsImportModalOpen(false),
|
|
13913
13942
|
onConfirm: handleConfirmImport,
|
|
13914
13943
|
session,
|
|
13915
|
-
parentDbs: ((
|
|
13944
|
+
parentDbs: ((_h = sceneDataRef.current) == null ? void 0 : _h.parent_dbs) || [],
|
|
13916
13945
|
onFetchAvailableFiles: import_parent_file_modal_get,
|
|
13917
13946
|
currentViewName: viewParams == null ? void 0 : viewParams.name,
|
|
13918
13947
|
currentAncestries: ancestryDataRef.current || []
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@lv-x-software-house/x_view",
|
|
3
|
-
"version": "1.2.4-dev.
|
|
3
|
+
"version": "1.2.4-dev.25",
|
|
4
4
|
"description": "Pacote privado contendo os componentes e lógica de renderização 3D do X View.",
|
|
5
5
|
"author": "iv.x - Engenharia de Software - ivxsoftwarehouse@gmail.com",
|
|
6
6
|
"license": "UNLICENSED",
|