Files
DDCZ/js/main.js

250 lines
8.2 KiB
JavaScript
Raw Permalink Normal View History

/* ===================================
应用主入口 - 模块编排与路由控制
=================================== */
import { SceneManager } from './scene/SceneManager.js';
import { MapInterface } from './ui/MapInterface.js';
import { ListInterface } from './ui/ListInterface.js';
import { DetailInterface } from './ui/DetailInterface.js';
import { SearchController } from './ui/SearchController.js';
import { UIUtils } from './ui/UIUtils.js';
class App {
constructor() {
// 3D平台 DOM 引用
this.appContainer = document.getElementById('app-container');
this.canvasContainer = document.getElementById('canvas-container');
this.mapInterface = document.getElementById('map-interface');
this.listInterface = document.getElementById('list-interface');
this.detailInterface = document.getElementById('detail-interface');
// UI 元素
this.uiLayer = document.getElementById('ui-layer');
this.hint = document.querySelector('.instruction-hint');
this.speedLines = document.getElementById('speed-lines');
this.cloudFog = document.getElementById('cloud-fog');
// 模块实例
this.sceneManager = null;
this.mapController = null;
this.listController = null;
this.detailController = null;
// 2D地图初始化标志防止重复初始化导致省级地图被覆盖
this.is2DInitialized = false;
this.init();
}
// 初始化应用
async init() {
// 初始化 3D 平台的控制器(但不启动)
this.mapController = new MapInterface(
this.mapInterface,
(cityName) => this.showList(cityName)
);
this.listController = new ListInterface(
this.listInterface,
(company) => this.showDetail(company),
() => this.backToMap()
);
this.detailController = new DetailInterface(
this.detailInterface,
() => this.backToList()
);
// 初始化搜索控制器PC端
const searchInput = document.getElementById('search-input');
if (searchInput) {
this.searchController = new SearchController(searchInput, {
onSelectProvince: (provinceName) => {
this.mapController.init('province', provinceName);
},
onSelectCity: (cityName) => {
this.showList(cityName);
},
onSelectCompany: (company) => {
// 设置当前城市为企业所属城市,以便返回时显示正确的列表
this.listController.currentCity = company.city;
this.showDetail(company);
}
});
}
// 初始化搜索控制器(移动端)
const searchInputMobile = document.getElementById('search-input-mobile');
if (searchInputMobile) {
this.searchControllerMobile = new SearchController(searchInputMobile, {
onSelectProvince: (provinceName) => {
this.mapController.init('province', provinceName);
},
onSelectCity: (cityName) => {
this.showList(cityName);
},
onSelectCompany: (company) => {
// 设置当前城市为企业所属城市,以便返回时显示正确的列表
this.listController.currentCity = company.city;
this.showDetail(company);
}
});
}
// 绑定全局函数和事件
this.bindGlobalFunctions();
// 将应用实例暴露给全局,供页面切换使用
window.appInstance = this;
}
// 切换到 3D 内推平台
switchToApp() {
// 显示 3D 容器
this.appContainer.classList.remove('hidden');
// 每次都重新初始化 3D 场景
this.init3DScene();
}
// 初始化 3D 场景(每次进入都重新加载)
init3DScene() {
// 如果有旧场景,先清理
if (this.sceneManager) {
this.sceneManager.dispose();
this.sceneManager = null;
}
// 重置UI状态
this.canvasContainer.style.display = 'block';
this.speedLines.style.display = 'block';
this.cloudFog.style.display = 'none'; // 云雾初始隐藏,转场时才显示
this.cloudFog.style.opacity = '0';
this.mapInterface.style.display = 'none';
// 创建场景管理器
this.sceneManager = new SceneManager(
this.canvasContainer,
() => this.onTransitionComplete()
);
// 初始化转场系统
this.sceneManager.initTransition({
uiLayer: this.uiLayer,
hint: this.hint,
speedLines: this.speedLines,
cloudFog: this.cloudFog
});
// 启动开场动画
this.sceneManager.startIntroSequence({
uiLayer: this.uiLayer,
hint: this.hint
});
}
// 转场完成回调3D地球 → 2D地图
onTransitionComplete() {
this.switchTo2D();
}
// 切换到2D地图界面
switchTo2D() {
// 防止重复初始化:如果已经初始化过,直接返回
if (this.is2DInitialized) {
console.log('⏭️ 2D地图已初始化跳过重复初始化');
return;
}
// 隐藏3D容器和特效层
this.canvasContainer.style.display = 'none';
this.speedLines.style.display = 'none';
// 先显示地图容器opacity: 0但display: block
this.mapInterface.style.display = 'block';
this.mapInterface.style.opacity = '0';
// 使用 requestAnimationFrame 确保浏览器完成布局渲染
requestAnimationFrame(() => {
requestAnimationFrame(async () => {
// 现在容器已经有了正确的尺寸可以安全初始化ECharts
await this.mapController.init('china');
// 地图初始化完成后立即调用resize确保尺寸正确
this.mapController.resize();
// 标记2D地图已初始化防止后续重复初始化
this.is2DInitialized = true;
// 延迟淡入,提升视觉效果
setTimeout(() => {
gsap.to(this.mapInterface, { opacity: 1, duration: 1 });
gsap.to(this.cloudFog, {
opacity: 0,
duration: 1,
onComplete: () => {
this.cloudFog.style.display = 'none';
}
});
}, 50);
});
});
}
// 显示企业列表
async showList(cityName) {
await this.mapController.hide();
this.listController.show(cityName);
}
// 显示企业详情
async showDetail(company) {
await this.listController.hide();
this.detailController.show(company);
}
// 返回列表
async backToList() {
await this.detailController.hide();
this.listController.show(this.listController.currentCity);
}
// 返回地图
async backToMap() {
await this.listController.hide();
this.mapController.show();
this.mapController.resize(); // 确保地图尺寸正确
}
// 绑定全局函数和事件
bindGlobalFunctions() {
// 地图界面logo点击返回首页
const mapLogoArea = document.getElementById('map-logo-area');
if (mapLogoArea) {
mapLogoArea.addEventListener('click', () => {
window.backToHome();
});
}
// 重置地图到全国视图
window.resetMapToChina = () => {
if (this.mapController) {
this.mapController.reset();
}
};
// 从列表返回地图
window.backToMap = () => {
this.backToMap();
};
// 从详情返回列表
window.backToList = () => {
this.backToList();
};
}
}
// 应用启动
const app = new App();