Browse Source

绘制电子地图

master
wanghongjun 1 week ago
parent
commit
f3bbb92fe5
  1. 132
      app/Http/Controllers/Admin/ParkingElectronicMapController.php
  2. 27
      app/Models/ParkingElectronicMap.php
  3. 16
      app/Services/AdminFloorService.php
  4. 72
      app/Services/ParkingElectronicMapService.php
  5. 9
      app/Services/ParkingSpaceService.php
  6. 33
      database/migrations/2026_04_23_143449_create_parking_electronic_map_table.php
  7. 1
      resources/lang/en/admin.php
  8. 1
      resources/lang/zh-CN/admin.php
  9. 3
      resources/lang/zh-CN/log.php
  10. 6
      resources/lang/zh-CN/validation.php
  11. 1
      resources/lang/zh-TW/admin.php
  12. 6
      routes/admin/api.php

132
app/Http/Controllers/Admin/ParkingElectronicMapController.php

@ -0,0 +1,132 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Models\ParkingElectronicMap;
use App\Services\AdminFloorService;
use App\Services\ApiResponseService;
use App\Services\ParkingElectronicMapService;
use App\Services\ParkingSpaceService;
use Exception;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Validator;
use Illuminate\Validation\ValidationException;
class ParkingElectronicMapController extends BaseController
{
protected ParkingElectronicMapService $service;
/**
* 构造函数
* @param ApiResponseService $responseService
* @param ParkingElectronicMapService $service
*/
public function __construct(
ApiResponseService $responseService,
ParkingElectronicMapService $service
) {
parent::__construct($responseService);
$this->service = $service;
}
/**
* 查询楼层
* @return JsonResponse
*/
public function floorList(): JsonResponse
{
try {
$data = [
'floor_list' => AdminFloorService::getSelectList()
];
return $this->responseService->success($data);
} catch (Exception $e) {
$m_prefix = __('exception.exception_handler.resource');
return $this->responseService->systemError(
$m_prefix . ':' . $e->getMessage()
);
}
}
/**
* 查询车位号码
* @param $id
* @return JsonResponse
*/
public function getParkingSpaceList($id): JsonResponse
{
try {
$this->saveValidator(['floor_id' => $id]);
$list = ParkingSpaceService::getSelectList($id);
$data = [
'parking_space_list' => $list
];
return $this->responseService->success($data);
} catch (Exception $e) {
$m_prefix = __('exception.exception_handler.resource');
return $this->responseService->systemError(
$m_prefix . ':' . $e->getMessage()
);
}
}
/**
* @param array $data
* @param int $is_save
* @return void
* @throws ValidationException
*/
protected function saveValidator(array $data, int $is_save = 0): void
{
$rules = [
'floor_id' => 'required|numeric',
];
$messages = [
'floor_id.required' => __('validation.map.f_empty'),
'floor_id.numeric' => __('validation.map.f_number')
];
if ($is_save) {
$rules['parking_space_id'] = 'required|numeric';
$messages['parking_space_id.required'] = __('validation.map.p_empty');
$messages['parking_space_id.numeric'] = __('validation.map.p_number');
}
$validator = Validator::make($data, $rules, $messages);
if ($validator->fails()) {
throw new ValidationException($validator);
}
}
public function save(Request $request): JsonResponse
{
try {
$data = $request->all();
$this->saveValidator($data, 1);
$this->service->saveModel($data);
return $this->responseService->success([], __('admin.save_succeeded'));
} catch (Exception $e) {
$m_prefix = __('admin.save_failed');
return $this->responseService->systemError(
$m_prefix . ':' . $e->getMessage()
);
}
}
public function index(Request $request): JsonResponse
{
try {
$data = $request->all();
$this->saveValidator($data);
$list = $this->service->getList($data);
return $this->responseService->success($list);
} catch (Exception $e) {
$m_prefix = __('exception.exception_handler.resource');
return $this->responseService->systemError(
$m_prefix . ':' . $e->getMessage()
);
}
}
}

27
app/Models/ParkingElectronicMap.php

@ -0,0 +1,27 @@
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
class ParkingElectronicMap extends Model
{
use HasFactory;
protected $table = 'parking_electronic_map';
protected $fillable = [
'floor_id',
'space_id',
'width',
'height',
'coordinate_x',
'coordinate_y'
];
protected $hidden = [
'created_at',
'updated_at'
];
}

16
app/Services/AdminFloorService.php

