学习Android的第二十一天

目录

[Android ProgressDialog (进度条对话框)](#Android ProgressDialog (进度条对话框))

例子

[Android DatePickerDialog 日期选择对话框](#Android DatePickerDialog 日期选择对话框)

例子

[Android TimePickerDialog 时间选择对话框](#Android TimePickerDialog 时间选择对话框)

[Android PopupWindow 悬浮框](#Android PopupWindow 悬浮框)

构造函数

方法

例子

官方文档

[Android OptionMenu 选项菜单](#Android OptionMenu 选项菜单)

例子

官方文档


Android ProgressDialog (进度条对话框)

Android ProgressDialog 已经在 API 26+ 中被废弃,ProgressDialog 不能直接从 XML 里创建。

例子

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools"
    android:orientation="vertical"
    android:gravity="center"
    tools:context=".MainActivity">
    <Button
        android:id="@+id/btn_show_normal_progress_dialog"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="显示普通ProgressDialog" />

    <Button
        android:id="@+id/btn_show_indeterminate_progress_dialog"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="显示不确定结束的ProgressDialog" />

    <Button
        android:id="@+id/btn_show_determinate_progress_dialog"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="显示确定结束的ProgressDialog" />

</LinearLayout>
java 复制代码
package com.example.myapplication;

import android.app.ProgressDialog;
import android.os.Bundle;
import android.os.Handler;
import android.view.View;
import android.widget.Button;

import androidx.appcompat.app.AppCompatActivity;

public class MainActivity extends AppCompatActivity {

    private ProgressDialog progressDialog;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Button btnShowNormal = findViewById(R.id.btn_show_normal_progress_dialog);
        Button btnShowIndeterminate = findViewById(R.id.btn_show_indeterminate_progress_dialog);
        Button btnShowDeterminate = findViewById(R.id.btn_show_determinate_progress_dialog);

        btnShowNormal.setOnClickListener(v -> {
            showProgressDialog(ProgressDialog.STYLE_SPINNER); // 普通ProgressDialog
        });

        btnShowIndeterminate.setOnClickListener(v -> {
            showProgressDialog(ProgressDialog.STYLE_HORIZONTAL); // 不确定结束的ProgressDialog
        });

        btnShowDeterminate.setOnClickListener(v -> {
            showDeterminateProgressDialog(); // 确定结束的ProgressDialog
        });
    }

    private void showProgressDialog(int style) {
        progressDialog = new ProgressDialog(MainActivity.this);
        progressDialog.setTitle("软件更新中");
        progressDialog.setMessage("软件正在更新中,请稍后...");
        progressDialog.setProgressStyle(style);
        progressDialog.setCancelable(false); // 防止用户取消
        progressDialog.show();

        // 模拟操作
        new Handler().postDelayed(() -> {
            progressDialog.dismiss();
        }, 3000); // 模拟3秒后关闭对话框
    }

    private void showDeterminateProgressDialog() {
        progressDialog = new ProgressDialog(MainActivity.this);
        progressDialog.setTitle("软件更新中");
        progressDialog.setMessage("软件正在更新中,请稍后...");
        progressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
        progressDialog.setMax(100); // 设置最大值
        progressDialog.setCancelable(false);
        progressDialog.show();

        // 模拟下载进度更新
        new Thread(() -> {
            int progress = 0;
            while (progress <= 100) {
                progressDialog.setProgress(progress);
                progress += 10;
                try {
                    Thread.sleep(500); // 模拟下载延迟
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
            progressDialog.dismiss();
        }).start();
    }
}

Android DatePickerDialog 日期选择对话框

当用户点击一个按钮,弹出日期选择对话框是一个常见的需求。

例子

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools"
    android:orientation="vertical"
    android:gravity="center"
    tools:context=".MainActivity">
    <Button
        android:id="@+id/btn_pick_date"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="选择日期"/>

</LinearLayout>
java 复制代码
package com.example.myapplication;

import android.app.DatePickerDialog;
import android.os.Bundle;
import android.widget.Button;

import androidx.appcompat.app.AppCompatActivity;

import java.util.Calendar;

public class MainActivity extends AppCompatActivity {

    private Button btnPickDate;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        btnPickDate = findViewById(R.id.btn_pick_date);

        btnPickDate.setOnClickListener(v -> showDatePickerDialog());
    }

    private void showDatePickerDialog() {
        // 获取当前日期
        Calendar calendar = Calendar.getInstance();
        int year = calendar.get(Calendar.YEAR);
        int month = calendar.get(Calendar.MONTH);
        int day = calendar.get(Calendar.DAY_OF_MONTH);

        // 创建并显示日期选择对话框
        DatePickerDialog datePickerDialog = new DatePickerDialog(this, (view, selectedYear, selectedMonth, selectedDay) -> {
            // 处理选择的日期
            String selectedDate = selectedYear + "-" + (selectedMonth + 1) + "-" + selectedDay;
            btnPickDate.setText(selectedDate); // 在按钮上显示选择的日期
        }, year, month, day);
        datePickerDialog.show();
    }
}

Android TimePickerDialog 时间选择对话框

Android TimePickerDialog ( 时间选择对话框 ) 会弹出一个对话框形式的时间选择器。

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools"
    android:orientation="vertical"
    android:gravity="center"
    tools:context=".MainActivity">
    <Button
        android:id="@+id/btn_pick_time"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="选择时间"/>

</LinearLayout>
java 复制代码
package com.example.myapplication;

import android.app.TimePickerDialog;
import android.os.Bundle;
import android.widget.Button;

import androidx.appcompat.app.AppCompatActivity;

import java.util.Calendar;
import java.util.TimeZone;

public class MainActivity extends AppCompatActivity {

    private Button btnPickTime;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        btnPickTime = findViewById(R.id.btn_pick_time);

        btnPickTime.setOnClickListener(v -> showTimePickerDialog());
    }

    private void showTimePickerDialog() {
        // 获取中国的当前时间
        Calendar calendar = Calendar.getInstance(TimeZone.getTimeZone("GMT+08:00")); // 设置时区为中国标准时间
        int hour = calendar.get(Calendar.HOUR_OF_DAY);
        int minute = calendar.get(Calendar.MINUTE);

        // 创建并显示时间选择对话框
        TimePickerDialog timePickerDialog = new TimePickerDialog(this, (view, selectedHour, selectedMinute) -> {
            // 处理选择的时间
            String selectedTime = String.format("%02d:%02d", selectedHour, selectedMinute);
            btnPickTime.setText(selectedTime); // 在按钮上显示选择的时间
        }, hour, minute, true); // 最后一个参数表示是否为24小时制
        timePickerDialog.show();
    }
}

PopupWindow 是一个弹出窗口控件,可以显示任意 View,并且浮动在当前 Activity 的顶部。通常用于悬浮在其他 UI 控件旁边,提供额外的信息或操作选项。与 AlertDialog 不同,PopupWindow 的位置可以自由设置,可以根据需要显示在屏幕的任何位置。

构造函数

PopupWindow 类的构造函数如下:

  1. PopupWindow(): 创建一个空的 PopupWindow 对象。
  2. PopupWindow(Context context): 使用指定的上下文创建 PopupWindow 对象。
  3. PopupWindow(Context context, AttributeSet attrs): 使用指定的上下文和属性集创建 PopupWindow 对象。
  4. PopupWindow(Context context, AttributeSet attrs, int defStyleAttr): 使用指定的上下文、属性集和样式资源创建 PopupWindow 对象。
  5. PopupWindow(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes): 使用指定的上下文、属性集、样式资源和主题资源创建 PopupWindow 对象。
  6. PopupWindow(View contentView): 使用指定的内容视图创建 PopupWindow 对象。
  7. PopupWindow(int width, int height): 创建指定宽高的 PopupWindow 对象。
  8. PopupWindow(View contentView, int width, int height): 使用指定的内容视图以及宽高创建 PopupWindow 对象。
  9. PopupWindow(View contentView, int width, int height, boolean focusable): 使用指定的内容视图、宽高和焦点设置创建 PopupWindow 对象。

方法

以下是一些重要的 PopupWindow 方法的说明:

  1. setContentView(View contentView): 设置 PopupWindow 显示的 View。
  2. getContentView(): 获取 PopupWindow 显示的 View。
  3. showAsDropDown(View anchor): 在指定控件正下方显示 PopupWindow,无偏移。
  4. showAsDropDown(View anchor, int xoff, int yoff): 在指定控件位置显示 PopupWindow,并可以设置偏移量。
  5. showAtLocation(View parent, int gravity, int x, int y): 在父控件指定位置显示 PopupWindow,可以设置具体位置、偏移量等。需要传入 Activity 中的任意一个 View 作为 parent 参数。
  6. setWidth(int width) / setHeight(int height): 设置 PopupWindow 的宽度和高度,也可以在构造方法中指定。
  7. setFocusable(true): 设置 PopupWindow 是否具有焦点。当设置为 true 时,PopupWindow 弹出后会处理触摸事件和物理按键事件,必须先让 PopupWindow 消失才能响应其他事件。
  8. setAnimationStyle(int style): 设置 PopupWindow 弹出和消失的动画效果。

例子

1、创建 res/layout/popup_content.xml 布局文件:

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:orientation="vertical"
    android:padding="16dp">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="弹出内容"
        android:textSize="16sp"
        android:textColor="@android:color/black" />

    <Button
        android:id="@+id/close_button"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="关闭"
        android:textColor="@android:color/white"
        android:background="@color/purple" />
</LinearLayout>

2、修改 res/layout/activity_main.xml 布局文件:

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools"
    android:orientation="vertical"
    android:gravity="center"
    tools:context=".MainActivity">
    <Button
        android:id="@+id/show_popup_button"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="显示弹出菜单" />

</LinearLayout>

3、修改 MainActivity.java:

java 复制代码
package com.example.myapplication;

import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.PopupWindow;

import androidx.appcompat.app.AppCompatActivity;

public class MainActivity extends AppCompatActivity {

    private PopupWindow popupWindow;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        // 创建一个 View 作为 PopupWindow 的内容视图
        View contentView = LayoutInflater.from(this).inflate(R.layout.popup_content, null);

        // 创建 PopupWindow 对象并设置内容视图、宽高
        popupWindow = new PopupWindow(contentView, ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);

        // 设置焦点,让 PopupWindow 弹出后处理触摸事件和物理按键事件
        popupWindow.setFocusable(true);

        // 找到触发弹出 PopupWindow 的按钮
        Button showPopupButton = findViewById(R.id.show_popup_button);
        showPopupButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // 在按钮下方显示 PopupWindow,无偏移
                popupWindow.showAsDropDown(v);
            }
        });

        // 找到关闭 PopupWindow 的按钮
        Button closeButton = contentView.findViewById(R.id.close_button);
        closeButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // 关闭 PopupWindow
                popupWindow.dismiss();
            }
        });
    }
}

