Android Studio开发基础知识(持续更新中~)

阅读本文需要有Java前端的基础,本文是我学习Android时的笔记。

大纲

  • 一、UI开发
    • AS快捷键
    • 布局
      • 1.线性布局(LinearLayout)
      • 2.相对布局(RelaviteLayout)
      • 3.针布局(FrameLayout)
      • 4.表格布局(TableLayout)
      • 5.绝对布局(AbsoluteLayout)
    • 常用控件
      • 1.TextView
      • 2.EditView
      • 3.Button
      • 4.RadioButton
      • 5.ImageView
      • 6.ProgressBar
    • 常见对话框
      • 1.AlertDialog
      • 2.单选(AlertDialog)
      • 3.多选(AlertDialog)
      • 4.消息对话框(Toast)
      • 5.自定义对话框
    • 样式和主题
      • 1.样式(styles.xml)
      • 2.主题(themes.xml)
    • 国际化(I18N)
    • 程序调试
      • 单元测试(test 模块)
      • LogCat
      • Debug
  • 二、Activity
      • 生命周期
      • 四种启动模式
      • 页面跳转
        • 案例(打开浏览器)
      • 数据传递
      • 数据回传

一、UI开发

AS快捷键

Info Key
复制行 Ctrl+D
删除行 Ctrl+Y
注释 Ctrl+/
注释2 Ctrl+Shift+/
撤销 Ctrl+Z
恢复 Ctrl+Shift+Z
显示结构 Ctrl+F12
格式化代码 Ctrl+Alt+L
打开设置 Ctrl+Alt+S
自动补全代码 Ctrl+Shift+Space
自动导包 Alt+Enter

布局

1.线性布局(LinearLayout)

一些重要属性

//控制子控件的排列方向

orientation="vertical"    //垂直
orientation="horizontal"    //水平

//设置权重(权重总和为分母,可用于屏幕按钮的适配)

layout_weight="1"

2.相对布局(RelaviteLayout)

Layout下的控件属性

控件位置 Info
layout_centerInParent 位于 父的 正中央
layout_centerVertical 位于 父的 垂直中
layout_centerHorizontal 位于 父的 水平中
layout_above 位于 某的 上
layout_below 位于 某的 下
layout_toLeftOf 位于 某的 左
layout_toRightOf 位于 某的 右
layout_alignParentTop 是否与父 顶 对齐
layout_alignParentLeft 是否与父 左 对齐
layout_alignParentRight 是否与父 右 对齐
layout_alignParentBottom 是否与父 底 对齐
layout_alignTop 与某的 上 对齐
layout_alignLeft 与某的 左 对齐
layout_alignRight 与某的 下 对齐
layout_alignBottom 与某的 右 对齐

与前端CSS类似

控件间距(Margin) 布局内边距(Padding)
layout_marginTop paddingTop
layout_marginBottom paddingBottom
layout_marginLeft paddingLeft
layout_marginRight paddingRight
padding

3.针布局(FrameLayout)

该布局为每个加入其中的控件创建一个空白区域(称为一帧,每个控件占据一帧),所以控件默认显示在左上角,先放的在最底层。

Key Info
foreground 设置容器的前景图
foregroundGravity 设置前景图显示位置

4.表格布局(TableLayout)

需要和TableRow标签配合使用,TableRow的数量决定表格的行数。

布局属性 Info
stretchColumns 设置列可 拉伸
shrinkColumns 设置列可 收缩
collapseColumns 设置列可 隐藏
控件属性 Info
layout_column 在控件少于单元格的情况下,指定显示的位置
layout_span 默认为1,可指定控件占几个单元格

5.绝对布局(AbsoluteLayout)

//布局属性
layout_x = "50dp";
layout_y = "100dp";

常用控件

1.TextView

控件属性 Info
text
textColor
textSize sp
textStyle bold,italic
gravity 文本位置
layout_width 控件高
layout_height wrap_content , match_parent
height 文本域高( 不常用)
width 文本域宽( 不常用)
maxLength 文本最大长度
phoneNumber 以电话形式显示
password 以密码形式显示

2.EditView

控件属性 Info
hint 提示文本
lines 设置固定行高
maxLines 最大行数
minLines 最小行数
password 以密码形式显示
phoneNumber 以电话形式显示
scrollHorizontally 水平滚动条
capitalize 首字母大写
editable 是否可编辑

background="@null"属性为去掉控件默认的下划线

3.Button

