地图订单修改
This commit is contained in:
@@ -571,24 +571,21 @@ Page({
|
|||||||
// 获取仓库信息
|
// 获取仓库信息
|
||||||
const warehouse = warehouses[warehouseIndex];
|
const warehouse = warehouses[warehouseIndex];
|
||||||
|
|
||||||
// 模拟终点坐标(实际应用中应该通过地图选择或搜索获取)
|
|
||||||
// 从已有仓库中获取一个坐标作为参考点
|
|
||||||
const referenceWarehouse = this.data.warehouses[0];
|
|
||||||
const endPoint = {
|
|
||||||
name: endName,
|
|
||||||
longitude: referenceWarehouse.address ? 102.715 + (Math.random() - 0.5) * 0.1 : 102.715,
|
|
||||||
latitude: referenceWarehouse.address ? 25.045 + (Math.random() - 0.5) * 0.1 : 25.045
|
|
||||||
};
|
|
||||||
|
|
||||||
// 创建订单数据
|
// 创建订单数据
|
||||||
const newOrder: Omit<Order, 'id' | 'createTime'> = {
|
const newOrder: Omit<Order, 'id' | 'createTime'> = {
|
||||||
startPoint: {
|
startPoint: {
|
||||||
id: warehouse.id,
|
id: warehouse.id,
|
||||||
name: warehouse.name,
|
name: warehouse.name,
|
||||||
longitude: 102.715, // 临时使用固定坐标
|
longitude: warehouse.longitude || 0,
|
||||||
latitude: 25.045 // 临时使用固定坐标
|
latitude: warehouse.latitude || 0
|
||||||
|
},
|
||||||
|
endPoint: {
|
||||||
|
name: endName,
|
||||||
|
// 后端服务器应该根据地址名称进行地理编码
|
||||||
|
// 这里只提供地址名称,由后端处理坐标获取
|
||||||
|
longitude: 0,
|
||||||
|
latitude: 0
|
||||||
},
|
},
|
||||||
endPoint,
|
|
||||||
status: 'pending',
|
status: 'pending',
|
||||||
goodsType,
|
goodsType,
|
||||||
goodsWeight
|
goodsWeight
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import { MainPageModule } from './modules/mainPageModule';
|
|||||||
|
|
||||||
// 导入类型定义
|
// 导入类型定义
|
||||||
import { IndexPageComponent } from '../../types';
|
import { IndexPageComponent } from '../../types';
|
||||||
|
import { API_BASE_URL } from '../../services/apiService';
|
||||||
|
|
||||||
// 主页面组件
|
// 主页面组件
|
||||||
Component<IndexPageComponent['data'], any, any, any, false>({
|
Component<IndexPageComponent['data'], any, any, any, false>({
|
||||||
@@ -94,6 +95,23 @@ Component<IndexPageComponent['data'], any, any, any, false>({
|
|||||||
return `${API_BASE_URL}${avatarPath}`;
|
return `${API_BASE_URL}${avatarPath}`;
|
||||||
},
|
},
|
||||||
|
|
||||||
|
// 格式化时间戳(用于wxml显示)
|
||||||
|
formatTimestamp(timestamp: number): string {
|
||||||
|
if (!timestamp) {
|
||||||
|
return '未知';
|
||||||
|
}
|
||||||
|
|
||||||
|
const date = new Date(timestamp);
|
||||||
|
return date.toLocaleString('zh-CN', {
|
||||||
|
year: 'numeric',
|
||||||
|
month: '2-digit',
|
||||||
|
day: '2-digit',
|
||||||
|
hour: '2-digit',
|
||||||
|
minute: '2-digit',
|
||||||
|
second: '2-digit'
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
|
||||||
// 处理货运人员底部弹窗关闭
|
// 处理货运人员底部弹窗关闭
|
||||||
onDeliveryPersonModalClose() {
|
onDeliveryPersonModalClose() {
|
||||||
|
|||||||
@@ -236,11 +236,11 @@
|
|||||||
<view class="modal-header">
|
<view class="modal-header">
|
||||||
<view class="delivery-person-header">
|
<view class="delivery-person-header">
|
||||||
<view class="delivery-person-avatar">
|
<view class="delivery-person-avatar">
|
||||||
<image src="{{currentDeliveryPerson.fullAvatarUrl}}" mode="aspectFill"></image>
|
<image src="{{currentDeliveryPerson.avatarPath ? currentDeliveryPerson.avatarPath : '/images/avatar.png'}}" mode="aspectFill"></image>
|
||||||
</view>
|
</view>
|
||||||
<view class="person-info-header">
|
<view class="person-info-header">
|
||||||
<view class="modal-title">{{currentDeliveryPerson.name}}</view>
|
<view class="modal-title">{{currentDeliveryPerson.name}}</view>
|
||||||
<view class="modal-subtitle">工号:{{currentDeliveryPerson.phone}}</view>
|
<view class="modal-subtitle">角色:{{currentDeliveryPerson.role}}</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
@@ -248,16 +248,16 @@
|
|||||||
<!-- 基础信息区 - 始终可见 -->
|
<!-- 基础信息区 - 始终可见 -->
|
||||||
<view class="modal-basic-info">
|
<view class="modal-basic-info">
|
||||||
<view class="detail-item">
|
<view class="detail-item">
|
||||||
<text class="detail-label">工号</text>
|
<text class="detail-label">用户ID</text>
|
||||||
<text class="detail-value">{{currentDeliveryPerson.phone}}</text>
|
<text class="detail-value">{{currentDeliveryPerson.userId}}</text>
|
||||||
</view>
|
|
||||||
<view class="detail-item">
|
|
||||||
<text class="detail-label">状态</text>
|
|
||||||
<text class="detail-value status-badge status-{{currentDeliveryPerson.status === 'idle' ? 'idle' : currentDeliveryPerson.status === 'busy' ? 'busy' : currentDeliveryPerson.status === 'delivering' ? 'delivering' : 'offline'}}">{{deliveryService.getDeliveryPersonStatusText(currentDeliveryPerson.status)}}</text>
|
|
||||||
</view>
|
</view>
|
||||||
<view class="detail-item">
|
<view class="detail-item">
|
||||||
<text class="detail-label">当前位置</text>
|
<text class="detail-label">当前位置</text>
|
||||||
<text class="detail-value">{{currentDeliveryPerson.currentLocation.address}}</text>
|
<text class="detail-value">经度:{{currentDeliveryPerson.longitude}},纬度:{{currentDeliveryPerson.latitude}}</text>
|
||||||
|
</view>
|
||||||
|
<view class="detail-item">
|
||||||
|
<text class="detail-label">最后更新时间</text>
|
||||||
|
<text class="detail-value">{{currentDeliveryPerson.timestamp ? formatTimestamp(currentDeliveryPerson.timestamp) : '未知'}}</text>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
import { UserInfo, Marker } from '../../../types';
|
import { UserInfo, Marker } from '../../../types';
|
||||||
import { avatarCache } from '../../../utils/avatarCache';
|
import { avatarCache } from '../../../utils/avatarCache';
|
||||||
|
import { API_BASE_URL } from '../../../services/apiService';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 页面数据管理模块
|
* 页面数据管理模块
|
||||||
@@ -203,19 +204,22 @@ export class DataModule {
|
|||||||
const processedPerson = { ...person };
|
const processedPerson = { ...person };
|
||||||
if (person.avatarPath) {
|
if (person.avatarPath) {
|
||||||
try {
|
try {
|
||||||
// 只有在用户已签到的情况下才使用头像缓存
|
// 将相对路径转换为完整URL
|
||||||
const app = getApp<any>();
|
let avatarUrl = person.avatarPath;
|
||||||
const isSignedIn = app.globalData.userInfo && app.globalData.userInfo.status === 'signed_in';
|
if (!avatarUrl.startsWith('http')) {
|
||||||
|
avatarUrl = `${API_BASE_URL}${avatarUrl}`;
|
||||||
if (isSignedIn) {
|
|
||||||
processedPerson.avatarPath = await avatarCache.getAvatarPath(person.avatarPath);
|
|
||||||
} else {
|
|
||||||
// 未签到状态,直接使用原始路径
|
|
||||||
processedPerson.avatarPath = person.avatarPath;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 使用头像缓存获取本地图片路径
|
||||||
|
processedPerson.avatarPath = await avatarCache.getAvatarPath(avatarUrl);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error('处理货运人员头像缓存失败:', error);
|
console.error('处理货运人员头像缓存失败:', error);
|
||||||
|
// 如果头像缓存失败,使用默认头像
|
||||||
|
processedPerson.avatarPath = '/images/user-avatar.png';
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
// 如果没有头像路径,使用默认头像
|
||||||
|
processedPerson.avatarPath = '/images/user-avatar.png';
|
||||||
}
|
}
|
||||||
|
|
||||||
this.pageContext.setData({ currentDeliveryPerson: processedPerson });
|
this.pageContext.setData({ currentDeliveryPerson: processedPerson });
|
||||||
|
|||||||
@@ -170,13 +170,14 @@ export class LocationModule {
|
|||||||
zIndex: 30,
|
zIndex: 30,
|
||||||
data: {
|
data: {
|
||||||
userId: user.userId,
|
userId: user.userId,
|
||||||
|
name: user.name || user.userName || `用户${user.userId}`,
|
||||||
role: userRole,
|
role: userRole,
|
||||||
|
avatarPath: user.avatarPath || undefined,
|
||||||
|
latitude: latitude, // 直接使用纬度字段
|
||||||
|
longitude: longitude, // 直接使用经度字段
|
||||||
|
timestamp: user.timestamp || lastUpdateTime,
|
||||||
lastUpdateTime: lastUpdateTime,
|
lastUpdateTime: lastUpdateTime,
|
||||||
currentLocation: {
|
status: user.status || 'online'
|
||||||
address: user.address || '位置信息获取中...',
|
|
||||||
longitude: longitude,
|
|
||||||
latitude: latitude
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -294,20 +295,20 @@ export class LocationModule {
|
|||||||
// 优先使用传入的用户数据中的头像信息
|
// 优先使用传入的用户数据中的头像信息
|
||||||
if (userData) {
|
if (userData) {
|
||||||
// 尝试使用avatarPath(相对路径)
|
// 尝试使用avatarPath(相对路径)
|
||||||
if (userData.avatarPath) {
|
if (userData.avatarPath && userData.avatarPath !== 'null') {
|
||||||
console.log(`📸 [LocationModule] 使用用户数据中的avatarPath: ${userData.avatarPath}`);
|
console.log(`📸 [LocationModule] 使用用户数据中的avatarPath: ${userData.avatarPath}`);
|
||||||
const fullAvatarUrl = `${API_BASE_URL}${userData.avatarPath}`;
|
const fullAvatarUrl = `${API_BASE_URL}${userData.avatarPath}`;
|
||||||
return await avatarCache.getAvatarPath(fullAvatarUrl);
|
return await avatarCache.getAvatarPath(fullAvatarUrl);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 尝试使用avatarUrl(完整URL)
|
// 尝试使用avatarUrl(完整URL)
|
||||||
if (userData.avatarUrl) {
|
if (userData.avatarUrl && userData.avatarUrl !== 'null') {
|
||||||
console.log(`📸 [LocationModule] 使用用户数据中的avatarUrl: ${userData.avatarUrl}`);
|
console.log(`📸 [LocationModule] 使用用户数据中的avatarUrl: ${userData.avatarUrl}`);
|
||||||
return await avatarCache.getAvatarPath(userData.avatarUrl);
|
return await avatarCache.getAvatarPath(userData.avatarUrl);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 尝试使用avatar(兼容字段)
|
// 尝试使用avatar(兼容字段)
|
||||||
if (userData.avatar) {
|
if (userData.avatar && userData.avatar !== 'null') {
|
||||||
console.log(`📸 [LocationModule] 使用用户数据中的avatar: ${userData.avatar}`);
|
console.log(`📸 [LocationModule] 使用用户数据中的avatar: ${userData.avatar}`);
|
||||||
return await avatarCache.getAvatarPath(userData.avatar);
|
return await avatarCache.getAvatarPath(userData.avatar);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,8 @@ import userService from '../../../services/userService';
|
|||||||
import { showToast } from '../../../utils/helpers';
|
import { showToast } from '../../../utils/helpers';
|
||||||
import { Marker } from '../../../types';
|
import { Marker } from '../../../types';
|
||||||
import { DataModule } from './dataModule';
|
import { DataModule } from './dataModule';
|
||||||
|
import warehouseService from '../../../services/warehouseService';
|
||||||
|
import deliveryService from '../../../services/deliveryPersonService';
|
||||||
|
|
||||||
export class MapModule {
|
export class MapModule {
|
||||||
private pageContext: any;
|
private pageContext: any;
|
||||||
@@ -152,15 +154,65 @@ export class MapModule {
|
|||||||
/**
|
/**
|
||||||
* 加载地图数据(仓库和货运人员)
|
* 加载地图数据(仓库和货运人员)
|
||||||
*/
|
*/
|
||||||
loadMapData(): void {
|
async loadMapData(): Promise<void> {
|
||||||
// 这里会调用具体的服务来获取数据
|
try {
|
||||||
// 目前使用模拟数据
|
// 调用具体的服务来获取数据
|
||||||
const markers = this.generateInitialMarkers();
|
const warehouses = await warehouseService.getWarehouses();
|
||||||
|
const deliveryPersons = await deliveryService.getDeliveryPersons();
|
||||||
|
|
||||||
|
// 生成标记点
|
||||||
|
const markers = this.generateMarkersFromData(warehouses, deliveryPersons);
|
||||||
|
|
||||||
|
// 更新数据模块中的标记点
|
||||||
|
this.dataModule.updateMarkers(markers);
|
||||||
|
|
||||||
|
console.log('地图数据加载完成');
|
||||||
|
} catch (error) {
|
||||||
|
console.error('加载地图数据失败:', error);
|
||||||
|
// 如果API调用失败,使用空标记点
|
||||||
|
this.dataModule.updateMarkers([]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 从数据生成标记点
|
||||||
|
*/
|
||||||
|
private generateMarkersFromData(warehouses: any[], deliveryPersons: any[]): Marker[] {
|
||||||
|
const markers: Marker[] = [];
|
||||||
|
|
||||||
// 更新数据模块中的标记点
|
// 添加仓库标记点
|
||||||
this.dataModule.updateMarkers(markers);
|
warehouses.forEach(warehouse => {
|
||||||
|
if (warehouse.longitude && warehouse.latitude) {
|
||||||
|
markers.push({
|
||||||
|
id: warehouse.id,
|
||||||
|
latitude: warehouse.latitude,
|
||||||
|
longitude: warehouse.longitude,
|
||||||
|
title: warehouse.name,
|
||||||
|
iconPath: '/images/warehouse-marker.png',
|
||||||
|
width: 30,
|
||||||
|
height: 30,
|
||||||
|
type: 'warehouse'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
console.log('地图数据加载完成');
|
// 添加货运人员标记点
|
||||||
|
deliveryPersons.forEach(person => {
|
||||||
|
if (person.longitude && person.latitude) {
|
||||||
|
markers.push({
|
||||||
|
id: person.id,
|
||||||
|
latitude: person.latitude,
|
||||||
|
longitude: person.longitude,
|
||||||
|
title: person.name,
|
||||||
|
iconPath: '/images/delivery-marker.png',
|
||||||
|
width: 30,
|
||||||
|
height: 30,
|
||||||
|
type: 'employee'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
return markers;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
import mapService from '../../../services/mapService';
|
||||||
import orderService from '../../../services/orderService';
|
import orderService from '../../../services/orderService';
|
||||||
import { Order } from '../../../types';
|
import { Order } from '../../../types';
|
||||||
import { showToast } from '../../../utils/helpers';
|
import { showToast } from '../../../utils/helpers';
|
||||||
@@ -76,13 +77,8 @@ export class OrderModule {
|
|||||||
|
|
||||||
console.log(`开始规划路线: 起点=${origin}, 终点=${destination}`);
|
console.log(`开始规划路线: 起点=${origin}, 终点=${destination}`);
|
||||||
|
|
||||||
// 这里应该调用地图服务的路线规划功能
|
// 调用地图服务的路线规划功能
|
||||||
// 目前先模拟一个简单的路线规划结果
|
const routeResult = await mapService.calculateRoute(origin, destination);
|
||||||
const routeResult = {
|
|
||||||
distance: 1500, // 1.5公里
|
|
||||||
duration: 300, // 5分钟
|
|
||||||
polyline: null // 路线数据
|
|
||||||
};
|
|
||||||
|
|
||||||
console.log('路线规划结果:', routeResult);
|
console.log('路线规划结果:', routeResult);
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
// 员工界面 - 全屏工作面板
|
// 员工界面 - 全屏工作面板
|
||||||
import { UserInfo } from '../../types';
|
import { UserInfo } from '../../types';
|
||||||
import userService from '../../services/userService';
|
import userService from '../../services/userService';
|
||||||
|
import statisticsService from '../../services/statisticsService';
|
||||||
|
|
||||||
Page({
|
Page({
|
||||||
data: {
|
data: {
|
||||||
@@ -81,15 +82,22 @@ Page({
|
|||||||
/**
|
/**
|
||||||
* 加载工作统计数据
|
* 加载工作统计数据
|
||||||
*/
|
*/
|
||||||
loadWorkStats() {
|
async loadWorkStats() {
|
||||||
// 模拟加载工作统计数据
|
try {
|
||||||
this.setData({
|
// 调用API获取工作统计数据
|
||||||
workStats: {
|
const workStats = await statisticsService.getWorkStats();
|
||||||
todayOrders: 8,
|
this.setData({ workStats });
|
||||||
completedOrders: 5,
|
} catch (error) {
|
||||||
pendingOrders: 3
|
console.error('加载工作统计数据失败:', error);
|
||||||
}
|
// 如果API调用失败,设置默认值
|
||||||
});
|
this.setData({
|
||||||
|
workStats: {
|
||||||
|
todayOrders: 0,
|
||||||
|
completedOrders: 0,
|
||||||
|
pendingOrders: 0
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -260,8 +260,10 @@ Page({
|
|||||||
},
|
},
|
||||||
endPoint: {
|
endPoint: {
|
||||||
name: endName,
|
name: endName,
|
||||||
longitude: 102.715 + (Math.random() - 0.5) * 0.1,
|
// 后端服务器应该根据地址名称进行地理编码
|
||||||
latitude: 25.045 + (Math.random() - 0.5) * 0.1
|
// 这里只提供地址名称,由后端处理坐标获取
|
||||||
|
longitude: 0,
|
||||||
|
latitude: 0
|
||||||
},
|
},
|
||||||
status: 'pending',
|
status: 'pending',
|
||||||
goodsType,
|
goodsType,
|
||||||
@@ -316,21 +318,17 @@ Page({
|
|||||||
success: (res) => {
|
success: (res) => {
|
||||||
if (res.confirm) {
|
if (res.confirm) {
|
||||||
// 调用删除订单接口
|
// 调用删除订单接口
|
||||||
// orderService.deleteOrder(orderId).then(() => {
|
orderService.deleteOrder(orderId).then((result) => {
|
||||||
// this.showSuccess('订单删除成功');
|
if (result.success) {
|
||||||
// this.refreshData();
|
this.showSuccess('订单删除成功');
|
||||||
// }).catch(error => {
|
this.refreshData();
|
||||||
// console.error('删除订单失败:', error);
|
} else {
|
||||||
// this.showError('删除订单失败');
|
this.showError(result.message || '删除失败');
|
||||||
// });
|
}
|
||||||
|
}).catch(error => {
|
||||||
// 暂时使用模拟删除
|
console.error('删除订单失败:', error);
|
||||||
const orders = this.data.orders.filter(order => order.id !== orderId);
|
this.showError('删除订单失败');
|
||||||
this.setData({
|
|
||||||
orders
|
|
||||||
});
|
});
|
||||||
this.filterOrders();
|
|
||||||
this.showSuccess('订单删除成功');
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -426,6 +424,11 @@ Page({
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
|
// 阻止事件冒泡
|
||||||
|
stopPropagation(e: any) {
|
||||||
|
// 阻止事件冒泡,不执行任何操作
|
||||||
|
},
|
||||||
|
|
||||||
// 返回上一页
|
// 返回上一页
|
||||||
goBack() {
|
goBack() {
|
||||||
wx.navigateBack();
|
wx.navigateBack();
|
||||||
|
|||||||
@@ -73,7 +73,7 @@
|
|||||||
</view>
|
</view>
|
||||||
|
|
||||||
<!-- 操作按钮 -->
|
<!-- 操作按钮 -->
|
||||||
<view class="order-actions" wx:if="{{item.status === 'pending'}}">
|
<view class="order-actions" wx:if="{{item.status === 'pending'}}" catchtap="stopPropagation">
|
||||||
<button class="action-btn assign-btn" bindtap="handleOrderTap" data-id="{{item.id}}">分配</button>
|
<button class="action-btn assign-btn" bindtap="handleOrderTap" data-id="{{item.id}}">分配</button>
|
||||||
<button class="action-btn delete-btn" bindtap="deleteOrder" data-id="{{item.id}}">删除</button>
|
<button class="action-btn delete-btn" bindtap="deleteOrder" data-id="{{item.id}}">删除</button>
|
||||||
</view>
|
</view>
|
||||||
|
|||||||
@@ -11,9 +11,9 @@ Page({
|
|||||||
totalOrders: 0, // 总订单数
|
totalOrders: 0, // 总订单数
|
||||||
completedOrders: 0, // 已完成订单数
|
completedOrders: 0, // 已完成订单数
|
||||||
pendingOrders: 0, // 待处理订单数
|
pendingOrders: 0, // 待处理订单数
|
||||||
deliveryRate: 0, // 配送成功率
|
averageDeliveryTime: 0, // 平均配送时间(分钟)
|
||||||
averageTime: 0 // 平均配送时间
|
timestamp: 0 // 数据时间戳
|
||||||
},
|
} as any,
|
||||||
// 系统统计数据
|
// 系统统计数据
|
||||||
systemStats: {
|
systemStats: {
|
||||||
employeeCount: 0, // 员工总数
|
employeeCount: 0, // 员工总数
|
||||||
@@ -103,15 +103,9 @@ Page({
|
|||||||
*/
|
*/
|
||||||
async getPersonalStats() {
|
async getPersonalStats() {
|
||||||
try {
|
try {
|
||||||
// 这里应该调用个人统计API
|
// 调用个人统计API
|
||||||
// 暂时使用模拟数据
|
const personalStats = await statisticsService.getPersonalStats();
|
||||||
return {
|
return personalStats;
|
||||||
totalOrders: 156,
|
|
||||||
completedOrders: 142,
|
|
||||||
pendingOrders: 14,
|
|
||||||
deliveryRate: 91.0,
|
|
||||||
averageTime: 45
|
|
||||||
};
|
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error('获取个人统计数据失败:', error);
|
console.error('获取个人统计数据失败:', error);
|
||||||
// 返回默认值
|
// 返回默认值
|
||||||
@@ -119,8 +113,8 @@ Page({
|
|||||||
totalOrders: 0,
|
totalOrders: 0,
|
||||||
completedOrders: 0,
|
completedOrders: 0,
|
||||||
pendingOrders: 0,
|
pendingOrders: 0,
|
||||||
deliveryRate: 0,
|
averageDeliveryTime: 0,
|
||||||
averageTime: 0
|
timestamp: Date.now()
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -451,15 +451,14 @@ async ServerLogin(code: string) {
|
|||||||
if (res.statusCode >= 200 && res.statusCode < 300) {
|
if (res.statusCode >= 200 && res.statusCode < 300) {
|
||||||
try {
|
try {
|
||||||
const data = JSON.parse(res.data);
|
const data = JSON.parse(res.data);
|
||||||
|
// 使用服务器返回的实际路径,而不是构造的路径
|
||||||
|
const avatarUrl = data.avatarPath ? `${API_BASE_URL}${data.avatarPath}` : data.avatarUrl;
|
||||||
resolve({
|
resolve({
|
||||||
success: true,
|
success: true,
|
||||||
avatarUrl: data.avatarUrl
|
avatarUrl: avatarUrl
|
||||||
});
|
});
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
resolve({
|
reject(new Error(`解析响应失败: ${error}`));
|
||||||
success: true,
|
|
||||||
avatarUrl: `${API_BASE_URL}/avatars/${employeeId}.jpg`
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
reject(new Error(`上传失败: HTTP ${res.statusCode}`));
|
reject(new Error(`上传失败: HTTP ${res.statusCode}`));
|
||||||
@@ -479,12 +478,13 @@ async ServerLogin(code: string) {
|
|||||||
*/
|
*/
|
||||||
async getEmployeeAvatar(employeeId: number): Promise<string> {
|
async getEmployeeAvatar(employeeId: number): Promise<string> {
|
||||||
try {
|
try {
|
||||||
// 尝试获取头像信息
|
// 使用RESTful API获取头像信息,确保路径一致性
|
||||||
const response = await this.request<{ avatarUrl: string }>(`/employees/${employeeId}/avatar`);
|
const response = await this.request<{ avatarPath: string }>(`/employees/${employeeId}/avatar`);
|
||||||
return response.avatarUrl || `${API_BASE_URL}/avatars/${employeeId}.jpg`;
|
// 使用服务器返回的实际路径
|
||||||
|
return response.avatarPath ? `${API_BASE_URL}${response.avatarPath}` : '/images/user-avatar.png';
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
// 如果获取失败,返回默认头像URL
|
// 如果获取失败,返回默认头像
|
||||||
return `${API_BASE_URL}/avatars/${employeeId}.jpg`;
|
return '/images/user-avatar.png';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
// 位置追踪服务 - 处理用户签到后的位置追踪和状态管理
|
// 位置追踪服务 - 处理用户签到后的位置追踪和状态管理
|
||||||
import { LocationData } from '../types';
|
// import { LocationData } from '../types'; // 已弃用,服务器不再使用嵌套对象
|
||||||
import apiService from './apiService';
|
import apiService from './apiService';
|
||||||
import userService from './userService';
|
import userService from './userService';
|
||||||
import mapService from './mapService';
|
import mapService from './mapService';
|
||||||
@@ -14,7 +14,9 @@ export interface OnlineUserInfo {
|
|||||||
name: string;
|
name: string;
|
||||||
avatarPath?: string; // 头像相对路径(服务器下发)
|
avatarPath?: string; // 头像相对路径(服务器下发)
|
||||||
role: string;
|
role: string;
|
||||||
lastLocation: LocationData;
|
latitude: number; // 纬度(直接字段,不再使用嵌套对象)
|
||||||
|
longitude: number; // 经度(直接字段,不再使用嵌套对象)
|
||||||
|
timestamp: number; // 时间戳(直接字段,不再使用嵌套对象)
|
||||||
lastUpdateTime: number;
|
lastUpdateTime: number;
|
||||||
status: 'online' | 'offline'| 'timeout';
|
status: 'online' | 'offline'| 'timeout';
|
||||||
}
|
}
|
||||||
@@ -220,7 +222,7 @@ class LocationTrackingService {
|
|||||||
/**
|
/**
|
||||||
* 获取当前位置
|
* 获取当前位置
|
||||||
*/
|
*/
|
||||||
public async getCurrentLocation(): Promise<LocationData> {
|
public async getCurrentLocation(): Promise<{ longitude: number; latitude: number; timestamp: number }> {
|
||||||
const userInfo = userService.getGlobalUserInfo();
|
const userInfo = userService.getGlobalUserInfo();
|
||||||
if (!userInfo || !userInfo.id) {
|
if (!userInfo || !userInfo.id) {
|
||||||
throw new Error('用户未登录');
|
throw new Error('用户未登录');
|
||||||
@@ -233,7 +235,6 @@ class LocationTrackingService {
|
|||||||
console.log('[位置追踪服务] 获取真实位置成功:', location);
|
console.log('[位置追踪服务] 获取真实位置成功:', location);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
userId: userInfo.id,
|
|
||||||
longitude: location.longitude,
|
longitude: location.longitude,
|
||||||
latitude: location.latitude,
|
latitude: location.latitude,
|
||||||
timestamp: Date.now()
|
timestamp: Date.now()
|
||||||
@@ -243,7 +244,6 @@ class LocationTrackingService {
|
|||||||
|
|
||||||
// 定位失败时返回默认位置作为降级方案
|
// 定位失败时返回默认位置作为降级方案
|
||||||
return {
|
return {
|
||||||
userId: userInfo.id,
|
|
||||||
longitude: 102.833722,
|
longitude: 102.833722,
|
||||||
latitude: 24.880095,
|
latitude: 24.880095,
|
||||||
timestamp: Date.now()
|
timestamp: Date.now()
|
||||||
@@ -417,22 +417,24 @@ class LocationTrackingService {
|
|||||||
// 处理在线用户列表消息(服务器发送当前在线用户列表)
|
// 处理在线用户列表消息(服务器发送当前在线用户列表)
|
||||||
console.log('👥 处理在线用户列表,用户数量:', message.users ? message.users.length : 0);
|
console.log('👥 处理在线用户列表,用户数量:', message.users ? message.users.length : 0);
|
||||||
if (message.users && Array.isArray(message.users)) {
|
if (message.users && Array.isArray(message.users)) {
|
||||||
this.triggerOnlineUserListCallbacks({
|
// 转换用户数据格式,确保与位置追踪服务兼容
|
||||||
type: 'onlineUserList',
|
const formattedUsers = message.users.map((user: any) => ({
|
||||||
users: message.users.map((user: any) => ({
|
|
||||||
userId: user.userId,
|
userId: user.userId,
|
||||||
name: user.name,
|
name: user.name,
|
||||||
role: user.role,
|
role: user.role,
|
||||||
userStatus: user.userStatus,
|
userStatus: user.userStatus,
|
||||||
lastUpdateTime: user.lastUpdateTime,
|
lastUpdateTime: user.lastUpdateTime,
|
||||||
latitude: user.locationData?.latitude || user.latitude,
|
latitude: user.latitude, // 直接使用latitude字段
|
||||||
longitude: user.locationData?.longitude || user.longitude,
|
longitude: user.longitude, // 直接使用longitude字段
|
||||||
timestamp: user.locationData?.timestamp || user.timestamp,
|
timestamp: user.timestamp, // 直接使用timestamp字段
|
||||||
avatarPath: user.avatarPath,
|
avatarPath: user.avatarPath || undefined, // 确保null转换为undefined
|
||||||
address: user.address
|
}));
|
||||||
}))
|
|
||||||
});
|
console.log('📊 转换后的在线用户数据:', formattedUsers);
|
||||||
}else {
|
|
||||||
|
// 关键修复:调用handleOnlineUserList方法填充onlineUsers Map
|
||||||
|
this.handleOnlineUserList(formattedUsers);
|
||||||
|
} else {
|
||||||
console.warn('❌ onlineUserList消息格式错误,users字段不存在或不是数组');
|
console.warn('❌ onlineUserList消息格式错误,users字段不存在或不是数组');
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@@ -444,32 +446,29 @@ class LocationTrackingService {
|
|||||||
if (message.users && Array.isArray(message.users)) {
|
if (message.users && Array.isArray(message.users)) {
|
||||||
// 转换用户数据格式,确保与位置追踪服务兼容
|
// 转换用户数据格式,确保与位置追踪服务兼容
|
||||||
const formattedUsers = message.users.map((user: any) => {
|
const formattedUsers = message.users.map((user: any) => {
|
||||||
// 支持多种数据格式:locationData字段或直接字段
|
|
||||||
const locationData = user.locationData || user;
|
|
||||||
|
|
||||||
// 验证必需字段是否存在
|
// 验证必需字段是否存在
|
||||||
if (!user.userId && !locationData.userId) {
|
if (!user.userId) {
|
||||||
console.error('❌ 用户数据缺少userId字段:', user);
|
console.error('❌ 用户数据缺少userId字段:', user);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (locationData.latitude === undefined || locationData.longitude === undefined) {
|
if (user.latitude === undefined || user.longitude === undefined) {
|
||||||
console.error('❌ 用户数据缺少位置信息:', user);
|
console.error('❌ 用户数据缺少位置信息:', user);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 对于位置更新消息,允许缺少name和role字段,从本地缓存中获取
|
// 对于位置更新消息,允许缺少name和role字段,从本地缓存中获取
|
||||||
const existingUser = this.onlineUsers.get(user.userId || locationData.userId);
|
const existingUser = this.onlineUsers.get(user.userId);
|
||||||
|
|
||||||
const formattedUser = {
|
const formattedUser = {
|
||||||
userId: user.userId || locationData.userId,
|
userId: user.userId,
|
||||||
name: user.name || user.userName || (existingUser ? existingUser.name : `用户${user.userId || locationData.userId}`),
|
name: user.name || user.userName || (existingUser ? existingUser.name : `用户${user.userId}`),
|
||||||
role: user.role || (existingUser ? existingUser.role : 'DRIVER'),
|
role: user.role || (existingUser ? existingUser.role : 'DRIVER'),
|
||||||
userStatus: user.userStatus !== false, // 转换为布尔值
|
userStatus: user.userStatus !== false, // 转换为布尔值
|
||||||
lastUpdateTime: user.lastUpdateTime || locationData.timestamp || Date.now(),
|
lastUpdateTime: user.lastUpdateTime || user.timestamp || Date.now(),
|
||||||
latitude: locationData.latitude,
|
latitude: user.latitude,
|
||||||
longitude: locationData.longitude,
|
longitude: user.longitude,
|
||||||
timestamp: locationData.timestamp || user.timestamp || Date.now(),
|
timestamp: user.timestamp || Date.now(),
|
||||||
avatarPath: user.avatarPath || (existingUser ? existingUser.avatarPath : undefined),
|
avatarPath: user.avatarPath || (existingUser ? existingUser.avatarPath : undefined),
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -478,16 +477,16 @@ class LocationTrackingService {
|
|||||||
console.error('❌ 用户数据缺少userId字段:', formattedUser);
|
console.error('❌ 用户数据缺少userId字段:', formattedUser);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
if (formattedUser.latitude === undefined || formattedUser.longitude === undefined) {
|
||||||
|
console.error('❌ 用户数据缺少位置信息:', formattedUser);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
return formattedUser;
|
return formattedUser;
|
||||||
}).filter((user: any) => user !== null); // 过滤掉无效数据
|
}).filter((user: any) => user !== null); // 过滤掉无效数据
|
||||||
|
|
||||||
console.log('📊 转换后的用户位置数据:', formattedUsers);
|
console.log('📊 转换后的用户位置数据:', formattedUsers);
|
||||||
|
this.handleOnlineUserList(formattedUsers);
|
||||||
this.triggerOnlineUserListCallbacks({
|
|
||||||
type: 'userLocationList',
|
|
||||||
users: formattedUsers
|
|
||||||
});
|
|
||||||
} else {
|
} else {
|
||||||
console.warn('❌ userLocationList消息格式错误,users字段不存在或不是数组');
|
console.warn('❌ userLocationList消息格式错误,users字段不存在或不是数组');
|
||||||
}
|
}
|
||||||
@@ -498,26 +497,6 @@ class LocationTrackingService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* 触发在线用户列表回调函数
|
|
||||||
* @param userList 在线用户列表数据
|
|
||||||
*/
|
|
||||||
private triggerOnlineUserListCallbacks(userList: any): void {
|
|
||||||
console.log('🔔 [apiService] 开始触发在线用户列表回调,消息类型:', userList.type);
|
|
||||||
console.log('📊 [apiService] 回调数据内容:', JSON.stringify(userList, null, 2));
|
|
||||||
|
|
||||||
|
|
||||||
try {
|
|
||||||
console.log('🔄 [apiService] 执行在线用户列表回调函数');
|
|
||||||
// 传递正确的数据格式:只传递users数组,而不是整个消息对象
|
|
||||||
this.handleOnlineUserList(userList.users);
|
|
||||||
console.log('✅ [apiService] 在线用户列表回调函数执行成功');
|
|
||||||
} catch (error) {
|
|
||||||
console.error('❌ [apiService] 在线用户列表回调函数执行失败:', error);
|
|
||||||
}
|
|
||||||
console.log('🏁 [apiService] 在线用户列表回调触发完成');
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 处理在线用户列表
|
* 处理在线用户列表
|
||||||
* @param userList 服务器下发的在线用户列表
|
* @param userList 服务器下发的在线用户列表
|
||||||
@@ -542,7 +521,7 @@ class LocationTrackingService {
|
|||||||
if (user && user.userId && user.latitude !== undefined && user.longitude !== undefined) {
|
if (user && user.userId && user.latitude !== undefined && user.longitude !== undefined) {
|
||||||
newUserIds.add(user.userId);
|
newUserIds.add(user.userId);
|
||||||
|
|
||||||
// 提取位置数据(支持多种数据格式)
|
// 提取位置数据(直接字段)
|
||||||
const latitude = user.latitude;
|
const latitude = user.latitude;
|
||||||
const longitude = user.longitude;
|
const longitude = user.longitude;
|
||||||
const timestamp = user.timestamp || user.lastUpdateTime || Date.now();
|
const timestamp = user.timestamp || user.lastUpdateTime || Date.now();
|
||||||
@@ -556,19 +535,11 @@ class LocationTrackingService {
|
|||||||
name: user.name || user.userName || (existingUser ? existingUser.name : `用户${user.userId}`),
|
name: user.name || user.userName || (existingUser ? existingUser.name : `用户${user.userId}`),
|
||||||
avatarPath: user.avatarPath || (existingUser ? existingUser.avatarPath : undefined),
|
avatarPath: user.avatarPath || (existingUser ? existingUser.avatarPath : undefined),
|
||||||
role: user.role || (existingUser ? existingUser.role : 'DRIVER'),
|
role: user.role || (existingUser ? existingUser.role : 'DRIVER'),
|
||||||
lastLocation: {
|
latitude: latitude, // 直接使用纬度字段
|
||||||
userId: user.userId,
|
longitude: longitude, // 直接使用经度字段
|
||||||
longitude: longitude,
|
timestamp: timestamp, // 直接使用时间戳字段
|
||||||
latitude: latitude,
|
|
||||||
timestamp: timestamp
|
|
||||||
},
|
|
||||||
lastUpdateTime: timestamp,
|
lastUpdateTime: timestamp,
|
||||||
status: user.userStatus === false ? 'offline' : 'online',
|
status: user.userStatus === false ? 'offline' : 'online',
|
||||||
// currentLocation: {
|
|
||||||
// address: user.address || (existingUser ? existingUser.currentLocation?.address : '位置信息获取中...'),
|
|
||||||
// longitude: longitude,
|
|
||||||
// latitude: latitude
|
|
||||||
// }
|
|
||||||
});
|
});
|
||||||
|
|
||||||
console.log(`[LocationTrackingService] 更新用户 ${user.userId} 位置: (${latitude}, ${longitude})`);
|
console.log(`[LocationTrackingService] 更新用户 ${user.userId} 位置: (${latitude}, ${longitude})`);
|
||||||
|
|||||||
@@ -260,6 +260,16 @@ class MapService {
|
|||||||
return R * c;
|
return R * c;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 计算路线(calculateRoute的别名方法)
|
||||||
|
* @param origin 起点坐标字符串 (经度,纬度)
|
||||||
|
* @param destination 终点坐标字符串 (经度,纬度)
|
||||||
|
* @returns 路线规划结果
|
||||||
|
*/
|
||||||
|
async calculateRoute(origin: string, destination: string): Promise<RoutePlanResult> {
|
||||||
|
return this.getDrivingRoute(origin, destination);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取路线规划(通用版本)
|
* 获取路线规划(通用版本)
|
||||||
* @param origin 起点坐标
|
* @param origin 起点坐标
|
||||||
|
|||||||
@@ -14,6 +14,27 @@ export interface StatisticsData {
|
|||||||
timestamp: number; // 数据时间戳
|
timestamp: number; // 数据时间戳
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 工作统计数据接口
|
||||||
|
*/
|
||||||
|
export interface WorkStats {
|
||||||
|
todayOrders: number; // 今日订单数
|
||||||
|
completedOrders: number; // 已完成订单数
|
||||||
|
pendingOrders: number; // 待处理订单数
|
||||||
|
timestamp: number; // 数据时间戳
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 个人统计数据接口
|
||||||
|
*/
|
||||||
|
export interface PersonalStats {
|
||||||
|
totalOrders: number; // 总订单数
|
||||||
|
completedOrders: number; // 已完成订单数
|
||||||
|
pendingOrders: number; // 待处理订单数
|
||||||
|
averageDeliveryTime: number; // 平均配送时间(分钟)
|
||||||
|
timestamp: number; // 数据时间戳
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 统计服务类
|
* 统计服务类
|
||||||
* 提供系统统计数据的获取和缓存功能
|
* 提供系统统计数据的获取和缓存功能
|
||||||
@@ -25,6 +46,13 @@ class StatisticsService {
|
|||||||
// 缓存超时时间(5分钟)
|
// 缓存超时时间(5分钟)
|
||||||
private readonly cacheTimeout = 5 * 60 * 1000;
|
private readonly cacheTimeout = 5 * 60 * 1000;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 构造函数
|
||||||
|
*/
|
||||||
|
constructor() {
|
||||||
|
// 不需要初始化HTTP客户端,直接使用apiService
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取系统统计数据
|
* 获取系统统计数据
|
||||||
* 采用一个API请求获取三个统计数据,后续操作客户端自行统计
|
* 采用一个API请求获取三个统计数据,后续操作客户端自行统计
|
||||||
@@ -101,6 +129,64 @@ class StatisticsService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取工作统计数据
|
||||||
|
*/
|
||||||
|
async getWorkStats(): Promise<WorkStats> {
|
||||||
|
try {
|
||||||
|
// 使用apiService的getOrderStats方法获取今日订单统计
|
||||||
|
const response = await apiService.getOrderStats('today');
|
||||||
|
|
||||||
|
// 转换API响应格式为WorkStats格式
|
||||||
|
return {
|
||||||
|
todayOrders: response.totalOrders || 0,
|
||||||
|
completedOrders: response.completedOrders || 0,
|
||||||
|
pendingOrders: response.inProgressOrders || 0,
|
||||||
|
timestamp: Date.now()
|
||||||
|
};
|
||||||
|
} catch (error) {
|
||||||
|
console.error('获取工作统计数据失败:', error);
|
||||||
|
// 如果API调用失败,返回默认值
|
||||||
|
return {
|
||||||
|
todayOrders: 0,
|
||||||
|
completedOrders: 0,
|
||||||
|
pendingOrders: 0,
|
||||||
|
timestamp: Date.now()
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取个人统计数据
|
||||||
|
* 由于API中没有直接的个人统计接口,这里返回默认值
|
||||||
|
* 实际应用中应该从订单服务中获取当前用户的订单统计
|
||||||
|
*/
|
||||||
|
async getPersonalStats(): Promise<PersonalStats> {
|
||||||
|
try {
|
||||||
|
// 在实际应用中,这里应该调用订单服务获取当前用户的订单统计
|
||||||
|
// 由于API限制,暂时返回默认值
|
||||||
|
console.warn('个人统计API不可用,返回默认值');
|
||||||
|
|
||||||
|
return {
|
||||||
|
totalOrders: 0,
|
||||||
|
completedOrders: 0,
|
||||||
|
pendingOrders: 0,
|
||||||
|
averageDeliveryTime: 0,
|
||||||
|
timestamp: Date.now()
|
||||||
|
};
|
||||||
|
} catch (error) {
|
||||||
|
console.error('获取个人统计数据失败:', error);
|
||||||
|
// 如果API调用失败,返回默认值
|
||||||
|
return {
|
||||||
|
totalOrders: 0,
|
||||||
|
completedOrders: 0,
|
||||||
|
pendingOrders: 0,
|
||||||
|
averageDeliveryTime: 0,
|
||||||
|
timestamp: Date.now()
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 手动刷新统计数据(清除缓存)
|
* 手动刷新统计数据(清除缓存)
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -113,19 +113,20 @@ export interface Order {
|
|||||||
deliveryPersonId?: number; // 货运人员ID
|
deliveryPersonId?: number; // 货运人员ID
|
||||||
}
|
}
|
||||||
|
|
||||||
// 货运人员接口
|
// 货运人员接口(扩展自员工信息,包含员工管理中的字段)
|
||||||
export interface DeliveryPerson {
|
export interface DeliveryPerson extends Omit<EmployeeInfo, 'role'> {
|
||||||
id: number;
|
|
||||||
name: string;
|
|
||||||
phone: string;
|
|
||||||
status: 'idle' | 'busy' | 'offline';
|
status: 'idle' | 'busy' | 'offline';
|
||||||
currentLocation: { // 当前位置
|
currentLocation: { // 当前位置
|
||||||
longitude: number;
|
longitude: number;
|
||||||
latitude: number;
|
latitude: number;
|
||||||
};
|
};
|
||||||
currentOrders: Order[]; // 当前订单列表
|
currentOrders: Order[]; // 当前订单列表
|
||||||
avatarPath?: string; // 头像相对路径(服务器返回的路径,如 "/avatars/1.jpg")
|
// 以下字段已从EmployeeInfo继承:
|
||||||
avatarThumbnail?: string; // 头像缩略图URL
|
// id: number; // 员工ID
|
||||||
|
// name: string; // 员工姓名
|
||||||
|
// phone: string; // 员工电话
|
||||||
|
// avatarPath?: string; // 头像相对路径
|
||||||
|
// avatarThumbnail?: string; // 头像缩略图URL
|
||||||
}
|
}
|
||||||
|
|
||||||
// 路径规划结果接口
|
// 路径规划结果接口
|
||||||
@@ -135,13 +136,13 @@ export interface RoutePlanResult {
|
|||||||
duration: number; // 预计时间(秒)
|
duration: number; // 预计时间(秒)
|
||||||
}
|
}
|
||||||
|
|
||||||
// 实时位置数据接口
|
// 实时位置数据接口(已弃用,服务器不再使用嵌套对象)
|
||||||
export interface LocationData {
|
// export interface LocationData {
|
||||||
userId: number; // 用户ID
|
// userId: number; // 用户ID
|
||||||
longitude: number; // 经度
|
// longitude: number; // 经度
|
||||||
latitude: number; // 纬度
|
// latitude: number; // 纬度
|
||||||
timestamp: number; // 时间戳
|
// timestamp: number; // 时间戳
|
||||||
}
|
// }
|
||||||
|
|
||||||
// 高德地图逆地理编码响应接口
|
// 高德地图逆地理编码响应接口
|
||||||
export interface AMapRegeoResponse {
|
export interface AMapRegeoResponse {
|
||||||
|
|||||||
@@ -23,7 +23,8 @@ class AvatarCache {
|
|||||||
* @returns 本地图片路径或Promise<string>
|
* @returns 本地图片路径或Promise<string>
|
||||||
*/
|
*/
|
||||||
public async getAvatarPath(avatarUrl: string): Promise<string> {
|
public async getAvatarPath(avatarUrl: string): Promise<string> {
|
||||||
if (!avatarUrl) {
|
if (!avatarUrl || avatarUrl === 'null' || avatarUrl.includes('null')) {
|
||||||
|
console.warn('❌ [AvatarCache] 无效的头像URL:', avatarUrl);
|
||||||
return this.getDefaultAvatarPath();
|
return this.getDefaultAvatarPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user