官方文档

  1. Android PopupWindow

Android OptionMenu 选项菜单

在Android中,OptionMenu(选项菜单)的创建和管理不是通过XML直接实例化或某个类的实例化方法实现的,而是通过Activity提供的几个生命周期方法进行动态创建和控制。

具体来说:

  • onCreateOptionsMenu(Menu menu):这是用于初始化选项菜单的方法,在这个方法里,我们可以调用getMenuInflater().inflate(R.menu.menu_main, menu);来加载预定义在XML文件中的菜单项,或者通过调用menu对象的add()方法动态添加菜单项。
  • onOptionsItemSelected(MenuItem item):当用户点击选项菜单中的某一项时,系统会调用此方法,我们可以在其中根据item的id进行相应的操作处理。
  • onPrepareOptionsMenu(Menu menu):在每次菜单即将显示前,系统都会调用此方法,以便我们可以根据当前应用的状态动态修改菜单项的状态或可见性等属性。
  • onOptionsMenuClosed(Menu menu):当选项菜单关闭后,系统会调用此回调方法,可以在此处执行菜单关闭后的清理工作。
  • onMenuOpened(int featureId, Menu menu):如果我们的应用支持旧版的API(如ActionBar的子菜单),当选项菜单打开时,系统可能会调用此方法通知我们菜单已打开。

