关于Include复用layout的文章,2017年写过俩篇;
于2020年综合为一篇 ~


  • 基础
  • 使用方式
  • 注意要点
  • 篇一
  • 项目结构图
  • include layout(被复用布局)
  • 引用include视图
  • Activity中调用include相关操作
  • 总结
  • 篇二
  • include layout(被复用布局)
  • 引用include layout
  • 基于 include layout 之上Activity的操作


基础

本篇主要讲的是include 标签,其主要作用体现在layout的复用性方面,也是布局优化中的重要体现之一 ~

include标签之所以能作为布局优化中的一环,主要是因为其自身的复用性,当多布局引用一个公用布局时,一般都会使用include标签,很大程度上节省了开发时间,不用重复造轮子~

使用方式

关于inlude标签的使用,我们通常需要一个被引用的layout,同时在需要引用地方通过include标签下的layout属性进行引入我们要复用的布局

通常通过以下类型方式,即可成功引入公用布局

include_layout - 被复用的布局

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
	android:id="@+id/include_ll"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:orientation="vertical" >
    
    <TextView
    	android:id="@+id/tv_1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:gravity="center"
        android:text="Include—item—1"
        />
</LinearLayout>

activity_main - 引入include标签,复用布局

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity" >

    <include
        android:id="@+id/include_main"
        layout="@layout/include_layout" />

</LinearLayout>

注意要点

引用布局只是其一,大多场景我们需要对inlude布局执行相关操作,关于这里有几点需要注意一下

  1. 我们如何操作include内的布局元素?

通常我们首先将include标签加上id,之后在调用时,通过第一次获取的View再次获取include内(被复用视图)控件

//我比较懒,直接链式写完了,一般不建议这么写
 TextView mTv1 = findViewById(R.id.include_main).findViewById(R.id.tv_1);
  1. include标签id和include根布局id有什么要注意的?

常规建议俩者共用一个id,或仅命名include标签的id,俩者同时命名,且id不同时,include根标签可能被报空,如下 ~

将上方的include布局的根布局加入不同id

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
	android:id="@+id/include_ll"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:orientation="vertical" >
    
    <TextView
    	android:id="@+id/tv_1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:gravity="center"
        android:text="Include—item—1"
        />
</LinearLayout>

调用示例

View layout_main = findViewById(R.id.include_main);
Log.i(TAG, "layout " + layout_main ); // 此时正常获取Layout

View layout_ll = findViewById(R.id.include_ll);
Log.i(TAG, "layout " + layout_ll); // 此时返回null

尝试解决

//可以用过这种方式解决报空问题,但是不建议这么操作
View layout = findViewById(R.id.include_main).findViewById(R.id.include_ll);
  1. 如果在include标签内使用常见的布局属性会不会有问题?

答案是肯定有问题的,布局会错位

简单引用

<include
        android:id="@+id/include_main"
        layout="@layout/include_layout" />

错误:属性引用(无效)

<include
        android:id="@+id/include_main"
        android:layout_marginTop="10dp"
        layout="@layout/include_layout" />

正确:属性引用(声明layout_width、layout_height)

<include
        android:id="@+id/include_main"
        android:layout_marginTop="10dp"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        layout="@layout/include_layout" />

篇一

篇一 :Android初级教程 - Include(复用layout)的使用方式(一)
发布时间:2017-01-09 14:01:43
地址:(4月17被我删除)

项目结构图

包含2个Activity,4个layout

android include androidinclude调用_android include

include layout(被复用布局)

include_layout1

<?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="wrap_content"
    android:orientation="vertical" >
    
    <TextView 
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:gravity="center"
        android:text="Include—item—1"
        />
</LinearLayout>

include_layout2

<?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"
    android:orientation="vertical" >
    
      <TextView 
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="include—item-2"
        android:gravity="center"
        android:id="@+id/tv_2"
        />
</LinearLayout>

引用include视图

activity_main

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity" >

    <include
        android:id="@+id/tv_1"
        layout="@layout/include_layout1" />
        
    <include
        layout="@layout/include_layout2" 
        />
</LinearLayout>

activity_secound

<?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"
    android:orientation="vertical" >
    
    <include 
        layout="@layout/include_layout2"
        />
</LinearLayout>

Activity中调用include相关操作

MainActivity

package com.example.includedemo;

import android.os.Bundle;
import android.app.Activity;
import android.content.Intent;
import android.graphics.Color;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;

public class MainActivity extends Activity {

	private TextView include_item2;
	private LinearLayout include_item1;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		//第一种方式-1-在当前布局设置Id,不过返回的都是最外层的布局,所以不对单体View作用,但可以改变其背景,颜色之类
		include_item1 = (LinearLayout)findViewById(R.id.tv_1);
		include_item1.setOnClickListener(new OnClickListener() {
			
			@Override
			public void onClick(View v) {
				Toast.makeText(MainActivity.this, "第一种方式include_item1", 0).show();		
				include_item1.setBackgroundColor(Color.BLUE);
			}
		});
		
