我的问题和标题一样。我正在尝试编写一个可以在2D平面上行驶的汽车进行处理的简单游戏。我想对汽车进行旋转,因为它似乎很关键,所以我按如下所述进行了操作:Rotating points in 2D
但是我的实现似乎有点失败。您会看到,当我按下向右箭头的左键时,汽车实际上在旋转,但随着旋转而尺寸缩小,几转后它完全消失了。你能告诉我我在这里想念什么吗?提前致谢!我的功能代码:
class Point
{
float x, y;
Point(float xx, float yy)
{
x = xx;
y = yy;
}
Point()
{
x = y = 0.0;
}
void Rotate(Point center, float angle)
{
float s = sin(angle);
float c = cos(angle);
y = center.y + ((y-center.y) * c + (x-center.x) * s);
x = center.x + ((x-center.x) * c - (y-center.y) * s);
}
}
class Car
{
Point LT;
Point RT;
Point LB;
Point RB;
Point center;
float r;
float acceleration;
Car()
{
LT = new Point(10, 10);
RT = new Point (30, 10);
LB = new Point(10, 50);
RB = new Point(30, 50);
r = sqrt(pow(15-30, 2) + pow(25-10, 2));
}
Car(Point lt, Point rt, Point lb, Point rb)
{
LT = lt;
RT = rt;
LB = lb;
RB = rb;
center = new Point(abs((LT.x - RT.x)/2), abs((LT.y - LB.y)/2));
r = sqrt(pow(center.x -LT.x, 2) + pow(center.y - LT.y, 2));
}
Car(Point Center, float w, float h)
{
center = Center;
LT = new Point(center.x - w/2, center.y - h/2);
RT = new Point (center.x + w/2, center.y - h/2);
LB = new Point(center.x - w/2, center.y + h/2);
RB = new Point(center.x + w/2, center.y + h/2);
r = sqrt(pow(center.x -LT.x, 2) + pow(center.y - LT.y, 2));
}
void Show()
{
fill(45, 128, 156);
beginShape();
vertex(LT.x, LT.y);
vertex(RT.x, RT.y);
vertex(RB.x, RB.y);
vertex(LB.x, LB.y);
endShape();
}
void Update()
{
}
void Turn(float angle)
{
LT.Rotate(center, angle);
RT.Rotate(center, angle);
RB.Rotate(center, angle);
LB.Rotate(center, angle);
}
void Accelerate(float accel)
{
}
}
在主要情况下,我只使用car.Show(),并且每按一次左高潮,我就翻-0.1,按一下右键就翻0.1。
编辑
如果您想查看完整的代码,请访问我的github repo
答案 0 :(得分:1)
不幸的是,目前我无法解释更多信息,但这是使用您指向的一种公式的更简单选择:
Car car = new Car();
void setup(){
size(300,300);
// this helps draw rectangles from centre (as opposed to corner (default))
rectMode(CENTER);
car.position.set(150,150);
}
void draw(){
background(255);
if(keyPressed){
if(keyCode == UP){
car.speed = 1;
}
}
car.draw();
}
void keyPressed(){
if(keyCode == LEFT){
car.steer -= radians(10);
}
if(keyCode == RIGHT){
car.steer += radians(10);
}
}
void keyReleased(){
if(keyCode == UP){
car.speed = 0;
}
}
class Car{
PVector position = new PVector();
PVector velocity = new PVector();
float speed;
float steer;
void update(){
// use the same polar to cartesian coordinates formulate for quick'n'dirty steering
velocity.set(cos(steer) * speed,sin(steer) * speed);
// update position based on velocity
position.add(velocity);
}
void draw(){
update();
// use a nested coordinate system to handle translation and rotation for us
// order of operations is important
pushMatrix();
translate(position.x,position.y);
rotate(steer);
rect(0,0,30,15);
popMatrix();
}
}
更新
缩小点的主要问题是旋转它们时要累积变形这些点。每次转换后,都没有x,y是什么的历史记录。相反,您应该返回经过转换的新点,从而“记住”旧的x,y位置。
Bellow是代码的经过调整的版本,减去了两个构造函数变体。 希望这些评论会有所帮助:
Car car = new Car();
void setup(){
size(300,300);
}
void draw(){
if(keyCode == UP){
if(keyPressed){
car.Accelerate(1);
}else{
car.Accelerate(0);
}
}
car.Update();
background(255);
car.Show();
}
void keyPressed(){
if(keyCode == LEFT){
car.Turn(radians(-3));
}
if(keyCode == RIGHT){
car.Turn(radians(+3));
}
}
class Point
{
float x, y;
Point(float xx, float yy)
{
x = xx;
y = yy;
}
Point()
{
x = y = 0.0;
}
Point Rotate(Point center, float angle)
{
float s = sin(angle);
float c = cos(angle);
// return a new point (a rotated copy), rather than overwriting this one
return new Point(center.x + ((x-center.x) * c - (y-center.y) * s),
center.y + ((y-center.y) * c + (x-center.x) * s));
}
// translate by another point
void AddToSelf(Point point){
this.x += point.x;
this.y += point.y;
}
// pretty print info when using println()
String toString(){
return "[Point x=" + x + " y="+ y +"]";
}
}
class Car
{
Point LT;
Point RT;
Point LB;
Point RB;
Point center;
float r;
float acceleration;
// car angle: used to compute velocity and update vertices
float angle;
// car position: used to offset rendering position of the corners
Point position;
// car velocity: amount by which position translates
Point velocity = new Point();
Car()
{
float x = 10;
float y = 10;
float w = 40;
float h = 20;
// setup corners with no translation
LT = new Point(0 , 0 );
RT = new Point(0 + w, 0 );
LB = new Point(0 , 0 + h);
RB = new Point(0 + w, 0 + h);
// setup initial position
position = new Point(x,y);
center = new Point(w / 2, h / 2);
r = sqrt(pow(15-30, 2) + pow(25-10, 2));
}
//Car(Point lt, Point rt, Point lb, Point rb)
//{
// LT = lt;
// RT = rt;
// LB = lb;
// RB = rb;
// center = new Point(abs((LT.x - RT.x)/2), abs((LT.y - LB.y)/2));
// r = sqrt(pow(center.x -LT.x, 2) + pow(center.y - LT.y, 2));
//}
//Car(Point Center, float w, float h)
//{
// center = Center;
// LT = new Point(center.x - w/2, center.y - h/2);
// RT = new Point (center.x + w/2, center.y - h/2);
// LB = new Point(center.x - w/2, center.y + h/2);
// RB = new Point(center.x + w/2, center.y + h/2);
// r = sqrt(pow(center.x -LT.x, 2) + pow(center.y - LT.y, 2));
//}
void Show()
{
fill(45, 128, 156);
beginShape();
// render corners offset by the car position
vertex(position.x + LT.x, position.y + LT.y);
vertex(position.x + RT.x, position.y + RT.y);
vertex(position.x + RB.x, position.y + RB.y);
vertex(position.x + LB.x, position.y + LB.y);
endShape(CLOSE);
}
void Update()
{
// update velocity based on car angle and acceleration
velocity.x = cos(angle) * acceleration;
velocity.y = sin(angle) * acceleration;
// update position based on velocity
position.AddToSelf(velocity);
}
void Turn(float angle)
{
this.angle += angle;
// replace the old point with the transformed points
// (rather than continuosly transforming the same point)
LT = LT.Rotate(center, angle);
RT = RT.Rotate(center, angle);
RB = RB.Rotate(center, angle);
LB = LB.Rotate(center, angle);
}
void Accelerate(float accel)
{
acceleration = accel;
}
}