feat: 新增师傅端功能及服务增项管理模块

- 新增师傅端路由和页面配置,切换登录后默认跳转到师傅大厅
- 新增服务分类图标上传功能和增项服务管理模块
- 新增订单、申诉、结算等模型关联关系及后台控制器
- 新增师傅端TabBar组件和消息页面跳转逻辑
- 新增文件上传接口和服务计算逻辑
- 新增各类SVG图标和空状态提示
这个提交包含在:
YuanWen
2026-11-03 15:45:21 +08:00
父节点 c01e8fc7d9
当前提交 361dffc7d8
共有 82 个文件被更改,包括 4787 次插入 和 531 次删除

查看文件

@@ -9,7 +9,7 @@ use think\Db;
*/
class Home extends Base
{
protected $noNeedLogin = ['index', 'cats', 'services', 'detail'];
protected $noNeedLogin = ['index', 'cats', 'services', 'detail', 'calc', 'specs', 'masterCount'];
/**
* 首页聚合:类目 + 热门服务 + 我的角标
@@ -57,6 +57,23 @@ class Home extends Base
->where('status', 'normal')
->order('weigh desc,id asc')
->select();
foreach ($cats as &$c) {
$icon = (string)$c['icon'];
if ($icon !== '') {
if (strpos($icon, 'http') === 0) {
$c['icon_url'] = $icon;
} elseif (strpos($icon, '/') !== false || strpos($icon, '.') !== false) {
$c['icon_url'] = cdnurl($icon, true);
} else {
$c['icon_url'] = '';
}
} else {
$c['icon_url'] = '';
}
}
unset($c);
$this->success('', ['list' => $cats]);
}
@@ -166,7 +183,7 @@ class Home extends Base
public function calc()
{
$serviceId = (int)$this->request->param('service_id');
$goodsListRaw = $this->request->param('goods_list');
$goodsListRaw = $this->request->param('goods_list/a');
$goodsList = [];
if (!empty($goodsListRaw)) {
$goodsList = is_array($goodsListRaw) ? $goodsListRaw : json_decode((string)$goodsListRaw, true);
@@ -472,12 +489,52 @@ class Home extends Base
} elseif ($type === 'quote') {
$priceText = '¥' . (float)$row['base_price'] . ' · 师傅报价';
}
// 解析工项
$serviceTypes = [];
if (!empty($row['service_types'])) {
$serviceTypes = is_array($row['service_types']) ? $row['service_types'] : json_decode($row['service_types'], true);
}
if (empty($serviceTypes)) {
$serviceTypes = [
['code' => 'install', 'name' => '安装', 'price' => (float)$row['base_price'], 'is_default' => 1],
['code' => 'repair', 'name' => '维修', 'price' => round((float)$row['base_price'] * 0.7, 2), 'is_default' => 0],
['code' => 'remove', 'name' => '拆旧', 'price' => round((float)$row['base_price'] * 0.5, 2), 'is_default' => 0],
['code' => 'deliver', 'name' => '送货到家', 'price' => 50.00, 'is_default' => 0],
];
}
// 解析增项
$addons = [];
if (!empty($row['addons'])) {
$addons = is_array($row['addons']) ? $row['addons'] : json_decode($row['addons'], true);
}
if (empty($addons)) {
// 获取类目通用增项
$catAddons = Db::name('service_addon')
->where('status', 'normal')
->where(function($q) use ($row) {
$q->where('cat_id', $row['cat_id'])->whereOr('cat_id', 0);
})
->order('weigh desc, id asc')
->limit(8)
->select();
foreach ($catAddons as $ca) {
$addons[] = [
'id' => (int)$ca['id'],
'name' => $ca['name'],
'unit' => $ca['unit'],
'price' => (float)$ca['default_price']
];
}
}
return [
'id' => (int)$row['id'],
'cat_id' => (int)$row['cat_id'],
'name' => $row['name'],
'cat_name' => isset($row['cat_name']) ? $row['cat_name'] : '',
'image' => $row['image'],
'image_url' => $row['image'] ? cdnurl($row['image'], true) : '',
'price_type' => $type,
'price_type_text' => $type === 'fixed' ? '一口价' : ($type === 'quote' ? '师傅报价' : '按面积计价'),
'base_price' => (float)$row['base_price'],
@@ -489,6 +546,8 @@ class Home extends Base
'free_floor' => isset($row['free_floor']) ? (int)$row['free_floor'] : 0,
'need_model' => isset($row['need_model']) ? (int)$row['need_model'] : 1,
'description' => isset($row['description']) ? $row['description'] : '',
'service_types' => $serviceTypes,
'addons' => $addons,
];
}
}