Android之应用资源

Android应用源码(物理)

  • 界面布局文件
  • Java源文件
  • 资源文件

应用资源概述

Android应用资源类型和存储方式

  • 无法通过R资源清单类访问的原生资源,保存在assets目录下
  • 可通过R资源清单类访问的资源,保存在res目录下
  • res目录下资源存储资源说明
  • /res/animator/:存放定义属性动画的XML文件
  • /res/anim/:存放定义补间动画的XML文件
  • /res/color/:存放定义不同状态下颜色列表的XML文件
  • /res/drawable/:存放各种位图文件,编译成各种Drawable对象的XML文件(BitmapDrawable、NinePatchDrawable、StateListDrawable、ShapeDrawable、AnimationDrawable、Drawable的其它各种子类对象)
  • /res/layout/:存放用户界面布局文件
  • /res/menu/:存放为应用程序定义的各种菜单资源(选项菜单、子菜单、上下文菜单)
  • /res/raw/:存放任意类型原生资源(音频、视频等),使用时通过调用Resource对象的openRawResource(int id)方法获取该资源的二进制输入流进而进行使用。
  • /res/values/:存放各种简单的XML文件(字符串值、整数值、颜色值、数组、尺寸、样式等),一般根据不同文件来存储不同类型的值。
  • /res/xml/:存放原生XML文件,通过Resource对象的getXML()方法进行访问。

资源使用

  • Java代码中使用资源清单项:[package_name.]R.resource_type.resource_name
// 获取图片资源
getWindow().setBackgroundDrawableResource(R.drawable.back);
// 获取字符串资源
getWindow().setTitle(getResources().getText(R.string.main_title))
  • Java代码中访问实际资源(通过Resources类对象调用下述方法)
  • getXXX(int id):根据资源清单ID来获取实际资源
  • getAssets():获取访问/assets/目录下资源的AssetManager对象
// 获取Resource对象
Resource res = Activity.this.getResources();
// 获取字符串资源
String titile = res.getText(R.string.main_title);
// 获取图片资源
Drawable logo = res.getDrawable(R.drawable.logo);
// 获取数组资源
int[] arr = res.getIntArray(R.array.books);
  • XML中使用资源


    hello
    #000000


    

字符串、颜色、尺寸资源

颜色值定义

  • Android颜色值常见的4种形式
  • #RGB:分别指定红、绿、蓝三原色的值(只支持0~f 16级颜色)来代表颜色
  • #ARGB:分别指定红、绿、蓝三原色的值(只支持0~f 16级颜色)及透明度(只支持0~f 16级颜色)来代表颜色
  • #RRGGBB:分别指定红、绿、蓝三原色的值(只支持00~ff 256级颜色)来代表颜色
  • #AARRGGBB:分别指定红、绿、蓝三原色的值(只支持00~ff 256级颜色)及透明度(只支持00~ff 256级颜色)来代表颜色

定义字符串、颜色、尺寸资源

  • 字符串定义(/res/values/strings.xml)
手机号
  • 颜色定义(/res/values/colors.xml)
 #Fda222
  • 尺寸定义(/res/values/dimens.xml)
 16dp

使用字符串、颜色、尺寸资源

  • 字符串、颜色、尺寸等资源使用前面已经说明,此处不做赘述。

数组资源

数组资源定义

  • array:普通 类型
    
        @drawable/ic_search_24dp
        @drawable/ic_search_24dp
        @drawable/ic_search_24dp
    
    
  • string-array:字符串类型
    
        张三
        李四
        王五
    
  • integer-array:整数型
    
        21
        35
        11
    

数组资源使用

  • 使用方法同字符串、颜色、尺寸等资源的使用类似,此处不做赘述。

Drawable资源

图片资源(XXX.png、XXX.jpg、XXX.gif)

  • 使用方法同字符串、颜色、尺寸等资源的使用类似,此处不做赘述。

