关键词:
什么是刘海屏?
随着iPhone X发布,刘海屏手机大行其道 ,Google Android P版本的发布,也引入了刘海屏的概念 即将发布的Android p也提供了对刘海屏的支持。像 华为P20 pro, vivo X21,OPPO R15 华为nova 3e,红米note6等手机厂商也纷纷推出自己的刘海屏手机app也要提前做好适配。
屏幕的正上方居中位置(下图黑色区域)会被挖掉一个孔,屏幕被挖掉的区域无法正常显示内容,这种类型的屏幕就是刘海屏,也有其他叫法:挖孔屏、凹凸屏等等,这里统一按刘海屏命名。
如果我们的的app没有适配android p的刘海屏,那么在显示的时候变会出现问题,
1)如没有状态栏,全屏显示的App,那么在Android P版本中显示如下
后果:导航栏中title被遮挡
2)如果有状态栏,全屏显示的App,那么在Android P版本中显示如下,你会发现UI出现了黑边,页码也看不清了
显示内容下移,头部出现黑条,底部出现遮挡
以上都是基于标准的刘海屏设计出现的情况,还有一些厂商自定义了刘海屏,即刘海屏的高度大于了状态栏,那么就会产生类似的问题,如下
1)状态栏背景高度写死的问题
如何适配刘海屏?
由于Android p正式版今日刚发布, 当前市面上的Android 刘海屏手机还不能用Android 官方提供的方案来解决,那怎么办呢?还好几个厂商自己给出了适配方案。
华为刘海屏适配方案 - 如 P20 pro
华为给出的文档最为详细,P20 pro预装系统对未做刘海屏适配处理的app有一定处理,处理逻辑如下
可见,会被华为系统做偏移处理的有2种情况:
1.未设置meta-data值,页面横屏状态
2.未设置meta-data值,页面竖屏状态,不显示状态栏
这2种情况都会出现后果二。如果你的app中页面没有这两种情况,例如都是竖屏且显示状态栏,你就可以淡定地不做处理。
现在我们知道原因了就可以对症下药了,这里给出我推荐的解决方案(官方给出的解决方案不止一种,可以根据自己的需要采用) 分为4步:
1.配置meta-data
<meta-data android:name="android.notch_support" android:value="true"/>
①对Application生效,意味着该应用的所有页面,系统都不会做竖屏场景的特殊下移或者是横屏场景的右移特殊处理:
② 对Activity生效,意味着可以针对单个页面进行刘海屏适配,设置了该属性的Activity系统将不会做特殊处理:
2.检测是否存在刘海屏
public static boolean hasNotchInScreen(Context context)
boolean ret = false;
try
ClassLoader cl = context.getClassLoader();
Class HwNotchSizeUtil = cl.loadClass("com.huawei.android.util.HwNotchSizeUtil");
Method get = HwNotchSizeUtil.getMethod("hasNotchInScreen");
ret = (boolean) get.invoke(HwNotchSizeUtil);
catch (ClassNotFoundException e)
Log.e("test", "hasNotchInScreen ClassNotFoundException");
catch (NoSuchMethodException e)
Log.e("test", "hasNotchInScreen NoSuchMethodException");
catch (Exception e)
Log.e("test", "hasNotchInScreen Exception");
finally
return ret;
3.获取刘海屏的参数
public static int[] getNotchSize(Context context)
int[] ret = new int[]0, 0;
try
ClassLoader cl = context.getClassLoader();
Class HwNotchSizeUtil = cl.loadClass("com.huawei.android.util.HwNotchSizeUtil");
Method get = HwNotchSizeUtil.getMethod("getNotchSize");
ret = (int[]) get.invoke(HwNotchSizeUtil);
catch (ClassNotFoundException e)
Log.e("test", "getNotchSize ClassNotFoundException");
catch (NoSuchMethodException e)
Log.e("test", "getNotchSize NoSuchMethodException");
catch (Exception e)
Log.e("test", "getNotchSize Exception");
finally
return ret;
4. UI适配
没错,第1步仅仅是告诉EMUI系统不要瞎操作你的页面,真正适配的活还要你自己干。
①判断是否刘海屏,代码上面给出了
②如果是刘海屏手机需要应用自己调整布局避开刘海区,布局原则:保证重要的文字、图片和视频信息、可点击的控件和图标还有应用弹窗等等布局建议显示在状态栏区域以下(安全区域);不重要,遮挡不会出现问题的布局可以延伸到状态栏区域(危险区域)显示,按照这种布局原则修改,可以一次修改就能适配所有的刘海屏手机:
vivo & OPPO刘海屏适配
vivo 和 OPPO官网仅仅给出了适配指导,没有给出具体方案,简单总结为:
如有是具有刘海屏的手机,竖屏显示状态栏,横屏不要在危险区显示重要信息或者设置点击事件。
那怎么知道是不是刘海屏手机呢?
OPPO判断方法:
public static boolean hasNotchInOppo(Context context)
return context.getPackageManager().hasSystemFeature("com.oppo.feature.screen.heteromorphism");
vivo的判断方法:
public static final int NOTCH_IN_SCREEN_VOIO=0x00000020;//是否有凹槽
public static final int ROUNDED_IN_SCREEN_VOIO=0x00000008;//是否有圆角
public static boolean hasNotchInScreenAtVoio(Context context)
boolean ret = false;
try
ClassLoader cl = context.getClassLoader();
Class FtFeature = cl.loadClass("com.util.FtFeature");
Method get = FtFeature.getMethod("isFeatureSupport",int.class);
ret = (boolean) get.invoke(FtFeature,NOTCH_IN_SCREEN_VOIO);
catch (ClassNotFoundException e)
Log.e("test", "hasNotchInScreen ClassNotFoundException");
catch (NoSuchMethodException e)
Log.e("test", "hasNotchInScreen NoSuchMethodException");
catch (Exception e)
Log.e("test", "hasNotchInScreen Exception");
finally
return ret;
google官方对刘海屏做的支持
首选要在build.gradle设置支持 , 其实只要注意如下两个属性就好,只有如下设置,才能正确使用Android P版本,其他的build.gradle的配置可以视自己的as版本自定义即可
compileSdkVersion ‘android-P’
targetSdkVersion ‘P’
在AS创建一个Android P(API 28)的模拟器,在设置中打开刘海屏
默认的Android P的模拟器是关闭刘海屏的,首先看下如何开启Android P的模拟器中的刘海屏,
1)启用开发者选项和调试
-> 打开 Settings 应用。
-> 选择 System。
-> 滚动到底部,然后选择 About phone。
-> 滚动到底部,点按 Build number 7 次。
-> 返回上一屏幕,在底部附近可找到 Developer options
2)在 Developer options 屏幕中,向下滚动至 Drawing 部分并选择 Simulate a display with a cutout
3)选择屏幕缺口的大小
如图所示,Google提供了四种刘海屏选择方案
一般选第四种
这里需要注意一个问题:使用Android P模拟器的时候,这里的模拟凹口屏的四个选项其实实质只改变了刘海屏的位置和宽度,高度(系统刘海屏不会超过状态栏),但是在真机中,这四个选项有可能对应不同的操作
Google默认的适配刘海屏策略是这样的
1) 如果应用未适配刘海屏,需要系统对全屏显示的应用界面做特殊移动处理(竖屏下移处理,横屏右移处),因此此处出现了黑边的现象;如果应用页面布局不能做到自适应,就会出现布局问题;如果应用布局能够做到自适应,也会有黑边无法全屏显示的体验问题
2)如果有状态栏的App,则不受刘海屏的影响(有状态肯定不是全屏,那么就不会有下移的风险)
google从Android P开始为刘海屏提供支持,目前提供了一个类和三种模式:
所以我们可用这个类判断是否有刘海的存在以及刘海的位置
DisplayCutout cutout = mContext.getDisplayCutout();
三种模式
A new window layout attribute, layoutInDisplayCutoutMode, allows your app to lay out its content around a device's cutouts. You can set this attribute to one of the following values:
-
LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER
第一种模式:
LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT :全屏窗口不会使用到刘海区域,非全屏窗口可正常使用刘海区域 // 仅仅当系统提供的bar完全包含了刘海区时才允许window扩展到刘海区,否则window不会和刘海区重叠,默认情况下,
第二种模式:
LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES :允许window扩展到刘海区(原文说的是短边的刘海区, 目前有刘海的手机都在短边,所以就不纠结了)
第三种模式:
LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER: 不允许window扩展到刘海区,窗口不允许和刘海屏重叠
public class AndroidPDemoActivity extends Activity
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
//给Activity设置为无title,全屏显示,这段代码在无刘海屏显示效果如下
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,WindowManager.LayoutParams.FLAG_FULLSCREEN);
WindowManager.LayoutParams lp = this.getWindow().getAttributes();
lp.layoutInDisplayCutoutMode = WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT;
this.getWindow().setAttributes(lp);
setContentView(R.layout.activity_android_p_demo_layout);
上述代码换成LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER, 可以看出显示效果和DEFAULT是一致的,LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER是不允许使用刘海屏区域,而LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT全屏窗口不允许使用刘海屏区域
来看LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES
可以看出LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES已经允许全屏app使用刘海屏了,只不过状态栏那边是白色。可以看出LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES已经允许全屏app使用刘海屏了,只不过状态栏那边是白色。
那我们要如何修复这个问题?采用沉浸式布局即可,即设置DecorView为SYSTEM_UI_FLAG_FULLSCREEN模式。
那何为沉浸式布局?这是Android 4.4 (API Level 19)引入一个新的概念,即真正的全屏模式:SystemUI(StatusBar和NavigationBar)也都被隐藏
布局的时候,你总不能在刘海屏区域内部放控件吧,所以这个时候我们就要计算状态栏高度了,在布局时候,要刻意避开这个区域
直接上代码:
//主activity
public class AndroidPDemoActivity extends Activity
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
DisplayCutoutDemo displayCutoutDemo = new DisplayCutoutDemo(this);
displayCutoutDemo.openFullScreenModel();
setContentView(R.layout.activity_android_p_demo_layout);
displayCutoutDemo.controlView();
/**
* 功能描述: 刘海屏控制
*/
public class DisplayCutoutDemo
private Activity mAc;
public DisplayCutoutDemo(Activity ac)
mAc = ac;
//在使用LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES的时候,状态栏会显示为白色,这和主内容区域颜色冲突,
//所以我们要开启沉浸式布局模式,即真正的全屏模式,以实现状态和主体内容背景一致
public void openFullScreenModel()
mAc.requestWindowFeature(Window.FEATURE_NO_TITLE);
WindowManager.LayoutParams lp = mAc.getWindow().getAttributes();
lp.layoutInDisplayCutoutMode = WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES;
mAc.getWindow().setAttributes(lp);
View decorView = mAc.getWindow().getDecorView();
int systemUiVisibility = decorView.getSystemUiVisibility();
int flags = View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
| View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_FULLSCREEN;
systemUiVisibility |= flags;
mAc.getWindow().getDecorView().setSystemUiVisibility(systemUiVisibility);
//获取状态栏高度
public int getStatusBarHeight(Context context)
int result = 0;
int resourceId = context.getResources().getIdentifier("status_bar_height","dimen", "android");
if (resourceId > 0)
result = context.getResources().getDimensionPixelSize(resourceId);
Log.d("hwj","**getStatusBarHeight**" + result);
return result;
public void controlView()
View decorView = mAc.getWindow().getDecorView();
if(decorView != null)
Log.d("hwj", "**controlView**" + android.os.Build.VERSION.SDK_INT);
Log.d("hwj", "**controlView**" + android.os.Build.VERSION_CODES.P);
WindowInsets windowInsets = decorView.getRootWindowInsets();
if(windowInsets != null)
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.P)
DisplayCutout displayCutout = windowInsets.getDisplayCutout();
//getBoundingRects返回List<Rect>,没一个list表示一个不可显示的区域,即刘海屏,可以遍历这个list中的Rect,
//即可以获得每一个刘海屏的坐标位置,当然你也可以用类似getSafeInsetBottom的api
Log.d("hwj", "**controlView**" + displayCutout.getBoundingRects());
Log.d("hwj", "**controlView**" + displayCutout.getSafeInsetBottom());
Log.d("hwj", "**controlView**" + displayCutout.getSafeInsetLeft());
Log.d("hwj", "**controlView**" + displayCutout.getSafeInsetRight());
Log.d("hwj", "**controlView**" + displayCutout.getSafeInsetTop());
<!--布局文件-->
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:background="@android:color/holo_blue_bright"
tools:context="com.hwj.android.learning.AndroidPDemoActivity">
<!--假设我们已经通过DisplayCutoutDemo.java的controlView方法提前
获得了刘海屏的坐标,则这里坐边距就可以设置了-->
<!--在你实际使用android p模拟器的时候,你会发现android.os.Build.VERSION_CODES.P的值居然等于10000
顾你是无法通过模拟器去实际使用DisplayCutoutDemo类的-->
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="800px"/>
<TextView
android:id="@+id/android_p_demo_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Hello World!"/>
</LinearLayout>
这里有一个需要关注的问题,在使用Android P模拟器的时,android.os.Build.VERSION_CODES.P的值居然等于10000,这说明在实际使用过程中你是无法通过模拟器去实际使用DisplayCutoutDemo类的,也就是无法去获取刘海屏的具体坐标
究其原因,我猜测是Android P版本还未正式发布,这只是一个debug版本,待正式发布,这个bug应该就会修复掉了。
但是只要我们掌握了适配原理,那就不用担心了
但是我们应该遵循的一个原则就是:不要在刘海屏那一栏显示内容,那一块我们称为非安全区域,尽量在安全区域去绘制UI
综述刘海屏的适配:
1)设置LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES模式
2)设置沉浸式布局模式
3)计算状态栏高度,进行布局;如果有特殊UI要求,则可以使用DisplayCutoutDemo类去获取刘海屏的坐标,完成UI
参考链接:
华为刘海屏适配官方文档 https://devcenter-test.huawei.com/consumer/cn/devservice/doc/50114
OPPO刘海屏适配官方文档 https://open.oppomobile.com/service/message/detail?id=61876
vivo刘海屏适配官方文档 https://dev.vivo.com.cn/documentCenter/doc/103
Android刘海屏适配方案 https://www.jianshu.com/p/62c6625db7ab
刘海屏适配 与WindowInsets https://blog.csdn.net/yi_master/article/details/80309757
google官方刘海屏适配方案 https://developer.android.com/about/versions/pie/android-9.0
android 沉浸式状态栏 https://blog.csdn.net/carlos1992/article/details/46773059#
小技巧:
1. //去除title
2. requestWindowFeature(Window.FEATURE_NO_TITLE);
3. //去掉Activity上面的状态栏 getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
4. //去掉虚拟按键全屏显示
5. getWindow().getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_HIDE_NAVIGATION);
在AndroidMainfest.xml中application中显式声明支持的最大屏幕高宽比(maximum aspect ratio),目前全面屏屏幕比例,将value设置为2.1(或者更大)即可适配一众全面屏手机
<meta-data
android:name="android.max_aspect"
android:value="2.1" />
函虚拟键全屏方法--在onWindowFocusChanged中调用如下函数:
/**
* 隐藏虚拟按键,并且全屏
*/
protected void hideBottomUIMenu()
//隐藏虚拟按键,并且全屏
if (Build.VERSION.SDK_INT > 11 && Build.VERSION.SDK_INT < 19) // lower api
View v = this.getWindow().getDecorView();
v.setSystemUiVisibility(View.GONE);
else if (Build.VERSION.SDK_INT >= 19)
//for new api versions.
View decorView = getWindow().getDecorView();
int uiOptions = View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY | View.SYSTEM_UI_FLAG_FULLSCREEN;
decorView.setSystemUiVisibility(uiOptions);
android屏幕适配异形屏适配②(需要异形屏适配情况|需要异形屏适配的android系统版本|刘海屏状态判定|异形屏适配调试-华为云调试)(代码片段)
...竖屏不需要适配3、正常有状态栏的界面横屏需要适配4、刘海屏状态判定二、异形屏适配调试-华为云调试屏幕适配参考文档:设备兼容性概览屏幕兼容性概览支持不同的像素密度声明受限屏幕支持异形屏适配参考文档:Google-支持刘... 查看详情
android屏幕适配异形屏适配②(需要异形屏适配情况|需要异形屏适配的android系统版本|刘海屏状态判定|异形屏适配调试-华为云调试)(代码片段)
...竖屏不需要适配3、正常有状态栏的界面横屏需要适配4、刘海屏状态判定二、异形屏适配调试-华为云调试屏幕适配参考文档:设备兼容性概览屏幕兼容性概览支持不同的像素密度声明受限屏幕支持异形屏适配参考文档:Google-支持刘... 查看详情
app适配安卓手机刘海屏(代码片段)
如果你想允许全屏界面内容显示到刘海区域,只要在AndroidManifest.xml文件里配置如下代码即可:<!--允许绘制到oppo、vivo刘海屏机型的刘海区域--><meta-dataandroid:name="android.max_aspect"android:value="2.2"/><!--适配华为(huawei)刘海... 查看详情
刘海屏时代来临,主流应用适配情况大调查
...商相继发布了16款带有“刘海“设计的手机,AndroidP也已全面支持刘海屏机型。为了保障用户能够在此类机型上有完美的使用体验,华为终端开放实验室选取国内TOP400主流应用,对“刘海屏”适配情况进行测试,速来围观吧!一... 查看详情
android全面屏处理(适配挖孔屏刘海屏)kotlin(代码片段)
测试机:Android11的XiaomiMIMAX3Android12的XiaomiK40Pro测试方法:1.该方法在api30后提示已经过时在onCreat()方法中,setContentView()前使用。window.setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,WindowManager.LayoutParams.FLAG_FULLSCREEN)测试结果... 查看详情
android屏幕适配异形屏适配①(异形屏类型:刘海屏水滴屏挖孔屏|沉浸式布局刘海屏适配|华为手机异形屏适配注意点)
文章目录一、异形屏类型:刘海屏、水滴屏、挖孔屏二、沉浸式布局刘海屏适配三、华为手机异形屏适配注意点屏幕适配参考文档:设备兼容性概览屏幕兼容性概览支持不同的像素密度声明受限屏幕支持异形屏适配参考文档:Google-... 查看详情
android屏幕适配异形屏适配①(异形屏类型:刘海屏水滴屏挖孔屏|沉浸式布局刘海屏适配|华为手机异形屏适配注意点)
文章目录一、异形屏类型:刘海屏、水滴屏、挖孔屏二、沉浸式布局刘海屏适配三、华为手机异形屏适配注意点屏幕适配参考文档:设备兼容性概览屏幕兼容性概览支持不同的像素密度声明受限屏幕支持异形屏适配参考文档:Google-... 查看详情
android刘海屏适配
参考技术A刘海屏幕的适配,在全面屏设置下,顶部有刘海的区域,有的会导致刘海把标题栏等内容遮盖如下图,这是美团的统一版本在小米和华为上的适配,可以看到小米的未遮挡内容,但在华为设备上,明显刘海遮住了一部... 查看详情
android适配刘海屏+沉浸式状态栏+启动页白屏解决方案(代码片段)
一、刘海屏适配可参考对应手机官方文档小米:dev.mi.com/console/doc/detail?pld=1160oppo、vivo:open.oppomobile.com/wiki/doc#id=10159在Manifest.xmlz中配置-application中插入<!--OPPO--><meta-dataandroid:na 查看详情
unity安卓适配刘海屏,水滴屏,异性屏(代码片段)
手机厂商一群弄潮儿,每次都能玩出新花样,各种奇形怪状的手机屏幕,为了增加玩家的沉浸感,我们开发游戏的话必须对异性屏幕进行适配。一般安卓方法适配其实网上有很多方案了,主流的一套还是谷歌官方的... 查看详情
和平精英刘海屏挡住了怎么办
...适配,也可以手动拖动调整到最完美的显示效果。如果是全面屏的话,直接拖动到0,然后就可以看到按钮都会没有空隙,观感比较舒适。如果是刘海屏的话,就选择50,这样设置可以让左右屏幕按钮显示距离顶部空出一块,不会... 查看详情
android挖孔屏适配(代码片段)
刘海屏刚出来那会儿,怎么看怎么丑,后面又是水滴屏,稍微有点顺眼,再就是挖孔屏,都是啥玩意。现在再看,刘海似乎也没那么丑了,居然还觉得挖孔的有点惊艳!需求前段时间在做挖孔屏适... 查看详情
屏相关知识介绍和屏幕适配(代码片段)
...loat=18/9=2;2960*1440(三星s8,s9)ratio_float=18.5/9=2.056;所谓全面屏的比例有如下:17:919:1018:918.5:9原来一般主流手机1920*1080分辨率16:9高宽比。如果没有单独去配置属性,会导致在超过17:9宽高比手机上,底部一大块黑底。&nb... 查看详情
android关于google刘海屏的解决方案(代码片段)
...文出自:【奥特曼超人的博客】推荐:android兼容所有刘海屏的方案大全android兼容huawei手机刘海屏解决方案android兼容vivo手机刘海屏解决方案android兼容oppo手机刘海屏解决方案android兼容小米xiaomi刘海 查看详情
html5移动端页面适配ios系统刘海屏(代码片段)
...8;安全区域)”,安全区域指屏幕内不受圆角、齐刘海、底部小黑条等元素影响的可视窗口。如下图:从iOS11开始,为了适配刘海屏,Apple公司对HTML的viewportmeta标签做了扩展<metaname= 查看详情
vuereact移动端适配viewpoint@mediaiphonex刘海屏适配
...个就是需要根据分辨率不同自适应页面大小第二个是对于刘海屏的特殊处理所以我们需要使用2套方案来完成移动端的适配网上有大量的文章来讲分辨率自适应方案,比如rem计算font-size字体大小来作为单位进行像素的换算,比如... 查看详情
android兼容huawei手机刘海屏解决方案(代码片段)
...文出自:【奥特曼超人的博客】推荐:android兼容所有刘海屏的方案大全android兼容huawei手机刘海屏解决方案andro 查看详情
苹果发布刘海屏macbookpro
MacBookPro的外观设计一如之前爆料的那样,升级全面屏,边框非常窄,顶部则是iPhone那样的刘海,集成了1080p前置摄像头。MacBookPro新品活动688红包等你抢机会不容错过http://iphone.adiannao.cn/7尺寸方面,新MacBookPro的... 查看详情