例子

1、在 res/menu/menu_main.xml 菜单文件中定义要显示的菜单项:

XML 复制代码
<!-- menu_main.xml -->
<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/menu_item1"
        android:title="选项 1" />
    <item
        android:id="@+id/menu_item2"
        android:title="选项 2" />
</menu>

2、修改 res/layout/activity_main.xml 布局文件:

XML 复制代码
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:tools="http://schemas.android.com/tools"
    android:orientation="vertical"
    android:gravity="center"
    tools:context=".MainActivity">
    <Button
        android:id="@+id/open_popup_menu_button"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="显示弹出菜单" />

</LinearLayout>

3、修改 MainActivity.java:

java 复制代码
package com.example.myapplication;

import android.os.Bundle;
import android.view.MenuItem;
import android.widget.Button;
import android.widget.PopupMenu;
import android.widget.Toast;

import androidx.appcompat.app.AppCompatActivity;

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Button openPopupMenuButton = findViewById(R.id.open_popup_menu_button);
        openPopupMenuButton.setOnClickListener(v -> {
            PopupMenu popupMenu = new PopupMenu(MainActivity.this, openPopupMenuButton);
            popupMenu.getMenuInflater().inflate(R.menu.menu_main, popupMenu.getMenu());

            popupMenu.setOnMenuItemClickListener(item -> {
                int id = item.getItemId();
                if (id == R.id.menu_item1) {
                    // 处理选中 选项 1 的事件
                    Toast.makeText(MainActivity.this, "选择了选项1", Toast.LENGTH_SHORT).show();
                    return true;
                } else if (id == R.id.menu_item2) {
                    // 处理选中 选项 2 的事件
                    Toast.makeText(MainActivity.this, "选择了选项2", Toast.LENGTH_SHORT).show();
                    return true;
                }
                return false;
            });

            popupMenu.show();
        });
    }
}

