Sign in to follow this  
Gross

Добавление зон и событий к ним

Recommended Posts

Пример создания зон, территорий, и событий когда игрок входит/покидает их.

Зоны будут 2х типов 2D и 3D, различия между ними в том что 3D зона имеет высоту равную ее радиусу, то есть если игрок находится выше или ниже радиуса зоны то он в ней не находится, 2D же зоны не имеют высоты и игрок находясь на любом уровне на/под ними все равно находится внутри.

Создаем в каталоге 'packages/keker' файл 'zones.js' объявим его в 'packages/keker/index.js' добавив туда строку:

require("./zones");

Добавляем в 'zones.js' этот код:

mp.Vector3.Distance = function (v1, v2){
	return (Math.sqrt(Math.pow((v2.x - v1.x),2) +
									Math.pow((v2.y - v1.y),2)+
									Math.pow((v2.z - v1.z),2)));
}

mp.Vector3.Distance2D = function (v1, v2){
	return (Math.sqrt(Math.pow((v2.x - v1.x),2) +
									Math.pow((v2.y - v1.y),2)));
}

var Zone = class Zone {
			constructor(n ,v, r, t){
				this.name = n; //  Название зоны
				this.center = v; // Центральная точка
				this.radius = r; // Радиус
				this.type = t; // Тип 2D или 3D
				this.insidePlayers = []; // Массив игроков находящихся в зоне
				this.interval = InitInterval(this);
			}
			BroadcastMessage(s){ // Фунция рассылки сообщения игрокам находящимся в нутри этой зоны
				this.insidePlayers.forEach(player => {
					player.outputChatBox(s);
				});
			}
		}

function InitInterval(zone){
	return setInterval(function(){
		mp.players.forEach(player => {
			let dist = (zone.type=="2D") ? mp.Vector3.Distance2D(player.position, zone.center) : mp.Vector3.Distance(player.position, zone.center);
			if(dist < zone.radius && zone.insidePlayers.indexOf(player) < 0){
				zone.insidePlayers.push(player);
				mp.events.call("playerEnterZone", zone, player);
			} else if (dist > zone.radius && zone.insidePlayers.indexOf(player) >= 0){
				zone.insidePlayers.splice(zone.insidePlayers.indexOf(player), 1);
				mp.events.call("playerExitZone", zone, player);
			}
		})
	}, 500);
}
		
var Zones = class Zones {
	constructor(){
		this._Zone = Zone;
		this.zones = [];
	}
	Add(n, v, r, t){
		if(this.zones[n])
			this.Remove(n);
		let z = new this._Zone(n, v, r, t);
		this.zones[n] = z;
		return z;
	}
	AddZone3D(n, v, r){
		return this.Add(n, v, r, '3D');
	}
	AddZone2D(n, v, r){
		return this.Add(n, v, r, '2D');
	}
	Remove(n){
		let z = this.zones[n];
		clearInterval(z.interval);
		delete this.zones[n];
	}
	Get(n){
		return this.zones[n];
	}
}

mp.Zones = new Zones();

mp.events.add({"playerQuit" : (player, reason, kickReason) =>
	{
		for(let key in mp.Zones.zones) { // Удаление игрока из зоны при выходе
			let zone = mp.Zones.zones[key];
			if (zone.insidePlayers.indexOf(player) >= 0){
				zone.insidePlayers.splice(zone.insidePlayers.indexOf(player), 1);
			}
		}
	}	
});

Теперь в любом удобном месте, или в 'events/common.js' добавляем события для зон:

mp.events.add({
	"playerEnterZone": (zone, player) => {
		/* Событие когда игрок вошел в зону
			на входе получаем zone - обьект зоны, и игрока - player
		*/
	},
	"playerExitZone": (zone, player) => {
		/* Событие когда игрок покинул зону
			на входе получаем zone - обьект зоны, и игрока - player
		*/
	}	
});

Методы и свойства для работы с зонами:

let zone = mp.Zones.AddZone3D("zone1", new mp.Vector3(10, 25, 46), 10); // Создает 3D зону с названием zone1, в точке X:10;Y:25;Z:46; и радиусом 10

let zone = mp.Zones.AddZone2D("zone1", new mp.Vector3(10, 25, 46), 10); // Создает 2D зону с названием zone1, в точке X:10;Y:25;Z:46; и радиусом 10

let zone = mp.Zones.Get('zone1'); // Получает зону с названием zone1

mp.Zones.Remove('zone1'); // Удаляет зону zone1

zone.BroadcastMessage("Сообщение"); // Рассылает игрокам находящимся в зоне чат сообщение;

zone.insidePlayers // Массив с игроками находящимися в зоне

zone.name // Название зоны

Прошу строго не судить так как это костыльный метод, пока данный функционал не добавят в API.

  • Like 1
  • Mask 1

Share this post


Link to post
Share on other sites

Хороший пример, но смотря на это, всё больше хочется клиентскую часть х_х

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Sign in to follow this  

  • Recently Browsing   0 members

    No registered users viewing this page.