SDL如何显示多张按键精灵找多张图小图

&&&&&& 如果我们要做一个游戏,会涉及到大量的图片,如果这些图片都用单个文件保存,那程序里会加载大量的图片,会有很多表面,处理起来很麻烦,一般会把游戏里使用的图片分类,一类图片保存到一个大图片里,使用的时候在按要求裁剪出需要的部分,这张大图就叫精灵图,裁剪出来的部分叫精灵。
&&&&& 下面我们做一个简单的例子,来演示一下如何裁剪精灵图,需要的图片有两张,第一张是背景图,随便用什么都可以,第二张是精灵图。我们会让精灵在地图上走动。
&&&&&&& 精灵图里是一个小人各种样子,小人大小都是一样的,图片大小为96*192,所以可以计算出每个小人(精灵)大小为32*48,这样我们就可以按照这个比例抠出精灵。
SDL_Surface *gpS//显示表面
SDL_Surface *gpBackG//背景表面
SDL_Surface *gpS//精灵表面
//显示背景图片
gpBackGround = loadImage("background.jpg");
SDL_BlitSurface(gpBackGround,NULL,gpScreen,NULL);
SDL_Flip(gpScreen);
//抠出第1副精灵的图
src[4][3];
src[0][0].x = src[0][0].y = 0;//精灵图左上角坐标
src[0][0].w = SPIRITWIDTH; //精灵的大小
src[0][0].h = SPIRITHEIGH;
SDL_BlitSurface(gpSpirit,&src[0],gpScreen,NULL);//在屏幕左上角显示第一个精灵
SDL_Flip(gpScreen);
&&&&&& 我们定义了一个SDL_Rect类型的数组src[4][3],每一个数组元素代表了一个精灵在大图上的位置,数组的每一行代表了图片上的每一行图片,然后设置src[0][0]各个成员的值,然后把gpSpirit传输到显示表面上,不过这次我们不是将整个表面传输,而是传输src[0][0]指示的大小,所以在屏幕上显示的不是整个精灵大图,而是由src[0][0]指示的第一个精灵的图。精灵图的裁剪就是这么简单。运行效果:
&&&&& 但精灵图的***背景也会显示,这会很难看,如何去除这个背景色呢?SDL中有一个函数可以设定图像的指定颜色透明。
&&&& int SDL_SetColorKey(SDL_Surface *surface, Uint32 flag, Uint32 key);
&&&& 参数:surface是指设定的是那个表面;
&&&&&&&&&&&&&& flag的值如下表所示
取消colorkey 功能
SDL_SRCCOLORKEY
以 key 为透明色。我们可以用& SDL_MapRGB() 来求得与 surface 的像素格式相符的颜色值。
SDL_RLEACCEL
用RLE (Run Length Encoding) 的方式来提高 Blit 的效率。
&&&& 其中key是要设定为透明的颜色,使用SDL_MapRGB()来取,为什么不能直接指定RGB颜色值呢,因为表面的颜色格式和RGB颜色格式不同,所以必须使用这个函数来返回将RGB颜色值转换成表面格式的颜色值。
&&&& Uint32 SDL_MapRGB(SDL_PixelFormat *fmt, Uint8 r, Uint8 g, Uint8 b);
&&&& 参数:fmt指定表面;r、g、b是颜色值,你可以通过画图软件取得指定图像的颜色值。
&& 有了这两个函数,我们就可以将精灵大图gpSpirit的背景颜色设成透明,显示的时候就没有背景色了。修改前面的代码:
gpBackGround = loadImage("background.jpg");
SDL_BlitSurface(gpBackGround,NULL,gpScreen,NULL);
SDL_Flip(gpScreen);
gpSpirit = loadImage("spirit.bmp");//载入精灵大图
colorkey= SDL_MapRGB(gpSpirit-&format, 255, 238, 187);
SDL_SetColorKey(gpSpirit, SDL_SRCCOLORKEY , colorkey ); //抠出第1副精灵的图 SDL_Rect&&& src[4][3];
src[0][0].x = src[0][0].y = 0;//精灵图左上角坐标
src[0][0].w = SPIRITWIDTH; //精灵的大小
src[0][0].h = SPIRITHEIGH;
SDL_BlitSurface(gpSpirit,&src[0][0],gpScreen,NULL);//在屏幕左上角显示第一个精灵
SDL_Flip(gpScreen);
  运行后显示效果:
  那么你是否还记得我们讲过的键盘事件检测?如果你会了键盘事件检测,我们可以做些有意思的尝试了,我们看一下精灵大图,会发现第一排小人是小人从上往下走的不同姿势,第二排从右往左走,第三排是从左往右走,第四排是从下往上走;那么我们是否可以通过键盘按键来让小人走路,转向呢?
  我们首先实现小人直行,要一直往前走,要不停的切换同一排小人图片,比如让小人从上往下走,第一幅图示src[0][0],下一步图示src[0][1],在走一步是src[0][2],那么我们可以设置一个变量step来标示下一步要出现的图片,其初值为0。
