1.发现官方Demo也出现了这个问题
先说解决办法:目前最好的方案就是交给原生侧处理,也有一种处理方式是退出flutterpage,重置承载的原生页面,但是这样再性能低的手机上会重复调用引擎,而且在原生给flutter传初始值的时候也会不断调用原生获取初始值,
在FlutterBoostFragment#onResume方法中,调用了platformPlugin.updateSystemUiOverlays()方法导致状态栏显示异常。
//继承 FlutterBoostActivity
abstract class SFBaseActivity extends FlutterBoostActivity
// 重写方法
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
@Override
public void onPostResume() {
super.onPostResume();
// getWindow().setStatusBarColor(0); // 这种方法解决不了这个问题,亲测
StatusBarUtil.setStatusBarTranslucent(this, true);
}
}
StatusBarUtil.setStatusBarTranslucent(this, true); 方法
// 设置状态栏颜色与字体颜色
public static void setStatusBarTranslucent(Activity acitivty, boolean isLightStatusBar) {
Window window = acitivty.getWindow();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT && Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
window.addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
} else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
window.clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
if (isLightStatusBar){
window.getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
| View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR);
}else {
window.getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
| View.SYSTEM_UI_FLAG_LAYOUT_STABLE);
}
window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
window.setStatusBarColor(Color.TRANSPARENT);
}
if (isXiaomi()) {
setXiaomiStatusBar(window, isLightStatusBar);
} else if (isMeizu()) {
setMeizuStatusBar(window, isLightStatusBar);
}
}
// 是否是小米手机
public static boolean isXiaomi() {
return "Xiaomi".equals(Build.MANUFACTURER);
}
// 设置小米状态栏
public static void setXiaomiStatusBar(Window window, boolean isLightStatusBar) {
Class<? extends Window> clazz = window.getClass();
try {
Class<?> layoutParams = Class.forName("android.view.MiuiWindowManager$LayoutParams");
Field field = layoutParams.getField("EXTRA_FLAG_STATUS_BAR_DARK_MODE");
int darkModeFlag = field.getInt(layoutParams);
Method extraFlagField = clazz.getMethod("setExtraFlags", int.class, int.class);
extraFlagField.invoke(window, isLightStatusBar ? darkModeFlag : 0, darkModeFlag);
} catch (Exception e) {
e.printStackTrace();
}
}
// 是否是魅族手机
public static boolean isMeizu() {
try {
Method method = Build.class.getMethod("hasSmartBar");
return method != null;
} catch (NoSuchMethodException e) {
}
return false;
}
// 设置魅族状态栏
public static void setMeizuStatusBar(Window window, boolean isLightStatusBar) {
WindowManager.LayoutParams params = window.getAttributes();
try {
Field darkFlag = WindowManager.LayoutParams.class.getDeclaredField("MEIZU_FLAG_DARK_STATUS_BAR_ICON");
Field meizuFlags = WindowManager.LayoutParams.class.getDeclaredField("meizuFlags");
darkFlag.setAccessible(true);
meizuFlags.setAccessible(true);
int bit = darkFlag.getInt(null);
int value = meizuFlags.getInt(params);
if (isLightStatusBar) {
value |= bit;
} else {
value &= ~bit;
}
meizuFlags.setInt(params, value);
window.setAttributes(params);
darkFlag.setAccessible(false);
meizuFlags.setAccessible(false);
} catch (Exception e) {
e.printStackTrace();
}
}
原因我认为就是 引擎的缓存,但是flutter的main方法进入会重复渲染造成的
在第二次进入到flutter页面后,由于前一次进入时已经设置过状态栏颜色,即 _latestStyle 并不为空,所以 第二次进入页面时,renderView 在_updateSystemChrome 时并不会真正调用到原生去设置状态栏。
在FlutterBoostFragment#onResume方法中,调用了platformPlugin.updateSystemUiOverlays()方法导致状态栏显示异常。
网友评论