745 lines
26 KiB
Python
745 lines
26 KiB
Python
"""
|
|
粒子效果系统
|
|
负责管理天气和季节的粒子效果,如雨滴、雪花、雾气等
|
|
"""
|
|
|
|
import time
|
|
import random
|
|
from typing import Dict, Any, List, Optional, Tuple
|
|
import math
|
|
|
|
class ParticleEffects:
|
|
"""
|
|
粒子效果系统
|
|
负责管理天气和季节的粒子效果,包括粒子生成、更新和渲染
|
|
"""
|
|
|
|
def __init__(self, plugin):
|
|
"""
|
|
初始化粒子效果系统
|
|
|
|
Args:
|
|
plugin: 天气和季节系统插件实例
|
|
"""
|
|
self.plugin = plugin
|
|
self.enabled = False
|
|
self.initialized = False
|
|
|
|
# 粒子类型配置
|
|
self.particle_types = {
|
|
'rain_drop': {
|
|
'name': '雨滴',
|
|
'shape': 'line', # 'point', 'line', 'sprite'
|
|
'size_range': (0.1, 0.5),
|
|
'speed_range': (10.0, 25.0),
|
|
'lifetime_range': (0.5, 2.0),
|
|
'color': (0.7, 0.7, 1.0, 0.8),
|
|
'gravity': 9.8,
|
|
'wind_influence': 0.5,
|
|
'spawn_rate': 100, # 每秒生成数量
|
|
'max_particles': 2000
|
|
},
|
|
'snow_flake': {
|
|
'name': '雪花',
|
|
'shape': 'sprite',
|
|
'size_range': (0.2, 1.0),
|
|
'speed_range': (0.5, 3.0),
|
|
'lifetime_range': (3.0, 8.0),
|
|
'color': (1.0, 1.0, 1.0, 0.9),
|
|
'gravity': 0.1,
|
|
'wind_influence': 1.0,
|
|
'spawn_rate': 80,
|
|
'max_particles': 1500
|
|
},
|
|
'hail_stone': {
|
|
'name': '冰雹',
|
|
'shape': 'sprite',
|
|
'size_range': (0.3, 1.5),
|
|
'speed_range': (15.0, 30.0),
|
|
'lifetime_range': (1.0, 4.0),
|
|
'color': (0.9, 0.9, 1.0, 0.95),
|
|
'gravity': 12.0,
|
|
'wind_influence': 0.3,
|
|
'spawn_rate': 50,
|
|
'max_particles': 1000
|
|
},
|
|
'fog_particle': {
|
|
'name': '雾气',
|
|
'shape': 'sprite',
|
|
'size_range': (5.0, 15.0),
|
|
'speed_range': (0.1, 0.5),
|
|
'lifetime_range': (8.0, 20.0),
|
|
'color': (0.8, 0.8, 0.8, 0.2),
|
|
'gravity': 0.0,
|
|
'wind_influence': 0.8,
|
|
'spawn_rate': 20,
|
|
'max_particles': 500
|
|
},
|
|
'leaf_particle': {
|
|
'name': '落叶',
|
|
'shape': 'sprite',
|
|
'size_range': (0.5, 2.0),
|
|
'speed_range': (1.0, 5.0),
|
|
'lifetime_range': (5.0, 15.0),
|
|
'color': (0.6, 0.5, 0.3, 0.7),
|
|
'gravity': 1.0,
|
|
'wind_influence': 1.5,
|
|
'spawn_rate': 10,
|
|
'max_particles': 200
|
|
},
|
|
'dust_particle': {
|
|
'name': '尘土',
|
|
'shape': 'sprite',
|
|
'size_range': (0.1, 0.8),
|
|
'speed_range': (0.5, 3.0),
|
|
'lifetime_range': (2.0, 8.0),
|
|
'color': (0.8, 0.7, 0.6, 0.5),
|
|
'gravity': 0.2,
|
|
'wind_influence': 1.2,
|
|
'spawn_rate': 30,
|
|
'max_particles': 800
|
|
}
|
|
}
|
|
|
|
# 粒子池
|
|
self.particle_pool = []
|
|
self.active_particles = []
|
|
|
|
# 粒子发射器
|
|
self.particle_emitters = {}
|
|
|
|
# 粒子系统配置
|
|
self.system_config = {
|
|
'max_total_particles': 10000,
|
|
'lod_levels': {
|
|
'low': 0.3,
|
|
'medium': 0.6,
|
|
'high': 1.0
|
|
},
|
|
'quality_level': 'medium',
|
|
'distance_fade': True,
|
|
'collision_detection': False,
|
|
'particle_lod_distance': 50.0
|
|
}
|
|
|
|
# 粒子物理配置
|
|
self.physics_config = {
|
|
'gravity': (0.0, -9.8, 0.0),
|
|
'air_resistance': 0.1,
|
|
'wind_vector': (1.0, 0.0, 0.0),
|
|
'wind_strength': 1.0
|
|
}
|
|
|
|
# 粒子更新配置
|
|
self.update_interval = 0.016 # 60 FPS
|
|
self.last_update_time = 0.0
|
|
self.accumulator = 0.0
|
|
|
|
# 统计信息
|
|
self.stats = {
|
|
'particles_spawned': 0,
|
|
'particles_destroyed': 0,
|
|
'active_particles': 0,
|
|
'emitters_active': 0,
|
|
'total_update_time': 0.0
|
|
}
|
|
|
|
print("✓ 粒子效果系统已创建")
|
|
|
|
def initialize(self) -> bool:
|
|
"""
|
|
初始化粒子效果系统
|
|
|
|
Returns:
|
|
是否初始化成功
|
|
"""
|
|
try:
|
|
# 初始化粒子池
|
|
self._initialize_particle_pool()
|
|
|
|
self.initialized = True
|
|
print("✓ 粒子效果系统初始化完成")
|
|
return True
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子效果系统初始化失败: {e}")
|
|
import traceback
|
|
traceback.print_exc()
|
|
return False
|
|
|
|
def enable(self) -> bool:
|
|
"""
|
|
启用粒子效果系统
|
|
|
|
Returns:
|
|
是否启用成功
|
|
"""
|
|
try:
|
|
if not self.initialized:
|
|
print("✗ 粒子效果系统未初始化")
|
|
return False
|
|
|
|
self.enabled = True
|
|
print("✓ 粒子效果系统已启用")
|
|
return True
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子效果系统启用失败: {e}")
|
|
import traceback
|
|
traceback.print_exc()
|
|
return False
|
|
|
|
def disable(self):
|
|
"""禁用粒子效果系统"""
|
|
try:
|
|
self.enabled = False
|
|
self._clear_all_particles()
|
|
print("✓ 粒子效果系统已禁用")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子效果系统禁用失败: {e}")
|
|
import traceback
|
|
traceback.print_exc()
|
|
|
|
def finalize(self):
|
|
"""清理粒子效果系统资源"""
|
|
try:
|
|
self.disable()
|
|
self.initialized = False
|
|
print("✓ 粒子效果系统资源已清理")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子效果系统资源清理失败: {e}")
|
|
import traceback
|
|
traceback.print_exc()
|
|
|
|
def update(self, dt: float):
|
|
"""
|
|
更新粒子效果系统状态
|
|
|
|
Args:
|
|
dt: 时间增量
|
|
"""
|
|
try:
|
|
if not self.enabled:
|
|
return
|
|
|
|
# 累积时间
|
|
self.accumulator += dt
|
|
|
|
# 固定时间步长更新
|
|
while self.accumulator >= self.update_interval:
|
|
self._update_particles(self.update_interval)
|
|
self._update_emitters(self.update_interval)
|
|
self.accumulator -= self.update_interval
|
|
|
|
# 更新统计信息
|
|
self.stats['total_update_time'] += dt
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子效果系统更新失败: {e}")
|
|
import traceback
|
|
traceback.print_exc()
|
|
|
|
def _initialize_particle_pool(self):
|
|
"""初始化粒子池"""
|
|
try:
|
|
pool_size = self.system_config['max_total_particles']
|
|
|
|
for i in range(pool_size):
|
|
particle = {
|
|
'id': i,
|
|
'type': None,
|
|
'position': [0.0, 0.0, 0.0],
|
|
'velocity': [0.0, 0.0, 0.0],
|
|
'size': 1.0,
|
|
'color': [1.0, 1.0, 1.0, 1.0],
|
|
'lifetime': 1.0,
|
|
'age': 0.0,
|
|
'active': False,
|
|
'gravity': 0.0,
|
|
'wind_influence': 0.0
|
|
}
|
|
self.particle_pool.append(particle)
|
|
|
|
print(f"✓ 粒子池初始化完成,大小: {pool_size}")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子池初始化失败: {e}")
|
|
|
|
def _update_particles(self, dt: float):
|
|
"""更新粒子"""
|
|
try:
|
|
# 获取当前风力
|
|
wind_vector = self.physics_config['wind_vector']
|
|
wind_strength = self.physics_config['wind_strength']
|
|
|
|
# 获取重力
|
|
gravity = self.physics_config['gravity']
|
|
|
|
particles_to_remove = []
|
|
|
|
for particle in self.active_particles:
|
|
if not particle['active']:
|
|
continue
|
|
|
|
# 更新年龄
|
|
particle['age'] += dt
|
|
|
|
# 检查是否超出生命周期
|
|
if particle['age'] >= particle['lifetime']:
|
|
particles_to_remove.append(particle)
|
|
continue
|
|
|
|
# 应用重力
|
|
particle['velocity'][0] += gravity[0] * particle['gravity'] * dt
|
|
particle['velocity'][1] += gravity[1] * particle['gravity'] * dt
|
|
particle['velocity'][2] += gravity[2] * particle['gravity'] * dt
|
|
|
|
# 应用风力影响
|
|
wind_effect = wind_strength * particle['wind_influence']
|
|
particle['velocity'][0] += wind_vector[0] * wind_effect * dt
|
|
particle['velocity'][1] += wind_vector[1] * wind_effect * dt
|
|
particle['velocity'][2] += wind_vector[2] * wind_effect * dt
|
|
|
|
# 更新位置
|
|
particle['position'][0] += particle['velocity'][0] * dt
|
|
particle['position'][1] += particle['velocity'][1] * dt
|
|
particle['position'][2] += particle['velocity'][2] * dt
|
|
|
|
# 应用空气阻力
|
|
air_resistance = self.physics_config['air_resistance']
|
|
particle['velocity'][0] *= (1.0 - air_resistance * dt)
|
|
particle['velocity'][1] *= (1.0 - air_resistance * dt)
|
|
particle['velocity'][2] *= (1.0 - air_resistance * dt)
|
|
|
|
# 移除死亡粒子
|
|
for particle in particles_to_remove:
|
|
self._deactivate_particle(particle)
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子更新失败: {e}")
|
|
|
|
def _update_emitters(self, dt: float):
|
|
"""更新粒子发射器"""
|
|
try:
|
|
# 根据当前天气激活相应的粒子发射器
|
|
self._update_weather_emitters()
|
|
|
|
# 更新所有激活的发射器
|
|
for emitter_name, emitter in self.particle_emitters.items():
|
|
if emitter['active']:
|
|
self._spawn_particles_from_emitter(emitter, dt)
|
|
|
|
except Exception as e:
|
|
print(f"✗ 发射器更新失败: {e}")
|
|
|
|
def _update_weather_emitters(self):
|
|
"""根据当前天气更新粒子发射器"""
|
|
try:
|
|
if not self.plugin.weather_manager:
|
|
return
|
|
|
|
current_weather = self.plugin.weather_manager.get_current_weather()
|
|
weather_info = self.plugin.weather_manager.get_weather_info(current_weather)
|
|
|
|
if not weather_info:
|
|
return
|
|
|
|
# 获取天气对应的粒子效果
|
|
particle_effect = weather_info.get('particle_effect')
|
|
|
|
# 检查是否需要激活或更新粒子发射器
|
|
if particle_effect and particle_effect in self.particle_types:
|
|
# 检查发射器是否已经存在
|
|
if particle_effect not in self.particle_emitters:
|
|
# 创建粒子发射器
|
|
self._create_particle_emitter(particle_effect)
|
|
else:
|
|
# 确保发射器处于激活状态
|
|
self.particle_emitters[particle_effect]['active'] = True
|
|
else:
|
|
# 停用所有天气相关的发射器
|
|
for emitter_name in list(self.particle_emitters.keys()):
|
|
if emitter_name in self.particle_types:
|
|
self.particle_emitters[emitter_name]['active'] = False
|
|
|
|
except Exception as e:
|
|
print(f"✗ 天气发射器更新失败: {e}")
|
|
|
|
def _create_particle_emitter(self, particle_type: str):
|
|
"""
|
|
创建粒子发射器
|
|
|
|
Args:
|
|
particle_type: 粒子类型
|
|
"""
|
|
try:
|
|
if particle_type not in self.particle_types:
|
|
return
|
|
|
|
emitter_config = self.particle_types[particle_type]
|
|
|
|
emitter = {
|
|
'name': particle_type,
|
|
'type': particle_type,
|
|
'config': emitter_config,
|
|
'position': [0.0, 50.0, 0.0], # 默认在空中
|
|
'area': [100.0, 0.0, 100.0], # 发射区域大小
|
|
'active': True,
|
|
'last_spawn_time': 0.0,
|
|
'spawn_accumulator': 0.0
|
|
}
|
|
|
|
self.particle_emitters[particle_type] = emitter
|
|
print(f"✓ 粒子发射器已创建: {emitter_config['name']}")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子发射器创建失败: {e}")
|
|
|
|
def _spawn_particles_from_emitter(self, emitter: Dict[str, Any], dt: float):
|
|
"""
|
|
从发射器生成粒子
|
|
|
|
Args:
|
|
emitter: 发射器数据
|
|
dt: 时间增量
|
|
"""
|
|
try:
|
|
config = emitter['config']
|
|
|
|
# 计算应该生成的粒子数量
|
|
emitter['spawn_accumulator'] += dt
|
|
spawn_interval = 1.0 / config['spawn_rate']
|
|
|
|
particles_to_spawn = int(emitter['spawn_accumulator'] / spawn_interval)
|
|
emitter['spawn_accumulator'] -= particles_to_spawn * spawn_interval
|
|
|
|
# 限制生成数量不超过最大粒子数
|
|
active_count = len([p for p in self.active_particles if p['type'] == emitter['type']])
|
|
max_particles = config['max_particles']
|
|
|
|
particles_to_spawn = min(particles_to_spawn, max_particles - active_count)
|
|
|
|
# 生成粒子
|
|
for i in range(particles_to_spawn):
|
|
self._spawn_particle(emitter)
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子生成失败: {e}")
|
|
|
|
def _spawn_particle(self, emitter: Dict[str, Any]):
|
|
"""
|
|
生成单个粒子
|
|
|
|
Args:
|
|
emitter: 发射器数据
|
|
"""
|
|
try:
|
|
# 检查是否还有可用的粒子
|
|
available_particle = None
|
|
for particle in self.particle_pool:
|
|
if not particle['active']:
|
|
available_particle = particle
|
|
break
|
|
|
|
if not available_particle:
|
|
# 粒子池已满,移除最老的粒子
|
|
if self.active_particles:
|
|
oldest_particle = self.active_particles[0]
|
|
self._deactivate_particle(oldest_particle)
|
|
available_particle = oldest_particle
|
|
else:
|
|
return # 无法生成新粒子
|
|
|
|
config = emitter['config']
|
|
|
|
# 初始化粒子属性
|
|
available_particle['type'] = emitter['type']
|
|
available_particle['active'] = True
|
|
|
|
# 随机位置(在发射器区域内)
|
|
half_area = [emitter['area'][i] / 2 for i in range(3)]
|
|
available_particle['position'][0] = emitter['position'][0] + random.uniform(-half_area[0], half_area[0])
|
|
available_particle['position'][1] = emitter['position'][1] # Y轴保持不变
|
|
available_particle['position'][2] = emitter['position'][2] + random.uniform(-half_area[2], half_area[2])
|
|
|
|
# 随机速度
|
|
speed = random.uniform(config['speed_range'][0], config['speed_range'][1])
|
|
angle = random.uniform(0, 2 * math.pi)
|
|
available_particle['velocity'][0] = math.cos(angle) * speed
|
|
available_particle['velocity'][1] = -random.uniform(0.5, 1.0) * speed # 主要向下
|
|
available_particle['velocity'][2] = math.sin(angle) * speed
|
|
|
|
# 随机大小
|
|
available_particle['size'] = random.uniform(config['size_range'][0], config['size_range'][1])
|
|
|
|
# 颜色
|
|
available_particle['color'] = list(config['color'])
|
|
|
|
# 生命周期
|
|
available_particle['lifetime'] = random.uniform(config['lifetime_range'][0], config['lifetime_range'][1])
|
|
available_particle['age'] = 0.0
|
|
|
|
# 物理属性
|
|
available_particle['gravity'] = config['gravity']
|
|
available_particle['wind_influence'] = config['wind_influence']
|
|
|
|
# 添加到激活列表
|
|
if available_particle not in self.active_particles:
|
|
self.active_particles.append(available_particle)
|
|
|
|
# 更新统计信息
|
|
self.stats['particles_spawned'] += 1
|
|
|
|
except Exception as e:
|
|
print(f"✗ 单个粒子生成失败: {e}")
|
|
|
|
def _deactivate_particle(self, particle: Dict[str, Any]):
|
|
"""
|
|
停用粒子
|
|
|
|
Args:
|
|
particle: 粒子数据
|
|
"""
|
|
try:
|
|
particle['active'] = False
|
|
|
|
# 从激活列表中移除
|
|
if particle in self.active_particles:
|
|
self.active_particles.remove(particle)
|
|
|
|
# 更新统计信息
|
|
self.stats['particles_destroyed'] += 1
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子停用失败: {e}")
|
|
|
|
def _clear_all_particles(self):
|
|
"""清除所有粒子"""
|
|
try:
|
|
for particle in self.active_particles:
|
|
particle['active'] = False
|
|
|
|
self.active_particles.clear()
|
|
print("✓ 所有粒子已清除")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子清除失败: {e}")
|
|
|
|
def get_active_particles(self) -> List[Dict[str, Any]]:
|
|
"""
|
|
获取激活的粒子列表
|
|
|
|
Returns:
|
|
激活的粒子列表
|
|
"""
|
|
return [p for p in self.active_particles if p['active']]
|
|
|
|
def get_particle_types_list(self) -> List[str]:
|
|
"""
|
|
获取所有粒子类型列表
|
|
|
|
Returns:
|
|
粒子类型名称列表
|
|
"""
|
|
return list(self.particle_types.keys())
|
|
|
|
def get_particle_type_info(self, particle_type: str) -> Optional[Dict[str, Any]]:
|
|
"""
|
|
获取粒子类型信息
|
|
|
|
Args:
|
|
particle_type: 粒子类型名称
|
|
|
|
Returns:
|
|
粒子类型信息字典或None
|
|
"""
|
|
try:
|
|
if particle_type in self.particle_types:
|
|
return self.particle_types[particle_type].copy()
|
|
return None
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子类型信息获取失败: {e}")
|
|
return None
|
|
|
|
def create_custom_emitter(self, emitter_name: str, config: Dict[str, Any]):
|
|
"""
|
|
创建自定义粒子发射器
|
|
|
|
Args:
|
|
emitter_name: 发射器名称
|
|
config: 发射器配置
|
|
"""
|
|
try:
|
|
emitter = {
|
|
'name': emitter_name,
|
|
'type': 'custom',
|
|
'config': config,
|
|
'position': config.get('position', [0.0, 0.0, 0.0]),
|
|
'area': config.get('area', [10.0, 0.0, 10.0]),
|
|
'active': config.get('active', True),
|
|
'last_spawn_time': 0.0,
|
|
'spawn_accumulator': 0.0
|
|
}
|
|
|
|
self.particle_emitters[emitter_name] = emitter
|
|
print(f"✓ 自定义粒子发射器已创建: {emitter_name}")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 自定义粒子发射器创建失败: {e}")
|
|
|
|
def activate_emitter(self, emitter_name: str):
|
|
"""
|
|
激活粒子发射器
|
|
|
|
Args:
|
|
emitter_name: 发射器名称
|
|
"""
|
|
try:
|
|
if emitter_name in self.particle_emitters:
|
|
self.particle_emitters[emitter_name]['active'] = True
|
|
print(f"✓ 粒子发射器已激活: {emitter_name}")
|
|
else:
|
|
print(f"✗ 粒子发射器不存在: {emitter_name}")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子发射器激活失败: {e}")
|
|
|
|
def deactivate_emitter(self, emitter_name: str):
|
|
"""
|
|
停用粒子发射器
|
|
|
|
Args:
|
|
emitter_name: 发射器名称
|
|
"""
|
|
try:
|
|
if emitter_name in self.particle_emitters:
|
|
self.particle_emitters[emitter_name]['active'] = False
|
|
print(f"✓ 粒子发射器已停用: {emitter_name}")
|
|
else:
|
|
print(f"✗ 粒子发射器不存在: {emitter_name}")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 粒子发射器停用失败: {e}")
|
|
|
|
def set_emitter_position(self, emitter_name: str, position: Tuple[float, float, float]):
|
|
"""
|
|
设置发射器位置
|
|
|
|
Args:
|
|
emitter_name: 发射器名称
|
|
position: 位置坐标(x, y, z)
|
|
"""
|
|
try:
|
|
if emitter_name in self.particle_emitters:
|
|
self.particle_emitters[emitter_name]['position'] = list(position)
|
|
print(f"✓ 发射器位置已设置: {emitter_name} = {position}")
|
|
else:
|
|
print(f"✗ 粒子发射器不存在: {emitter_name}")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 发射器位置设置失败: {e}")
|
|
|
|
def set_emitter_area(self, emitter_name: str, area: Tuple[float, float, float]):
|
|
"""
|
|
设置发射器区域大小
|
|
|
|
Args:
|
|
emitter_name: 发射器名称
|
|
area: 区域大小(x, y, z)
|
|
"""
|
|
try:
|
|
if emitter_name in self.particle_emitters:
|
|
self.particle_emitters[emitter_name]['area'] = list(area)
|
|
print(f"✓ 发射器区域已设置: {emitter_name} = {area}")
|
|
else:
|
|
print(f"✗ 粒子发射器不存在: {emitter_name}")
|
|
|
|
except Exception as e:
|
|
print(f"✗ 发射器区域设置失败: {e}")
|
|
|
|
def set_physics_config(self, config: Dict[str, Any]):
|
|
"""
|
|
设置物理配置
|
|
|
|
Args:
|
|
config: 物理配置字典
|
|
"""
|
|
self.physics_config.update(config)
|
|
print(f"✓ 物理配置已更新: {self.physics_config}")
|
|
|
|
def get_physics_config(self) -> Dict[str, Any]:
|
|
"""
|
|
获取物理配置
|
|
|
|
Returns:
|
|
物理配置字典
|
|
"""
|
|
return self.physics_config.copy()
|
|
|
|
def set_system_config(self, config: Dict[str, Any]):
|
|
"""
|
|
设置系统配置
|
|
|
|
Args:
|
|
config: 系统配置字典
|
|
"""
|
|
self.system_config.update(config)
|
|
print(f"✓ 系统配置已更新: {self.system_config}")
|
|
|
|
def get_system_config(self) -> Dict[str, Any]:
|
|
"""
|
|
获取系统配置
|
|
|
|
Returns:
|
|
系统配置字典
|
|
"""
|
|
return self.system_config.copy()
|
|
|
|
def set_update_interval(self, interval: float):
|
|
"""
|
|
设置更新间隔
|
|
|
|
Args:
|
|
interval: 更新间隔(秒)
|
|
"""
|
|
self.update_interval = max(0.001, min(0.1, interval))
|
|
print(f"✓ 粒子更新间隔设置为: {interval} 秒")
|
|
|
|
def get_stats(self) -> Dict[str, Any]:
|
|
"""
|
|
获取统计信息
|
|
|
|
Returns:
|
|
统计信息字典
|
|
"""
|
|
self.stats['active_particles'] = len(self.active_particles)
|
|
self.stats['emitters_active'] = len([e for e in self.particle_emitters.values() if e['active']])
|
|
return self.stats.copy()
|
|
|
|
def reset_stats(self):
|
|
"""重置统计信息"""
|
|
self.stats = {
|
|
'particles_spawned': 0,
|
|
'particles_destroyed': 0,
|
|
'active_particles': 0,
|
|
'emitters_active': 0,
|
|
'total_update_time': 0.0
|
|
}
|
|
print("✓ 粒子效果系统统计信息已重置")
|
|
|
|
def is_emitter_active(self, emitter_name: str) -> bool:
|
|
"""
|
|
检查发射器是否激活
|
|
|
|
Args:
|
|
emitter_name: 发射器名称
|
|
|
|
Returns:
|
|
发射器是否激活
|
|
"""
|
|
if emitter_name in self.particle_emitters:
|
|
return self.particle_emitters[emitter_name]['active']
|
|
return False |