package model

// EnemyType names an archetype family (legacy consts for tuning / combat branches).
type EnemyType string

const (
	EnemyWolf           EnemyType = "wolf"
	EnemyBoar           EnemyType = "boar"
	EnemyZombie         EnemyType = "zombie"
	EnemySpider         EnemyType = "spider"
	EnemyOrc            EnemyType = "orc"
	EnemySkeletonArcher EnemyType = "skeleton_archer"
	EnemyBattleLizard   EnemyType = "battle_lizard"
	EnemyFireDemon      EnemyType = "fire_demon"
	EnemyIceGuardian    EnemyType = "ice_guardian"
	EnemySkeletonKing   EnemyType = "skeleton_king"
	EnemyWaterElement   EnemyType = "water_element"
	EnemyForestWarden   EnemyType = "forest_warden"
	EnemyLightningTitan EnemyType = "lightning_titan"
)

type SpecialAbility string

const (
	AbilityBurn           SpecialAbility = "burn"
	AbilitySlow           SpecialAbility = "slow"
	AbilityCritical       SpecialAbility = "critical"
	AbilityPoison         SpecialAbility = "poison"
	AbilityFreeze         SpecialAbility = "freeze"
	AbilityIceSlow        SpecialAbility = "ice_slow"
	AbilityStun           SpecialAbility = "stun"
	AbilityDodge          SpecialAbility = "dodge"
	AbilityRegen          SpecialAbility = "regen"
	AbilityBurst          SpecialAbility = "burst"
	AbilityChainLightning SpecialAbility = "chain_lightning"
	AbilitySummon         SpecialAbility = "summon"
)

// Enemy is a DB template row or a runtime-scaled instance.
// Slug is the unique `enemies.type` column (JSON "type" for API — visual key).
// Archetype groups templates for quests and some combat logic.
type Enemy struct {
	ID               int64            `json:"id"`
	Slug             string           `json:"type"` // DB `type` — unique template key
	Archetype        string           `json:"archetype"`
	Biome            string           `json:"biome,omitempty"` // canonical world band id (e.g. meadow, forest)
	Name             string           `json:"name"`
	HP               int              `json:"hp"`
	MaxHP            int              `json:"maxHp"`
	Attack           int              `json:"attack"`
	Defense          int              `json:"defense"`
	Speed            float64          `json:"speed"`
	CritChance       float64          `json:"critChance"`
	MinLevel         int              `json:"minLevel"`
	MaxLevel         int              `json:"maxLevel"`
	BaseLevel        int              `json:"baseLevel"`
	LevelVariance    float64          `json:"levelVariance"`
	MaxHeroLevelDiff int              `json:"maxHeroLevelDiff"`
	HPPerLevel       float64          `json:"hpPerLevel"`
	AttackPerLevel   float64          `json:"attackPerLevel"`
	DefensePerLevel  float64          `json:"defensePerLevel"`
	XPPerLevel       float64          `json:"xpPerLevel"`
	GoldPerLevel     float64          `json:"goldPerLevel"`
	Level            int              `json:"level,omitempty"`
	XPReward         int64            `json:"xpReward"`
	GoldReward       int64            `json:"goldReward"`
	SpecialAbilities []SpecialAbility `json:"specialAbilities,omitempty"`
	IsElite          bool             `json:"isElite"`
	AttackCount      int              `json:"-"`
}

func (e *Enemy) IsAlive() bool {
	return e.HP > 0
}

func (e *Enemy) HasAbility(a SpecialAbility) bool {
	for _, ab := range e.SpecialAbilities {
		if ab == a {
			return true
		}
	}
	return false
}

// EnemyTemplates is all rows loaded from DB (order undefined).
var EnemyTemplates []Enemy

var enemyTemplatesBySlug map[string]Enemy

// SetEnemyTemplates replaces global templates and rebuilds slug index.
func SetEnemyTemplates(next []Enemy) {
	EnemyTemplates = next
	m := make(map[string]Enemy, len(next))
	for _, e := range next {
		if e.Slug != "" {
			m[e.Slug] = e
		}
	}
	enemyTemplatesBySlug = m
}

// EnemyBySlug returns a template by DB `type` (slug).
func EnemyBySlug(slug string) (Enemy, bool) {
	if enemyTemplatesBySlug == nil {
		return Enemy{}, false
	}
	e, ok := enemyTemplatesBySlug[slug]
	return e, ok
}

// TemplatesByArchetype returns templates with the given archetype.
func TemplatesByArchetype(archetype string) []Enemy {
	var out []Enemy
	for _, e := range EnemyTemplates {
		if e.Archetype == archetype {
			out = append(out, e)
		}
	}
	return out
}

// FirstTemplateByArchetype returns one template for archetype-keyed logic (e.g. loot/sim).
func FirstTemplateByArchetype(archetype string) (Enemy, bool) {
	for _, e := range EnemyTemplates {
		if e.Archetype == archetype {
			return e, true
		}
	}
	return Enemy{}, false
}