StateListDrawable资源

  • StateListDrawable用于组织多个Drawable对象,当使用StateListDrawable作为目标组件的背景、前景图片时,StateListDrawable对象所显示的Drawable对象会随目标组件状态的改变而自动切换。
  • StateListDarwable对象的XML文件根元素为 select 元素。该元素可以包含多个 item 子元素。该元素一般具有如下两种属性:
  • android:color 或者 android:drawable :指定颜色或者Drawable对象
  • android:state_xxx :指定一个特定状态
  • StateListDrawable的 item 子元素所支持的状态有如下几种:
  • android:state_active:代表是否处于激活状态
  • android:state_checkable:代表是否处于可勾选状态
  • android:state_checked:代表是否处于已经选状态
  • android:state_enabled:代表是否处于可用状态
  • android:state_first:代表是否处于开始状态
  • android:state_focused:代表是否处于已得到焦点状态
  • android:state_last:代表是否处于结束状态
  • android:state_middle:代表是否处于中间状态
  • android:state_pressed:代表是否处于已被按下状态
  • android:state_selected:代表是否处于已被选中状态
  • android:state_window_focused:代表窗口是否处于已得到焦点状态
  • 示例:


    
    
    
    



    
    
    
    



    
    

LayerDrawable资源

  • LayerDrawable与StateListDarwable类似,也是包含一个Drawable数组,因此系统会按这些Drawable对象的数组顺序来绘制它们,索引最大的Drawable对象将会被绘制在最上面。
  • LayerDarwable对象的XML文件的根元素为 layer-list ,该元素可以包含多个 item 元素,一般可以指定如下属性:
  • android:drawable:指定作为LayerDrawable元素之一的Drawable对象。
  • android:id:为该Drawable对象指定一个标识。
  • android:buttom|top|left|button:它们用于指定一个长度值,用于指定该Drawable对象绘制到目标组件的指定位置。
  • 示例:


    
    
    
    



    
        
    

    
        
    

    
        
    

ShapeDrawable资源

  • ShapeDrawable用于定义一个基本的几何图形(如矩形、圆等),定义ShapeDrawable的根元素是 shape ,shape可指定如下属性:
  • android:shape = [“rectangle”|“oval”|“line”|“ring”]
  • 定义ShapeDrawable对象的完整语法:


    
    
    
    

    
    
    
    
    
    
    
    

  • 示例:



    
    

    
    
    



    
    

    
    
    



    
    
    
    

  • 设置渐变点击效果:
  
  
  
  
      
          
              
                  
  
                  
                  
                  
              
          
          
              
                  
  
                  
                  
                  
              
          
      
  
 

ClipDrawable资源

  • ClipDrawable代表从其它位图上截取一个“图片片段”,在XML文件中定义ClipDrawable对象使用 clip 元素。一般可以指定如下属性:
  • android:drawable:指定截取的源Drawable对象
  • android:clipOrientation:指定截取方向,可设置水平截取或者竖直截取
  • android:gravity:指定截取时的对齐方式
  • clip元素的完整语法:




AnimationDrawable资源

  • AnimationDrawable代表一个动画,Android即支持传统的逐帧动画,也支持通过平移、变换计算出来的补间动画。定义补间动画的XML资源文件以 set 元素作为根元素,该元素有如下四个子元素:
  • alpha:设置透明度的改变
  • scale:设置图片进行缩放变换
  • translate:设置图片进行位移变换
  • rotate:设置图片进行旋转
  • 定义补间动画的XML资源一般放置在/res/anmi/路径下。定义思路比较简单:设置一张图片的开始状态(透明度、位置、缩放比、旋转角度等),结束状态(类似开始状态的设置),动画的持续时间。Android系统会使用动画效果把这张图片从开始状态变换的结束状态。
  • 补间动画语法:


    
    
    
    

    
    
    
    
    
    
    
    
    


  • 示例:


    
    

    
    


    private void initViewAnim() {
        // 加载动画资源
        animation = AnimationUtils.loadAnimation(this, R.anim.animation_drawable_example);
        // 设置动画结束后保留结束状态
        animation.setFillAfter(true);

    }
            case R.id.btn_anim:
                // 开始动画
                ivAnim.startAnimation(animation);
                break;