		//第一种方式-2-如对其整个空间的背景之类无特殊要求直接一套操作完毕。
//		findViewById(R.id.tv_1).setOnClickListener(new OnClickListener() {
//			
//			@Override
//			public void onClick(View v) {
//				Toast.makeText(MainActivity.this, "第一种方式include_item1", 0).show();
//			}
//		});
		
		//第二种方式-在子item布局进行id设置,使用较为方便!而且自由!
		include_item2 = (TextView) findViewById(R.id.tv_2);
		include_item2.setOnClickListener(new OnClickListener() {
			
			@Override
			public void onClick(View v) {
				Toast.makeText(MainActivity.this, "第二种方式include_item2", 0).show();
				//很明显我们可以对此控件进行操作
				include_item2.setText("Go to Bed to  sleep");
				startActivity(new Intent(MainActivity.this,SecoundActivity.class));
			}
		});
	}
}

SecoundActivity

package com.example.includedemo;

import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.TextView;
import android.widget.Toast;

public class SecoundActivity extends Activity {

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_secound);
		
		TextView mSecound = (TextView) findViewById(R.id.tv_2);
		mSecound.setText("Secound页面,填充Include");
		mSecound.setOnClickListener(new OnClickListener() {
			
			@Override
			public void onClick(View v) {
				Toast.makeText(SecoundActivity.this, "触发Include", 0).show();
			}
		});
	}
}

总结

包含遇到的问题和需要注意的点

  • 三种方式,一种主Xml设置id,一种item的Xml设置id,一种单纯填充布局。
  • 主Xml设置id的话,我们大多时候只能获取最外层的View,作用比较小,往往改一个背景,颜色之类的,意义不大(需要注意:如果在运行中layout出现占满整个布局的情况下,需要看一下item的最外层layout是否是match,这是处理方式之一,同时也可以在使用处的Xml进行宽度,高度的限制)。
  • 这里的话我们主要使用在item处设置id的方式来在开发中使用,这样使用起来更加的灵活,可以随心所欲的设置item的任何事件,不管是修改text的属性,还是设置onClick,亦或换换颜色,换换背景之类的(需要注意:find之后返回对应的View类即可)。
  • 在不同的Activity中获取item的id进行设置处理,并不会造成影响俩者的影响,所以不必在意。
  • 一切均自己所想,如有不足,请您指出,如有误导,非常抱歉。
  • 希望各位君,2017开开心心

篇二

基于之前不足之处,将不完善之处通过此篇为大家带入更清晰的使用方式,注释已经详细为大家解答,敬请阅读 ~

注意点:此文的双重tag - 及为俩次find id后的控件

  1. 首先复用的layout注意布局,外部布局一般高度都是wrop的。不然你会发现显示不全
  2. 如果我们复用的layout只在当前布局复用一次的话,可以直接find到复用 layout的布局的id直接处理逻辑
  3. 反之如果我们在当前布局,多次复用layout我们就需要通过双重tag获得具体事件操作

include layout(被复用布局)

Inclde Layout(我们要复用的视图)

<?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="wrap_content"
    android:orientation="vertical" >
    
    <TextView 
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:id="@+id/include_text"
        android:text="复用 Layout"
        android:layout_gravity="center"
        />
</LinearLayout>

引用include layout

activity_main

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >

    <include
        android:id="@+id/main_text"
        layout="@layout/include_layout"
        />
    <include
        android:id="@+id/secound_text"
        layout="@layout/include_layout"
        />
</LinearLayout>

基于 include layout 之上Activity的操作

MainActivity code

package com.example.includeall;

import android.os.Bundle;
import android.app.Activity;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.TextView;
import android.widget.Toast;

public class MainActivity extends Activity {
	private TextView mSecound;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		//第一种方式的进阶版使用针对在主layout多次复用layout的处理方式
		
		//第一个复用layout的使用
		// 首先获取当前布局的Layout id,这里我们直接返回View!!!因为我们并不确定我们当前复用的layout就是TextView等
		View mMain = findViewById(R.id.main_text);
		// 之后通过之前获取的id再次获取Include layout的 id
		TextView mInculde = (TextView) mMain.findViewById(R.id.include_text);
		// 如果我们只是获取当前复用layout的id控件操作,是会报错的
		// mMain.setText("xxxxx");
		mInculde.setText("在主Layout操作Inclue的Layout,与我们之前的直接查找复用Layout中的id效果是一样的!");

		//第二个复用layout的使用
		mSecound = (TextView) findViewById(R.id.secound_text).findViewById(R.id.include_text);
		mSecound.setText("在同一个布局,复用了俩次相同的子布局页面, 我们需要通过双重tag操作");
		mSecound.setOnClickListener(new OnClickListener() {
			@Override
			public void onClick(View v) {
				Toast.makeText(getApplication(), "执行自己的相关逻辑操作", 0)
				.show();				
			}
		});
		
		/**此为复用layout的直接id,---目前发现只给复用的第一个layout显示相关的操作!!!*/
		TextView mTwo = (TextView) findViewById(R.id.include_text);
		mTwo.setOnClickListener(new OnClickListener() {
			@Override
			public void onClick(View v) {
				Toast.makeText(getApplication(), "使用之前的第二种方式操作,效果一样没有区别对待,实现的效果都建立在第一个视图之上", 0)
						.show();
			}
		});
	}
}