/**
 * Player Privacy Panel Menu Wrapper
 * 
 * Wrapper class that adapts PlayerPrivacyPanel to FoundryVTT's settings menu system.
 * The settings menu system expects a constructor that accepts options,
 * but PlayerPrivacyPanel requires DI dependencies. This wrapper handles that.
 */

import { PlayerPrivacyPanel } from './PlayerPrivacyPanel.js';

/**
 * Static references to DI dependencies (set during module initialization).
 */
let _adapter = null;
let _playerPrivacyManager = null;
let _portraitFallbackHandler = null;

/**
 * Flag to track if dependencies have been initialized.
 */
let _isInitialized = false;

/**
 * Initialize static dependencies.
 * Called once during module initialization.
 * @param {import('../../foundry/FoundryAdapter.js').FoundryAdapter} adapter
 * @param {import('../../core/PlayerPrivacyManager.js').PlayerPrivacyManager} playerPrivacyManager
 * @param {import('../../core/PortraitFallbackHandler.js').PortraitFallbackHandler} [portraitFallbackHandler]
 */
export function initPlayerPrivacyPanelMenu(adapter, playerPrivacyManager, portraitFallbackHandler = null) {
  if (!adapter || typeof adapter !== 'object') {
    throw new TypeError('initPlayerPrivacyPanelMenu: adapter is required');
  }
  if (!playerPrivacyManager || typeof playerPrivacyManager !== 'object') {
    throw new TypeError('initPlayerPrivacyPanelMenu: playerPrivacyManager is required');
  }
  
  _adapter = adapter;
  _playerPrivacyManager = playerPrivacyManager;
  _portraitFallbackHandler = portraitFallbackHandler;
  _isInitialized = true;
}

/**
 * Check if dependencies have been initialized.
 * @returns {boolean}
 */
export function isInitialized() {
  return _isInitialized;
}

/**
 * Conditional base class — test environment lacks foundry globals.
 */
const _MenuAppBase =
  typeof foundry !== 'undefined' &&
  foundry.applications?.api?.ApplicationV2
    ? foundry.applications.api.ApplicationV2
    : class _FallbackMenuApp {
        static DEFAULT_OPTIONS = {};
        constructor() {}
        get rendered() { return this._rendered ?? false; }
        set rendered(v) { this._rendered = v; }
        get element() { return this._element ?? null; }
        set element(v) { this._element = v; }
        async render() { this._rendered = true; }
        async close() { this._rendered = false; }
      };

/**
 * PlayerPrivacyPanelMenu - Wrapper for Foundry settings menu.
 * When instantiated by Foundry, it creates a PlayerPrivacyPanel with the current user as target.
 * Extends ApplicationV2 so it passes Foundry's registerMenu validation.
 */
export class PlayerPrivacyPanelMenu extends _MenuAppBase {
  /**
   * @param {object} [options] - Foundry options (unused, but required by settings menu API)
   */
  constructor(options = {}) {
    super(options);
    if (!_isInitialized) {
      throw new Error('PlayerPrivacyPanelMenu: Dependencies not initialized. Call initPlayerPrivacyPanelMenu first.');
    }
    
    // Get the current user's ID
    const currentUser = _adapter.users.current?.();
    if (!currentUser?.id) {
      throw new Error('PlayerPrivacyPanelMenu: Cannot determine current user ID');
    }
    
    // Validate that id is a non-empty string
    if (typeof currentUser.id !== 'string' || currentUser.id.length === 0) {
      throw new TypeError('PlayerPrivacyPanelMenu: current user ID must be a non-empty string');
    }
    
    // Create the actual panel with DI
    this._panel = new PlayerPrivacyPanel(
      _adapter,
      _playerPrivacyManager,
      currentUser.id,
      _portraitFallbackHandler,
      options
    );
  }

  /**
   * Delegate render to the inner panel.
   * @param {boolean|object} [force] - Render options
   * @returns {Promise<void>}
   */
  async render(force) {
    return this._panel.render(force);
  }

  /**
   * Delegate close to the inner panel.
   * @returns {Promise<void>}
   */
  async close() {
    return this._panel.close();
  }

  /**
   * Get the inner panel.
   * @returns {PlayerPrivacyPanel}
   */
  get panel() {
    return this._panel;
  }

  // Delegate all other properties/methods to the inner panel
  /**
   * Get rendered state from inner panel.
   * @returns {boolean}
   */
  get rendered() {
    return this._panel.rendered;
  }

  /**
   * Get element from inner panel.
   * @returns {HTMLElement|null}
   */
  get element() {
    return this._panel.element;
  }
}