功能:演示精灵图裁剪
6 #include &stdio.h&
7 #include &stdlib.h&
8 #include "SDL.h"
10 #include &windows.h&
13 //屏幕尺寸
14 #define SCREENWIDTH
15 #define SCREENHEIGH
16 #define BPP
18 //精灵尺寸
19 #define SPIRITWIDTH
20 #define SPIRITHEIGH
22 SDL_Surface *gpS//显示表面
23 SDL_Surface *gpBackG//背景表面
24 SDL_Surface *gpS//精灵表面
26 SDL_Event myE//事件
28 SDL_Surface *loadImage(char *aFilename);
29 char *localeToUTF8(char *src);
31 int main(int argc,char *argv[])
int quit = 0;
char caption[20]={"兵"};
SDL_Rect src[4][3];
int spiritX = 0;//小球的初始坐标
int spiritY = 0;
int speed = 5;
int step = 0;//步伐
if((SDL_Init(SDL_INIT_VIDEO)==-1)) //初始化视频子系统
printf("Unable to init SDL: %s\n", SDL_GetError());
atexit(SDL_Quit);// 注册SDL_Quit,当退出时调用,使得退出时程序自动清理
//创建32位600*480窗口
gpScreen = SDL_SetVideoMode(SCREENWIDTH,SCREENHEIGH, BPP, SDL_HWSURFACE | SDL_HWPALETTE | SDL_DOUBLEBUF );
if(!gpScreen)
printf("%s\n",caption);
SDL_WM_SetCaption(localeToUTF8("兵棋"),NULL);
//SDL_WM_SetCaption(caption,NULL);
SDL_EnableKeyRepeat(500,30);//起动粘连键
gpBackGround = loadImage("background.jpg");
SDL_BlitSurface(gpBackGround,NULL,gpScreen,NULL);
SDL_Flip(gpScreen);
gpSpirit = loadImage("spirit.bmp");//载入精灵大图
colorkey= SDL_MapRGB(gpSpirit-&format, 255, 238, 187);
SDL_SetColorKey(gpSpirit, SDL_SRCCOLORKEY , colorkey );
//设定每一个精灵在精灵大图上的位置
for (i = 0;i&4;i++)
for (j = 0;j&3;j++)
src[i][j].x = j*SPIRITWIDTH;
src[i][j].y = i*SPIRITHEIGH;
src[i][j].w = SPIRITWIDTH;
src[i][j].h = SPIRITHEIGH;
//抠出第1副精灵的图
dst.x=dst.y = 0;
SDL_BlitSurface(gpSpirit,&src[0][0],gpScreen,&dst);//在屏幕左上角显示第一个精灵
SDL_Flip(gpScreen);
while (!quit)
while (SDL_PollEvent(&myEvent))
switch (myEvent.type)
case SDL_QUIT:
case SDL_KEYDOWN:
switch(myEvent.key.keysym.sym)
case SDLK_DOWN:
spiritY = (spiritY+SPIRITHEIGH)&SCREENHEIGH?(SCREENHEIGH-SPIRITHEIGH):spiritY;
case SDLK_MINUS:
speed=speed&0?speed:0;
case SDLK_EQUALS:
SDL_BlitSurface(gpBackGround,NULL,gpScreen,NULL);
dst.x = spiritX;
dst.y = spiritY;
dst.w = SPIRITWIDTH;
dst.h = SPIRITHEIGH;
SDL_BlitSurface(gpSpirit,&src[0][step],gpScreen,&dst);
SDL_Flip(gpScreen);
case SDL_KEYUP:
switch(myEvent.key.keysym.sym)
case SDLK_LEFT:
printf("小人的坐标:(%d,%d)\n",spiritX,spiritY);
case SDLK_RIGHT:
printf("小人的坐标:(%d,%d)\n",spiritX,spiritY);
case SDLK_UP:
printf("小人的坐标:(%d,%d)\n",spiritX,spiritY);
case SDLK_DOWN:
printf("小人的坐标:(%d,%d)\n",spiritX,spiritY);
//system("pause");
148 /*--------------------------------------------------------------------
char *filename
图像文件的名字
返回值: SDL_Surface * 返回指向图像表面的指针
154 ----------------------------------------------------------------------*/
155 SDL_Surface *loadImage(char *aFilename)
SDL_Surface* loadedImage = NULL;
SDL_Surface* optimizedImage = NULL;
//载入图像
loadedImage = IMG_Load( aFilename);
if( NULL != loadedImage )//If the image loaded
//创建优化图像
optimizedImage = SDL_DisplayFormat( loadedImage );
//释放loadImage
SDL_FreeSurface( loadedImage );
return optimizedI
174 /*--------------------------------------------------------------------
中文字符串
返回值: char * UTF8字符串
将汉字转换成UTF8字符串
180 ----------------------------------------------------------------------*/
181 char *localeToUTF8(char *src)
static char *buf = NULL;
wchar_t *unicode_
free(buf);
buf = NULL;
nRetLen = MultiByteToWideChar(CP_ACP,0,src,-1,NULL,0);
unicode_buf = (wchar_t*)malloc((nRetLen+1)*sizeof(wchar_t));
MultiByteToWideChar(CP_ACP,0,src,-1,unicode_buf,nRetLen);
nRetLen = WideCharToMultiByte(CP_UTF8,0,unicode_buf,-1,NULL,0,NULL,NULL);
buf = (char*)malloc(nRetLen+1);
WideCharToMultiByte(CP_UTF8,0,unicode_buf,-1,buf,nRetLen,NULL,NULL);
free(unicode_buf);
  第73-82行将每个小人的位置存储到src数组里,这样我们显示图像就不会错了,第101行我们检测了是否按下了&键,如果按下了,我们把step的值加1,显示下一步的图片,但向下行走只有三幅图片,所以当step等于3时,应当将其置成0,这一步在第113行用了一个模运算完成,接下来就是定位将图片显示在屏幕上的位置,这个在键盘检测教程就已经说了,这不在累述,然后显示。运行结果可以看到很像一个人在行走。  
  现在,程序还有一点问题,就是不能转向,我们可以再设一个变量direct表示方向,其值为0表示向下,1向左,2向右,3向上,并且direct的值对应src行下标,然后再增加对其他三个方向的检测就可以了。另外我们在这个教程里设置了应用程序的名字并且名字是中文,所以需要加载windows.h头文件,这个会在后续章节讲述。
  这个程序没有对小人进行碰撞检测,所以小人遇树撞树,以后会做碰撞检测的讲解,完整的代码请点击下载。
