【Android LibGDX游戏引擎开发教程】第05期:图形图像的绘制(上)基础类的使用和详解

       由于平常工作和生活琐事的种种原因,所以这个系列的教程更新的有点慢,还请大家见谅。在这期的主题中,博

主给大家来的教学是关于图形图像的绘制,要知道一个最基本的应用程序都会有一个精美的图像,那么就更别说一个

成功的游戏了,首先要有绚丽的图片背景才是吸引玩家试玩的关键,不是嘛?

          在这篇文章中主要讲解到的有TextureSpriteBatchSpritePixmap这四个类。

 

一、Texture和SpriteBatch

 

1、Texture介绍

 

我们先来看一下官方API文档,如下图所示:

       该类存放在com.badlogic.gdx.graphics包下,继承自Object,实现了Disposable接口,凡是实现了该接口的类,

都应该在程序结束时对该类进行销毁(上上一篇文章中提到过)。

 

2、Texture用途

    

       其实就是承装获取到的目的图片的容器,为了方便大家理解我就这里打一个比方,比如:你盛一碗粥,从锅里盛

来需要用到汤勺,这个汤勺就相当于Texture,他们都是用来获取东西的一个容器,是中间者。

 

3、SpriteBatch介绍

      该类存放在com.badlogic.gdx.graphics.g2d的包下,也是继承自Object,实现了Disposable接口。

 

4、SpriteBatch用途

 

     SpriteBatch可以把许多相同纹理一起描述并一起送入GPU,同时赋予纹理和坐标以便每个图形的绘制。其实可以

SpriteBatch理解为就是一个画笔,没有画笔是画不了画的。

     它的用法,首先声明类名,实例化、在绘制的的时候分三步,必须先调用begin()方法,然后再调用draw()
 
法,最 后画完了调用end()结束,这个顺序是绘制的固定格式,也是应该背下来的。

 

5、实现的效果图

 

     

       大家肯定会觉得奇怪为什么显示的图片会出现在下方?等下讲解代码的时候我在详细解释。

 

6、项目结构图

 

 

7、详细代码编写

 

package com.yangyu.mylibgdx01;

import com.badlogic.gdx.ApplicationListener;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.graphics.GL10;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.g2d.SpriteBatch;

public class MyGame implements ApplicationListener {
	//绘图用的SpriteBatch  
    private SpriteBatch batch;  
    
    //纹理  
    private Texture texture;
    
	@Override
	public void create() {
		batch = new SpriteBatch();
		texture = new Texture(Gdx.files.internal("image1.jpg"));
	}

	@Override
	public void dispose() {
		batch.dispose();
	    texture.dispose();
	}

	@Override
	public void pause() {

	}

	@Override
	public void render() {
		Gdx.gl.glClear(GL10.GL_COLOR_BUFFER_BIT); // 清屏
		batch.begin();
		batch.draw(texture, 0, 0, 480, 320);
		batch.end();  
	}

	@Override
	public void resize(int arg0, int arg1) {

	}

	@Override
	public void resume() {

	}

}


 

<1> 让我们来详细分析一下这段代码,先看这行代码:

texture = new Texture(Gdx.files.internal("image1.jpg"));
 
     Texture一般都是作为传入的参数使用的,这行代码是获取图片的常用写法,还可以在assert文件夹下再增加文件
夹,特别注 意读取的文件 必须注明格式,比如这个文件是“.jpg”格式就必须写明是“.jpg”格式的,否则会报错(找不
到此图 片)。
 
     这里简单介绍下Gdx.files,它是libgdx的文件模块,主要提供以下5大功能:读取文件,写入文件、复制文件、移动文件、列出文件和目录。其中获取文件有几种方法: 
 
<1> Classpath:路径相对于classpath,文件通常为只读; 

<2> Internal:内部文件路径相对于程序根目录或者android 的assets文件夹;

<3> External:外部文件路径是相对于SD卡根目录;

<4> Absolute:assets文件夹本身就是存储资源的文件夹,而且相比resource文件夹,它其中的资源不会生成R中

的ID,用来放图片很是合适。

 

<2> 这里还有个地方需要注意,libgdx绘制的图片必须是2的n次方分辨率(如32*32,256*512)的图片否则识别

了,那么为什么libgdx要使用2的N次方的图片呢?

    
      因为Android上画图可以使用OpenGL ES,分两个不兼容的版本:OpenGL ES 1.x和 OpenGL ES 2.0。
 
它们之间的一个重要区别就是:OpenGL ES 1.x的图片大小必须是2的整数次幂,而OpenGL ES 2.0则无此要求。而
 
libgdx在早期使用OpenGL es1.x 的版本所以只支持2的整数次幂的图像,并一直沿用至今,新版本(0.9.8)中允许开
 
发者使用OpenGL ES 2.0,这样使用OpenGL ES 2.0就可以不用管图片分辨率的问题了。android系统对opengl es的
 
支持情况: OpenGL ES 1.0--------->andoid 1.0-2.1(api 7)而 OpenGL ES 2.0------------>android 2.2(api 8)以上,但是
 
