EG/plugins/user/pathfinding_algorithms/plugin.py
2025-12-12 16:16:15 +08:00

616 lines
24 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

"""
路径规划算法插件主文件
提供多种路径规划算法的实现和可视化工具
"""
import time
import json
from plugins.plugin_manager import BasePlugin
from .core.algorithm_manager import AlgorithmManager
from .visualization.visualization_manager import VisualizationManager
from .editor.pathfinding_editor import PathfindingEditor
class Plugin(BasePlugin):
"""
路径规划算法插件
提供多种经典和现代路径规划算法的实现
"""
def __init__(self, plugin_manager, name):
super().__init__(plugin_manager, name)
self.config = {
"version": "1.0.0",
"author": "EG Team",
"description": "路径规划算法插件,包含多种经典和现代路径规划算法实现"
}
# 核心组件
self.algorithm_manager = None
self.visualization_manager = None
self.editor = None
# GUI元素
self.gui_elements = []
# 事件处理器
self.event_handlers = {}
# 插件状态
self.is_initialized = False
self.is_enabled = False
# 性能监控
self.performance_stats = {
'initialization_time': 0.0,
'enable_time': 0.0,
'last_update_time': 0.0,
'total_updates': 0
}
# 当前场景数据
self.current_grid = None
self.current_start = (0, 0)
self.current_goal = (9, 9)
def initialize(self) -> bool:
"""
初始化插件
"""
try:
if self.is_initialized:
return True
init_start_time = time.time()
print(f"初始化路径规划算法插件: {self.name}")
# 初始化算法管理器
self.algorithm_manager = AlgorithmManager()
# 初始化可视化管理器
self.visualization_manager = VisualizationManager(self.plugin_manager.world)
# 初始化编辑器
self.editor = PathfindingEditor(
self.plugin_manager.world,
self.algorithm_manager,
self.visualization_manager
)
self.is_initialized = True
self.performance_stats['initialization_time'] = time.time() - init_start_time
print("✓ 路径规划算法插件初始化完成")
return True
except Exception as e:
print(f"✗ 路径规划算法插件初始化失败: {e}")
import traceback
traceback.print_exc()
return False
def enable(self) -> bool:
"""
启用插件
"""
if not super().enable():
return False
if self.is_enabled:
return True
try:
enable_start_time = time.time()
print(f"启用路径规划算法插件: {self.name}")
# 启用可视化管理器
if self.visualization_manager:
self.visualization_manager.enable()
# 注册事件处理器
self._register_event_handlers()
# 创建GUI界面
self._create_gui()
self.is_enabled = True
self.performance_stats['enable_time'] = time.time() - enable_start_time
print("✓ 路径规划算法插件启用成功")
return True
except Exception as e:
print(f"✗ 路径规划算法插件启用失败: {e}")
import traceback
traceback.print_exc()
return False
def disable(self) -> bool:
"""
禁用插件
"""
if not super().disable():
return False
if not self.is_enabled:
return True
try:
print(f"禁用路径规划算法插件: {self.name}")
# 清理GUI界面
self._cleanup_gui()
# 移除事件处理器
self._unregister_event_handlers()
# 禁用可视化管理器
if self.visualization_manager:
self.visualization_manager.disable()
self.is_enabled = False
print("✓ 路径规划算法插件禁用成功")
return True
except Exception as e:
print(f"✗ 路径规划算法插件禁用失败: {e}")
import traceback
traceback.print_exc()
return False
def finalize(self):
"""
清理插件资源
"""
print(f"清理路径规划算法插件资源: {self.name}")
# 清理所有组件
if self.editor:
self.editor.cleanup()
self.editor = None
if self.visualization_manager:
self.visualization_manager.cleanup()
self.visualization_manager = None
if self.algorithm_manager:
self.algorithm_manager = None
self.is_initialized = False
self.is_enabled = False
self.current_grid = None
def _register_event_handlers(self):
"""
注册事件处理器
"""
world = self.plugin_manager.world
# 路径规划系统控制快捷键
self.event_handlers['f1'] = self.toggle_editor
self.event_handlers['f2'] = self.toggle_visualization
self.event_handlers['f3'] = self.run_demo
self.event_handlers['f4'] = self.clear_visualization
self.event_handlers['f5'] = self.compare_algorithms
self.event_handlers['f6'] = self.show_stats
self.event_handlers['f7'] = self.generate_report
self.event_handlers['f8'] = self.optimize_paths
self.event_handlers['f9'] = self.generate_random_scenario
self.event_handlers['f10'] = self.toggle_animation
self.event_handlers['f11'] = self.show_algorithm_info
self.event_handlers['f12'] = self.export_detailed_report
# 注册事件
for event, handler in self.event_handlers.items():
world.accept(event, handler)
world.accept(event.upper(), handler) # 同时注册大写事件
def _unregister_event_handlers(self):
"""
移除事件处理器
"""
world = self.plugin_manager.world
for event in self.event_handlers.keys():
world.ignore(event)
world.ignore(event.upper())
self.event_handlers.clear()
def _create_gui(self):
"""
创建GUI界面
"""
try:
world = self.plugin_manager.world
# 检查是否有GUI管理器
if not hasattr(world, 'gui_manager') or not world.gui_manager:
print("⚠ GUI管理器不可用跳过GUI创建")
return
gui_manager = world.gui_manager
# 创建路径规划控制面板
panel_button = gui_manager.createGUIButton(
pos=(0.02, 0, 0.75),
text="路径规划",
size=0.06
)
self.gui_elements.append(panel_button)
# 创建功能按钮
functions = [
("编辑器 [F1]", self.toggle_editor),
("可视化 [F2]", self.toggle_visualization),
("运行演示 [F3]", self.run_demo),
("清除视图 [F4]", self.clear_visualization),
("算法比较 [F5]", self.compare_algorithms),
("显示统计 [F6]", self.show_stats),
("生成报告 [F7]", self.generate_report),
("优化路径 [F8]", self.optimize_paths),
("随机场景 [F9]", self.generate_random_scenario),
("动画切换 [F10]", self.toggle_animation),
("算法信息 [F11]", self.show_algorithm_info),
("导出报告 [F12]", self.export_detailed_report)
]
for i, (name, callback) in enumerate(functions):
button = gui_manager.createGUIButton(
pos=(0.02, 0, 0.68 - i * 0.055),
text=name,
size=0.045
)
self.gui_elements.append(button)
world.accept(f"pathfinding_function_{i}", callback)
except Exception as e:
print(f"⚠ GUI创建失败: {e}")
def _cleanup_gui(self):
"""
清理GUI界面
"""
try:
world = self.plugin_manager.world
if hasattr(world, 'gui_manager') and world.gui_manager:
gui_manager = world.gui_manager
# 删除所有GUI元素
for element in self.gui_elements:
gui_manager.deleteGUIElement(element)
self.gui_elements.clear()
except Exception as e:
print(f"⚠ GUI清理失败: {e}")
# 事件处理方法
def toggle_editor(self):
"""切换编辑器显示"""
if self.editor:
self.editor.toggle_visibility()
print("✓ 编辑器显示已切换")
def toggle_visualization(self):
"""切换可视化显示"""
if self.visualization_manager:
self.visualization_manager.toggle_visibility()
print("✓ 可视化显示已切换")
def run_demo(self):
"""运行演示"""
if self.algorithm_manager and self.visualization_manager:
print("✓ 运行路径规划演示...")
# 运行一个简单的演示
from .utils.demo_scenarios import create_simple_grid
self.current_grid = create_simple_grid(10, 10)
self.current_start = (0, 0)
self.current_goal = (9, 9)
# 使用A*算法查找路径
path, stats = self.algorithm_manager.find_path("astar", self.current_grid, self.current_start, self.current_goal)
if path:
print(f"✓ 找到路径,长度: {len(path)}")
print(f" 访问节点数: {stats.get('nodes_visited', 0)}")
print(f" 耗时: {stats.get('time_taken', 0):.6f}")
# 可视化路径
self.visualization_manager.visualize_path(path, self.current_grid)
self.visualization_manager.visualize_grid(self.current_grid)
else:
print("✗ 未找到路径")
def clear_visualization(self):
"""清除可视化"""
if self.visualization_manager:
self.visualization_manager.clear_visualization()
print("✓ 可视化已清除")
def compare_algorithms(self):
"""比较算法性能"""
if self.algorithm_manager:
print("✓ 比较路径规划算法...")
from .utils.demo_scenarios import create_simple_grid
self.current_grid = create_simple_grid(20, 20)
self.current_start = (0, 0)
self.current_goal = (19, 19)
algorithms = ["astar", "dijkstra", "bfs", "dfs"]
results = {}
for algorithm in algorithms:
path, stats = self.algorithm_manager.find_path(algorithm, self.current_grid, self.current_start, self.current_goal)
results[algorithm] = {
"path_length": len(path) if path else 0,
"nodes_visited": stats.get("nodes_visited", 0),
"time_taken": stats.get("time_taken", 0),
"success": stats.get("success", False)
}
print("=== 算法性能比较 ===")
for algorithm, result in results.items():
print(f"{algorithm}:")
print(f" 路径长度: {result['path_length']}")
print(f" 访问节点数: {result['nodes_visited']}")
print(f" 耗时: {result['time_taken']:.6f}")
print(f" 成功: {'' if result['success'] else ''}")
def show_stats(self):
"""显示统计信息"""
if self.algorithm_manager:
stats = self.algorithm_manager.get_stats()
print("=== 路径规划算法统计 ===")
for key, value in stats.items():
if key != 'algorithm_usage':
print(f" {key}: {value}")
print(" 算法使用统计:")
for algo, count in stats.get('algorithm_usage', {}).items():
print(f" {algo}: {count}")
def generate_report(self):
"""生成报告"""
if self.algorithm_manager:
print("✓ 生成路径规划算法报告...")
report = self.algorithm_manager.generate_report()
# 简化输出报告摘要
print(f"报告生成时间: {time.ctime(report.get('timestamp', 0))}")
print(f"总算法数: {len(report.get('algorithms', []))}")
print(f"总测试数: {report.get('total_tests', 0)}")
print(f"成功率: {report.get('success_rate', 0):.2%}")
def optimize_paths(self):
"""优化路径"""
print("✓ 路径优化功能...")
if self.current_grid and self.algorithm_manager:
# 根据网格特点推荐算法
rows = len(self.current_grid)
cols = len(self.current_grid[0]) if rows > 0 else 0
obstacle_count = sum(sum(row) for row in self.current_grid)
obstacle_density = obstacle_count / (rows * cols) if rows * cols > 0 else 0
recommended_algo = self.algorithm_manager.get_algorithm_recommendation(
(rows, cols), obstacle_density, True)
print(f" 根据当前场景特点推荐算法: {recommended_algo}")
def generate_random_scenario(self):
"""生成随机场景"""
if self.visualization_manager:
print("✓ 生成随机路径规划场景...")
from .utils.demo_scenarios import create_random_grid
self.current_grid = create_random_grid(15, 15, 0.25) # 25%障碍物
self.current_start = (0, 0)
self.current_goal = (14, 14)
self.visualization_manager.visualize_grid(self.current_grid)
print("✓ 随机场景已生成")
def toggle_animation(self):
"""切换动画"""
if self.visualization_manager:
# 这里可以实现动画切换逻辑
print("✓ 动画切换功能待实现...")
def show_algorithm_info(self):
"""显示算法信息"""
if self.algorithm_manager:
algorithms = self.algorithm_manager.get_available_algorithms()
print("=== 可用算法信息 ===")
for algo in algorithms:
description = self.algorithm_manager.get_algorithm_description(algo)
complexity = self.algorithm_manager.get_algorithm_complexity(algo)
print(f"{algo}:")
print(f" 描述: {description}")
print(f" 复杂度: {complexity}")
print()
def export_detailed_report(self):
"""导出详细报告"""
if self.algorithm_manager:
print("✓ 导出详细报告...")
timestamp = int(time.time())
filename = f"pathfinding_report_{timestamp}.json"
success = self.algorithm_manager.export_report(filename)
if success:
print(f"✓ 详细报告已导出到: {filename}")
else:
print("✗ 导出详细报告失败")
def get_info(self) -> dict:
"""
获取插件信息
"""
info = super().get_info()
info.update({
"version": self.config.get("version", "1.0.0"),
"author": self.config.get("author", "EG Team"),
"description": self.config.get("description", "路径规划算法插件"),
"is_enabled": self.is_enabled,
"is_initialized": self.is_initialized,
"available_algorithms": self.algorithm_manager.get_available_algorithms() if self.algorithm_manager else []
})
return info
# 公共接口方法
def find_path(self, algorithm, grid, start, goal):
"""查找路径"""
if self.algorithm_manager:
return self.algorithm_manager.find_path(algorithm, grid, start, goal)
return None, {}
def add_algorithm(self, name, algorithm_class, description=""):
"""添加新算法"""
if self.algorithm_manager:
self.algorithm_manager.add_algorithm(name, algorithm_class, description)
def remove_algorithm(self, name):
"""移除算法"""
if self.algorithm_manager:
self.algorithm_manager.remove_algorithm(name)
def get_available_algorithms(self):
"""获取可用算法列表"""
if self.algorithm_manager:
return self.algorithm_manager.get_available_algorithms()
return []
def get_algorithm_description(self, algorithm):
"""获取算法描述"""
if self.algorithm_manager:
return self.algorithm_manager.get_algorithm_description(algorithm)
return ""
def set_algorithm_parameter(self, algorithm, parameter, value):
"""设置算法参数"""
if self.algorithm_manager:
self.algorithm_manager.set_algorithm_parameter(algorithm, parameter, value)
def get_algorithm_parameters(self, algorithm):
"""获取算法参数"""
if self.algorithm_manager:
return self.algorithm_manager.get_algorithm_parameters(algorithm)
return {}
def visualize_path(self, path, grid=None):
"""可视化路径"""
if self.visualization_manager:
self.visualization_manager.visualize_path(path, grid)
def visualize_grid(self, grid):
"""可视化网格"""
if self.visualization_manager:
self.visualization_manager.visualize_grid(grid)
def visualize_visited_nodes(self, visited_nodes):
"""可视化已访问节点"""
if self.visualization_manager:
self.visualization_manager.visualize_visited_nodes(visited_nodes)
def visualize_open_list(self, open_list):
"""可视化开放列表"""
if self.visualization_manager:
self.visualization_manager.visualize_open_list(open_list)
def clear_path_visualization(self):
"""清除路径可视化"""
if self.visualization_manager:
self.visualization_manager.clear_path_visualization()
def set_visualization_settings(self, settings):
"""设置可视化参数"""
if self.visualization_manager:
self.visualization_manager.set_settings(settings)
def get_visualization_settings(self):
"""获取可视化参数"""
if self.visualization_manager:
return self.visualization_manager.get_settings()
return {}
def enable_visualization_animation(self, enable=True):
"""启用可视化动画"""
if self.visualization_manager:
self.visualization_manager.enable_animation(enable)
def update(self, dt: float):
"""更新插件状态"""
self.performance_stats['total_updates'] += 1
self.performance_stats['last_update_time'] = time.time()
# 更新编辑器
if self.editor:
self.editor.update(dt)
# 更新可视化动画
if self.visualization_manager:
self.visualization_manager.update_animation(dt)
def batch_test_algorithms(self, algorithms, test_cases):
"""批量测试算法"""
if self.algorithm_manager:
return self.algorithm_manager.batch_test(algorithms, test_cases)
return {}
def compare_algorithms_detailed(self, algorithms, grid, start, goal):
"""详细比较算法"""
if self.algorithm_manager:
return self.algorithm_manager.compare_algorithms(algorithms, grid, start, goal)
return {}
def get_cached_performance_data(self, algorithm):
"""获取缓存的性能数据"""
if self.algorithm_manager:
return self.algorithm_manager.get_cached_performance_data(algorithm)
return []
def clear_performance_cache(self):
"""清除性能缓存"""
if self.algorithm_manager:
self.algorithm_manager.clear_performance_cache()
def reset_statistics(self):
"""重置统计信息"""
if self.algorithm_manager:
self.algorithm_manager.reset_stats()
print("✓ 统计信息已重置")
def validate_grid_data(self, grid):
"""验证网格数据"""
if self.algorithm_manager:
return self.algorithm_manager.validate_grid(grid)
return {'valid': False, 'error': '算法管理器未初始化'}
def get_algorithm_complexity(self, algorithm):
"""获取算法复杂度信息"""
if self.algorithm_manager:
return self.algorithm_manager.get_algorithm_complexity(algorithm)
return "未知"
def benchmark_algorithm(self, algorithm, grid, start, goal, iterations=100):
"""对算法进行基准测试"""
if self.algorithm_manager and algorithm in self.algorithm_manager.algorithms:
# 创建算法实例
algo_class = self.algorithm_manager.algorithms[algorithm]
algo_instance = algo_class()
# 设置参数
if algorithm in self.algorithm_manager.algorithm_parameters:
for param, value in self.algorithm_manager.algorithm_parameters[algorithm].items():
if hasattr(algo_instance, param):
setattr(algo_instance, param, value)
# 执行基准测试
if hasattr(algo_instance, 'benchmark'):
return algo_instance.benchmark(grid, start, goal, iterations)
else:
print(f"算法 {algorithm} 不支持基准测试")
return {}
return {}
def optimize_algorithm_for_grid(self, algorithm, grid):
"""为特定网格优化算法"""
if algorithm == 'jps' and self.algorithm_manager:
from .algorithms.jps import JPS
jps_instance = JPS()
jps_instance.optimize_for_map(grid)
print(f"✓ JPS算法已为当前网格优化")
else:
print(f"算法 {algorithm} 不支持自动优化")