Learning XNA 4.0 第三章(3)

在项目中增加一个精灵

  好了,我就不多说了,这一次我是认真的。让我们开始。您的项目到目前为止是令人乏味的。现在,让我们绘制一副图像到您游戏的屏幕上。

  XNA中所有的图形、声音、特效和其它东西都要通过一个称为内容管道的东西加载。本质上内容管道将诸如.jpg文件、.bmp文件、.png文件和其它格式的文件在编译过程中转换成一种XNA很容易使用的内部格式。对于其它类型的资源也是如此,比如声音文件、3D模型和字体等等,后面的章节将会深入地探讨。XNA框架很大的一点好处就是不同文件类型对于XNA都是透明的。如果您在游戏中添加了一个图像文件,内容管道在编译过程中能够识别它,您不需要为图像格式而担心。(稍后的章节会更深入讨论到内容管道。)

  下载本章的源码到您的硬盘上。这样您就可以得到本章剩下部分需要用到的图像文件,并把它们加入到您的项目中。

  打开Visual Studio的解决方案资源管理器(Solution Explorer),看看您的解决方案。您会看到您的解决方案中有两个项目:一个项目名为Collision,另一个名为CollisionContent。您在游戏中使用的全部资源(图形,声音,模型等)都应该添加到CollisionContent项目中。因为我喜欢一切都井井有条,所以我建议在CollissionContent项目中为每种内容类型创建一个子文件夹,添加每种资源到合适的文件夹中。要做到这一点,请用鼠标右键点击CollissionContent项目,选择Add→New Folder。将新建的文件夹命名为Images。然后在CollisionContent\Images文件夹上点击鼠标右键,选泽Add→Existing Item(如图3-2)。

o_3-2.jpg
图3-2 添加一张图片到您的解决方案中


  在打开的文件查找对话框中,在您下载的本章源码文件夹内定位logo.png文件。此文件位于BasicSprite\Collision\CollisionConten\Images文件夹下。选择此图像文件,然后点击Add(添加)按钮关闭对话框,您选择的文件就会出现在解决方案资源管理器的CollisionContent\Images文件夹下,同时文件也拷贝到您的项目的CollisionContent\Images文件夹中。

  现在生成您的项目,点击Build(生成)→Build Solution(生成解决方案),将使内容管道尝试编译您刚才添加的图像文件。如果没有生成错误的话,就说明内容管道可以识别文件格式并能将它转换成XNA的内部格式,而且XNA已经做好加载和使这些用图像文件的准备了。

  内容管道使用资源名称(asset name)来访问内容资源。另一种确认您的图像文件可以被内容管道识别的方法是查看新添加项目的属性,右键点击解决方案资源管理器中刚才添加的图像文件,选择属性,如图3-3。

o_3-3.jpg
图3-3 图像文件的属性


  如图所示,在图3-3中,您添加的logo.png文件默认的资源名是logo,或者说就是不包括扩展名的图像文件名,默认情况下,所有的资源名都是以没有扩展名的文件名来表示的。

  如果您可以在属性窗口中看到Asset Name属性,就说明内容管道可以识别您的图像文件。当然您也可以改变资源名,项目中的资源名要求是唯一的,不过只有在同一个文件夹下才做这样的要求。这是在CollissionContent项目中使用子文件夹来组织资源的另一个好处——您可以让多个资源拥有同样的资源名,只要它们存在于CollissionContent项目下不同的文件夹中。这似乎是个只会把事情搞复杂的坏主意,但这实际上很常见而且很有用。举例来说,您有一个字体文件、一个特效文件和一个图形文件,都用于爆炸效果中,那么如果把它们都命名为“explosion”并分别放到它们各自所属类型的文件夹下,会让事情变得更简单。

  您也许还注意到了图3-3中Asset Name属性下面的两个属性:Content Importer和Conten Processor,它们被设置成Texture-XNA Framework,表明内容管道验证过您添加到项目中的图像文件:并且它们准备被内容管道作为纹理对象来使用。在计算机图形学中纹理指应用到3D物体表面的2D图像,在本书的3D部分我们这样会做。不过现在我们只是直接将这些纹理绘制到2D游戏的屏幕上。

加载并绘制精灵

  现在您的解决方案中加载了一幅图像并且能够被内容管道所识别,已经准备好将它绘制到屏幕上。不过在您能够在代码中访问它之前,您需要将资源从内容管道加载到变量中以便操作它们。

  用来存储图像的默认对象是Texture2D。在Game1.cs代码文件中的GraphicDevice

  Manager和SpriteBatch的变量声明下面添加一个Texture2D变量:

