WindowManager的使用

发布于:2024-08-24 ⋅ 阅读:(138) ⋅ 点赞:(0)

WindowManager简介

WindowManager是Android系统中的一个核心类,它负责管理窗口的创建、显示、位置和大小等。WindowManager通常用于创建浮动窗口、自定义窗口布局或管理系统的顶级窗口。

WindowManager的作用

  1. 创建窗口:可以在屏幕上创建额外的窗口,这些窗口可以是浮动的、半透明的或具有特定的尺寸和位置。
  2. 管理窗口布局:可以更改窗口的位置、大小和布局属性。
  3. 管理屏幕方向:可以获取屏幕的方向信息,并据此调整窗口的布局。
  4. 处理输入事件:可以处理窗口接收到的触摸和其他输入事件。

使用场景

  1. 浮动窗口:例如,实现悬浮球、悬浮菜单等功能。
  2. 自定义布局:例如,创建自定义的登录界面或对话框。
  3. 屏幕截图:例如,截取屏幕的一部分。
  4. 屏幕方向管理:例如,根据屏幕方向调整布局。

使用WindowManager创建一个浮动窗口

import android.app.Activity;
import android.content.Context;
import android.graphics.PixelFormat;
import android.view.Gravity;
import android.view.MotionEvent;
import android.view.View;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.LinearLayout;

public class FloatingWindowActivity extends Activity {

    private WindowManager windowManager;
    private View floatingView;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        // 获取WindowManager服务
        windowManager = (WindowManager) getSystemService(Context.WINDOW_SERVICE);

        // 创建浮动窗口的布局
        LinearLayout layout = new LinearLayout(this);
        layout.setLayoutParams(new LinearLayout.LayoutParams(
                LinearLayout.LayoutParams.WRAP_CONTENT,
                LinearLayout.LayoutParams.WRAP_CONTENT));
        layout.setOrientation(LinearLayout.VERTICAL);
        layout.setBackgroundColor(0x80FFFFFF); // 设置背景颜色

        // 创建一个按钮
        Button button = new Button(this);
        button.setText("Click me!");
        layout.addView(button);

        // 设置浮动窗口的参数
        WindowManager.LayoutParams params = new WindowManager.LayoutParams(
                WindowManager.LayoutParams.WRAP_CONTENT,
                WindowManager.LayoutParams.WRAP_CONTENT,
                WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY,
                WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
                PixelFormat.TRANSLUCENT);

        // 设置初始位置
        params.gravity = Gravity.CENTER;
        params.x = 0;
        params.y = 0;

        // 添加浮动窗口
        floatingView = layout;
        windowManager.addView(floatingView, params);

        // 处理点击事件
        button.setOnClickListener(v -> {
            // 移动窗口
            params.x += 100;
            params.y += 100;
            windowManager.updateViewLayout(floatingView, params);
        });

        // 处理触摸事件
        floatingView.setOnTouchListener((v, event) -> {
            switch (event.getAction()) {
                case MotionEvent.ACTION_DOWN:
                    // 获取手指按下时的位置
                    params.x = (int) event.getRawX();
                    params.y = (int) event.getRawY();
                    break;
                case MotionEvent.ACTION_MOVE:
                    // 更新位置
                    params.x = (int) event.getRawX() - (int) event.getX();
                    params.y = (int) event.getRawY() - (int) event.getY();
                    windowManager.updateViewLayout(floatingView, params);
                    break;
            }
            return true;
        });
    }
}
  1. 获取WindowManager服务

    • 使用getSystemService(Context.WINDOW_SERVICE)获取WindowManager服务。
  2. 创建浮动窗口的布局

    • 创建一个LinearLayout作为浮动窗口的布局,并添加一个Button
    • 设置背景颜色和布局参数。
  3. 设置窗口参数

    • 创建一个WindowManager.LayoutParams对象,并设置窗口的类型、标志、格式等。
    • 设置初始位置为屏幕中心。
  4. 添加窗口

    • 使用windowManager.addView()将浮动窗口添加到屏幕上。
  5. 处理点击事件

    • Button设置点击监听器,点击时移动窗口的位置。
  6. 处理触摸事件

    • 为浮动窗口设置触摸监听器,实现窗口的拖动。

使用WindowManager实现屏幕方向管理

