通过例子分析Cocos2d-x的Resolution

本文详细介绍了在跨平台游戏开发中如何设置不同的分辨率策略来确保游戏在各种设备上如iPhone和iPad都能正常显示。文章通过实例展示了不同分辨率策略(如kResolutionExactFit、kResolutionNoBorder和kResolutionShowAll等)的效果,并解释了如何计算scale factor。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

例子:Use images for iPhone 5 in iPad.

假设

  • 原图像大小是:1136 x 640 (For iPhone 5)
  • Screen中实际的坐标系统是:1024 x 768 (iPad)
    Screen中预想的坐标系统是:480 x 320 (iPhone坐标)

  • 设置预想坐标和显示方式:
    CCEGLView::sharedOpenGLView()->setDesignResolutionSize(480, 320, ResolutionPolicy);
    预想坐标就是你在程序中使用的坐标系统,为了保持iPhone和iPad使用同一个坐标系统,我们都使用480x320.
    ResolutionPolicy:
    当我们设置完预想坐标,在x和y方向都有一个放大因子:
    scaleX = 1024.0 / 480.0 = 2.13
    scaleY = 768.0 / 320.0 = 2.4
    kResolutionExactFit:      x和y方向的放大因子分别取scaleX和scaleY
    kResolutionNoBorder:   scaleX = scaleY = max(scaleX, scaleY)
    kResolutionShowAll:        scaleX = scaleY = min(scaleX, scaleY)
    kResolutionFixedHeight:  scaleY = scaleX = scaleY
    kResolutionFixedWidth:   
     scaleX = scaleY = scaleX


  • 设置scale factor:
    CCDirector::sharedDirector()->setContentScaleFactor(factor);
    这里的ContentScaleFactor是
      Screen中实际的坐标系统 与
      Screen中预想的坐标系统 之间的关系。
      当设置setContentScaleFactor(2)时,在code中1个point相当于2 pixels。


  • 在CCLayer中render sprite:

    CCSprite *bgSprite = CCSprite::create("1136x640.png");
    bgSprite->setPosition(ccp(winSize.width * 0.5f, winSize.height * 0.5f));
    addChild(bgSprite);


设置ResolutionPolicy:
  • kResolutionExactFit 
    字面意思就是完全显示,就是整个sprite在目标屏幕中完全显示。如果sprite尺寸与目标屏幕不符合,不可避免的会进行拉伸。显示效果如下

CCDirector::sharedDirector()->setContentScaleFactor(2.4); 

其实就是,分别计算x和y方向上的scale因子,并把他们应用到图像上去。
即:scaleX = 目标屏幕width /  预想的坐标系统x =960 / 480
      scaleY = 目标屏幕height /  预想的坐标系统y =640 / 320
可以看到,最后连button都变形了,这种方式不可取。

 

  • kResolutionNoBorder
    scale因子取的是MAX(scaleX, scaleY).
    它保证了full screen显示,但是有部分会显示不了,就像下图,在y方向上完全显示了,但是x方向上有部分没有显示出来,可以看到sprite有部分没有显示,button也没有显示。
    这时仅仅通过 WinSize 满足不了我们的设计需求,所以引入了 VisibleSize 与 VisibleOrigin 概念。FrameSize 是实际的屏幕分辨率,而 VisibleSize 是在 WinSize 之内,保持 FrameSize 的宽高比所能占用的最大区域,即可见区域的大小。
    在本例中,

    visibleSize : 426.666, 320.0   <-  ( 1024 / 2.4, 640 / 2.4 )
    visibleOrigin : 26.666, 0.0     <-   ( (480 * 2.4 - 1024) * 0.5, (320 * 2.4 - 640) * 0.5 )

CCDirector::sharedDirector()->setContentScaleFactor(2);

  • kResolutionShowAll

    scale因子取的是MIN(scaleX, scaleY).
    他能保证sprite能完全显示,但是可能会留下黑边。这条黑边可以接受input事件的。如下图。
CCDirector::sharedDirector()->setContentScaleFactor(2);
这里图片也没有完全显示,因为图片并不是480x320的图片,如果图片图片跟预想坐标一致,一定能完全显示。

设置scale factor:
CCDirector::sharedDirector()->setContentScaleFactor(factor);
这里的ContentScaleFactor是
  Screen中实际的坐标系统 与
  Screen中预想的坐标系统 之间的关系。
  当设置setContentScaleFactor(2)时,在code中1个point相当于2 pixels。

设置CCEGLView::sharedOpenGLView()->setDesignResolutionSize(480, 320kResolutionNoBorder);
这时的
visibleSize:(426.66, 320)
visibleOrigin: (26.66, 0.0)

1.如果设置setContentScaleFactor(768.0 / 320.0), 即2.4
2. 如果设置setContentScaleFactor(1024.0 / 480.0), 即2.13
3. 如果设置setContentScaleFactor(640.0 / 320.0), 即2
可见在随着factor的变小,图像在放大。
为什么呢?
可以这么理解,当前屏幕显示的坐标是
origin:(26.66, 0)
size:  (426.66, 320)
如果设置setContentScaleFactor(2),那么实际的能显示的屏幕坐标是
origin:(26.66 * 2, 0 * 2)         -> (53.32, 0)
size:  (426.66 * 2, 320 * 2 )  -> (853.32, 640.0)
当要显示1136 x 640的图像时,y方向上刚好能全部显示,x方向只能显示一部分。(实际上,图片被放大了。)

      
Ref:

resolutionPolicy的值有:

enum ResolutionPolicy

{

    // The entire application is visible in the specified area without trying to preserve the original aspect ratio.

    // Distortion can occur, and the application may appear stretched or compressed.

    kResolutionExactFit,

    // The entire application fills the specified area, without distortion but possibly with some cropping,

    // while maintaining the original aspect ratio of the application.

    kResolutionNoBorder,

    // The entire application is visible in the specified area without distortion while maintaining the original

    // aspect ratio of the application. Borders can appear on two sides of the application.

    kResolutionShowAll,

    // The application takes the height of the design resolution size and modifies the width of the internal

    // canvas so that it fits the aspect ratio of the device

    // no distortion will occur however you must make sure your application works on different

    // aspect ratios

    kResolutionFixedHeight,

    // The application takes the width of the design resolution size and modifies the height of the internal

    // canvas so that it fits the aspect ratio of the device

    // no distortion will occur however you must make sure your application works on different

    // aspect ratios

    kResolutionFixedWidth,

 

    kResolutionUnKnown,

};


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值