我需要单击鼠标按钮,您可以在2轴上旋转图形。释放鼠标按钮时,图形将在原始位置旋转。通过小转动,一切都按照应有的方式进行,但是在图形的大转动(<180)时,图形不会返回其原始位置。
我没有看到任何错误。帮助我。
public class WaitActionScren extends Base3dGameScreen {
private static final int DEFAULT_INERT_VALUE = 5;
private int sumRotateX = 0, sumRotateY = 0;
private boolean isUp = false;
/**
* Constructor.
*
* @param game {@link MagicSphere} instance.
*/
public WaitActionScren(MagicSphere game) {
super(game);
}
@Override
public void create() {
super.create();
bitmapFontCache.setColor(Color.GREEN);
Gdx.input.setInputProcessor(new TouchEvents());
}
@Override
public void render(float deltaTime) {
Gdx.gl.glViewport(0, 0, Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
Gdx.gl.glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT);
modelBatch.begin(cam);
modelBatch.render(instanceSphere, lights);
modelBatch.end();
}
@Override
public void update(float deltaTime) {
if (isUp) {
int inertValue = getInertValue(sumRotateX);
instanceSphere.transform.rotate(0, 1, 0, inertValue);
System.err.println("rotate_x : " + inertValue);
sumRotateX += inertValue;
inertValue = getInertValue(sumRotateY);
instanceSphere.transform.rotate(1, 0, 0, inertValue);
System.err.println("rotate_y : " + inertValue);
sumRotateY += inertValue;
}
}
// TODO non static.
private static int getInertValue(int sumRotate) {
if(sumRotate > 0) {
if (sumRotate < DEFAULT_INERT_VALUE) {
return -sumRotate;
}
return -DEFAULT_INERT_VALUE;
}
if(sumRotate < 0) {
if (sumRotate > -DEFAULT_INERT_VALUE) {
return -sumRotate;
}
return DEFAULT_INERT_VALUE;
}
return 0;
}
@Override
public void dispose() {
}
@Override
public void pause() {
}
@Override
public void resume() {
}
class TouchEvents implements InputProcessor {
private int oldX = 0, oldY = 0;
@Override
public boolean keyDown(int keycode) {
return false;
}
@Override
public boolean keyUp(int keycode) {
return false;
}
@Override
public boolean keyTyped(char character) {
return false;
}
@Override
public boolean touchDown(int screenX, int screenY, int pointer, int button) {
return false;
}
@Override
public boolean touchUp(int screenX, int screenY, int pointer, int button) {
oldX = 0;
oldY = 0;
isUp = true;
return false;
}
@Override
public boolean touchDragged(int screenX, int screenY, int pointer) {
if (oldX != 0 || oldY != 0) {
float change;
change = screenX - oldX;
instanceSphere.transform.rotate(0, 1, 0, change);
System.err.println("X: " + change);
sumRotateX += change;
change = screenY - oldY;
instanceSphere.transform.rotate(1, 0, 0, change);
System.err.println("X: " + change);
sumRotateY += change;
}
oldX = screenX;
oldY = screenY;
isUp = false;
return false;
}
@Override
public boolean mouseMoved(int screenX, int screenY) {
return false;
}
@Override
public boolean scrolled(int amount) {
return false;
}
}
}
答案 0 :(得分:1)
没有相关的图书馆对我来说很难确定,但我认为你可能会陷入轮换问题的顺序;那就是如果你围绕y轴旋转90度然后围绕z轴旋转90度,这与围绕z旋转然后y旋转不同。所以考虑到你总是旋转大约y然后大约x,当你来撤消一个旋转你并没有真正撤消它时,你正在进行更圆的旋转。
为了证明这一点,让我们从沿x轴指向的矢量开始,我们将围绕y和z旋转90度,但是以不同的顺序
正如您所看到的操作顺序非常重要,因此如果您先旋转x然后y,为了撤消您需要旋转-y然后-x。
答案 1 :(得分:0)
我已经达到了预期的效果。我希望这对某人有用。
public class WaitActionScren extends Base3dGameScreen {
private static final float DEFAULT_INERT_VALUE = 7f;
private float sumY = 0;
private float sumX = 0;
private boolean isUp = false;
/**
* Constructor.
*
* @param game {@link MagicSphere} instance.
*/
public WaitActionScren(MagicSphere game) {
super(game);
}
@Override
public void create() {
super.create();
bitmapFontCache.setColor(Color.GREEN);
Gdx.input.setInputProcessor(new TouchEvents());
}
@Override
public void render(float deltaTime) {
Gdx.gl.glViewport(0, 0, Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
Gdx.gl.glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT);
modelBatch.begin(cam);
modelBatch.render(instanceSphere, lights);
modelBatch.end();
}
@Override
public void update(float deltaTime) {
if (isUp) {
Quaternion rotation = new Quaternion();
instanceSphere.transform.getRotation(rotation);
float xInert = getInertValue(sumX);
float yInert = getInertValue(sumY);
sumX += xInert;
sumY += yInert;
Vector3 v3 = new Vector3(sumY, sumX, 0);
float len = v3.len();
v3 = v3.nor();
rotation.setFromAxis(v3.x, v3.y, v3.z, len);
instanceSphere.transform.set(rotation);
}
}
private float getInertValue(float sumRotate) {
if(sumRotate > 0.0f) {
if (sumRotate < DEFAULT_INERT_VALUE) {
return -sumRotate;
}
return -DEFAULT_INERT_VALUE;
}
if(sumRotate < 0.0f) {
if (sumRotate > -DEFAULT_INERT_VALUE) {
return -sumRotate;
}
return DEFAULT_INERT_VALUE;
}
return 0;
}
@Override
public void dispose() {
}
@Override
public void pause() {
}
@Override
public void resume() {
}
class TouchEvents implements InputProcessor {
private float oldX = 0.0f, oldY = 0.0f;
@Override
public boolean keyDown(int keycode) {
return false;
}
@Override
public boolean keyUp(int keycode) {
return false;
}
@Override
public boolean keyTyped(char character) {
return false;
}
@Override
public boolean touchDown(int screenX, int screenY, int pointer, int button) {
oldX = screenX;
oldY = screenY;
return false;
}
@Override
public boolean touchUp(int screenX, int screenY, int pointer, int button) {
oldX = 0.0f;
oldY = 0.0f;
isUp = true;
return false;
}
@Override
public boolean touchDragged(int screenX, int screenY, int pointer) {
float changeX;
float changeY;
changeX = screenX - oldX;
changeY = screenY - oldY;
sumX += changeX;
sumY += changeY;
Vector3 v3 = new Vector3(sumY, sumX, 0.0f);
float length = v3.len();
v3 = v3.nor();
Quaternion rotation = new Quaternion();
instanceSphere.transform.getRotation(rotation);
rotation.setFromAxis(v3.x, v3.y, v3.z, length);
instanceSphere.transform.set(rotation);
oldX = screenX;
oldY = screenY;
isUp = false;
return false;
}
@Override
public boolean mouseMoved(int screenX, int screenY) {
return false;
}
@Override
public boolean scrolled(int amount) {
return false;
}
}
}