在Android中,WindowManager主要用于管理窗口的创建和布局,但它并不直接负责屏幕方向的管理。屏幕方向通常是通过ActivityFragment的配置来自动处理的。然而,如果你想在WindowManager创建的自定义窗口中根据屏幕方向调整布局,可以通过以下步骤实现:

  1. 获取屏幕方向:使用Display类来获取当前屏幕的方向。
  2. 根据方向调整布局:根据获取的方向动态调整窗口的布局参数。

使用WindowManager根据屏幕方向调整窗口的位置

import android.app.Activity;
import android.content.Context;
import android.graphics.Point;
import android.os.Bundle;
import android.util.DisplayMetrics;
import android.view.Display;
import android.view.Gravity;
import android.view.View;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.LinearLayout;

public class ScreenOrientationActivity extends Activity {

    private WindowManager windowManager;
    private View floatingView;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        // 获取WindowManager服务
        windowManager = (WindowManager) getSystemService(Context.WINDOW_SERVICE);

        // 创建浮动窗口的布局
        LinearLayout layout = new LinearLayout(this);
        layout.setLayoutParams(new LinearLayout.LayoutParams(
                LinearLayout.LayoutParams.WRAP_CONTENT,
                LinearLayout.LayoutParams.WRAP_CONTENT));
        layout.setOrientation(LinearLayout.VERTICAL);
        layout.setBackgroundColor(0x80FFFFFF); // 设置背景颜色

        // 创建一个按钮
        Button button = new Button(this);
        button.setText("Click me!");
        layout.addView(button);

        // 获取屏幕尺寸
        Display display = windowManager.getDefaultDisplay();
        Point size = new Point();
        display.getSize(size);
        int screenWidth = size.x;
        int screenHeight = size.y;

        // 获取屏幕方向
        int orientation = getResources().getConfiguration().orientation;

        // 根据屏幕方向设置窗口参数
        WindowManager.LayoutParams params = new WindowManager.LayoutParams(
                WindowManager.LayoutParams.WRAP_CONTENT,
                WindowManager.LayoutParams.WRAP_CONTENT,
                WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY,
                WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
                PixelFormat.TRANSLUCENT);

        // 设置初始位置
        if (orientation == Configuration.ORIENTATION_LANDSCAPE) {
            // 横屏
            params.gravity = Gravity.CENTER;
            params.x = 0;
            params.y = 0;
        } else {
            // 竖屏
            params.gravity = Gravity.TOP | Gravity.CENTER_HORIZONTAL;
            params.x = 0;
            params.y = 0;
        }

        // 添加浮动窗口
        floatingView = layout;
        windowManager.addView(floatingView, params);

        // 处理点击事件
        button.setOnClickListener(v -> {
            // 移动窗口
            params.x += 100;
            params.y += 100;
            windowManager.updateViewLayout(floatingView, params);
        });

        // 监听屏幕方向变化
        DisplayMetrics metrics = new DisplayMetrics();
        display.getMetrics(metrics);
        display.addCallback(new Display.OnDisplayChangeListener() {
            @Override
            public void onDisplayChanged(Display display) {
                int newOrientation = getResources().getConfiguration().orientation;
                if (newOrientation != orientation) {
                    orientation = newOrientation;
                    // 根据新的屏幕方向调整窗口位置
                    if (orientation == Configuration.ORIENTATION_LANDSCAPE) {
                        // 横屏
                        params.gravity = Gravity.CENTER;
                        params.x = 0;
                        params.y = 0;
                    } else {
                        // 竖屏
                        params.gravity = Gravity.TOP | Gravity.CENTER_HORIZONTAL;
                        params.x = 0;
                        params.y = 0;
                    }
                    windowManager.updateViewLayout(floatingView, params);
                }
            }
        });
    }
}
  1. 获取屏幕尺寸

    • 使用Display.getSize(Point)方法获取屏幕的宽度和高度。
  2. 获取屏幕方向

    • 使用getResources().getConfiguration().orientation获取当前屏幕的方向。
  3. 设置窗口参数

    • 根据屏幕方向设置窗口的初始位置。
    • 对于横屏模式,将窗口居中显示。
    • 对于竖屏模式,将窗口放置在顶部中央。
  4. 监听屏幕方向变化

    • 使用Display.addCallback()方法注册一个监听器,当屏幕方向改变时更新窗口的位置。
  5. 处理点击事件

    • Button设置点击监听器,点击时移动窗口的位置。

网站公告

今日签到

点亮在社区的每一天
去签到