// Gotanda Guide — category manager
// Inline UI to add/edit/delete categories. Built-in categories
// (defined in data.jsx) can be edited but not deleted.

const { useState: useCatState } = React;

const BUILTIN_CAT_IDS = new Set([
  'all', 'izakaya', 'ramen', 'sushi', 'cafe', 'bar',
  'hotel', 'shop', 'sight', 'work',
]);
const CATS_LS = 'gg_categories';

function loadCategories(defaults) {
  try {
    const raw = localStorage.getItem(CATS_LS);
    if (raw) return JSON.parse(raw);
  } catch {}
  return defaults;
}
function saveCategories(cats) {
  try { localStorage.setItem(CATS_LS, JSON.stringify(cats)); } catch {}
}

function CategoryManager({ lang, categories, onChange, onClose }) {
  const T = (ja, en) => (lang === 'ja' ? ja : en);
  const [list, setList] = useCatState(categories);
  const [draft, setDraft] = useCatState({
    id: '', icon: '', ja: '', en: '', keyword: '', type: '',
  });
  const [error, setError] = useCatState('');

  const update = (idx, patch) => {
    setList((arr) => {
      const next = arr.slice();
      const c = next[idx];
      next[idx] = {
        ...c,
        ...patch,
        label: { ...c.label, ...(patch.label || {}) },
      };
      return next;
    });
  };

  const remove = (idx) => {
    setList((arr) => arr.filter((_, i) => i !== idx));
  };

  const move = (idx, dir) => {
    setList((arr) => {
      const next = arr.slice();
      const j = idx + dir;
      if (j < 0 || j >= next.length) return arr;
      // 'all' is anchored to the front
      if (next[idx].id === 'all' || next[j].id === 'all') return arr;
      [next[idx], next[j]] = [next[j], next[idx]];
      return next;
    });
  };

  const add = () => {
    setError('');
    const id = draft.id.trim().toLowerCase().replace(/[^a-z0-9_-]/g, '');
    if (!id) { setError(T('IDを入力（半角英数）', 'Enter an ID (alphanum)')); return; }
    if (list.some((c) => c.id === id)) { setError(T('そのIDは既に存在します', 'ID already exists')); return; }
    if (!draft.ja.trim() && !draft.en.trim()) { setError(T('日本語または英語名を入力', 'Enter a label')); return; }
    const newCat = {
      id,
      icon: draft.icon.trim() || '◎',
      label: {
        ja: draft.ja.trim() || draft.en.trim(),
        en: draft.en.trim() || draft.ja.trim(),
      },
      keyword: draft.keyword.trim() || draft.ja.trim(),
      type: draft.type.trim() || 'establishment',
    };
    setList((arr) => [...arr, newCat]);
    setDraft({ id: '', icon: '', ja: '', en: '', keyword: '', type: '' });
  };

  const save = () => {
    saveCategories(list);
    onChange(list);
    onClose();
  };

  const reset = () => {
    if (!confirm(T('カテゴリを初期状態に戻しますか？', 'Reset categories to defaults?'))) return;
    localStorage.removeItem(CATS_LS);
    onChange(window.__GG.CATEGORIES);
    onClose();
  };

  return (
    <div className="cat-mgr">
      <div className="cat-list">
        {list.map((c, i) => {
          const isBuiltin = BUILTIN_CAT_IDS.has(c.id);
          const isAll = c.id === 'all';
          return (
            <div key={c.id} className={`cat-row ${isBuiltin ? 'is-builtin' : ''}`}>
              <div className="cat-move">
                <button
                  className="cat-mv-btn"
                  onClick={() => move(i, -1)}
                  disabled={isAll || i <= 1}
                  title={T('上へ', 'Move up')}
                >↑</button>
                <button
                  className="cat-mv-btn"
                  onClick={() => move(i, 1)}
                  disabled={isAll || i === list.length - 1}
                  title={T('下へ', 'Move down')}
                >↓</button>
              </div>
              <input
                className="cat-icon-input"
                value={c.icon}
                onChange={(e) => update(i, { icon: e.target.value.slice(0, 2) })}
                title={T('アイコン', 'Icon')}
              />
              <div className="cat-id">{c.id}{isBuiltin && <span className="cat-builtin-tag">標準</span>}</div>
              <input
                className="gp-input cat-name-input"
                value={c.label?.ja || ''}
                onChange={(e) => update(i, { label: { ja: e.target.value } })}
                placeholder="JA"
              />
              <input
                className="gp-input cat-name-input"
                value={c.label?.en || ''}
                onChange={(e) => update(i, { label: { en: e.target.value } })}
                placeholder="EN"
              />
              <input
                className="gp-input cat-name-input"
                value={c.keyword || ''}
                onChange={(e) => update(i, { keyword: e.target.value })}
                placeholder={T('検索ワード', 'Search keyword')}
                disabled={isAll}
                style={isAll ? { opacity: 0.4 } : undefined}
              />
              <button
                className="cat-del"
                onClick={() => remove(i)}
                disabled={isBuiltin}
                title={isBuiltin ? T('標準カテゴリは削除できません', 'Built-in cannot be deleted') : T('削除', 'Delete')}
              >
                ×
              </button>
            </div>
          );
        })}
      </div>

      <div className="cat-add">
        <div className="gp-lbl" style={{ marginBottom: 6 }}>
          {T('新しいカテゴリを追加', 'Add a new category')}
        </div>
        <div className="cat-add-grid">
          <input
            className="gp-input"
            placeholder={T('ID (例: sweets)', 'ID (e.g. sweets)')}
            value={draft.id}
            onChange={(e) => setDraft({ ...draft, id: e.target.value })}
          />
          <input
            className="gp-input"
            placeholder={T('アイコン (例: 甘)', 'Icon (e.g. 甘)')}
            value={draft.icon}
            onChange={(e) => setDraft({ ...draft, icon: e.target.value })}
          />
          <input
            className="gp-input"
            placeholder={T('日本語名', 'Japanese name')}
            value={draft.ja}
            onChange={(e) => setDraft({ ...draft, ja: e.target.value })}
          />
          <input
            className="gp-input"
            placeholder={T('英語名', 'English name')}
            value={draft.en}
            onChange={(e) => setDraft({ ...draft, en: e.target.value })}
          />
          <input
            className="gp-input"
            placeholder={T('Places検索キーワード', 'Places keyword')}
            value={draft.keyword}
            onChange={(e) => setDraft({ ...draft, keyword: e.target.value })}
          />
          <input
            className="gp-input"
            placeholder={T('Places type (任意)', 'Places type (optional)')}
            value={draft.type}
            onChange={(e) => setDraft({ ...draft, type: e.target.value })}
          />
        </div>
        <div style={{ display: 'flex', gap: 10, marginTop: 10, alignItems: 'center' }}>
          <button className="btn-primary" onClick={add} style={{ flex: 'none' }}>
            ＋ {T('追加', 'Add')}
          </button>
          {error && <div className="imp-msg imp-err" style={{ margin: 0, padding: '6px 10px' }}>{error}</div>}
        </div>
      </div>

      <div className="cat-actions">
        <button className="btn-primary" onClick={save}>
          {T('保存して適用', 'Save & apply')}
        </button>
        <button className="btn-secondary" onClick={reset}>
          {T('初期に戻す', 'Reset')}
        </button>
        <button className="btn-secondary" onClick={onClose}>
          {T('閉じる', 'Close')}
        </button>
      </div>

      <div className="gp-hint" style={{ marginTop: 8 }}>
        {T(
          'Places検索キーワードは「Google Places」タブから検索する際に使われます。Placesタイプは任意です（例: bakery, gym, museum）。',
          'The keyword is used when searching from the Google Places tab. Places type is optional (e.g. bakery, gym, museum).'
        )}
      </div>
    </div>
  );
}

Object.assign(window, { CategoryManager, loadCategories, saveCategories, BUILTIN_CAT_IDS });
