添加后台区域标记大屏位置功能
parent
bdc88db320
commit
5fde7566f4
|
|
@ -10,8 +10,9 @@ use Slowlyo\OwlAdmin\Controllers\AdminController;
|
|||
use App\Services\Admin\RegionService;
|
||||
use Slowlyo\OwlAdmin\Renderers\Button;
|
||||
use App\Admin\Components;
|
||||
use App\Models\Device;
|
||||
use App\Models\MonitorMode;
|
||||
use App\Models\Region;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class RegionController extends AdminController
|
||||
{
|
||||
|
|
@ -50,7 +51,9 @@ class RegionController extends AdminController
|
|||
amisMake()->Operation()->label(__('admin.actions'))->buttons([
|
||||
$this->showRegion(),
|
||||
$this->rowEditButton(true, 'lg'),
|
||||
$this->rowDeleteButton()
|
||||
$this->rowDeleteButton(),
|
||||
amisMake()->Button()->label('设置大屏位置')->level('link')->actionType('url')->blank(true)
|
||||
->url(url('/regions-position').'/'.'${id}')
|
||||
]),
|
||||
]);
|
||||
|
||||
|
|
@ -93,4 +96,32 @@ class RegionController extends AdminController
|
|||
])->size('full')->actions([])
|
||||
);
|
||||
}
|
||||
|
||||
public function setRegionPosition($id, Request $request){
|
||||
$region = Region::find($id);
|
||||
$x = $region?->position_x ?? 0;
|
||||
$y = $region?->position_y ?? 0;
|
||||
return view('region-position', compact('id', 'x', 'y'));
|
||||
}
|
||||
|
||||
public function saveRegionPosition(Request $request)
|
||||
{
|
||||
$id = $request->input('id', 0);
|
||||
$positionX = $request->input('x', 0);
|
||||
$positionY = $request->input('y', 0);
|
||||
$region = Region::find($id);
|
||||
if(!$region){
|
||||
return response()->json(['code'=>1, 'msg'=> '非法请求']);
|
||||
}
|
||||
if($positionX <= 0 || $positionY <= 0){
|
||||
return response()->json(['code'=>2, 'msg'=>'请点击地图,标记位置']);
|
||||
}
|
||||
$region->update([
|
||||
'position_x'=> $positionX,
|
||||
'position_y'=> $positionY
|
||||
]);
|
||||
//直接关闭窗口
|
||||
echo '<script>window.opener=null;window.close();</script>';
|
||||
return ;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Binary file not shown.
|
After Width: | Height: | Size: 8.8 MiB |
|
|
@ -0,0 +1 @@
|
|||
!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e():"function"==typeof define&&define.amd?define(e):(t="undefined"!=typeof globalThis?globalThis:t||self).uuidv4=e()}(this,(function(){"use strict";var t,e=new Uint8Array(16);function o(){if(!t&&!(t="undefined"!=typeof crypto&&crypto.getRandomValues&&crypto.getRandomValues.bind(crypto)||"undefined"!=typeof msCrypto&&"function"==typeof msCrypto.getRandomValues&&msCrypto.getRandomValues.bind(msCrypto)))throw new Error("crypto.getRandomValues() not supported. See https://github.com/uuidjs/uuid#getrandomvalues-not-supported");return t(e)}var n=/^(?:[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}|00000000-0000-0000-0000-000000000000)$/i;function r(t){return"string"==typeof t&&n.test(t)}for(var i=[],u=0;u<256;++u)i.push((u+256).toString(16).substr(1));return function(t,e,n){var u=(t=t||{}).random||(t.rng||o)();if(u[6]=15&u[6]|64,u[8]=63&u[8]|128,e){n=n||0;for(var f=0;f<16;++f)e[n+f]=u[f];return e}return function(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,o=(i[t[e+0]]+i[t[e+1]]+i[t[e+2]]+i[t[e+3]]+"-"+i[t[e+4]]+i[t[e+5]]+"-"+i[t[e+6]]+i[t[e+7]]+"-"+i[t[e+8]]+i[t[e+9]]+"-"+i[t[e+10]]+i[t[e+11]]+i[t[e+12]]+i[t[e+13]]+i[t[e+14]]+i[t[e+15]]).toLowerCase();if(!r(o))throw TypeError("Stringified UUID is invalid");return o}(u)}}));
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 2.5 KiB |
|
|
@ -0,0 +1,176 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>在地图上打标点</title>
|
||||
<style>
|
||||
/* html,body{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
} */
|
||||
canvas {
|
||||
cursor: crosshair;
|
||||
width:1350px;
|
||||
height: 900px;
|
||||
}
|
||||
|
||||
</style>
|
||||
<script src="{{asset('/admin/js/uuidv4.min.js')}}"></script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<canvas id="myCanvas"></canvas>
|
||||
<div style="position: relative;top:-900px;left: 1360px;width: 100px;">
|
||||
<form id='positionForm' action="{{url('regions-position/save')}}" method="post" enctype="multipart/form-data">
|
||||
@csrf
|
||||
<input type="hidden" name="id" value="{{$id}}">
|
||||
<input type="hidden" name="x" id="x" value="{{$x}}">
|
||||
<input type="hidden" name="y" id="y" value="{{$y}}">
|
||||
<button type="submit" onclick="return submitXY(this.form)">保存</button>
|
||||
<button onclick="script:window.close();">返回</button>
|
||||
</form>
|
||||
</div>
|
||||
<script>
|
||||
const canvas = document.getElementById("myCanvas");
|
||||
const ctx = canvas.getContext("2d");
|
||||
const sx = '{{$x}}';
|
||||
const sy = '{{$y}}';
|
||||
|
||||
const map = new Image();
|
||||
map.src = "/admin/dashboard-map.png";
|
||||
map.onload = function () {
|
||||
resizeCanvas();
|
||||
drawMarkers();
|
||||
};
|
||||
|
||||
const markerImage = new Image();
|
||||
markerImage.src = "/admin/map-marker.png";
|
||||
const markerRadius = 15;
|
||||
|
||||
const markers = [];
|
||||
|
||||
if(sx >0 && sy >0) {
|
||||
markers.push({id: uuidv4(),
|
||||
x:sx,
|
||||
y:sy,
|
||||
selected: false});
|
||||
}
|
||||
|
||||
function addMarker(x, y) {
|
||||
const marker = {
|
||||
id: uuidv4(),
|
||||
x,
|
||||
y,
|
||||
selected: false
|
||||
};
|
||||
markers.length = 0;
|
||||
markers.push(marker);
|
||||
document.getElementById("x").value = x;
|
||||
document.getElementById("y").value = y;
|
||||
console.log("新增", marker);
|
||||
drawMarkers();
|
||||
}
|
||||
|
||||
function drawMarkers() {
|
||||
ctx.clearRect(0, 0, canvas.width, canvas.height);
|
||||
|
||||
// 获取父容器的宽度和高度
|
||||
const canvasWrapper = document.getElementById("myCanvas");
|
||||
const canvasWrapperWidth = canvasWrapper.offsetWidth;
|
||||
const canvasWrapperHeight = canvasWrapper.offsetHeight;
|
||||
// 设置Canvas的大小为父容器的大小
|
||||
canvas.width = canvasWrapperWidth;
|
||||
canvas.height = canvasWrapperHeight;
|
||||
|
||||
// 绘制地图图片并调整大小以铺满Canvas
|
||||
const scale = Math.max(canvas.width / map.width, canvas.height / map.height);
|
||||
const newWidth = map.width * scale;
|
||||
const newHeight = map.height * scale;
|
||||
const offsetX = (canvas.width - newWidth) / 2;
|
||||
const offsetY = (canvas.height - newHeight) / 2;
|
||||
ctx.drawImage(map, offsetX, offsetY, newWidth, newHeight);
|
||||
|
||||
markers.forEach(marker => {
|
||||
|
||||
// if (marker.selected) {
|
||||
// ctx.beginPath();
|
||||
// ctx.arc(marker.x, marker.y, 15, 0, 8 * Math.PI);
|
||||
// ctx.strokeStyle = "red";
|
||||
// ctx.stroke();
|
||||
// }
|
||||
|
||||
ctx.drawImage(markerImage, marker.x - markerRadius, marker.y - markerRadius, markerRadius * 2, markerRadius * 2);
|
||||
});
|
||||
}
|
||||
|
||||
function resizeCanvas() {//初始化地图
|
||||
drawMarkers();
|
||||
}
|
||||
|
||||
window.addEventListener("resize", resizeCanvas);
|
||||
|
||||
let isDragging = false;
|
||||
let dragIndex = -1;
|
||||
|
||||
canvas.addEventListener("mousedown", event => {
|
||||
const x = event.offsetX;
|
||||
const y = event.offsetY;
|
||||
|
||||
markers.forEach((marker, index) => {
|
||||
if (x >= marker.x - markerRadius / 2 && x <= marker.x + markerRadius / 2 && y >= marker.y - markerRadius / 2 && y <= marker.y + markerRadius / 2) {
|
||||
isDragging = true;
|
||||
dragIndex = index;
|
||||
markers[index].selected = true;
|
||||
} else {
|
||||
markers[index].selected = false;
|
||||
}
|
||||
});
|
||||
|
||||
if (!isDragging) {
|
||||
addMarker(x, y);
|
||||
}
|
||||
|
||||
drawMarkers();
|
||||
});
|
||||
|
||||
canvas.addEventListener("mousemove", event => {
|
||||
if (isDragging) {
|
||||
const x = event.offsetX;
|
||||
const y = event.offsetY;
|
||||
|
||||
markers[dragIndex].x = x;
|
||||
markers[dragIndex].y = y;
|
||||
|
||||
drawMarkers();
|
||||
}
|
||||
});
|
||||
|
||||
canvas.addEventListener("mouseup", event => {
|
||||
isDragging = false;
|
||||
dragIndex = -1;
|
||||
});
|
||||
|
||||
function submitXY(theform)
|
||||
{
|
||||
var ttx = document.getElementById("x").value;
|
||||
var tty = document.getElementById("y").value;
|
||||
if(ttx <=0 || tty <=0){
|
||||
alert('请点击地图,标记位置');
|
||||
return false;
|
||||
}
|
||||
|
||||
var res = theform.submit();
|
||||
|
||||
if($res['code'] != undefined){
|
||||
if($res['code'] > 0){
|
||||
alert($res['msg']);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
|
|
@ -20,3 +20,6 @@ Route::prefix('callback')->group(function () {
|
|||
Route::get('/', function () {
|
||||
return view('welcome');
|
||||
});
|
||||
|
||||
$router->get('regions-position/{id}', [\App\Admin\Controllers\RegionController::class, 'setRegionPosition']);
|
||||
$router->post('regions-position/save', [\App\Admin\Controllers\RegionController::class, 'saveRegionPosition']);
|
||||
|
|
|
|||
Loading…
Reference in New Issue