Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/actionscript-3/7.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Actionscript 3 As3:不在对象中移动?这背后的逻辑是什么?_Actionscript 3_Logic_Collision Detection_Hittest - Fatal编程技术网

Actionscript 3 As3:不在对象中移动?这背后的逻辑是什么?

Actionscript 3 As3:不在对象中移动?这背后的逻辑是什么?,actionscript-3,logic,collision-detection,hittest,Actionscript 3,Logic,Collision Detection,Hittest,我有一个可以控制我的角色的功能 我在舞台上还有一部叫做《刺客桌》的电影 我想让角色不能在桌子上移动,也就是说让桌子像墙一样工作 我有以下代码: if(!this.hitTestObject(_root.assassin_table)) { if(upKeyDown) { gotoAndStop(4); y-=Math.cos(rotation/-180*Math.PI)*(mainSpeed +7); x-=Math.sin(rot

我有一个可以控制我的角色的功能

我在舞台上还有一部叫做《刺客桌》的电影

我想让角色不能在桌子上移动,也就是说让桌子像墙一样工作

我有以下代码:

if(!this.hitTestObject(_root.assassin_table))
{
    if(upKeyDown)
    {
        gotoAndStop(4);
        y-=Math.cos(rotation/-180*Math.PI)*(mainSpeed +7);
        x-=Math.sin(rotation/-180*Math.PI)*(mainSpeed +7);

    }
    if(!upKeyDown)
    {
        gotoAndStop(3);
    }
 }
但是,如果我碰了桌子,我就不能动了

我知道这是因为
如果(!this.hitTestObject(\u root.刺客\u table))
,但我不理解不移动对象背后的逻辑。我更希望有一个近乎像素完美的碰撞检测系统,但因为很难在网上找到任何不令人困惑的好信息,所以我现在还是使用hitTestObject:)

编辑:尝试了一些东西,但效果不是很好

    if(!_root.assassinDead && !teleporting && this.currentFrame != 5)
        {
            if(this.hitbox.hitTestObject(_root.assassin_table))
            {
                _root.assassin_table.gotoAndStop(2);

                if(this.x > _root.assassin_table.x)
                {
                    trace("Can't move right");
                    canMoveRight = false;
                }

                if(this.x <_root.assassin_table.x)
                {
                    trace("Can't move left");
                    canMoveLeft = false;
                }

                if(this.y > _root.assassin_table.y)
                {
                    trace("Can't move up");
                    canMoveUp = false;
                }

                if(this.y < _root.assassin_table.y)
                {
                    trace("Can't move down");
                    canMoveDown = false;
                }
            }
            else
            {
                canMoveRight = true;
                canMoveLeft = true;
                canMoveUp = true;
                canMoveDown = true;
            }
        }
旋转是由这个决定的:

this.rotation = Math.atan2((stage.mouseY - this.y), (stage.mouseX - this.x)) * 180/ Math.PI + 90;

您应该为四个不同的移动方向分离hittest功能。 我的意思是,你不应该使用这个“hitTestObject”的东西,它只返回一个布尔值“true”或“false”,这对你来说是行不通的

您需要一个类似“testPoint(player.x,player.y);”的函数,并在给定位置返回对象,这样您就可以在游戏中实现它

   if (upKeyDown && testPoint(player.x, player.y - mainSpeed +7) == null) y-=Math.cos(rotation/-180*Math.PI)*(mainSpeed +7);

player.y-mainSpeed+7
//检查plus mainSpeed+7,因为试图在播放器进入对象内部堆栈之前停止播放器

基本上,您的逻辑流应该如下所示:

var debug:Shape = new Shape;
debug.addEventListener( Event.ENTER_FRAME, function():void
{
    debug.graphics.clear();
    debug.graphics.lineStyle( 2.0, 0xff0000 );

    // char (again assuming anchor point is top left)
    debug.graphics.drawRect( char.x, char.y, char.width, char.height );

    // table
    debug.graphics.drawRect( table.x, table.y, table.width, table.height );
});

// add our debug. NOTE: make sure it's above everything
stage.addChild( debug );
  • 样本输入(按键)
  • 移动字符
  • 检查碰撞
  • 如果发生碰撞,则将角色移动到其所接触对象的“外部”
在您的特定情况下,如果您的角色位于表的左侧,并且您要向右移动,那么首先,您要移动角色。在新位置,检查是否有碰撞。如果你有一个集合,那么因为你是从左边移动的,我们想要在我们碰撞的对象的左边,在这个例子中是表格,所以我们将角色定位在表格的左边

第一部分(检查角色是否击中桌子)称为碰撞检测。移动角色使其超出表的边界称为碰撞响应。碰撞检测是一个相当大的领域,它取决于你正在制作的游戏类型;你可以做基于网格的、基于命中测试的(如果你没有很多对象)、基于物理的、基于数学的等等。碰撞响应可以是任何东西,取决于你想对碰撞做出什么反应-你可以摧毁对象(钉子上的气球)、改变它的速度(角色在泥泞中奔跑)、反弹(球离开墙壁),或停止任何进一步的移动(角色靠墙)

为了让事情变得更简单:

  • 分开你的系统-例如,你的输入不应该依赖于你的碰撞。如果向上键是向下的,只需注册这个事实-你以后如何处理它(让你的角色移动)取决于你自己
  • 将对象在内存中的位置与其在屏幕上的位置分开-这将允许您移动对象,对碰撞等做出反应,并且只有在一切正常时,才更新图形(阻止图形进入墙中,只会跳出下一帧)
  • 一次求解一个轴-例如,先在x轴上碰撞,然后在y轴上碰撞
  • 很少需要像素完美的碰撞:)不旋转的长方体和圆将比你想象的要有效得多
  • 有些关联-对象的形状不一定是与之碰撞的形状-例如,桌子碰撞形状可能只是一个长方体;您的角色碰撞形状可能只是一个圆
更新

这使我有时能够在桌子上走动

假设我们要将角色和表格作为方框进行碰撞,您需要考虑它们的大小-即,我们不只是比较
x
值,而是将角色方框的右侧与表格方框的左侧进行比较。例如:

// assumes objects have their anchor point in the top left - if its
// not the case, adjust as you see fit
if( char.x + char.width > table.x ) // right side of the char is overlapping the left side of the table
    canMoveRight = false;
else if( char.x < table.x + table.width ) // left side of char vs right side of table
    canMoveLeft = false;

// etc

我有点困惑。这段代码是如何确保它是针对_root.刺客_表的?谢谢你的文本。它真的帮助我理解了一切:)好吧,我遇到了一个问题!我将在主假设中添加问题。顺便说一句,有点不相关,通常是
Math.cos()
代表
x
Math.sin()
代表
y
var debug:Shape = new Shape;
debug.addEventListener( Event.ENTER_FRAME, function():void
{
    debug.graphics.clear();
    debug.graphics.lineStyle( 2.0, 0xff0000 );

    // char (again assuming anchor point is top left)
    debug.graphics.drawRect( char.x, char.y, char.width, char.height );

    // table
    debug.graphics.drawRect( table.x, table.y, table.width, table.height );
});

// add our debug. NOTE: make sure it's above everything
stage.addChild( debug );