/* 文件名:NewWorldMap.nut 路径:Project/NewWorldMap/NewWorldMap.nut 创建日期:2024-10-27 10:24 文件用途:新世界地图 */ class NewWorldMapC extends LenheartNewUI_Windows { //调试模式 // DeBugMode = true; //不是窗口 // NoWindow = true; //是否可见 // Visible = false; //世界 World = null; //区域 Region = null; //当前自身所在世界 SelfMapWorld = 0; //当前自身所在区域 SelfMapRegion = 0; //当前地图浏览区域 MapRegion = -1; //Img WorldMapImg = null; StepImg = null; Ani = null; Timer = Clock(); constructor(gObjectId, gX, gY, gWidth, gHeight, gTitleH) { Childrens = []; Region = []; World = []; //注册控件 RegisterWidget(); LenheartNewUI_Windows.constructor(gObjectId, gX, gY, gWidth, gHeight, gTitleH); InitData(); // printT(Region); LoadImg(); } function LoadImg() { WorldMapImg = Rindro_Image("worldmap.img"); StepImg = {}; } function InitData() { //读取世界 local WorldLst = R_Utils.GetLstArr("region/world.lst", "region/"); foreach(Path in WorldLst) { InitWorld(Path); } //读取区域 local RegionLst = R_Utils.GetLstArr("region/region.lst", "region/"); foreach(Path in RegionLst) { InitRegion(Path); } //读取小地图 InitMiniMap(); } function InitWorld(Path) { local Data = R_Utils.GetFileTableByHandle(Path, function(DataT, IO, i) { local str = Rindro_Script.UnpackData(IO, i); i += 5; //城镇编号 if (str == "[areas]") { DataT.Areas <- []; while (true) { local Ret = Rindro_Script.UnpackData(IO, i); i += 5; if (Ret == "[/areas]") break; DataT.Areas.append((Ret.tointeger() - 9)); } } //背景 else if (str == "[background]") { DataT.Background <- {}; DataT.Background.path <- Rindro_Script.UnpackData(IO, i); i += 5; DataT.Background.frame <- Rindro_Script.UnpackData(IO, i).tointeger() - 9; i += 5; } //坐标 else if (str == "[pos]") { local Index = Rindro_Script.UnpackData(IO, i).tointeger() - 9; i += 5; local Path = Rindro_Script.UnpackData(IO, i); i += 5; DataT["pos_" + Index] <- []; DataT["pos_" + Index].append(Path); while (true) { local Ret = Rindro_Script.UnpackData(IO, i); i += 5; if (Ret == "[/pos]") break; DataT["pos_" + Index].append((Ret.tointeger() - 9)); } } return i; }.bindenv(this)); World.append(Data); printT(Data); } function InitRegion(Path) { local RegionData = R_Utils.GetScriptFileReader(Path); if (RegionData) { local Data = {}; if (RegionData.Size >= 7) { //创建Blob对象 local IO = Sq_Point2Blob(L_sq_P2I(RegionData.Buffer.C_Object), RegionData.Size); //以5为单步从第二位开始遍历字节 local i = 2; while (true) { if (i< RegionData.Size && RegionData.Size - i >= 5) { local str = Rindro_Script.UnpackData(IO, i); i += 5; //城镇编号 if (str == "[towns]") { Data.Towns <- {}; while (true) { local Ret = Rindro_Script.UnpackData(IO, i); i += 5; if (Ret == "[/towns]") break; Data.Towns.rawset((Ret.tointeger() - 9), {}); } } //名称 else if (str == "[name]" || str == "[english name]" || str == "[minimap]") { local RealKey = str.slice(1, str.len() - 1); local Ret = Rindro_Script.UnpackData(IO, i); if (str == "[name]") Ret = Sq_ConvertWideChar(Ret, "big5") Data[RealKey] <- Ret; i += 5; } } else break; } } Region.append(Data); } } function InitMiniMap() { foreach(Pos, Value in Region) { local Path = "region/" + Value.minimap.tolower(); local MiniMapData = R_Utils.GetScriptFileReader(Path); if (MiniMapData) { local Data = {}; if (MiniMapData.Size >= 7) { //创建Blob对象 local IO = Sq_Point2Blob(L_sq_P2I(MiniMapData.Buffer.C_Object), MiniMapData.Size); //以5为单步从第二位开始遍历字节 local i = 2; while (true) { if (i< MiniMapData.Size && MiniMapData.Size - i >= 5) { local str = Rindro_Script.UnpackData(IO, i); i += 5; //城镇编号 if (str == "[image]") { Data.Image <- {}; while (true) { local Ret = Rindro_Script.UnpackData(IO, i); i += 5; if (Ret == "[/image]") break; Ret = Ret.slice(1, -1); local imgpath = Rindro_Script.UnpackData(IO, i); i += 5; local imgframe = Rindro_Script.UnpackData(IO, i).tointeger() - 9; i += 5; Data.Image.rawset(Ret, { path = imgpath, frame = imgframe }); } } } else break; } } Region[Pos].Data <- Data; } } } function RegisterWidget() { // //关闭按钮 // local CloseButton = LenheartNewUI_BaseButton(278, 0, 11, 12, "interface/lenheartwindowcommon.img", 276); // CloseButton.OnClick = function() { // this.Visible = false; // }.bindenv(this); // Childrens.append(CloseButton); } function GetMoveOffset(L, R) { return (-L) + (L.tofloat() * (R.tofloat() / 100.0)).tointeger() } //绘制主界面 function DrawMain(obj) { local Config = Region[SelfMapRegion]; //绘制背景 WorldMapImg.DrawExPng(0, 0, -83, 0, 0xffffffff, 0.84, 0.84); //绘制地图背景 DrawLogic(Config); local UniRate = sq_GetAccel(0, 100, Clock() - Timer, 1000); local AccRate = sq_GetAccel(0, 100, Clock() - Timer, 1000, true); //绘制左上云1 WorldMapImg.DrawExPng(1, GetMoveOffset(100, AccRate), 0, 0, sq_RGBA(255, 255, 255, ((UniRate.tofloat() / 100.0) * 255.0).tointeger()), 0.84, 0.84); //绘制左上云2 WorldMapImg.DrawExPng(2, GetMoveOffset(100, AccRate), GetMoveOffset(50, AccRate), 0, sq_RGBA(255, 255, 255, ((UniRate.tofloat() / 100.0) * 255.0).tointeger()), 0.84, 0.84); //绘制左下云 WorldMapImg.DrawExPng(3, GetMoveOffset(100, AccRate), 404 + GetMoveOffset(-50, AccRate), 0, sq_RGBA(255, 255, 255, ((UniRate.tofloat() / 100.0) * 255.0).tointeger()), 0.84, 0.84); //绘制右上云 WorldMapImg.DrawExPng(4, 868 + GetMoveOffset(-100, AccRate), 0, 0, sq_RGBA(255, 255, 255, ((UniRate.tofloat() / 100.0) * 255.0).tointeger()), 0.84, 0.84); //绘制右下云 WorldMapImg.DrawExPng(5, 762 + GetMoveOffset(-100, AccRate), 389 + GetMoveOffset(-50, AccRate), 0, sq_RGBA(255, 255, 255, ((UniRate.tofloat() / 100.0) * 255.0).tointeger()), 0.84, 0.84); // local ani = obj.getVar().GetAnimationMap("test", "common/test.ani"); // sq_SetfRotateAngle(ani, sq_ToRadian(60.0)); // sq_AnimationProc(ani); // sq_drawCurrentFrame(ani, 200, 200, true); // Ani.Draw(400, 400); local angle = (GetMoveOffset(135, UniRate).tofloat()) % 360; //中心点 local centerX = 120.0 * 0.6 / 2; local centerY = 120.0 * 0.6 / 2; local Lenght = sqrt(centerX * centerX + centerY * centerY); local atan = sq_ToDegree(sq_Atan2(centerY, centerX)); local NextAngle = (atan + angle).tointeger(); local NextX = (Lenght * sq_CosTable(NextAngle)); local NextY = (Lenght * sq_SinTable(NextAngle)); local newRelX = (centerX - NextX); local newRelY = (centerY - NextY); WorldMapImg.DrawExPng(7, 20, 470, 0, sq_RGBA(255, 255, 255, ((UniRate.tofloat() / 100.0) * 255.0).tointeger()), 0.6, 0.6); WorldMapImg.DrawExPng(6, 39 + newRelX, 489 + newRelY, sq_ToRadian(-angle.tofloat()), 0xffffffff, 0.6, 0.6); } function Show(obj) { DrawMain(obj); LenheartNewUI_Windows.Show(obj); } function GetImgObject(path) { if (!(StepImg.rawin(path))) StepImg.rawset(path, Rindro_Image(path)); return StepImg[path]; } // 环绕数法判断点是否在多边形内 function IsPointInPolygonWindingNumber(x, y, polygon) { local windingNumber = 0; local n = polygon.len(); for (local i = 0; i< n; ++i) { local x1 = polygon[i][0]; local y1 = polygon[i][1]; local x2 = polygon[(i + 1) % n][0]; local y2 = polygon[(i + 1) % n][1]; if (y1 <= y) { if (y2 > y && ((x2 - x1) * (y - y1) - (x - x1) * (y2 - y1) > 0)) { windingNumber++; } } else { if (y2 <= y && ((x2 - x1) * (y - y1) - (x - x1) * (y2 - y1)< 0)) { windingNumber--; } } } return windingNumber != 0; } //绘制世界 function DrawWorld(Config) { local MapCurIndex = SelfMapWorld; local BackgroundData = World[MapCurIndex].Background; local UniRate = sq_GetAccel(0, 250, Clock() - Timer, 1500); local BackgroundDataImgObj = GetImgObject(BackgroundData.path); BackgroundDataImgObj.DrawExPng(BackgroundData.frame, 0, -60, 0, sq_RGBA(255, 255, 255, UniRate), 1.32, 1.32); foreach(index in World[MapCurIndex].Areas) { // print(index); if (!(World[MapCurIndex].rawin("pos_" + index))) continue; local Config = World[MapCurIndex]["pos_" + index]; local BackgroundDataImgObj = GetImgObject(Config[0]); local PointArr = []; for (local i = 4; i< Config.len(); i += 2) { local Buf = []; Buf.append(Config[i]); Buf.append(Config[i + 1]); PointArr.append(Buf); } if (IsPointInPolygonWindingNumber(IMouse.GetXPos().tofloat(), IMouse.GetYPos().tofloat(), PointArr)) { BackgroundDataImgObj.DrawExPng(Config[1], Config[2], Config[3] - 60, 0, sq_RGBA(255, 255, 255, UniRate), 1.32, 1.32); } foreach(pos in PointArr) { L_sq_DrawImg("interface/windowcommon.img", 50, pos[0], pos[1]); } } } //绘制区域 function DrawArea(Config) { } //绘制城镇地图 function DrawTownMap(Config) { // local UniRate = sq_GetAccel(250, 0, Clock() - 3000 - Timer, 1000); // local BackgroundData = Config.Data.Image.background; // if (!(StepImg.rawin(BackgroundData.path))) StepImg.rawset(BackgroundData.path, Rindro_Image(BackgroundData.path)); // StepImg[BackgroundData.path].DrawExPng(BackgroundData.frame, 0, -8, 0, sq_RGBA(255, 255, 255, UniRate), 1.0, 1.055); } //绘制逻辑 function DrawLogic(Config) { //绘制世界 DrawWorld(Config); //绘制区域 DrawArea(Config); //绘制城镇 DrawTownMap(Config); } //同步自身现在在哪个地图区域 function SyncSelfMapRegion() { local Town = L_sq_GetTownIndex(); foreach(AreaIndex, Areaobj in Region) { foreach(TownIndex, Townobj in Areaobj.Towns) { if (TownIndex == Town) { SelfMapRegion = AreaIndex; } } } } //同步自身现在在哪个地图世界 function SyncSelfMapWorld() { foreach(WorldIndex, Worldobj in World) { foreach(AreaIndex, Areaobj in Worldobj.Areas) { if (AreaIndex == SelfMapRegion) { SelfMapWorld = WorldIndex; } } } } //逻辑入口 function Proc(obj) { SyncSelfMapRegion(); SyncSelfMapWorld(); LenheartNewUI_Windows.SyncPos(X, Y); } //简便性能高的开平方 function sqrt(sum) { local i = (sum / 2).tofloat(); local isb = 0; for (isb = 0; isb< 10; isb++) { i = (i - ((i * i - sum) / (2 * i))).tofloat(); } return i; } } getroottable().rawdelete("NewWorldMap_Obj"); function Lenheart_NewWorldMap_Fun(obj) { local RootTab = getroottable(); if (!RootTab.rawin("NewWorldMap_Obj")) { RootTab.rawset("NewWorldMap_Obj", true); LenheartNewUI_CreateWindow(NewWorldMapC, "新世界地图", 0, 0, getroottable().Rindro_Scr_Width, 600, 0); } } getroottable()["LenheartFuncTab"].rawset("NewWorldMapFuncN", Lenheart_NewWorldMap_Fun);