Texture2D texture;

  现在,您需要将实际的图像文件加载到Texture2D变量中。可以使用Game类的Content属性来访问内容管道中的数据。Content属性是ContentManager类型,可以用来访问所有加载到内容管道中的对象。ContentManager类有一个Load方法可以让您将内容加载到不同类型的XNA对象中。

  就像之前说的那样,所有图像、声音和其它内容资源的加载都在LoadContent方法中完成。添加以下代码到LoadContent方法中:

texture = Content.Load<Texture2D>(@"Images/logo");

  传入Content.Load方法的参数是图像文件的路径,以解决方案资源管理器中的Content节点开始。字符串前面加上@符号表示逐字解释字符串,忽略字符串中的转义序列,所以以下两行代码将产生相同的字符串:

string str1 = @"images\logo"; 
string str2 = "images\\logo";

  同样请注意参数中使用的是资源名而不是文件名。

  ContentManager类的Load方法是一个泛型方法,需要一个类型参数来指定您想要访问哪种类型的变量。目前的情况下,您正在处理一个图像文件并且期望返回一个Texture2D对象。

  现在图像文件已经加载到texture变量中并可以使用了。XNA中所有的绘制工作都要在Draw方法中完成,因此请添加以下三行代码到Draw方法中,位于Clear方法的调用之后:

spriteBatch.Begin(); 
spriteBatch.Draw(texture, Vector2.Zero, Color.White); 
spriteBatch.End();

  这三行代码将图像绘制到屏幕的左上角。选择Debug→Start Debugging,您将会看到类似图3-4的画面。

  让我们看看这三行代码,首先需要注意的是三行代码都用到了一个SpriteBatch类的对象(spriteBatch)。这个变量在您创建项目的时候被声明,然后在LoadContent方法中被初始化。

  本质上,这里发生的事情就是XNA用SpriteBatch对象的Begin和End方法通知图形设备将要发送一个精灵(或2D图像)。在XNA游戏过程中图形设备会接收大量的数据,而且数据会有不同的格式和类型。无论何时您向图形设备输送数据,都需要先让它知道数据类型,以便它能够正确地进行处理。因此,您不能只是随意地多次调用SpriteBatch.Draw,您首先需要通过调用SpriteBatch.Begin来通知显卡精灵数据正在发送。

  Draw方法有三个参数,如表格3-1所述。

  尝试改变一下Draw调用的参数——具体的说是位置地染色颜色参数。在2D中,XNA使用Vector2结构体来定义坐标。Vector2.Zero是将Vector2的X,Y坐标置零的简化方式(和new Vector2(0, 0)是一样的作用)。

o_3-4.jpg
图3-4 XNA LOGO图像出现在屏幕的左上角

表3-1 Draw方法参数

参数

类型

描述

Texture

Texture2D

您想要绘制的图像的Texture2D对象.

Position

Vector2

您想要开始绘制图像的位置(2D坐标).通常图像从左上角开始绘制.

 Color

Color

染色颜色.指定为White将不会为图像染色,否则将图像染色为指定颜色.

  在2D XNA游戏中,X,Y屏幕坐标(0, 0)是屏幕的左上角,X轴正方向向右,Y轴正方向向下。

  如果您想要使图像在游戏窗口中居中,您需要找到窗口的中心点并且适当的偏移左上角坐标。您可以通过访问Game类的Window.ClientBounds属性来获得窗口的大小。当游戏运行于窗口模式时,Window.ClientBounds.X和Window.ClientBounds.Y相当于游戏窗口的左上角坐标,而Window.ClientBounds的Width和Height值总是等于窗口的宽度和高度,在窗口或全屏模式下都是如此。在Xbox 360和Windows Phone 7上Window.ClientBounds.X和Window.ClientBounds.Y总是为0,而Window.Client

  Bounds的Width属性和Height属性总是等于画面的宽和高(因为Windows Phone 7和Xbox 360游戏总是以全屏模式运行)。

  将Window.ClientBounds的Width和Height值除以2将得到屏幕中心点的坐标。要准确地将图像居中,需要将屏幕中心点坐标偏移图像宽和高的一半。因为传入Draw方法的位置参数并不代表绘制图像的中心,而是左上角。您可以通过Texture2D类的对象(texture)的Width和Height属性来获得图像的尺寸。用以下的代码替换SpriteBatch.Draw方法的调用,从而使图像居中:

spriteBatch.Draw(texture,
	new Vector2(
		(Window.ClientBounds.Width / 2) - (texture.Width / 2),
		(Window.ClientBounds.Height / 2) - (texture.Height / 2)
	),
	Color.White);

转载于:https://www.cnblogs.com/peixiaoxing/archive/2011/01/13/1934883.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值