一个有效的方法来检查对象拦截在AS3视线方法来、视线、对象、有效

2023-09-08 13:41:37 作者:浅唱你给的伤痛゛

我已经有一段时间了一直在努力制定出一个有效的方法,看看什么是看不见别的东西的路线。一个很好的例子是有一个球体发射火箭时,你是否能看到你 - 但显然不是,如果你后面的墙

下面就是我一般去了解这样做:

 函数投(结束:游戏物体,墙:阵列,精度:UINT = 10):对象
{
    VAR XP:数= skin.x;
    VAR YP:数= skin.y;

    VAR昂:数= Math.atan2(end.skin.y  -  YP,end.skin.x  -  XP);
    VAR xvel:数= Math.cos(ANG)*准确性;
    VAR yvel:数= Math.sin(ANG)*准确性;

    变种I:UINT = 0;
    对(我;我< 800 /精度; I + =精度)
    {
        XP + = xvel;
        YP + = yvel;

        VAR记者:游戏物体;
        每个(十墙壁)
        {
            如果(j.skin.hitTestPoint(XP,YP))
                返程{可见:假的,X:XP,Y:YP};
        }
    }

    返回{可见:真};
}
 

使用,这将是基本上是:

  VAR的景象:对象=投(播放器,无法通行);

如果(sight.visible)跟踪('可以看到');
其他跟踪(无法看到 - 在碰撞'+ sight.x +,+ sight.y);
 
销售冠军对待顾客的8大方法,看看你差在哪儿

作品,但我们知道这会非常慢随着每一个新的火箭添加或作为不可逾越的对象的数量增加了。

我假设有说我失去了一个非常简单有效的方式 - 我的意思是,所有的游戏做(暗黑破坏神,等等),与数百名敌人,除非你看见没有做任何事情。

想法?

解决方案   

我的意思是,所有的游戏做(暗黑破坏神,等等)   数百名敌人,不做   除非任何你是可见的。

电玩游戏像暗黑利用基于区块的引擎,以便减少来计算碰撞,视线和AI行为线所需计算的次数;基于区块的引擎出生的,你必须为你的游戏引擎的具体关注。

由于绝对坐标,它是微不足道找出哪些特定的瓷砖任何敌人并把这种以一个x,y地图上的坐标。一旦你有瓷砖,它不应该是太困难的缩小支票的需要,以找出是否还有一个目的是在望运行数量。

以一个基于区块的发动机还,寻路也是根据瓷砖的游戏引擎非常有用,可以很容易地完成任务;路径距离和/或复杂性可以让你轻松计算出,如果两个对象可以看到对方。 (机会是,如果你需要去四十步,或在迷宫一样的路径中的对象是不可见的对方)

基于区块的发动机大幅减少开销问题,你开始考虑的问题。

I've for a while now been trying to work out an efficient way to see if something is in something else's line of sight. A good example is having a sphere that fires a rocket at you if it can see you - but obviously not if you're behind a wall.

Here's how I generally went about doing this:

function cast(end:GameObject, walls:Array, accuracy:uint=10):Object
{
    var xp:Number = skin.x;
    var yp:Number = skin.y;

    var ang:Number = Math.atan2(end.skin.y - yp, end.skin.x - xp);
    var xvel:Number = Math.cos(ang)*accuracy;
    var yvel:Number = Math.sin(ang)*accuracy;

    var i:uint = 0;
    for(i; i<800/accuracy; i+=accuracy)
    {
        xp += xvel;
        yp += yvel;

        var j:GameObject;
        for each(j in walls)
        {
            if(j.skin.hitTestPoint(xp, yp))
                return {visible:false, x:xp, y:yp};
        }
    }

    return {visible:true};
}

The use of this would be basically:

var sight:Object = cast(player, impassable);

if(sight.visible) trace('can see');
else trace('cant see - collision at ' + sight.x + ", " + sight.y);

Works, but as we know this will get extremely slow with each new rocket added or as the amount of impassable objects increases.

I'm assuming there's a really simple efficient way that I'm missing - I mean, all games do it (Diablo, etc) with hundreds of enemies that don't do anything unless you're visible.

Ideas?

解决方案

I mean, all games do it (Diablo, etc) with hundreds of enemies that don't do anything unless you're visible.

Games like diablo use tile based engines in order to reduce the number of computations needed to calculate collision, line of sight and AI behavior; tile based engines were born of the exact concerns you have for your game engine.

Given absolute coordinates, it is trivial to figure out which specific tile any enemy is in and translate that to an x,y coordinate on your map. Once you have that tile, it shouldn't be too difficult to narrow down the number of "checks" you need to run in order to figure out if another object is in sight.

Taking a tile based engine further, pathfinding is also very useful in tile based game engines and can accomplish your task quite easily; path distance and/or complexity can allow you to EASILY figure out if 2 objects can "see" each other. (Chances are if you need to go forty steps, or in a maze-like path the objects aren't visible to each other)

Tile based engines drastically reduce the overhead problems you're beginning to consider.