Java Libgdx有两个用自己的坐标系绘制的不同视图吗?

Java Libgdx有两个用自己的坐标系绘制的不同视图吗?,java,libgdx,Java,Libgdx,请看以下截图: 我想将我的UI分为两部分,控件和游戏绘图区域,但我不希望控件与绘图区域重叠,我希望游戏绘图区域的0,0,从控件区域上方开始 这可能与您的相机有关吗?您可以使用两台相机,并将其放置在图像中所示的位置。我认为这篇文章可以给你一个提示:正如你所说的,你希望每个视图都有自己的坐标系,因此,正如朱利安所回答的那样,可以做到这一点,但正确使用它并不是全部 要使其完全工作,您应该有两个独立的正交摄影机,一个用于游戏绘制视图,另一个用于控制视图。我还建议为每个摄影机创建2个视口贴图。根据我的经

请看以下截图:

我想将我的UI分为两部分,控件和游戏绘图区域,但我不希望控件与绘图区域重叠,我希望游戏绘图区域的
0,0
,从控件区域上方开始


这可能与您的相机有关吗?

您可以使用两台相机,并将其放置在图像中所示的位置。我认为这篇文章可以给你一个提示:

正如你所说的,你希望每个视图都有自己的坐标系,因此,正如朱利安所回答的那样,可以做到这一点,但正确使用它并不是全部

要使其完全工作,您应该有两个独立的
正交摄影机
,一个用于游戏绘制视图,另一个用于控制视图。我还建议为每个摄影机创建2个
视口
贴图。根据我的经验,在多摄像机环境下工作时,始终为其创建关联
视口。更好地用于将来可能引入的更改(即适应任何屏幕分辨率)、调试目的,如检查触摸、位置等

所以,将分割技术与摄影机/视口管理相结合,您将拥有强大的系统来独立处理每个区域

代码

我提供了以下代码,因为它在我的游戏中使用和工作,但改变了变量名,以满足您的需要。它在Kotlin中,但应该相对容易地将其视为Java。 你首先初始化游戏区域的东西

// create a camera
gameAreaCamera = OrthographicCamera()
gameAreaCamera.setToOrtho(false, GAME_WIDTH, GAMEVIEW_HEIGHT)
gameAreaCamera.update()

// create a viewport associated with camera
gameAreaViewport = ExtendViewport(GAME_WIDTH, GAMEVIEW_HEIGHT, gameAreaCamera)
// create a camera
controlAreaCamera = OrthographicCamera()
controlAreaCamera.setToOrtho(false, GAME_WIDTH, CONTROLVIEW_HEIGHT)
controlAreaCamera.update()

// create a viewport associated with camera
controlAreaViewport = ExtendViewport(GAME_WIDTH, CONTROLVIEW_HEIGHT, controlAreaCamera)
接下来,控制区的东西

// create a camera
gameAreaCamera = OrthographicCamera()
gameAreaCamera.setToOrtho(false, GAME_WIDTH, GAMEVIEW_HEIGHT)
gameAreaCamera.update()

// create a viewport associated with camera
gameAreaViewport = ExtendViewport(GAME_WIDTH, GAMEVIEW_HEIGHT, gameAreaCamera)
// create a camera
controlAreaCamera = OrthographicCamera()
controlAreaCamera.setToOrtho(false, GAME_WIDTH, CONTROLVIEW_HEIGHT)
controlAreaCamera.update()

// create a viewport associated with camera
controlAreaViewport = ExtendViewport(GAME_WIDTH, CONTROLVIEW_HEIGHT, controlAreaCamera)
PS:注意每个视图的宽度和高度。根据你的意图,它将占据这个区域

现在,在
render()
方法中应该有类似的内容

override fun render() {
    // clear screen
    Gdx.gl.glClearColor(0.0f, 0.0f, 0.0f, 1.0f)
    Gdx.gl20.glClear(GL20.GL_COLOR_BUFFER_BIT)

    // draw game area
    drawGameArea()
    // draw control area
    drawControlArea()
}
对于您的
drawGameArea()
假设
sb
是您的
SpriteBatch
,并在当前类中维护它

private fun drawGameArea() {
    // the following twos to let system know we will operate against game area's camera
    // set the projection matrix
    sb.projectionMatrix = gameAreaCamera.combined
    // set gl viewport
    Gdx.gl.glViewport(0,0,GAME_WIDTH, GAMEVIEW_HEIGHT)

    // draw your stuff here...
    sb.begin()
    ...
    sb.end()
}
对于
drawControlArea()

注意
Gdx.gl.glViewport()
我们为它提供了目标矩形区域来绘制东西。
Viewport
s不是直接使用的,但它更多的是告诉系统哪种屏幕大小调整策略才能将游戏的图形适应到屏幕中,并达到更好的调试目的。你可以读更多

最常用的两个选项是
ExtendViewport
FitViewport
。如果您希望游戏显示并覆盖屏幕的整个区域,而不影响纵横比,并且没有黑条(左侧或右侧为黑色),
extendedviewport
很可能就是您想要的,或者如果您想要类似的效果,但有黑条,则游戏屏幕对于每个玩家都是相同的(因此与宽屏幕播放器相比没有优势)然后选择
FitViewport

检查用户界面点击率

我想你会需要这个,所以我也应该包括在内。 每当需要检查用户是否单击(或点击)此类UI元素时,可以在其相应的
update()
方法中使用以下内容来检查触摸位置是否在此类对象的边界区域内

以下代码非常安全,可以很好地与
ExtendViewport
配合使用,但它也应该与其他
视口
配合使用,因为该代码不需要来自
ExtendViewport
的任何特定信息。因此它是通用的

fun update(dt: Float, cam: Camera: viewport: Viewport) {
    // convert screen coordinate to world coordinate
    val location = Vector3(Gdx.input.getX(), Gdx.input.getY(), 0f)
    cam.unproject(location, viewport.screenX.toFloat(), viewport.screenY.toFloat(), viewport.screenWidth.toFloat(), viewport.screenHeight.toFloat())

    if ((Gdx.input.isTouched() && 
    boundingRect.contains(location.x, location.y)) {
        // do something here...
    }
}