@ -175,4 +175,20 @@ class AdminFloorService
throw $e; throw $e;
} }
} }
// 获取楼层列表
public static function getSelectList(): array
{
$column = [
'id as floor_id',
'name as floor_name',
'image_url as pic_url'
];
$list = AdminFloor::query()->whereNull('deleted_at')->select($column)
->get()->toArray();
foreach ($list as &$item) {
$item['pic_url'] = env('app_url') . $item['pic_url'];
}
return $list;
}
} }

72
app/Services/ParkingElectronicMapService.php

@ -0,0 +1,72 @@
<?php
namespace App\Services;
use App\Models\AdminFloor;
use App\Models\ParkingElectronicMap;
use App\Models\ParkingSpace;
class ParkingElectronicMapService extends BaseService
{
public function saveModel(array $data)
{
$floor_id = $data['floor_id'];
$space_id = $data['parking_space_id'];
$saveData = $where = [
'floor_id' => $floor_id,
'space_id' => $space_id
];
$res = ParkingElectronicMap::query()->where($where)->get()->toArray();
$saveData['width'] = $data['width'] ?? '0';
$saveData['height'] = $data['height'] ?? '0';
$saveData['coordinate_x'] = $data['coordinate_x'] ?? '';
$saveData['coordinate_y'] = $data['coordinate_y'] ?? '';
if ($res) {
$saveData['update_at'] = get_datetime();
$model = ParkingElectronicMap::query()->findOrFail($res[0]['id']);
$oldValues = $model->toArray();
$model->update($saveData);
$this->logService->logUpdated($model, $oldValues, 'map.save');
} else {
$saveData['create_at'] = get_datetime();
$model = ParkingElectronicMap::query()->create($saveData);
$this->logService->logCreated($model, 'map.save');
}
}
public function getList($params): array
{
$floor_id = $params['floor_id'];
$where = [
'floor_id' => $floor_id
];
if (isset($params['parking_space_id'])
&& !empty($params['parking_space_id'])
) {
$where['space_id'] = $params['parking_space_id'];
}
$columns = [
'id',
'floor_id',
'space_id',
'width',
'height',
'coordinate_x',
'coordinate_y'
];
$list = ParkingElectronicMap::query()->where($where)->select($columns)
->get()->toArray();
foreach ($list as &$item) {
$item['floor_name'] = AdminFloor::query()->where('id', $item['floor_id'])
->value('name');
$item['parking_space_number'] = ParkingSpace::query()->where(
'id',
$item['space_id']
)->value('number');
unset($item['floor_id'], $item['space_id']);
}
return $list;
}
}

9
app/Services/ParkingSpaceService.php

@ -147,4 +147,13 @@ class ParkingSpaceService extends BaseService
throw $e; throw $e;
} }
} }
// 获取车位列表
public static function getSelectList($floor_id): array
{
$columns = ['id as parking_space_id', 'number as parking_space_number'];
return ParkingSpace::query()->where('floor_id', $floor_id)->select(
$columns
)->get()->toArray();
}
} }

33
database/migrations/2026_04_23_143449_create_parking_electronic_map_table.php

@ -0,0 +1,33 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*/
public function up(): void
{
Schema::create('parking_electronic_map', function (Blueprint $table) {
$table->id();
$table->integer('floor_id')->comment('楼层id');
$table->integer('space_id')->default('')->comment('车位号码');
$table->string('width', 20)->default('')->comment('宽');
$table->string('height', 20)->default('')->comment('高');
$table->string('coordinate_x', 20)->default('')->comment('坐标X');
$table->string('coordinate_y', 20)->default('')->comment('坐标y');
$table->timestamps();
});
}
/**
* Reverse the migrations.
*/
public function down(): void
{
Schema::dropIfExists('parking_electronic_map');
}
};

1
resources/lang/en/admin.php

