真3D麻将游戏桌面适配任意分辨率

图1:欢乐麻将微信小游戏版

 

大部分同学应该都处理过2D麻将桌的适配,从iPhoneX(目前最长的移动设备)到iPad(目前最短的移动设备)

无非就是根据长宽比来选择最适合的适配方式。麒麟子之前写过一遍,传送门:棋牌UI全分辨率适配方案

但3D的适配则不是通过缩放来的,因为3D看到的画面,大部分是调整摄相机参数得来的。我们常见的设备有以下分辨率

2.16 : 1  iPhoneX系列为代表

2:1 华为、小米等2018年后出的Android手机为代表

16:9 苹果6以及同时期的Android手机为代表

1024:768 iPad为代表。

麒麟子打开了麻将的代表作,欢乐麻将。在不同设备下玩了一圈后总结出了欢乐麻将的适配规则。

1、设计分辨率是 16:9, (常见的就是1280 x 720)

2、在宽于16:9的设备上,它什么都没做,只是简单地把桌面保持左右撑满。

3、在高于16:9的设备上,它会保持左右两边不变,让高显示得更多一点。

要实现以上目标,我们需要做如下处理就行。

1、U3D编辑器中,使用16:9的预览窗口,调整好摄相机和画面。

2、切换为1024x768的分辨率,保持摄相机不动(最好是在运行模式下调,这样16:9的参数就不会影响),调整好桌面的缩放和位置。

3、记录下1024x768的参数 缩放和位移。

4、在代码中,通过真实横纵比(宽/高) 与 设计横纵比(1280/720) 进行比较

a、如果更宽(真实横纵比 > 设计横纵比),则将背景的scaleX放大,放大倍数 = 真实横纵比 / 设计横纵比。

b、如果更高(真实横纵比 > 设计横纵比),则将桌面缩小和位移。

缩小的方式就是插值, 设计分辨率下的缩放和位移,我们作为初值,1024 x 768下的值作为目标值(刚刚U3D编辑器中编辑的时候,我们需要把这个值记下来)。 插值的计算如下:(代码中的Laya.stage.height / Laya.stage.width 就是真实高/真实宽,大家根据自己用的引擎来调整 即可)

			let fromRatio = 720 / 1280;
			let targetRatio = 768 / 1024;
			let curRatio = Laya.stage.height / Laya.stage.width;
			let factor = (curRatio - fromRatio) / (targetRatio - fromRatio);

有了这个factor我们只需要做一个线性插值,就能得到不同分辨率下的桌面缩放和位移了。

最后上几张图

iPhone6/7/8效果
iPhoneX效果

 

iPad效果

代码与工程相关比较多,不方便抽出来,如果有需要的朋友,可以联系我一起探讨。

发布了232 篇原创文章 · 获赞 542 · 访问量 118万+
展开阅读全文

在 android 平板上的动画显示错误

05-27

我开发一个android程序,开始于启动画面。程序在模拟器和真机上可以运行,但是平板上不行。 package com.example.project; import android.app.Activity; import android.content.Intent; import android.os.Bundle; import android.util.Log; import android.view.Window; import android.view.WindowManager; import android.view.animation.AlphaAnimation; import android.view.animation.Animation; import android.view.animation.LinearInterpolator; import android.view.animation.TranslateAnimation; import android.widget.ImageView; import android.widget.TextView; public class Splashscreen extends Activity { private static String TAG=Splashscreen.class.getName(); private static long SLEEP_TIME=6; TextView tv; ImageView iv; @Override protected void onCreate(Bundle savedInstanceState) { // TODO Auto-generated method stub super.onCreate(savedInstanceState); this.requestWindowFeature(Window.FEATURE_NO_TITLE); this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN); setContentView(R.layout.splash1); TranslateAnimation translate = new TranslateAnimation(Animation.RELATIVE_TO_PARENT,0,Animation.RELATIVE_TO_PARENT,0,Animation.ABSOLUTE,250,Animation.ABSOLUTE,0); translate.setDuration(3000); translate.reset(); translate.setFillAfter(true); tv=(TextView)findViewById(R.id.tt1); tv.startAnimation(translate); iv=(ImageView)findViewById(R.id.i1); Animation anim1= new AlphaAnimation(1, 0); anim1.setDuration(1000); anim1.setInterpolator(new LinearInterpolator()); anim1.setRepeatCount(1); anim1.setRepeatMode(Animation.REVERSE); iv.startAnimation(anim1); IntentLauncher launcher=new IntentLauncher(); launcher.start(); } private class IntentLauncher extends Thread { public void run() { try{ Thread.sleep(SLEEP_TIME*1000); }catch(Exception e) { Log.e(TAG,e.getMessage()); } Intent i=new Intent(Splashscreen.this,Login_or_up.class); Splashscreen.this.startActivity(i); 错误显示在logcat中: 05-25 18:04:45.434: D/AndroidRuntime(613): Shutting down VM 05-25 18:04:45.454: W/dalvikvm(613): threadid=1: thread exiting with uncaught exception (group=0x4001d800) 05-25 18:04:45.464: E/AndroidRuntime(613): FATAL EXCEPTION: main 05-25 18:04:45.464: E/AndroidRuntime(613): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.project/com.example.project.Splashscreen}: java.lang.NullPointerException 05-25 18:04:45.464: E/AndroidRuntime(613): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2663) 05-25 18:04:45.464: E/AndroidRuntime(613): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2679) 05-25 18:04:45.464: E/AndroidRuntime(613): at android.app.ActivityThread.access$2300(ActivityThread.java:125) 05-25 18:04:45.464: E/AndroidRuntime(613): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2033) 05-25 18:04:45.464: E/AndroidRuntime(613): at android.os.Handler.dispatchMessage(Handler.java:99) 05-25 18:04:45.464: E/AndroidRuntime(613): at android.os.Looper.loop(Looper.java:123) 05-25 18:04:45.464: E/AndroidRuntime(613): at android.app.ActivityThread.main(ActivityThread.java:4627) 05-25 18:04:45.464: E/AndroidRuntime(613): at java.lang.reflect.Method.invokeNative(Native Method) 05-25 18:04:45.464: E/AndroidRuntime(613): at java.lang.reflect.Method.invoke(Method.java:521) 05-25 18:04:45.464: E/AndroidRuntime(613): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:868) 05-25 18:04:45.464: E/AndroidRuntime(613): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:626) 05-25 18:04:45.464: E/AndroidRuntime(613): at dalvik.system.NativeStart.main(Native Method) 05-25 18:04:45.464: E/AndroidRuntime(613): Caused by: java.lang.NullPointerException 05-25 18:04:45.464: E/AndroidRuntime(613): at com.example.project.Splashscreen.onCreate(Splashscreen.java:38) 05-25 18:04:45.464: E/AndroidRuntime(613): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1047) 05-25 18:04:45.464: E/AndroidRuntime(613): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2627) 05-25 18:04:45.464: E/AndroidRuntime(613): ... 11 more 05-25 18:04:47.394: I/Process(613): Sending signal. PID: 613 SIG: 9 如何解决这个问题? 问答

没有更多推荐了,返回首页

©️2019 CSDN 皮肤主题: Age of Ai 设计师: meimeiellie

分享到微信朋友圈

×

扫一扫,手机浏览