http://www.jcodecraeer.com/a/anzhuokaifa/androidkaifa/2014/0731/1640.html

本篇博客是http://www.cnblogs.com/longjunhao/p/8973729.html的后续

问题:上篇博客中,如果在onCreate中就需要获取statusbar的高度,当kill进程之后再次进入oncreate时,由于新增的statusBarHelperView还没有绘制完成导致statusbar获取失败。

解决方案:

方案1:在onCreate中调用statusbar时,做个延迟操作。但是这种方案不太好,毕竟是如果手机比较卡的时候可能也会失败

方案2:给statusHelperView增加绘制完的监听:mStatusBarHelperView.getViewTreeObserver().addOnGlobalLayoutListener(mGlobalLayoutListener);当绘制完成后会调用该监听中的onGlobalLayout方法,然后再通过回调,当执行onGlobalLayout时再获取statusbar的高度,在上面博客中的工具类中新增如下方法:

package com.smartisanos.ime.util;

import android.content.Context;
import android.graphics.PixelFormat;
import android.os.Handler;
import android.os.Message;
import android.view.Gravity;
import android.view.View;
import android.view.ViewTreeObserver;
import android.view.WindowManager; import com.smartisanos.ime.IMEApp; public class StatusBarHelper {
private Context mContext;
private View mStatusBarHelperView;
private static StatusBarHelper mStatusBarHelper = new StatusBarHelper();
private static final int MSG_INIT_STATUS_BAR = 1;
private static final int MSG_REMOVE_STATUS_BAR = 2;
private static final long MSG_REMOVE_DELAY_TIME = 500L; private StatusBarHelperViewLayoutListener mStatusBarHelperViewLayoutListener; private Handler mStatusBarHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case MSG_INIT_STATUS_BAR:
mStatusBarHandler.removeMessages(MSG_REMOVE_STATUS_BAR);
initStatusBarHelperView();
break;
case MSG_REMOVE_STATUS_BAR:
removeStatusBarView();
break;
}
}
}; private StatusBarHelper() {
mContext = IMEApp.getContext();
} public static StatusBarHelper getInstance() {
return mStatusBarHelper;
} private void initStatusBarHelperView() {
if (mStatusBarHelperView != null) {
return;
}
WindowManager wm = (WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE);
mStatusBarHelperView = new View(mContext);
WindowManager.LayoutParams lp = new WindowManager.LayoutParams();
lp.flags = WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL
| WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE;
lp.gravity = Gravity.LEFT | Gravity.TOP;
lp.type = WindowManager.LayoutParams.TYPE_SYSTEM_OVERLAY;
lp.format = PixelFormat.TRANSLUCENT;
mStatusBarHelperView.getViewTreeObserver().addOnGlobalLayoutListener(mGlobalLayoutListener);
wm.addView(mStatusBarHelperView, lp);
} public void addStatusBarHelperView() {
Message message = mStatusBarHandler.obtainMessage(StatusBarHelper.MSG_INIT_STATUS_BAR);
mStatusBarHandler.sendMessage(message);
} public void removeStatusBarHelperView() {
Message message = mStatusBarHandler.obtainMessage(StatusBarHelper.MSG_REMOVE_STATUS_BAR);
mStatusBarHandler.sendMessageDelayed(message, StatusBarHelper.MSG_REMOVE_DELAY_TIME);
} public int getStatusBarHeight() {
if (mStatusBarHelperView == null) {
return 0;
}
int[] windowParams = new int[2];
int[] screenParams = new int[2];
mStatusBarHelperView.getLocationInWindow(windowParams);
mStatusBarHelperView.getLocationOnScreen(screenParams);
return screenParams[1] - windowParams[1];
} private void removeStatusBarView() {
if (mStatusBarHelperView != null) {
mStatusBarHelperView.getViewTreeObserver().removeOnGlobalLayoutListener(mGlobalLayoutListener);
WindowManager wm = (WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE);
wm.removeView(mStatusBarHelperView);
mStatusBarHelperView = null;
}
} private ViewTreeObserver.OnGlobalLayoutListener mGlobalLayoutListener = new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
if (mStatusBarHelperViewLayoutListener != null) {
mStatusBarHelperViewLayoutListener.updateStatusBarHeightWhenGlobalLayout();
}
}
}; public interface StatusBarHelperViewLayoutListener {
void updateStatusBarHeightWhenGlobalLayout();
} public void setStatusBarHelperViewLayoutListener(StatusBarHelperViewLayoutListener listener) {
mStatusBarHelperViewLayoutListener = listener;
} public void onConfigurationChanged() {//此处和本博客无关
removeStatusBarView();
initStatusBarHelperView();
}
}

这样在onCreate中调用的时候,只需要回调方法即可:

        StatusBarHelper.getInstance().setStatusBarHelperViewLayoutListener(new StatusBarHelper.StatusBarHelperViewLayoutListener() {
@Override
public void updateStatusBarHeightWhenGlobalLayout() {
if (mStatusBarHeight != IMEContext.config().getStatusBarHeight() && isShowing()) {
mStatusBarHeight = IMEContext.config().getStatusBarHeight();
//当helpeView绘制完成之后,判断mStatusBarHeight(此全局变量是onCreate中获取的)和新的不相等后,执行相应的操作(eg:update操作)
}
}
});