模拟器上即使是4.2的系统,也只有open es 1.0可用所以还是建议大家用安卓真机进行调试,模拟器很容易报错
 
不识别OpenGL ES 2.0。
 

图片是2的n次方是这个引擎的一大悲哀,不过有没有办法可以解决呢?答案是肯定的。

解决方法:

① 在MainActivity.java类中,把initialize()方法中的useGL2IfAvailable参数改为true就行了,就可以随便任何分

辨率图片不必是2的N次方了。不过需要特别注意的是最好在安卓真机上进行调试,模拟器很容易报错不识别

OpenGLES 2.0,如下图所示:

 

② 还有一种方法实现起来会稍微复杂一点,所以博主会在后面的文章对其进行详细的介绍。

 

<3> 获取完图片,然后调用batch.draw(texture,x,y,height,width)方法绘制图形

batch.draw(texture, 0, 0, 480, 320);

   这里的(x,y)是绘图的起点坐标,(height,width)绘制图形的大小,libgdx使用的是笛卡尔坐标系,以左下角

为原点,绘制方向是由下向上,由左到右。如下图所示:

 

二、TextureRegion类

 

1、TextureRegion介绍

该类存放在com.badlogic.gax.graphics.g2d包下,该类的子类有Sprite、TextureAtlas、AtlasRegion。

 

2、API的定义

大概的意思是说:定义了一个矩形区域的纹理,使用左上角的顶点为坐标系统的原点,x轴指向右,Y轴指向下。

 

3、TextureRegion用途

 

     实际操作中我们也经常使用图片的一部分,或者将多个图片资源集合在一个图片文件中。而要显示图片的一部分

就可以使用TextureRegion类。其实可以理解为就是截图工具,从左上角开始截图,然后可以定义截图的大小。

     TextureRegion一般都是截取texture,然后定义截取起点(x,y)随后再定义宽高(width,height),如果
  宽高是正数,那么就是沿x、y正方向截取,如果是负就是沿x、y负方向截取,方向只和宽高的正负有关。
 
    
比如:textureRegion = new(texture, 0 ,0 , 48, 48),他对应的截图区域和方向,如下图:

 

 textureRegion = new(texture, 48 , 48 , -48, -48),他对应的截图区域和方向,如下图:

 

4、实现效果图

 

                    正向截图                                                                       反向截图

                  

 

5、项目结构图

 

6、详细代码编写

package com.yangyu.mylibgdx01;

import com.badlogic.gdx.ApplicationListener;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.graphics.GL10;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.g2d.SpriteBatch;
import com.badlogic.gdx.graphics.g2d.TextureRegion;

public class MyGame implements ApplicationListener {
	//绘图用的SpriteBatch  
    private SpriteBatch batch;  
    
    //纹理  
    private Texture texture;
    
    public TextureRegion textureRegion;
    
	@Override
	public void create() {
		batch = new SpriteBatch();
		
		texture = new Texture(Gdx.files.internal("image1.jpg"));
		
//		textureRegion = new TextureRegion(texture, 0, 0, 512, 256);
		textureRegion = new TextureRegion(texture, 512, 256, -512, -256);

	}

	@Override
	public void dispose() {
		batch.dispose();
	    texture.dispose();
	}

	@Override
	public void pause() {

	}

	@Override
	public void render() {
		Gdx.gl.glClear(GL10.GL_COLOR_BUFFER_BIT); // 清屏
		batch.begin();
//		batch.draw(texture, 0, 0, 480, 320);
		batch.draw(textureRegion, 0, 0, 480, 320);

		batch.end();  
	}

	@Override
	public void resize(int arg0, int arg1) {

	}

	@Override
	public void resume() {

	}

}

 


 三、Sprite类

 

1、Sprite介绍

      该类在com.badlogic.gdx.graphics.g2d包下,继承自TextureRegion类,它的子类有TextureAtlas、AtlasSprite。

 

2、API的定义

 

先来看一下官方的解释,如下图所示:

 

3、Sprite用途

 

        TextureRegion的加强版,比TextureRegion多了一些功能,如:可以指定位置、颜色、旋转等。
 
其实Sprite的功能就是以上的集合。但是Sprite更方便,它用一个对象描述了一切,但是同时加入了很多
 
TextureRegion和Texture没有的东西,如位置、颜色、旋转等等。

 

4、实现效果图

 

 

5、详细代码编写

package com.yangyu.mylibgdx03;

import com.badlogic.gdx.ApplicationListener;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.graphics.GL10;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.g2d.Sprite;
import com.badlogic.gdx.graphics.g2d.SpriteBatch;
import com.badlogic.gdx.graphics.g2d.TextureRegion;

public class MyGame implements ApplicationListener {
	public SpriteBatch batch;

	// 声明纹理
	public Texture texture;

	public Sprite sprite;

