欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

详解android6.0版本下悬浮窗实现

程序员文章站 2023-10-23 14:47:47
悬浮窗在安卓中实现起来还是比较容易的,这几天在网上温习了相关资料,运行在我安卓6.0手机上才发现,原来在6.0手机上不是行的。 第一反应肯定是权限相关问题,做了相关处...

悬浮窗在安卓中实现起来还是比较容易的,这几天在网上温习了相关资料,运行在我安卓6.0手机上才发现,原来在6.0手机上不是行的。

第一反应肯定是权限相关问题,做了相关处理后,果然让悬浮窗原形毕露了。直接贴代码。

public class mainactivity extends appcompatactivity {
  private static final int alert_window_permission_code = 100;
  private button start_float;

  @override
  protected void oncreate(bundle savedinstancestate) {
    super.oncreate(savedinstancestate);
    setcontentview(r.layout.activity_main);
    start_float = (button) findviewbyid(r.id.start_float);
    this.start_float.setonclicklistener(new view.onclicklistener() {
      @override
      public void onclick(view view) {
        if (build.version.sdk_int > 22) {
          sdk23permission();
        } else {
          startservice(new intent(mainactivity.this, floatservice.class));
          finish();
        }
      }
    });
  }

  /**
   * @description 安卓6.0下权限处理
   * @author ldm
   * @time 2017/3/20 15:00
   */
  public void sdk23permission() {
    if (!settings.candrawoverlays(this)) {
      toast.maketext(mainactivity.this, "当前无权限使用悬浮窗,请授权!", toast.length_short).show();
      intent intent = new intent(settings.action_manage_overlay_permission,
          uri.parse("package:" + getpackagename()));
      startactivityforresult(intent, alert_window_permission_code);
    } else {
      startservice(new intent(mainactivity.this, floatservice.class));
      finish();
    }
  }

  /**
   * 用户返回
   */
  protected void onactivityresult(int requestcode, int resultcode, intent data) {
    if (requestcode == alert_window_permission_code) {
      if (!settings.candrawoverlays(this)) {
        toast.maketext(mainactivity.this, "权限授予失败,无法开启悬浮窗", toast.length_short).show();
      } else {
        startservice(new intent(mainactivity.this, floatservice.class));
        finish();
      }

    }
  }
}

对应service:

public class floatservice extends service {
  @nullable
  @override
  public ibinder onbind(intent intent) {
    return null;
  }

  @override
  public void oncreate() {
    floatviewutils.getinstance(this).addfloatview();
    super.oncreate();
  }
}

简单地floatview:

public class floatview extends view {
  public static final int width = 150;
  public static final int height = 150;
  private paint circlepaint;
  private paint textpaint;
  private static final string text = "50%";

  public floatview(context context) {
    this(context, null, 0);
  }

  public floatview(context context, @nullable attributeset attrs) {
    this(context, attrs, 0);
  }

  public floatview(context context, @nullable attributeset attrs, int defstyleattr) {
    super(context, attrs, defstyleattr);
    initpaints();
  }

  /**
   * @description 初始化相关画笔paint
   * @author ldm
   * @time 2017/3/20
   */
  private void initpaints() {
    circlepaint = new paint();
    circlepaint.setantialias(true);
    circlepaint.setcolor(color.gray);
    textpaint = new paint();
    //设置抗锯齿
    textpaint.setantialias(true);
    //设置字体大小
    textpaint.settextsize(30);
    //设置颜色
    textpaint.setcolor(color.white);
    //设置(仿)粗体
    textpaint.setfakeboldtext(true);
  }

  @override
  protected void onmeasure(int widthmeasurespec, int heightmeasurespec) {
    setmeasureddimension(width, height);
  }

  @override
  protected void ondraw(canvas canvas) {
    super.ondraw(canvas);
    canvas.drawcircle(width / 2, height / 2, width / 2, circlepaint);
    float textwidth = textpaint.measuretext(text);
    float x = width / 2 - textwidth / 2;
    paint.fontmetrics fms = textpaint.getfontmetrics();
    float dy = -(fms.descent + fms.ascent) / 2;
    float y = height / 2 + dy;
    canvas.drawtext(text, x, y, textpaint);
  }
}

以及floatview管理工具类:

public class floatviewutils {
  private static floatviewutils instance;
  private context mcontext;
  private windowmanager manager;
  private floatview floatview;

  private floatviewutils(context mcontext) {
    this.mcontext = mcontext;
    manager = (windowmanager) mcontext.getsystemservice(context.window_service);
    floatview = new floatview(mcontext);
  }

  public static floatviewutils getinstance(context mcontext) {
    if (null == instance) {
      synchronized (floatviewutils.class) {
        if (null == instance) {
          instance = new floatviewutils(mcontext);
        }
      }
    }
    return instance;
  }

  public void addfloatview() {
    windowmanager.layoutparams lp = new windowmanager.layoutparams();
    //悬浮窗口大小
    lp.width = floatview.width;
    lp.height = floatview.height;
    // 调整悬浮窗口位置
    lp.gravity = gravity.left | gravity.center;
    // 以屏幕左上角为原点,设置x、y初始值
//    lp.x = 0;
//    lp.y = 0;
    //设置悬浮窗口类型
    lp.type = windowmanager.layoutparams.type_phone;
    //设置悬浮窗口不接受焦点及触摸事件
    lp.flags = windowmanager.layoutparams.flag_not_focusable | windowmanager.layoutparams.flag_not_touchable;
    //设置图片格式,效果为背景透明
    lp.format = pixelformat.rgba_8888;
    manager.addview(floatview, lp);
  }
}

最后不要忘记在androidmanifest.xml中添加权限(当然还有注册service):

复制代码 代码如下:

<uses-permission android:name="android.permission.system_alert_window"/>

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。