/**
 * Inventory and Crafting System Manager
 * Handles instruments, materials, equipment, and crafting
 */

export class InventoryManager {
  store: any;
  
  constructor(gameStore: any) {
    this.store = gameStore;
  }

  /**
   * Add an instrument to inventory
   * @param {Object} instrument - Instrument object
   */
  addInstrument(instrument) {
    this.store.getState().addInstrument(instrument);
  }

  /**
   * Check if player has an instrument
   * @param {string} instrumentId - Instrument identifier
   * @returns {boolean} - Has instrument
   */
  hasInstrument(instrumentId) {
    const { instruments } = this.store.getState().player.inventory;
    return instruments.some(inst => inst.id === instrumentId);
  }

  /**
   * Get instrument by ID from inventory
   * @param {string} instrumentId - Instrument identifier
   * @returns {Object|null} - Instrument or null
   */
  getInstrument(instrumentId) {
    const { instruments } = this.store.getState().player.inventory;
    return instruments.find(inst => inst.id === instrumentId) || null;
  }

  /**
   * Equip an instrument in a slot
   * @param {string} slot - Equipment slot (guitar, keyboard, drums, microphone, studio)
   * @param {string} instrumentId - Instrument identifier
   * @returns {boolean} - Success
   */
  equipInstrument(slot, instrumentId) {
    if (!this.hasInstrument(instrumentId)) {
      return false;
    }

    this.store.getState().equipInstrument(slot, instrumentId);
    return true;
  }

  /**
   * Unequip an instrument from a slot
   * @param {string} slot - Equipment slot
   */
  unequipInstrument(slot) {
    this.store.getState().equipInstrument(slot, null);
  }

  /**
   * Get currently equipped instruments
   * @returns {Object} - Equipped instruments
   */
  getEquippedInstruments() {
    return this.store.getState().player.inventory.equipped;
  }

  /**
   * Calculate total equipment bonus
   * @returns {Object} - Bonuses { rockBonus: 0.3, jazzBonus: 0.1, qualityMultiplier: 1.5 }
   */
  calculateEquipmentBonus(allInstruments) {
    const equipped = this.getEquippedInstruments();
    const bonuses = {
      rockBonus: 0,
      jazzBonus: 0,
      bluesBonus: 0,
      classicalBonus: 0,
      electronicBonus: 0,
      qualityMultiplier: 1.0,
      fanMultiplier: 1.0
    };

    Object.values(equipped).forEach(instrumentId => {
      if (instrumentId) {
        const instrument = allInstruments.find(inst => inst.id === instrumentId);
        if (instrument && instrument.stats) {
          Object.keys(instrument.stats).forEach(stat => {
            if (stat.includes('Bonus')) {
              bonuses[stat] = (bonuses[stat] || 0) + instrument.stats[stat];
            } else if (stat.includes('Multiplier')) {
              bonuses[stat] *= instrument.stats[stat];
            }
          });
        }
      }
    });

    return bonuses;
  }

  /**
   * Add crafting materials
   * @param {string} materialId - Material identifier
   * @param {number} quantity - Quantity to add
   */
  addMaterial(materialId, quantity) {
    this.store.getState().addMaterial(materialId, quantity);
  }

  /**
   * Check if player has enough materials
   * @param {string} materialId - Material identifier
   * @param {number} quantity - Required quantity
   * @returns {boolean} - Has enough
   */
  hasMaterials(materialId, quantity) {
    const { materials } = this.store.getState().player.inventory;
    return (materials[materialId] || 0) >= quantity;
  }

  /**
   * Check if a recipe can be crafted
   * @param {Object} recipe - Crafting recipe
   * @returns {boolean} - Can craft
   */
  canCraft(recipe) {
    if (!recipe.craftingMaterials) return false;

    for (const material of recipe.craftingMaterials) {
      if (!this.hasMaterials(material.item, material.quantity)) {
        return false;
      }
    }

    return true;
  }

  /**
   * Craft an item from a recipe
   * @param {Object} recipe - Crafting recipe
   * @returns {boolean} - Success
   */
  craftItem(recipe) {
    if (!this.canCraft(recipe)) {
      return false;
    }

    // Remove materials
    recipe.craftingMaterials.forEach(material => {
      this.store.getState().removeMaterial(material.item, material.quantity);
    });

    // Add crafted instrument
    this.addInstrument(recipe);

    return true;
  }

  /**
   * Get all craftable recipes based on available materials
   * @param {Array} allRecipes - All crafting recipes
   * @returns {Array} - Craftable recipes
   */
  getCraftableRecipes(allRecipes) {
    return allRecipes.filter(recipe => this.canCraft(recipe));
  }

  /**
   * Dismantle an instrument for materials
   * @param {string} instrumentId - Instrument to dismantle
   * @param {Object} instrument - Instrument definition with materials
   * @returns {boolean} - Success
   */
  dismantleInstrument(instrumentId, instrument) {
    if (!this.hasInstrument(instrumentId)) {
      return false;
    }

    // Remove from inventory
    const { instruments } = this.store.getState().player.inventory;
    const newInstruments = instruments.filter(inst => inst.id !== instrumentId);
    
    // Return 50% of materials
    if (instrument.craftingMaterials) {
      instrument.craftingMaterials.forEach(material => {
        const returnAmount = Math.floor(material.quantity * 0.5);
        this.addMaterial(material.item, returnAmount);
      });
    }

    return true;
  }

  /**
   * Get total inventory value (for statistics)
   * @param {Array} allInstruments - All instrument definitions
   * @returns {number} - Total value
   */
  getTotalInventoryValue(allInstruments) {
    const { instruments } = this.store.getState().player.inventory;
    
    return instruments.reduce((total, inst) => {
      const definition = allInstruments.find(d => d.id === inst.id);
      return total + (definition?.value || 0);
    }, 0);
  }
}