	@Override
	public void create() {

		batch = new SpriteBatch();
		// 实例化texture
		texture = new Texture(Gdx.files.internal("xianjian.jpg"));
		TextureRegion region = new TextureRegion(texture, 0, 0, 256, 512);
		sprite = new Sprite(region);

		// 设置绘制的大小
		sprite.setSize(256, 512);
		// 设置旋转的中心点为屏幕的中心点
		sprite.setOrigin(sprite.getWidth() / 2, sprite.getHeight() / 2);
		// 以中心点为旋转中心,设置旋转的角度
		sprite.setRotation(50);
		// 设置图片的起始位置
		sprite.setPosition(150, 110);
		// 颜色就设置为粉色
		sprite.setColor(1, 0, 1, 1);
	}

	@Override
	public void dispose() {
		batch.dispose();
		texture.dispose();
	}

	@Override
	public void render() {
		Gdx.gl.glClearColor(1, 1, 1, 1);// 设置背景颜色为白色
		Gdx.gl.glClear(GL10.GL_COLOR_BUFFER_BIT);// 清屏
		batch.begin();
		sprite.draw(batch);
		batch.end();
	}

	@Override
	public void resize(int width, int height) {
	}

	@Override
	public void pause() {
	}

	@Override
	public void resume() {
	}

}

 

我们来详细分析一下这段代码:

<1> 在前面已经说过了, TextureRegion是Sprite的加强版,Sprite包含TextureRegion的功能:

TextureRegion region = new TextureRegion(texture, 0, 0, 256, 512);
		sprite = new Sprite(region);

可以把这两行代码替换为:

sprite = new Sprite(texture, 0, 0, 256, 512);

 

<2>可以通过sprite的setColor方法为图形着色:

sprite.setColor(1, 0, 1, 1);

其中颜色的表述都是介于0到1之间的数。


<3>  关于清屏:

Gdx.gl.glClearColor(1, 1, 1, 1);// 设置背景颜色为白色
		Gdx.gl.glClear(GL10.GL_COLOR_BUFFER_BIT);// 清屏

    可能大家不能理解为什么要清屏?其实很简单,OpenGL中我们是将纹理贴上去的,但是要绘制动画,或者绘制

另外的图片时候,他会残留上一张的痕迹,所以只有清屏后,才能显示新的图片,这个感兴趣的同学可以自己去测试

一下,这两行代码,如果是很熟悉的libgdx的新手同学的话可以当做固定格式来用,编程的时候在render()方法中

都是必须加入的,也不需要大家理解,建议大家直接背下来

 

四、 Pixmap类

 

1、Pixmap介绍

该类存放在com.badlogic.gdx.graphics包下,继承自Object,实现了Disposable接口。

 

2、Pixmap用途

 

     Libgdx所提供的像素级图像渲染用类,由于Libgdx目前以JNI方式自带图像解码器,所以我们可以直接将Pixmap理

解为一个Android中 Bitmap的替代者,两者间实现细节虽有差别,但具体作用却大同小异。Pixmap支持Alpha、

LuminanceAlpha、RGB565、 RGBA4444、RGB888、RGBA8888等五种图像彩色模式,支持png、jpg、bmp等三

种图像文件的读取和加载。一般来说,Pixmap 必须和Texture混用才能真正显示画面。不过在事实上,Libgdx的

Texture里已经内置有Pixmap了。

3、实现效果图

 

 

4、代码详细编写

package com.yangyu.mylibgdx04;

import com.badlogic.gdx.ApplicationListener;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.graphics.Color;
import com.badlogic.gdx.graphics.GL10;
import com.badlogic.gdx.graphics.Pixmap;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.g2d.SpriteBatch;

public class MyGame implements ApplicationListener {
	// 准备绘图用SpriteBatch
	SpriteBatch spriteBatch;

	// Pixmap是Libgdx提供的针对opengl像素操作的上级封装,它可以凭空构建一个像素贴图,
	// 但是它的现实必须通过Texture。
	Pixmap pixmap;

	// 准备Texture
	Texture texture;

	public void create() {
		// 构建SpriteBatch
		spriteBatch = new SpriteBatch();

		// 构建Pixmap(在Android环境使用internal加载模式时,文件必须放置于assets文件夹下)
		pixmap = new Pixmap(Gdx.files.internal("image1.jpg"));

		// 绘制一个蓝方块到Ball图像之上
		pixmap.setColor(Color.BLUE.r, Color.BLUE.g, Color.BLUE.b, Color.BLUE.a);
		pixmap.drawRectangle(15, 15, 40, 40);

		// 以指定Pixmap构建Texture
		texture = new Texture(pixmap);
	}

	public void dispose() {
		// 注入Texture后的pixmap已经没用,可以注销
		pixmap.dispose();

		spriteBatch.dispose();

		texture.dispose();
	}

	public void pause() {
	}

	public void render() {
		// 清屏
		Gdx.gl.glClear(GL10.GL_COLOR_BUFFER_BIT);
		// 初始化绘图调用
		spriteBatch.begin();
		// 绘制精灵到游戏屏幕
		spriteBatch.draw(texture, 100, 180);
		// 结束绘图调用
		spriteBatch.end();
	}

	public void resize(int width, int height) {
	}

	public void resume() {
	}

}


          

              这一期图形图像绘制的基本内容差不多就讲完了,下一期会更加精彩!

 

源码下载地址(包含本期中所有的示例讲解)

  • 2
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值