@ -52,6 +52,7 @@ return [
'delete_failed' => 'Delete failed !', 'delete_failed' => 'Delete failed !',
'update_succeeded' => 'Update succeeded !', 'update_succeeded' => 'Update succeeded !',
'save_succeeded' => 'Save succeeded !', 'save_succeeded' => 'Save succeeded !',
'save_failed' => 'Save failed !',
'refresh_succeeded' => 'Refresh succeeded !', 'refresh_succeeded' => 'Refresh succeeded !',
'login_successful' => 'Login successful', 'login_successful' => 'Login successful',
'logout_successful' => 'Logout successful', 'logout_successful' => 'Logout successful',

1
resources/lang/zh-CN/admin.php

@ -52,6 +52,7 @@ return [
'delete_failed' => '删除失败 !', 'delete_failed' => '删除失败 !',
'update_succeeded' => '更新成功 !', 'update_succeeded' => '更新成功 !',
'save_succeeded' => '保存成功 !', 'save_succeeded' => '保存成功 !',
'save_failed' => '失败成功 !',
'refresh_succeeded' => '刷新成功 !', 'refresh_succeeded' => '刷新成功 !',
'login_successful' => '登录成功 !', 'login_successful' => '登录成功 !',
'logout_successful' => '登出成功 !', 'logout_successful' => '登出成功 !',

3
resources/lang/zh-CN/log.php

@ -51,5 +51,8 @@ return [
'create' => '创建VIP名单', 'create' => '创建VIP名单',
'update' => '更新VIP名单', 'update' => '更新VIP名单',
'delete' => '删除VIP名单' 'delete' => '删除VIP名单'
],
'map' => [
'save' => '绘制电子地图保存'
] ]
]; ];

6
resources/lang/zh-CN/validation.php

@ -76,5 +76,11 @@ return [
'attr_id_numeric' => '车位属性数据必须是数字', 'attr_id_numeric' => '车位属性数据必须是数字',
'ids_empty' => '车位数据不能为空', 'ids_empty' => '车位数据不能为空',
'ids_array' => '车位数据必须是数组', 'ids_array' => '车位数据必须是数组',
],
'map' => [
'f_empty' => '楼层编号不能为空',
'f_number' => '楼层编号必须是数字',
'p_empty' => '车位编号必须是数字',
'p_number' => '车位编号必须是数字'
] ]
]; ];

1
resources/lang/zh-TW/admin.php

@ -52,6 +52,7 @@ return [
'delete_failed' => '刪除失敗!', 'delete_failed' => '刪除失敗!',
'update_succeeded' => '更新成功!', 'update_succeeded' => '更新成功!',
'save_succeeded' => '儲存成功!', 'save_succeeded' => '儲存成功!',
'save_failed' => '儲存失敗!',
'refresh_succeeded' => '成功重新整理!', 'refresh_succeeded' => '成功重新整理!',
'login_successful' => '成功登入!', 'login_successful' => '成功登入!',
'logout_successful' => '成功登出!', 'logout_successful' => '成功登出!',

6
routes/admin/api.php

@ -7,6 +7,7 @@ use App\Http\Controllers\Admin\IndexController;
use App\Http\Controllers\Admin\VipAccessRecordController; use App\Http\Controllers\Admin\VipAccessRecordController;
use App\Http\Controllers\Admin\VipListController; use App\Http\Controllers\Admin\VipListController;
use App\Http\Controllers\Admin\OperationLogController; use App\Http\Controllers\Admin\OperationLogController;
use App\Http\Controllers\Admin\ParkingElectronicMapController;
use App\Http\Controllers\Admin\ParkingLicensePlateController; use App\Http\Controllers\Admin\ParkingLicensePlateController;
use App\Http\Controllers\Admin\ParkingReservationController; use App\Http\Controllers\Admin\ParkingReservationController;
use App\Http\Controllers\Admin\ParkingSpaceController; use App\Http\Controllers\Admin\ParkingSpaceController;
@ -66,6 +67,11 @@ Route::group(['prefix' => 'admin'], function () {
Route::put('/spaceAttr/{id}', [ParkingSpaceAttributesController::class, 'update']); Route::put('/spaceAttr/{id}', [ParkingSpaceAttributesController::class, 'update']);
Route::delete('/spaceAttr/{id}', [ParkingSpaceAttributesController::class, 'destroy']); Route::delete('/spaceAttr/{id}', [ParkingSpaceAttributesController::class, 'destroy']);
Route::get('/spaceAttr/rule', [ParkingSpaceAttributesController::class, 'rule']); Route::get('/spaceAttr/rule', [ParkingSpaceAttributesController::class, 'rule']);
// 绘制电子地图
Route::get('/map/index', [ParkingElectronicMapController::class, 'index']);
Route::get('/map/floorList', [ParkingElectronicMapController::class, 'floorList']);
Route::get('/map/parkingSpaceList/{id}', [ParkingElectronicMapController::class, 'getParkingSpaceList']);
Route::post('/map/save', [ParkingElectronicMapController::class, 'save']);
// VIP名单 // VIP名单
Route::get('/vipList', [VipListController::class, 'index']); Route::get('/vipList', [VipListController::class, 'index']);

Loading…
Cancel
Save