属性动画资源

  • Animator代表一个属性动画,但它只是一个抽象类,通常会使用它的子类:AnimatorSet、ValueAnimator、ObjectAnimator、TimeAnimator等。
  • 属性动画的XML文件以下述三个元素中的任意一个作为根元素:
  • set:它是一个父元素,用于包含 objectAnimator、animator、set 子元素,该元素定义的资源代表AnimatorSet对象。
  • objectAnimator:用于定义ObjectAnimator动画。
  • animator:用于定义ValueAnimator动画。
  • 定义属性动画语法:



    
    
    
    
    
        
    
    

  • 示例:



    private class MyAnimationView extends View {
        public MyAnimationView(Context context){
            super(context);
            // 加载动画资源
            ObjectAnimator objectAnimator = (ObjectAnimator) AnimatorInflater.loadAnimator(
                    ResourceActivity.this,R.animator.property_animation_example);
            objectAnimator.setEvaluator(new ArgbEvaluator());
            // 对该View本身应用属性动画
            objectAnimator.setTarget(this);
            // 开始指定动画
            objectAnimator.start();

        }
    }
    private void initViewPropertyAnim() {
        llAnim.addView(new MyAnimationView(this));
    }

XML资源

定义原始XML资源

  • 原始的XML资源一般保存在/res/xml/文件夹下,在Java程序中获取实际的XML文件,使用Resources的如下方法来获取:
  • XmlResourceParser getXml(int id):获取XML文档,并使用一个XmlPullParser来解析XML文档,该方法返回的是一个解析器对象(XmlResourceParser 是XmlPullParser的子类对象)。
  • InputStream openRawResource(int id):获取XML文档对应的输入流。
  • 获取XML文档一般直接调用getXml(int id)方法获取,并对XML文档进行解析。Android默认使用内置的Pull解析器来解析XML文档。处理使用Pull解析器外,还可以使用DOM或者SAX对XML文档进行解析。

使用原始XML资源



    java
    android
    javaee