官方文档

  1. Android menus
相关推荐
没有了遇见16 分钟前
Android RecycleView 条目进入和滑出屏幕的渐变阴影效果
android
站在巨人肩膀上的码农1 小时前
去掉长按遥控器power键后提示关机、飞行模式的弹窗
android·安卓·rk·关机弹窗·power键·长按·飞行模式弹窗
LIN-JUN-WEI1 小时前
[ESP32]VSCODE+ESP-IDF环境搭建及blink例程尝试(win10 win11均配置成功)
c语言·开发语言·ide·vscode·单片机·学习·编辑器
呼啦啦--隔壁老王1 小时前
屏幕旋转流程
android
人生何处不修行1 小时前
实战:Android 15 (API 35) 适配 & 构建踩坑全记录
android
用户2018792831671 小时前
gralde的《依赖契约法典》
android
艾莉丝努力练剑3 小时前
【C语言】学习过程教训与经验杂谈:思想准备、知识回顾(三)
c语言·开发语言·数据结构·学习·算法
ZZZS05163 小时前
stack栈练习
c++·笔记·学习·算法·动态规划
位东风3 小时前
【c++学习记录】状态模式,实现一个登陆功能
c++·学习·状态模式
Star Curry4 小时前
【新手小白的嵌入式学习之路】-STM32的学习_GPIO 8种模式学习心得
stm32·嵌入式硬件·学习