判断状态栏是否显示以及获取状态栏高度的方法,及工具类列子【续:及OnGlobalLayoutListener的利用】的更多相关文章

  1. JS获取div高度的方法

    有时在写页面时,需要获取一个div的高度.怎么才能获取呢?哈哈,先上结论.有两种方法. offsetHeight .clientHeight getComputedStyle offsetHeight ...

  2. 在spring中获取代理对象代理的目标对象工具类

    昨天晚上一哥们需要获取代理对象的目标对象,查找了文档发现没有相应的工具类,因此自己写了一个分享给大家.能获取JDK动态代理/CGLIB代理对象代理的目标对象. 问题描述:: 我现在遇到个棘手的问题,要 ...

  3. 可以获取JVM信息的一些管理工具类

    一些可以获取JVM信息的java工具类 BufferPoolMXBean.class ClassLoadingMXBean.class CompilationMXBean.class GarbageC ...

  4. 获取JVM转储文件的Java工具类

    在上期文章如何获取JVM堆转储文件中,介绍了几种方法获取JVM的转储文件,其中编程方法是里面唯一一个从JVM内部获取的方法.这里就不演示了其他方法获取正在运行的应用程序的堆转储,重点放在了使用编程来获 ...

  5. js中获取窗口高度的方法

    取窗口滚动条滚动高度 function getScrollTop() { var scrollTop=0; if(document.documentElement&&document. ...

  6. ios5 中文键盘高度变高覆盖现有ui问题的解决方案(获取键盘高度的方法)(转载)

    背景: ios5之前,iphone上的键盘的高度是固定为216.0px高的,中文汉字的选择框是悬浮的,所以不少应用都将此高度来标注键盘的高度(包括米聊也是这么做的). 可是在ios5中,键盘布局变了, ...

  7. 获取当前应用的系统路径工具类和java的System.getProperty()方法介绍

    java的System.getProperty()方法可以获取的值,如下: 对于Java程序,无论是未打包的还是打包的JAR或WAR文件,有时候都需要获取它运行所在目录信息,如何做到这一点呢? /** ...

  8. 数据库表中MAX ID获取,确保每次调用没有重复工具类(NumberUtil)

    下面这个类是获取数据库中一个字段的最大值.配置在数据库中. public class NoFactory { private final static Logger cLogger = Logger. ...

  9. java根据身份证号和获取用户年龄和性别的工具类

    import java.text.SimpleDateFormat; import java.util.Date; import java.util.HashMap; import java.util ...

随机推荐

  1. 解决CentOS下service 功能 不能使用 bash: service: command not found

    首先检查自己是否 使用的是root用户 在centos系统中,如果/sbin目录下没有service这个命令,就会出现 bash: service: command not found 解决步骤如下: ...

  2. Redis 底层数据结构之跳跃表

    文章参考 <Redis 设计与实现>黄建宏 Redis(2) 跳跃表 跳跃表 跳跃表 skiplist 是一种有序数据结构,它通过在每个节点中维持多个指向其他节点的指针,从而达到快速访问节 ...

  3. Flask(1)- 简介

    背景 为啥要学,很久之前就学过点,没写文章 最近因为要写机器人工具,其实就是简单的纯服务端工具 反正 flask 也挺简单,一天快速过完 概念会直接搬教程的,实操自己敲一遍再总结 参考教程 https ...

  4. webpack(6)webpack处理图片

    图片处理url-loader(webpack5之前的处理方式) 在项目开发中,我们时长会需要使用到图片,比如在img文件夹中有图片test1.png,然后在normal.css中会引用到图片 body ...

  5. robotframework安装robotframework-requests库遇到的几种问题

    robotframework-requests库依赖于requests库,所以如果安装robotframework-requests库后,在RF中的RequestsLibrary不能使用或者使用pyt ...

  6. shell运维习题训练

    注:初学shell,以下为本人自己写的答案,如果有更好的,请指教! 1. 求2个数之和: 2. 计算1-100的和 3. 将一目录下所有的文件的扩展名改为bak 4.编译并执行当前目录下的所有.c文件 ...

  7. linux学习之路第九天(磁盘分区,挂载详解)

    磁盘分区,挂载 -----分区基础知识 分区的方式 1)mbr分区: 1.最多支持四个主分区 2.系统只能安装在主分区 3.扩展分区要占一个主分区 4.mbr最大只支持2TB,但拥有最好的兼容性 -- ...

  8. Acunetix临时扫描是不够的

    Web漏洞扫描程序通常被视为即席工具.最初,所有漏洞扫描程序都是这种工具,并且当前的开源Web应用程序安全解决方案仍遵循该模型.但是,随着Web技术的复杂性和可用性的大幅增加,临时模型已经过时,无法满 ...

  9. Spring Boot 2.x基础教程:使用@Scheduled实现定时任务

    我们在编写Spring Boot应用中经常会遇到这样的场景,比如:我需要定时地发送一些短信.邮件之类的操作,也可能会定时地检查和监控一些标志.参数等. 创建定时任务 在Spring Boot中编写定时 ...

  10. mongodb,redis,mysql的区别和具体应用场景(转)

    一.MySQL 关系型数据库. 在不同的引擎上有不同 的存储方式. 查询语句是使用传统的sql语句,拥有较为成熟的体系,成熟度很高. 开源数据库的份额在不断增加,mysql的份额页在持续增长. 缺点就 ...