阅读(...) 评论()CAD批量打图精灵用户手册_百度文库
两大类热门资源免费畅读
续费一年阅读会员,立省24元!
CAD批量打图精灵用户手册
上传于||暂无简介
阅读已结束,如果下载本文需要使用1下载券
想免费下载本文?
定制HR最喜欢的简历
下载文档到电脑,查找使用更方便
还剩12页未读,继续阅读
定制HR最喜欢的简历
你可能喜欢欢迎来到DIVCSS5查找CSS资料与学习DIV CSS布局技术!您的位置: >
> div css sprites精灵-图像拼合 CSS贴图定位网页背景素材图片拼合定位布局技术教程篇与css sprites实例篇
css sprites拼合背景图片素材实现布局效果截图
一、什么是css sprites
css sprites直译过来就是CSS精灵。通常被解释为&CSS图像拼合&或&CSS贴图定位&。其实就是通过将多个图片融合到一张图里面,然后通过背景定位技术技巧布局网页背景。这样做的好处也是显而易见的,因为图片多的话,会增加http的请求,无疑促使了网站性能的减低,特别是图片特别多的网站,如果能用css sprites降低图片数量,带来的将是速度的提升。
css sprites是什么通俗解释:CSS Sprites其实就是把网页中一些背景图片整合拼合成一张图片中,再利用DIV CSS的&&,&&,&&的组合进行背景定位,background-position可以用数字能精确的定位出背景图片在布局盒子对象位置。
二、适合与不适合DIV CSS sprites拼合布局
1、适合:一般小图标素材
小的图标ico类素材,一般图标很小十多像素几十像素的宽度高度,这种适合拼合成一张图实现sprites background背景定位布局。多小ico太多自然加载网页时瞬间会消耗些http iis链接数,但很快加载完又会释放。
2、不适合:大图大背景
大背景一般用于网页背景,拼合时,设置为网页背景时所有背景都会显示出来。大图拼接拼合会增大图片大小,网络带宽不好的访问者访问时由于背景图大文件大会加载稍慢些,所以大图不推荐拼接拼合来使用css sprites背景定位布局。
3、sprites适合推荐小结
一般此sprites拼合布局用于局部小盒子布局不适合大背景大布局背景使用。比如小局部布局小图标背景、小导航背景等DIVCSS布局。
三、div css sprites优势与缺点劣势判断选择
1、sprites优势:
若干小图标拼合成一张图后布局,减少http iis请求数,对于大战大流量网站来说隐形优势很显然的,从而隐形地提升了网站性能。对于大流量网站来说本来http请求数比较宝贵,使用 Sprites这样可以大大的提高了页面的性能,这是CSS Sprites最大的优点,也是其被广泛传播和应用的主要原因,同时也减少图片文件数目。
2、sprites缺点
在图片合并的时候,你要把多张图片有序的合理的合并成一张图片,还要留好只够的空间,防止板块内不会出现不必要的背景,如果留空间或拼合位置不合适,在布局时容易出现布局这个盒子对象时,设置背景出现拼合相邻图片,干扰图片的情况;
CSS Sprites在开发的时候比较麻烦,你要通过photoshop(PS)或其他工具测量计算每一个背景单元的精确位置,这是针线活,没什么难度,但是很繁琐;
CSS Sprites在维护的时候比较麻烦,sprites是一般双刃剑,如果页面背景有少许改动,一般就要改这张合并的图片,无需改的地方最好不要动,这样避免改动更多的css,如果在原来的地方放不下,有只能(最好)往下加图片,这样图片的字节就增加了,因为每次的图片改动都得往这个图片删除或添加内容,显得稍微繁琐,而且重新算图片的位置(尤其是这种上千px的图)也是一件颇为不爽的事情
由于图片的位置需要固定为某个绝对数值,这就失去了诸如center之类的灵活性。
3、DIVCSS5推荐小结
犹豫拼接图片需要一定经验技巧(做实践即可快速掌握)、测量定位数值、修改不是那么灵活等原因,一般小网站站、小流量网站、一般企业网站不是很推荐使用CSS Sprites,因为使用CSS Sprites会比普通单个背景图片布局要耗费时间和精力,所以不是很推荐小站。但这个布局技巧也必须要学会掌握灵活布局才是目的。小站HTTP请求数丰富这点拼接其实也起不来什么优势反而会浪费宝贵时间。相反大网站大流量网站推荐使用,这样比较值得。
四、div css sprites实例示例教程
1、素材与要实现效果截图
拼合ico图标素材实现列表不同图标效果截图
2、sprites实例教程解释介绍
首先这些图标素材是放在同一张图片上(PS拼合),然后实现成列表类布局,列表每个前图标不同。使用div css sprites实现此布局(其实使用background样式实现)。
首先此列表布局我们使用,每个站一行排版,对设置padding实现四周内容与边框一定间距效果,因为每个li前面图标不同,但此背景图片是拼合在一张图片上,所以这里做li里开始使用实现这个不同图标效果,每个图标不同为了区别span所以对span设置不同class,不同class对应设置定位相应的图标。
3、实例教程准备
1)、初始化模板使用:为了兼容各大浏览器,仍然这里使用DIVCSS5提供初始化模板,在此模板基础上修改设置符合本实例CSS样式。
2)、图标素材,这里直接为大家提供拼接好的图标素材图片一张,命名为&ico.png&,如下图,可直接另存为保存使用。
sprites案例图片素材(直接点击图片鼠标右键可以另存为保存使用)
4、先布局出效果,再css sprites设置不同背景图标样式
1)、关键代码:
&class=&Sprites&&&&&&&class=&a1&&href=&#&WORD文章标题&&&&&&class=&a2&&href=&#&PPT内容标题&&&&&&class=&a3&&href=&#&Excel内容标题&&&&&&class=&a4&&href=&#&PDF内容标题&&&&&&class=&a5&&href=&#&文本文档标题&&
为了区别不同效果对加入不同。
ul.Sprites{&margin:0&&border:1px&solid&#F00;&width:300&padding:10}&ul.Sprites&li{&height:24&font-size:14line-height:24&text-align:&overflow:hidden}&ul.Sprites&li&span{&float:&width:17padding-top:5height:17&&overflow:background:url(ico.png)&no-repeat}&ul.Sprites&li&a{&padding-left:5px}&
3)、效果截图
未使用sprites技术引入背景图片效果截图
4)、使用css sprites设置定位背景完整关键CSS代码
ul.Sprites{&margin:0&&border:1px&solid&#F00;&width:300&padding:10}&ul.Sprites&li{&height:24&font-size:14line-height:24&text-align:&overflow:hidden}&ul.Sprites&li&span{&float:&width:17padding-top:5height:17&&overflow:background:url(ico.png)&no-repeat}&ul.Sprites&li&a{&padding-left:5px}&ul.Sprites&li&span.a1{&background-position:&-62px&-32px}&ul.Sprites&li&span.a2{&background-position:&-86px&-32px}&ul.Sprites&li&span.a3{&background-position:&-110px&-32px}&ul.Sprites&li&span.a4{&background-position:&-133px&-32px}&ul.Sprites&li&span.a5{&background-position:&-158px&-32px}&
最终实现浏览器效果测试效果图
div css sprites案例效果截图
5)、css sprites关键代码与解释
ul.Sprites&li&span.a1{&background-position:&-62px&-32px}&ul.Sprites&li&span.a2{&background-position:&-86px&-32px}&ul.Sprites&li&span.a3{&background-position:&-110px&-32px}&ul.Sprites&li&span.a4{&background-position:&-133px&-32px}&ul.Sprites&li&span.a5{&background-position:&-158px&-32px}&
首先对ul.Sprites li span引入背景
ul.Sprites li span{ background:url(ico.png) no-repeat} 给span设置。
再分别对不同span class设置对于图标背景定位具体值
ul.Sprites li span.a1{ background-position: -62px -32px}设置背景图片作为对应盒子对象背景后向左&拖动&62px,向上&拖动&32px开始显示此背景图标
ul.Sprites li span.a2{ background-position: -86px -32px}设置背景图片作为对应盒子对象背景后向左&拖动&86px,向上&拖动&32px开始显示此背景图标
ul.Sprites li span.a3{ background-position: -110px -32px}设置背景图片作为对应盒子对象背景后向左&拖动&110px,向上&拖动&32px开始显示此背景图标
ul.Sprites li span.a4{ background-position: -133px -32px}设置背景图片作为对应盒子对象背景后向左&拖动&133px,向上&拖动&32px开始显示此背景图标
ul.Sprites li span.a5{ background-position: -158px -32px}设置背景图片作为对应盒子对象背景后向左&拖动&158px,向上&拖动&32px开始显示此背景图标
关键:背景background-position有两个数值,前一个代表靠左距离值(可为正可为负),第二个数值代表靠上距离值(可为正可为负)
背景background-position有两个数值可以为正可以为负,当为正数时,代表背景图片作为对象盒子背景图片时靠左和考上多少距离多少开始显示背景图片;当为负数时代表背景图片作为盒子对象背景图片,将背景图片拖动超出盒子对象左边多远,拖动超出盒子对象上边多远开始显示此背景图片。
6)、背景图片定位数值获取
向左&拖动&,向上&拖动&这些这PS获取图文教程
利用切片工具获取对应小图标在图片文件中位置
通过ps软件利用切片工具画出要显示图片区域后,双击即可弹出&切片详细卡&,可以得到X(靠左距离值),Y(靠上距离值)即可获得对应图片素材在大图中位置。
五、在线样式与下载
1、在线样式
2、打包下载
六、DIV CSS sprites技巧技术总结
CSS sprites其实就是对background样式的扩展应用,以前设置背景background-position常见为正数值,设置背景靠左靠上距离多少开始显示图片,为负数值后,是将图片拖离左边上边多少像素开始显示图片,下载本案例多次修改修改数值,观察观察能找到规律很快就会作为此技巧,同时学会PS切片工具获取距离值。如需转载,请注明文章出处和来源网址:我要分享到:上一篇: 下一篇: 必备CSS教程 Essential CSS Tutorials• • • • • • • ()• • ()• ()• • • • • • • • • • •
必备HTML基础教程 Essential HTML Tutorials •
• () • () • () •
• () •
• () •
• &最新文章NEWS• • • • • • • • • • 相关文章RELATED• • • • • • • • • • CSS EFFECTS / CSS MODULE如对文章有任何疑问请提交到,或有任何网页制作CSS问题立即到发贴求解 或 直接DIVCSS5网页顶部搜索遇到DIVCSS疑问。文章修订日期: 14:52
原创:本文 DIVCSS5版权所有。
学习与资源分享平台

参考资料

 

随机推荐