// 根据 XML 资源的ID获取解析该资源的解析器
        // XmlResoureParser是XmlPullParser的子类
        XmlResourceParser xrp = getResources().getXml(R.xml.books);

        StringBuilder sb = new StringBuilder("");
        // 还没有到xml文档的结尾处
        try {
            while (xrp.getEventType() != XmlResourceParser.END_DOCUMENT) {
                // 如果遇到开始标签
                if (xrp.getEventType() == XmlResourceParser.START_TAG) {
                    // 获取该标签的标签名
                    String tagName = xrp.getName();
                    // 如果遇到book标签
                    if (tagName.equals("book")) {
                        // 根据属性名来获取属性值
                        String bookName = xrp.getAttributeValue(null, "price");
                        sb.append("价格:");
                        sb.append(bookName);
                        // 根据属性索引来获取属性值
                        String bookPrice = xrp.getAttributeValue(1);
                        sb.append("    出版日期:");
                        sb.append(bookPrice);
                        sb.append("    书名:");
                        // 获取文本节点的值
                        sb.append(xrp.nextText());

                    }
                    sb.append("\n");

                }
                // 获取解析器的下一个事件
                xrp.next();

            }
            etXml.setText(sb.toString());
        } catch (XmlPullParserException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

布局资源

  • Layout资源文件保存在/res/layout/文件夹下,在Java代码中和XML中的使用同其它资源类似。

菜单资源

  • 菜单资源一般保存在/res/menu/文件夹下,以 menu 为根元素,子元素有如下两种:
  • item:定义菜单项
  • group:将多个item元素包装成一个菜单组。
  • item元素可以指定如下属性:
  • android:id:为菜单指定一个唯一标识
  • title:指定菜单项的标题
  • icon:指定菜单的图标
  • alphabeticShortcut:为菜单项指定字符串快捷键
  • numericShortcut:为菜单项指定数字快捷键
  • checkable:设置该菜单项是否可选
  • checked:设置该菜单项是否已经被选中
  • visible:设置该菜单项是否可见
  • enable:设置该菜单项是否可用
  • group元素可以指定如下属性:
  • checkableBehavier:指定该组菜单的选择行为,可指定为none(不选)、all(多选)、single(单选)三个值。
  • menuCategory:对菜单进行分类,指定菜单的优先级,有效值为container、system、secondary、alternative。
  • visible:指定改组菜单是否可见。
  • enable:指定改组菜单是否可用。
  • 在程序中定义了菜单项资源后,接下来是重写onCreateOptionsMenu(用于创建选项菜单)、onCreateContextMenu(用以创建上下文菜单)方法,在这些方法中调用MenuInflater对象的inflate方法加载指定资源对应的菜单即可。
  • 示例:


    
        
        
        
        
    





    
        
            
            
                
                
                
                

            
        

    

    
    
    
    

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // 装填R.menu.menu_main的菜单,并添加到menu中
        MenuInflater inflater = new MenuInflater(this);
        inflater.inflate(R.menu.menu_main,menu);
        return super.onCreateOptionsMenu(menu);
    }

    @Override
    public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) {
        super.onCreateContextMenu(menu, v, menuInfo);
        // 装填R.menu.context对应的菜单,并添加到menu中
        MenuInflater inflater = new MenuInflater(this);
        inflater.inflate(R.menu.context,menu);
        menu.setHeaderIcon(R.drawable.nvshengtouxiang);
        menu.setHeaderTitle("请选择背景颜色");

    }

    /**
     * 上下文菜单中菜单项被点击是触发该方法
     * @param item
     * @return
     */
    @Override
    public boolean onContextItemSelected(MenuItem item) {
        // 勾选该菜单项
        item.setChecked(true);
        switch (item.getItemId()){
            case R.id.red:
                item.setChecked(true);
                tvMenu.setBackgroundColor(Color.RED);
                break;
            case R.id.green:
                item.setChecked(true);
                tvMenu.setBackgroundColor(Color.GREEN);
                break;
            case R.id.blue:
                item.setChecked(true);
                tvMenu.setBackgroundColor(Color.BLUE);
                break;
        }

        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        if (item.isCheckable()){
            // 勾选该菜单项
            item.setChecked(true);
        }
        // 判断单击的是那个菜单项,并有针对性的作出响应
        switch (item.getItemId()){
            case R.id.menu_01:
                tvMenu.setText("menu_01");
                break;
            case R.id.menu_02:
                tvMenu.setText("menu_02");
                break;
            case R.id.menu_03:
                tvMenu.setText("menu_03");
                break;
            case R.id.plain_item:
                tvMenu.setText("plain_item");
                break;
        }

        return true;
    }

样式资源

  • Style资源保存在/res/style/文件夹下,其根元素为 resource 元素,该元素可包含多个 style 子元素,每个 style 元素定义一个样式。style 一般可指定如下两个属性:
  • name:样式名
  • parent:指定该样式所继承的父样式,此时的继承符合Java的继承规则。
  • style元素可以包含多个 item 元素,每一个 item 元素定义一个格式项。
  • 示例:
    
    
    
    

主题资源

  • 与样式资源非常类似,保存在/res/values/目录下,以 resource 元素为根元素,style 元素为子元素。
  • 其与样式资源的区别主要体现在:
  • 主题不能作用于单个View,主题应对整个应用中的所有Activity起作用,或者对指定的Activity起作用。
  • 主题定义的格式应该是改变窗口外观的格式,例如窗口标题、窗口外观等。

属性资源

  • 属性资源文件保存在/res/values/文件夹下,其根元素也是 resource 元素,resource 元素包含下述两个子元素:
  • attr 子元素:定义一个属性
  • declare-styleable子元素:定义一个styleable对象,每个styleable对象就是一组attr属性集合
  • 在自定义组件的构造器中通过AttributeSet对象来获取属性。
  • 示例:
    
    
    
    
        
    