点击事件的两种实现方法

	<Button
        android:id="@+id/btn1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"/>
        
	//onClick方法已经弃用了
    <Button
        android:id="@+id/btn2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:onClick="click"/>

	//lambda表达式
	btn1.setOnClickListener(view -> {
        btn1.setText("btn1");
    });
    
	public void click(View v){
		btn2.setText("btn2");
	}

按钮点击事件较多的情况下,实现OnClickListener接口,重写onClick方法:

public class MainActivity implements View.OnClickListener{
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_login);
        //TODO 初始化N个控件...
    }
    
    @Override
    public void onClick(View v){
        switch(v.getId()){
            case R.id.btn1:
                btn1.setText("btn1");
            case R.id.btn2:
                btn1.setText("btn2");
            //......
        }
    }
}

4.RadioButton

Radiobutton 需要与 RadioGroup 配合使用

//RadioGroup控件的属性 控制子控件的排列方向
orientation="vertical"    //垂直
orientation="horizontal"    //水平

//RadioButtion控件的属性 设置按钮默认为选中状态
checked="ture"

监听事件(setOnCheckedChangeListener)

radioGroup.setOnCheckedChangeListener(new RadioGroup.OnCheckedChangeListener() {
            @Override
            public void onCheckedChanged(RadioGroup radioGroup, int i) {
                if(i == R.id.rbtn){
                    //TODO
                }else{
                    //TODO
            }
        });

5.ImageView

//background是背景,会根据控件大小进行伸缩	
<ImageButton
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:background="@drawable/bg"/>
//src是前景,以原图大小显示
<ImageButton
        android:layout_width="100dp"
        android:layout_height="100dp"
        android:background="@drawable/ic_launcher_background"
        android:src="@drawable/ic_launcher_foreground"/>

6.ProgressBar

ProgressBar的属性

Key Info
indeterminate 不确定模式,动画无限循环
indeterminateDrawable 设置不确定模式是否可drawable
max 进度的最大值
maxHeight 进度Widget最大高
maxWidth 进度Widget最大宽
minHeight 进度Widget最小高
minWidth 进度Widget最小宽
progress 进度默认值,0~max
progressBackgroundTint 背景颜色
secondaryProgress 定义二级进度值,0~max

ProgressBar的方法

Function Info
getMax() 返回最大值
getProgress() 返回进度
getSecondaryProgressBy() 返回次要进度
incrementProgressBy() 指定增长的进度,正数增加,负数减少
isIndeterminate() 是否为不确定模式
setLndeterminate() 设置为不确定模式

系统提供的样式

style=“@andorid:style/*” Info
Widget.progressBar.Horizontal 水平进度条
Widget.progressBar.Inverse 普通环形(默认)
Widget.progressBar.Large 大环形
Widget.progressBar.Small 小环形

自定义进度条比较复杂,不展开

另外,对话框形式的进度条ProgressDialog已被弃用,不建议使用。

常见对话框

1.AlertDialog

AlertDialog.Builder dialog = new AlertDialog.Builder(this)
                        .setTitle("密码错误")
                        .setIcon(R.drawable.ic_launcher_background)
                        .setPositiveButton("确定",null)
                        .setNegativeButton("取消",null)
                        .setMessage("123");
dialog.show();

2.单选(AlertDialog)

new AlertDialog.Builder(this)
    .setTitle("选择性别")
    .setSingleChoiceItems(new String[]{"男", "女"}, 0,
                      new DialogInterface.OnClickListener() {
                          @Override
                          public void onClick(DialogInterface dialogInterface, int i) {
                                }
                            })
    .setPositiveButton("确定",null)
    .show();

setSingleChoiceItems()方法需要设置三个参数:

  1. 建立数组,用于显示选项内容
  2. 参数是否默认选中:0表示选中第一个,-1表示默认不选中
  3. 设立监听,允许对话框被点击

3.多选(AlertDialog)

//lambda表达式
new AlertDialog.Builder(this)
    	.setTitle("选择性别")
        .setMultiChoiceItems(new String[]{"a", "b", "c", "d", "e", "f"},
                     new boolean[]{true, true, false, false, true, true}, 
                     ((dialogInterface, i, b) -> {
                     
                     }))
        .setPositiveButton("确定",null)
        .show();

setMultiChoiceItems()方法需要设置三个参数:

  1. String[] 建立数组,用于显示选项内容
  2. boolean[] 建立数组,参数是否默认选中
  3. 设立监听,允许对话框被点击(相比单选多了一个boolean参数)

4.消息对话框(Toast)

//轻量级信息提醒机制
//别忘了在最后的show方法
Toast.makeText(this,"hello",Toast.LENGTH_SHORT).show();
Toast.makeText(this,"hello",Toast.LENGTH_LONG).show();

5.自定义对话框

新建一个my_dialog.xml文件


<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        android:background="#fff"
        android:orientation="vertical">
        <TextView
            android:id="@+id/tv_title"
            android:layout_width="match_parent"
            android:layout_height="40dp"
            android:background="#08F"
            android:gravity="center"
            android:text="自定义对话框"
            android:textColor="#fff"
            android:textSize="18sp"
            android:visibility="visible"/>
        <LinearLayout
            android:id="@+id/ll_content"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:gravity="center">
            <TextView
                android:id="@+id/tv_msg"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:gravity="center"
                android:minHeight="100dp"
                android:paddingTop="15dp"
                android:paddingRight="20dp"
                android:paddingBottom="15dp"
                android:paddingLeft="20dp"
                android:textColor="#4e5052"
                android:textSize="16sp"/>

        LinearLayout>
        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="60dp"
            android:layout_gravity="bottom"
            android:background="#EEE"
            android:gravity="center"
            android:orientation="horizontal">
            <Button
                android:id="@+id/btn_ok"
                android:layout_width="114dp"
                android:layout_height="40dp"
                android:layout_marginLeft="20dp"
                android:background="#6200ee"
                android:gravity="center"
                android:text="确定"
                android:textColor="#FFF"
                android:textSize="15sp"/>
            <Button
                android:id="@+id/btn_cancel"
                android:layout_width="114dp"
                android:layout_height="40dp"
                android:layout_marginLeft="20dp"
                android:layout_marginRight="20dp"
                android:background="#d0d0d0"
                android:gravity="center"
                android:text="取消"
                android:textColor="#666"
                android:textSize="15sp"/>

        LinearLayout>
    LinearLayout>
FrameLayout>

PS:按钮的颜色改不了,就在values/themes.xml中修改

<style name="Theme.Textbook_test01" parent="Theme.MaterialComponents.DayNight.DarkActionBar.Bridge">

新建MyDialog.java文件,继承Dialog类

public class MyDialog extends Dialog {
    private String dialogMessage;
    private TextView tvMsg;
    private Button btnOK;
    private Button btnCancel;
    //构造方法
    public MyDialog(Context context,String dialogMessage){
        super(context);
        this.dialogMessage = dialogMessage;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        //去除标题
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        //引入自定义对话框布局
        setContentView(R.layout.my_dialog);
        
        tvMsg=findViewById(R.id.tv_msg);
        btnOK=findViewById(R.id.btn_ok);
        btnCancel=findViewById(R.id.btn_cancel);
        //设置自定义对话框显示内容
        tvMsg.setText(dialogMessage);
        
        btnOK.setOnClickListener(view -> {
            //TODO 确认后的操作
        });
        btnCancel.setOnClickListener(view -> {
            dismiss();//关闭当前对话框
        });
    }
}

在MainActivity.java中创建对象

new MyDialog(this,"我是自定义的Dialog").show();

样式和主题

当style和theme的属性发生冲突时,style的优先级要高于theme

1.样式(styles.xml)

安卓中的样式类似与网页中CSS样式,可以让设计与内容分离。

在res/values下新建styles.xml。


<resources>
    <style name="textStyle_one">
        "android:layout_width">match_parent
        "android:layout_height">wrap_content
        "android:textColor">#999
        "android:textSize">35sp
    style>
    <style name="textStyle_two" parent="@style/textStyle_one">
        "android:textSize">25sp
    style>
resources>

其中name属性是样式名称,parent属性表示继承某个样式

通过标签定义样式。

在布局文件中引用样式:

   <TextView
        android:id="@+id/tv1"
        style="@style/textStyle_one"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="test样式1"
        tools:ignore="MissingConstraints" />
    <TextView
        style="@style/textStyle_two"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="test样式2"
        app:layout_constraintTop_toBottomOf="@+id/tv1"
        tools:ignore="MissingConstraints" />

2.主题(themes.xml)

主题是应用到整个Activity和Application的样式,要在AndroidManifest.xml文件中引用。

	
    <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
        "colorPrimary">@color/purple_500
        "colorPrimaryDark">@color/purple_200
        "colorAccent">@color/purple_700
    style>
    <style name="grayTheme" parent="Theme.AppCompat.Light.DarkActionBar">
        "android:background">#999
    style>

AndroidManifest.xml中应用主题

	
	<activity
            android:name=".SelectTraActivity"
            android:theme="@style/grayTheme"
            android:exported="false" />

注意,在定义主题时,需用到parent属性去继承"Theme.AppCompat.Light.DarkActionBar"来保证兼容性。

注意,在java代码中也可以引用主题,需在onCreate()方法内添加.setTheme(R.style.grayTheme)方法,该方法通常放在setContentView()方法之后。

国际化(I18N)

让不同国家的人看到不同的效果,就需要用到这个功能。

右键 res文件夹 —> New —> Values resource file —>

文件名 string.xml ,Directory name和type 为values —>

选Locale —> 选国家—>选语言—>确定

在对应的文件下修改对应的资源,就能实现不同语言下看到不同的效果

程序调试

androidTest是整合测试。可以打包为apk运行在设备上,可以实时查看细节。

test是单元测试类。运行在本地开发机上,速度快。

单元测试(test 模块)

要测试的方法直接写在test模块的类里,要加上@Test

public class ExampleUnitTest {
    @Test
    public void addition_isCorrect() {
        assertEquals(4, 2 + 2);
    }
    @Test
    public void test() throws Exception{
        final int expected =2;
        final int reality =2;
        //断言,expected期望的参数值与reality相同
        assertEquals(expected,reality);
    }
}

LogCat

Logcat在编辑器的最下面一栏的中间。可以通过限定精确查找。

静态方法 级别 Translate
Log.v() Vebose 详细信息(低)
Log.d() Debug 调试信息
Log.i() Info 一般信息
Log.w() Warning 警告信息
Log.e() Error 错误信息
Assert 断言(高)

Debug

打断点:单击代码右侧

功能 快捷键
Step Over 执行下一句 F8
Step Info 当见到方法,进入此方法 F7
Force Step Info 用于研究源码
Step Out 跳出改方法
Resume Program 执行下一个断点 F9
Stop app 停止调试
View Breakpoints 查看所有断点

二、Activity

生命周期

方法 状态 Info
onCreate() 页面创建时
onStart() 启动状态 页面可见时
onResume() 运行状态 可获取焦点,与用户交互时
onPause() 暂停状态 被其他页面覆盖或锁屏时
onStop() 停止状态 页面不可见时
onDestroy() 销毁状态 页面销毁时
onRestart() 从停止状态重新启动时

四种启动模式

Mainifest.xml中通过activity标签的launchMode属性可以设置启动模式。

  1. standard模式:【不会检测Activity是否重复】
  2. singleTop模式:【相同Activity且同时位于堆栈顶端(top)时才会重复处理】
  3. singleTask模式:【一个堆栈仅可以有可以实例的task,顶出其他Activity
  4. singlesrance模式:【一个系统仅仅一个这样的Activity

页面跳转

  1. 显式跳转

    Intent intent =new Intent();
    intent.setClass(this,目标页面.class);
    startActivity(intent);
    
    //简化
    startActivity(new Intent(this,目标页面.class));
    
    
  2. 隐式跳转

    通过指定的action和category寻找目标Activity,使用隐式intent还可以启动其他app中的Activity。

    Intent intent = new Intent();
    intent.setAction("action");
    startActivity(intent);
    
    //简化
    startActivity(new Intent("action"));
    
    

案例(打开浏览器)

//MainActivity.xml
	//在按钮的点击事件中

	Intent intent = new Intent();
	//这是安卓系统内置的Action,通过这个Action可以和浏览器进行匹配
	intent.setAction("android.intent.action.VIEW");
	//设置要打开的网址
	//Uri.parse()方法把 网址字符串 解析成 Uri对象 ,传入setData()方法。
	intent.setData(Uri.parse("http://www.baidu.com"));
	startActivity(intent);

数据传递

//页面1.xml
Intent intent = new Intent();
intent.setClass(LoginActivity.this,SelectTraActivity.class);
intent.putExtra("n1","我是要传递的数据");
intent.putExtra("n2",123);
startActivity(intent);

//页面2.xml
String n1 = getIntent().getStringExtra("n1");
String n2 = getIntent().getIntExtra("n2");

数据回传

目前 startActivityForResult() 已被弃用,替代方案为 Activity Result API 组件,这里不展开。

startActivityForResult(Intent intent,int requestCode);

该方法也用于启动Activity,并且能在页面销毁时返回数据。

实际应用:微信发朋友圈时,进入图库选好照片后,会返回到发表状态页面并带回所选的图片信息。

//页面1.xml
Intent intent = new Intent(this,Activity02.class);
startActivityForResult(intent,1);

@Override
    protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        if(requestCode == 1){
            if (resultCode ==1){
                String str = data.getStringExtra("name");
            }
        }
    }
//页面2.xml
Intent intent = new Intent();
intent.putExtra("name","abcdefg");
setResult(1,intent);

你可能感兴趣的:(android,studio,android)