import type { DialogueFlowStep, JsonObject } from "../editorCore";
import type { ItemQuestAdvancedContext } from "./editorContexts";

type ItemQuestAdvancedPanelsProps = {
  ctx: ItemQuestAdvancedContext;
};

export default function ItemQuestAdvancedPanels({ ctx }: ItemQuestAdvancedPanelsProps) {
  const {
    activeType,
    selectedRecord,
    activeEditTab,
    addItemActionEntry,
    selectedItemActions,
    selectedIndex,
    isStepCollapsed,
    setStepCollapsed,
    getItemActionSummary,
    moveItemActionEntry,
    deleteItemActionEntry,
    getPlainObjectArray,
    patchSelectedRecordArray,
    patchItemActionFlowSteps,
    createFlowStep,
    FLOW_KIND_LABELS,
    getFlowStepSummary,
    conditionTypeOptions,
    getDefaultConditionValue,
    renderConditionValueField,
    patchSelectedRecord,
    selectedQuestSteps,
    getQuestStepSummary,
    moveQuestStepEntry,
    deleteQuestStepEntry,
    patchQuestSteps,
    addQuestStepEntry,
  } = ctx;

  return (
    <>
      {activeType === "items" && selectedRecord && activeEditTab === "Actions" ? (
        <div className="mini-editor">
          <div className="mini-editor-head">
            <h4>Item Action Flow</h4>
            <div className="flow-add-buttons">
              <button type="button" className="success" onClick={addItemActionEntry}>+ Action</button>
            </div>
          </div>

          {selectedItemActions.length === 0 ? <p className="muted">No item actions yet. Add one above.</p> : null}
          {selectedItemActions.map((actionEntry, actionIndex) => {
            const actionCardKey = `item-action-${selectedIndex}-${actionIndex}`;
            const collapsed = isStepCollapsed(actionCardKey);
            const actionFlowSteps = getPlainObjectArray(actionEntry.flowSteps) as unknown as DialogueFlowStep[];
            return (
              <div
                key={actionCardKey}
                className={`flow-step ${collapsed ? "collapsed" : "expanded"}`}
              >
                <div
                  className="flow-step-head flow-step-toggle"
                  role="button"
                  tabIndex={0}
                  onClick={() => setStepCollapsed(actionCardKey, !collapsed)}
                  onKeyDown={(event) => {
                    if (event.key === "Enter" || event.key === " ") {
                      event.preventDefault();
                      setStepCollapsed(actionCardKey, !collapsed);
                    }
                  }}
                >
                  <div>
                    <strong>{actionIndex + 1}. {String(actionEntry.action || "Action")}</strong>
                    {collapsed ? <p className="flow-summary">{getItemActionSummary(actionEntry, actionIndex)}</p> : null}
                  </div>

                  {!collapsed ? (
                    <div className="flow-step-actions flow-expanded-actions" onClick={(event) => event.stopPropagation()}>
                      <button type="button" onClick={() => moveItemActionEntry(actionIndex, -1)} disabled={actionIndex === 0}>-</button>
                      <button type="button" onClick={() => moveItemActionEntry(actionIndex, 1)} disabled={actionIndex >= selectedItemActions.length - 1}>+</button>
                      <button type="button" className="danger" onClick={() => deleteItemActionEntry(actionIndex)}>Remove</button>
                    </div>
                  ) : null}
                </div>

                {!collapsed ? (
                  <div className="dialogue-node-editor">
                    <label>Action Name</label>
                    <input
                      value={String(actionEntry.action || "")}
                      onChange={(event) => patchSelectedRecordArray("actionsList", (entries) => entries.map((entry, idx) => (idx === actionIndex ? { ...entry, action: event.target.value } : entry)))}
                    />
                    <label>Action Flow</label>
                    <div className="mini-editor">
                      <div className="mini-editor-head">
                        <h4>Timeline</h4>
                        <div className="flow-add-buttons">
                          <button type="button" className="success" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => [...steps, createFlowStep("condition", actionCardKey)])}>+ Condition</button>
                          <button type="button" className="success" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => [...steps, createFlowStep("action", actionCardKey)])}>+ Action</button>
                          <button type="button" className="success" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => [...steps, createFlowStep("jump", actionCardKey)])}>+ Jump</button>
                          <button type="button" className="success" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => [...steps, createFlowStep("choice", actionCardKey)])}>+ Choice</button>
                          <button type="button" className="success" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => [...steps, createFlowStep("text", actionCardKey)])}>+ Text Screen</button>
                          <button type="button" className="success" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => [...steps, createFlowStep("end", actionCardKey)])}>+ End</button>
                        </div>
                      </div>

                      {actionFlowSteps.length === 0 ? <p className="muted">No nested steps yet.</p> : null}
                      {actionFlowSteps.map((step, stepIndex) => {
                        const stepCollapsed = isStepCollapsed(step.id);
                        const nextStep = actionFlowSteps[stepIndex + 1];
                        const stepConditionType = String(step.conditionType || "always");
                        return (
                          <div key={step.id} className={`flow-step ${stepCollapsed ? "collapsed" : "expanded"}`}>
                            <div
                              className="flow-step-head flow-step-toggle"
                              role="button"
                              tabIndex={0}
                              onClick={() => setStepCollapsed(step.id, !stepCollapsed)}
                              onKeyDown={(event) => {
                                if (event.key === "Enter" || event.key === " ") {
                                  event.preventDefault();
                                  setStepCollapsed(step.id, !stepCollapsed);
                                }
                              }}
                            >
                              <div>
                                <strong>{stepIndex + 1}. {FLOW_KIND_LABELS[step.kind]}</strong>
                                {stepCollapsed ? <p className="flow-summary">{getFlowStepSummary(step)}</p> : null}
                              </div>
                              {stepCollapsed && nextStep ? <p className="flow-next-preview">Next: ({stepIndex + 2}) {FLOW_KIND_LABELS[nextStep.kind]} - {getFlowStepSummary(nextStep).slice(0, 45)}</p> : null}
                              {!stepCollapsed ? (
                                <div className="flow-step-actions flow-expanded-actions" onClick={(event) => event.stopPropagation()}>
                                  <button type="button" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => {
                                    const target = stepIndex - 1;
                                    if (target < 0) { return steps; }
                                    const next = [...steps];
                                    const [moved] = next.splice(stepIndex, 1);
                                    next.splice(target, 0, moved);
                                    return next;
                                  })} disabled={stepIndex === 0}>-</button>
                                  <button type="button" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => {
                                    const target = stepIndex + 1;
                                    if (target >= steps.length) { return steps; }
                                    const next = [...steps];
                                    const [moved] = next.splice(stepIndex, 1);
                                    next.splice(target, 0, moved);
                                    return next;
                                  })} disabled={stepIndex >= actionFlowSteps.length - 1}>+</button>
                                  <button type="button" className="danger" onClick={() => patchItemActionFlowSteps(actionIndex, (steps) => steps.filter((_, idx) => idx !== stepIndex))}>Remove</button>
                                </div>
                              ) : null}
                            </div>

                            {!stepCollapsed && step.kind === "text" ? (
                              <textarea
                                value={String(step.text || "")}
                                onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, text: event.target.value } : entry)))}
                                placeholder="Screen text"
                              />
                            ) : null}

                            {!stepCollapsed && step.kind === "jump" ? (
                              <input
                                value={String(step.nextId || "")}
                                onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, nextId: event.target.value } : entry)))}
                                placeholder="Next step or target"
                              />
                            ) : null}

                            {!stepCollapsed && step.kind === "action" ? (
                              <div className="flow-step-grid">
                                <input
                                  value={String(step.reactionType || "none")}
                                  onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, reactionType: event.target.value } : entry)))}
                                  placeholder="Action type"
                                />
                                <input
                                  value={String(step.reactionValue || "")}
                                  onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, reactionValue: event.target.value } : entry)))}
                                  placeholder="Action value"
                                />
                              </div>
                            ) : null}

                            {!stepCollapsed && step.kind === "condition" ? (
                              <div className="flow-step-grid">
                                <select
                                  value={stepConditionType}
                                  onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, conditionType: event.target.value, conditionValue: getDefaultConditionValue(event.target.value) } : entry)))}
                                >
                                  {conditionTypeOptions.map((opt: string) => (
                                    <option key={`item-action-cond-${actionIndex}-${step.id}-${opt}`} value={opt}>{opt}</option>
                                  ))}
                                </select>
                                {renderConditionValueField(stepConditionType, String(step.conditionValue || ""), (nextValue: string) => {
                                  patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, conditionValue: nextValue } : entry)));
                                })}
                                <label className="inline-check">
                                  <input
                                    type="checkbox"
                                    checked={Boolean(step.conditionNot)}
                                    onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, conditionNot: event.target.checked } : entry)))}
                                  />
                                  not
                                </label>
                                <input
                                  value={String(step.text || "")}
                                  onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, text: event.target.value } : entry)))}
                                  placeholder="Outcome text"
                                />
                              </div>
                            ) : null}

                            {!stepCollapsed && step.kind === "choice" ? (
                              <div className="flow-step-grid">
                                <input
                                  value={String(step.text || "")}
                                  onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, text: event.target.value } : entry)))}
                                  placeholder="Choice label"
                                />
                                <input
                                  value={String(step.nextId || "")}
                                  onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, nextId: event.target.value } : entry)))}
                                  placeholder="Next target"
                                />
                                <select
                                  value={stepConditionType}
                                  onChange={(event) => patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, conditionType: event.target.value, conditionValue: getDefaultConditionValue(event.target.value) } : entry)))}
                                >
                                  {conditionTypeOptions.map((opt: string) => (
                                    <option key={`item-action-choice-cond-${actionIndex}-${step.id}-${opt}`} value={opt}>{opt}</option>
                                  ))}
                                </select>
                                {renderConditionValueField(stepConditionType, String(step.conditionValue || ""), (nextValue: string) => {
                                  patchItemActionFlowSteps(actionIndex, (steps) => steps.map((entry, idx) => (idx === stepIndex ? { ...entry, conditionValue: nextValue } : entry)));
                                })}
                              </div>
                            ) : null}

                            {!stepCollapsed && step.kind === "end" ? <p className="muted">Stops this action flow here.</p> : null}
                          </div>
                        );
                      })}
                    </div>
                  </div>
                ) : null}
              </div>
            );
          })}
        </div>
      ) : null}

      {activeType === "quests" && selectedRecord && activeEditTab === "Conditions" ? (
        <div className="mini-editor">
          <div className="mini-editor-head">
            <h4>Quest Requirements</h4>
            <div className="flow-add-buttons">
              <button type="button" className="success" onClick={() => patchSelectedRecord((record) => ({
                ...record,
                requirements: [...getPlainObjectArray(record.requirements), { conditionType: "always", conditionValue: "" }],
              }))}>+ Requirement</button>
            </div>
          </div>

          {getPlainObjectArray(selectedRecord.requirements).length === 0 ? <p className="muted">No requirements yet.</p> : null}
          {getPlainObjectArray(selectedRecord.requirements).map((requirement: JsonObject, requirementIndex: number) => {
            const requirementCollapsed = isStepCollapsed(`quest-req-${selectedIndex}-${requirementIndex}`);
            const requirementType = String(requirement.conditionType || "always");
            return (
              <div key={`quest-req-${selectedIndex}-${requirementIndex}`} className={`flow-step ${requirementCollapsed ? "collapsed" : "expanded"}`}>
                <div className="flow-step-head flow-step-toggle" role="button" tabIndex={0} onClick={() => setStepCollapsed(`quest-req-${selectedIndex}-${requirementIndex}`, !requirementCollapsed)}>
                  <div>
                    <strong>{requirementIndex + 1}. {requirementType}</strong>
                    {requirementCollapsed ? <p className="flow-summary">{String(requirement.conditionValue || "Always")}</p> : null}
                  </div>
                  {!requirementCollapsed ? (
                    <div className="flow-step-actions flow-expanded-actions">
                      <button type="button" className="danger" onClick={() => patchSelectedRecord((record) => ({
                        ...record,
                        requirements: getPlainObjectArray(record.requirements).filter((_, idx: number) => idx !== requirementIndex),
                      }))}>Remove</button>
                    </div>
                  ) : null}
                </div>
                {!requirementCollapsed ? (
                  <div className="dialogue-node-editor">
                    <label>Condition Type</label>
                    <select
                      value={requirementType}
                      onChange={(event) => patchSelectedRecord((record) => ({
                        ...record,
                        requirements: getPlainObjectArray(record.requirements).map((entry, idx: number) => idx === requirementIndex ? { ...entry, conditionType: event.target.value } : entry),
                      }))}
                    >
                      {conditionTypeOptions.map((opt: string) => (
                        <option key={`quest-req-${selectedIndex}-${requirementIndex}-${opt}`} value={opt}>{opt}</option>
                      ))}
                    </select>
                    <label>Condition Value</label>
                    {renderConditionValueField(requirementType, String(requirement.conditionValue || ""), (nextValue: string) => patchSelectedRecord((record) => ({
                      ...record,
                      requirements: getPlainObjectArray(record.requirements).map((entry, idx: number) => idx === requirementIndex ? { ...entry, conditionValue: nextValue } : entry),
                    })))}
                  </div>
                ) : null}
              </div>
            );
          })}
        </div>
      ) : null}

      {activeType === "quests" && selectedRecord && activeEditTab === "Steps" ? (
        <div className="mini-editor">
          <div className="mini-editor-head">
            <h4>Quest Steps</h4>
            <div className="flow-add-buttons">
              <button type="button" className="success" onClick={addQuestStepEntry}>+ Step</button>
            </div>
          </div>

          {selectedQuestSteps.length === 0 ? <p className="muted">No quest steps yet.</p> : null}
          {selectedQuestSteps.map((step: JsonObject, stepIndex: number) => {
            const stepCardKey = `quest-step-${selectedIndex}-${stepIndex}`;
            const stepCollapsed = isStepCollapsed(stepCardKey);
            return (
              <div key={stepCardKey} className={`flow-step ${stepCollapsed ? "collapsed" : "expanded"}`}>
                <div className="flow-step-head flow-step-toggle" role="button" tabIndex={0} onClick={() => setStepCollapsed(stepCardKey, !stepCollapsed)}>
                  <div>
                    <strong>{stepIndex + 1}. {getQuestStepSummary(step, stepIndex)}</strong>
                    {stepCollapsed ? <p className="flow-summary">{String(step.conditionType || "always")}</p> : null}
                  </div>
                  {!stepCollapsed ? (
                    <div className="flow-step-actions flow-expanded-actions">
                      <button type="button" onClick={() => moveQuestStepEntry(stepIndex, -1)} disabled={stepIndex === 0}>-</button>
                      <button type="button" onClick={() => moveQuestStepEntry(stepIndex, 1)} disabled={stepIndex >= selectedQuestSteps.length - 1}>+</button>
                      <button type="button" className="danger" onClick={() => deleteQuestStepEntry(stepIndex)}>Remove</button>
                    </div>
                  ) : null}
                </div>
                {!stepCollapsed ? (
                  <div className="dialogue-node-editor">
                    <label>Step ID</label>
                    <input
                      value={String(step.stepID || stepIndex + 1)}
                      onChange={(event) => patchQuestSteps((entries) => entries.map((entry, idx) => idx === stepIndex ? { ...entry, stepID: Math.max(1, Number(event.target.value) || stepIndex + 1) } : entry))}
                    />
                    <label>Step Key</label>
                    <input
                      value={String(step.id || "")}
                      onChange={(event) => patchQuestSteps((entries) => entries.map((entry, idx) => idx === stepIndex ? { ...entry, id: event.target.value } : entry))}
                    />
                    <label>Step Name</label>
                    <input
                      value={String(step.name || "")}
                      onChange={(event) => patchQuestSteps((entries) => entries.map((entry, idx) => idx === stepIndex ? { ...entry, name: event.target.value } : entry))}
                    />
                    <label>Condition Type</label>
                    <select
                      value={String(step.conditionType || "always")}
                      onChange={(event) => patchQuestSteps((entries) => entries.map((entry, idx) => idx === stepIndex ? { ...entry, conditionType: event.target.value } : entry))}
                    >
                      {conditionTypeOptions.map((opt: string) => (
                        <option key={`quest-step-cond-${stepIndex}-${opt}`} value={opt}>{opt}</option>
                      ))}
                    </select>
                    <label>Condition Value</label>
                    {renderConditionValueField(String(step.conditionType || "always"), String(step.conditionValue || ""), (nextValue: string) => {
                      patchQuestSteps((entries) => entries.map((entry, idx) => idx === stepIndex ? { ...entry, conditionValue: nextValue } : entry));
                    })}
                  </div>
                ) : null}
              </div>
            );
          })}
        </div>
      ) : null}
    </>
  );
}