package com.fpp.status.customview;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.os.Handler;
import android.os.Message;
import android.util.AttributeSet;
import android.widget.ImageView;

import com.fpp.status.R;

import java.util.Timer;
import java.util.TimerTask;

/**
 * @author fupengpeng
 * @description 描述
 * @data 2018/4/18 0018 15:26
 */

public class AlphaImageView extends ImageView {

    // 图片透明度每次改变的大小
    private int alphaDelta = 0;
    // 记录图片当前的透明度
    private int curAlpha = 0;
    // 每隔多少毫秒透明度改变一次
    private final int SPEED = 300;
    Handler handler = new Handler(){
        @Override
        public void handleMessage(Message msg) {
            if (msg.what == 0x123){
                // 每次增加curAlpha的值
                curAlpha += alphaDelta;
                if (curAlpha > 255){
                    curAlpha = 255;
                }
                // 修改该ImageView的透明度
                AlphaImageView.this.setAlpha(curAlpha);
            }
        }
    };

    public AlphaImageView(Context context, AttributeSet attrs){
        super(context,attrs);
        TypedArray typedArray = context.obtainStyledAttributes(attrs, R.styleable.AlphaImageView);
        // 获取duration参数
        int duration = typedArray.getInt(R.styleable.AlphaImageView_duration,0);
        // 计算图片透明度每次改变的大小
        alphaDelta = 255 * SPEED / duration;

    }

    @Override
    protected void onDraw(Canvas canvas) {
        this.setImageAlpha(curAlpha);
        super.onDraw(canvas);
        final Timer timer = new Timer();
        // 按固定间隔发送消息,通知系统改变图片的透明度
        timer.schedule(new TimerTask() {
            @Override
            public void run() {
                Message msg = new Message();
                msg.what = 0x123;
                if (curAlpha >= 255){
                    timer.cancel();
                }else {
                    handler.sendMessage(msg);
                }
            }
        },0,SPEED);

    }
}

            

原始资源

  • 除了上述各资源以外,Android可能还用到其他资源(例如声音等),而这些资源一般保存在下述两个目录下:
  • 位于 /res/raw/ 目录下,Android SDK 会处理该目录下的原始资源,Android SDK 会在R清单类中为该目录下的资源生成一个索引项。其在Java代码中和XML中使用同上述资源类似。
  • 位于 /assets/ 目录下,该目录下是更加彻底的原始资源,Android应用通过AssetManager来管理该目录下的原始资源。AssetManager是一个专门管理 /assets/ 目录下的原始资源的管理器类,一般使用 InputStream open(String fileName)方法(获取资源文件的输入流)和AssetFileDescriptor openFd(String fileName)方法(获取对资源文件进行描述的对应的AssetFileDescriptor对象,再通过AssetFileDescriptor对象获取原始资源。)来获取对应的资源文件。
  • 示例:
    // 播放assets文件夹下的声音文件
    public void assets(View resource) {
        // 获取应用的AssetManager
        AssetManager am = getAssets();
        try {
            // 获取指定文件对应的AssetFileDescriptor
            AssetFileDescriptor afd = am.openFd("haojiubujian.mp3");
            MediaPlayer mediaPlayer2 = new MediaPlayer();
            // 使用MediaPlayer加载指定的声音文件
            mediaPlayer2.setDataSource(afd.getFileDescriptor());
            mediaPlayer2.prepare();
            // 播放声音
            mediaPlayer2.start();

        } catch (IOException e) {
            e.printStackTrace();
        }

    }
    // 播放raw文件夹下的声音文件
    public void raw(View resource) {
        // 直接根据声音文件的id来创建MediaPlayer
        MediaPlayer mediaPlayer1 = MediaPlayer.create(this, R.raw.haojiubujian);
        // 播放声音
        mediaPlayer1.start();
    }
   /**
     * 播放raw文件夹下视频文件
     */
    private void playRawVideo() {
        mVideoView.setVideoURI(Uri.parse("android.resource://" + getPackageName() + "/raw/" + R.raw.massif));
        mVideoView.start();
    }

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