2

我正在尝试根据三角形的指向方向将三角形旋转并移动到某个方向。理论上,我计算方向的正弦和余弦(0-360 度)并将这些值添加到 x 和 y 位置,对吗?它只是行不通。

此外,三角形应该在开始时指向上方,而不是下方。

public void speedUp() {
  float dirX, dirY;
  speed *= acceleration;
  if(speed > 50) speed = 50;
  println("dir: " + direction + " x: " + cos(direction) + " y: " + sin(direction));
  dirX = cos(direction);
  dirY = sin(direction);
  xPos+=dirX;
  yPos+=dirY;
}

public void redraw() {
  GL gl = pgl.beginGL();  // always use the GL object returned by beginGL
  gl.glTranslatef(xPos, yPos, 0);
  gl.glRotatef(direction, 0, 0, 1000);

  gl.glBegin(GL.GL_TRIANGLES);
  gl.glColor4f(0.1, 0.9, 0.7, 0.8);
  gl.glVertex3f(-10, -10, 0);    // lower left vertex
  gl.glVertex3f( 10, -10, 0);    // lower right vertex
  gl.glVertex3f( 0,  15, 0);    // upper vertex
  gl.glEnd();
}
4

4 回答 4

5

你的单位搞砸了。度数glRotatef除外,三角函数需要弧度。这是最明显的错误。


此外,speed从不在您的代码段中使用。我想你以某种方式使用它的每一帧,但在你粘贴的代码中:

xPos+=dirX

这基本上是“向位置添加方向” - 没有多大意义,除非你想“在被调用的那一刻立即将它在给定方向上精确移动 1 个单位speedUp()。连续移动的通常方法是:

// each frame:
xPos += dirX * speed * deltaTime;
yPos += dirY * speed * deltaTime;
于 2010-11-21T13:18:12.673 回答
5

看起来您需要从极坐标(使用角度和半径移动)转换为笛卡尔坐标(使用 x 和 y 移动)。

公式看起来有点像这样:

x = cos(angle) * radius;
y = sin(angle) * radius;

因此,正如@Lie Ryan 所提到的,您还需要乘以速度(这是您在极坐标中的半径)。

要么以度为单位,但在使用 cos,sin 时使用弧度(),因为它们与弧度一起使用,或者使用弧度,并使用带有glRotatef的度(),由你决定

此外,您可能想看看 glPushMatrix() 和 glPopMatrix()。基本上,它们允许您嵌套转换。无论您对块进行什么转换,它们只会在本地影响该块。

这就是我的意思,使用 w,a,s,d 键:

import processing.opengl.*;
import javax.media.opengl.*;

float direction = 0;//angle in degrees
float speed = 0;//radius
float xPos,yPos;

void setup() {
  size(600, 500, OPENGL);
}

void keyPressed(){
  if(key == 'w') speed += 1;
  if(key == 'a') direction -= 10;
  if(key == 'd') direction += 10;
  if(key == 's') speed -= 1;
  if(speed > 10) speed = 10;
  if(speed < 0) speed = 0;
  println("direction: " + direction + " speed: " + speed);
}

void draw() {
  //update
  xPos += cos(radians(direction)) * speed;
  yPos += sin(radians(direction)) * speed;
  //draw
  background(255);
  PGraphicsOpenGL pgl = (PGraphicsOpenGL) g; 
  GL gl = pgl.beginGL();
  gl.glTranslatef(width * .5,height * .5,0);//start from center, not top left

  gl.glPushMatrix();
  {//enter local/relative
    gl.glTranslatef(xPos,yPos,0);
    gl.glRotatef(direction-90,0,0,1);
    gl.glColor3f(.75, 0, 0);
    gl.glBegin(GL.GL_TRIANGLES);
    gl.glVertex2i(0, 10);
    gl.glVertex2i(-10, -10);
    gl.glVertex2i(10, -10);
    gl.glEnd();
  }//exit local, back to global/absolute coords
  gl.glPopMatrix();

  pgl.endGL();
}

您实际上不需要 { } 来进行 push 和 pop 矩阵调用,我将它们添加为视觉辅助工具。此外,您可以通过连接您的转换来完成此操作,而无需推送/弹出,但是当您需要它们时,知道它们就在那里很方便。当你想从那个三角形中射出一些 GL_LINES 时可能会派上用场...... pew pew pew!

高温高压

于 2010-11-21T14:25:24.340 回答
3

你显然是 OpenGl 的新手,所以我建议你,看看四元数来做你的 roations。这里有两篇关于这个问题的非常好的文章:GamedevNehe。我建议您使用 JMonkeyEngine 中的 Quaternion 类。只需删除可保存和其他一些接口,您就可以轻松使用它们。它们位于:JMonkey Source

我还将 JME 数学课程用于我自己的项目。我已经剥离了大部分依赖项,你可以从这里下载一些类:Volume Shadow。但是缺少四元数类,但您将需要 Vector3f :D。

于 2010-11-21T13:04:13.577 回答
3

尝试这个:

dirX = speed * cos(direction);
dirY = speed * sin(direction);
于 2010-11-21T13:22:37.223 回答