zoukankan      html  css  js  c++  java
  • Material Design 使用总结

    本文对Material Design Library里面的库类的使用做一个简单的汇总,方便以后能快速查询、快速上手使用。本文包括以下内容:

    • Color Palette
    • Toolbar
    • AppBarLayout
    • CollapsingToolbarLayout
    • CoordinatorLayout
    • DrawerLayout、NavigationView
    • Floating Action Button (FAB)
    • Snackbar
    • TabLayout
    • TextInputLayout

    如有遗漏,欢迎大家留言告知。我会持续补充,谢谢~。

    要使用Material Design Library ,首先得将依赖库加入到项目中,在appbuild.gradle中(dependencies{ }),添加如下:

     compile 'com.android.support:design:24.0.0'

    1 Color Palette

    我们可以定义状态栏、ActionBar(或ToolBar)、导航栏等等颜色。可以通过如下方式:

    修改res/values/styles.xml文件如下:

    <resources>
    
        <!-- Base application theme. -->
        <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
            <!-- Customize your theme here. -->
            <item name="colorPrimary">@color/colorPrimary</item>
            <item name="colorPrimaryDark">@color/colorPrimaryDark</item>
            <item name="colorAccent">@color/colorAccent</item>
        </style>
    
    </resources>

    当然了,可自定义的不仅仅就上面示例中的3个,你还可以自定义如下图所示的区域的颜色:

    Color Palette

    例如,你可以修改窗口背景色:

     <item name="android:windowBackground">@color/colorAccent</item>
    • 1
    • 1

    2 Toolbar、AppBarLayout、CollapsingToolbarLayout

    参考我的另一篇文章【玩转AppBarLayout,更酷炫的顶部栏 】

    3 CoordinatorLayout

    参考我的另一篇文章【CoordinatorLayout的使用如此简单 】

    4 DrawerLayout、NavigationView

    在很多应用中都使用到了Drawer导航,在Design Support Library中,提供了DrawerLayout,看看如何使用的吧!

    首先,需要将Android.support.v4.widget.DrawerLayout作为布局的根标签,然后android.support.design.widget.NavigationView作为其中的子标签。如下所示:

    <?xml version="1.0" encoding="utf-8"?>
    <android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        android:id="@+id/drawer_layout"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:fitsSystemWindows="true">
    
        <RelativeLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent">
    
            <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_centerInParent="true"
                android:text="hello world!" />
    
        </RelativeLayout>
    
        <android.support.design.widget.NavigationView
            android:id="@+id/navigation_view"
            android:layout_width="wrap_content"
            android:layout_height="match_parent"
            android:layout_gravity="start"
            app:headerLayout="@layout/drawer_header"
            app:menu="@menu/drawer" />
    </android.support.v4.widget.DrawerLayout>
    

    NavigationView包含两个引用,一个是导航里面的头部,另一个是菜单项,res/layout/drawer_header如下:

    <?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="150dp"
        android:background="?attr/colorPrimaryDark"
        android:gravity="bottom"
        android:orientation="vertical"
        android:padding="16dp"
        android:theme="@style/ThemeOverlay.AppCompat.Dark">
    
        <TextView
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="头部"
            android:textAppearance="@style/TextAppearance.AppCompat.Body1" />
    
    </LinearLayout>

    res/menu/drawer.xml如下:

    <?xml version="1.0" encoding="utf-8"?>
    <menu xmlns:android="http://schemas.android.com/apk/res/android">
    
        <group android:checkableBehavior="single">
            <item
                android:id="@+id/home"
                android:checked="true"
                android:icon="@drawable/home"
                android:title="主页" />
            <item
                android:id="@+id/theme"
                android:icon="@drawable/theme"
                android:title="主题" />
            <item
                android:id="@+id/settings"
                android:icon="@drawable/setting"
                android:title="设置" />
        </group>
    
        <item android:title="二级菜单">
            <menu>
                <item
                    android:icon="@drawable/favorite"
                    android:title="收藏" />
                <item
                    android:icon="@drawable/ablum"
                    android:title="相册" />
                <item
                    android:icon="@drawable/friends"
                    android:title="好友" />
            </menu>
        </item>
    
    </menu>

    然后,可以在我们的Activity里面响应菜单点击:

    
    public class MainActivity extends Activity 
                   implements NavigationView.OnNavigationItemSelectedListener {
    
        private DrawerLayout mDrawerLayout;
        private NavigationView mNavigationView;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
    
            mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
            mNavigationView = (NavigationView) findViewById(R.id.navigation_view);
    
            mNavigationView.setNavigationItemSelectedListener(this);
    
    
        }
    
        @Override
        public boolean onNavigationItemSelected(MenuItem menuItem) {
    
    
            // int id = menuItem.getItemId();
            String title = (String) menuItem.getTitle();
            Toast.makeText(this, "您点击了 " + title, Toast.LENGTH_SHORT).show();
    
            return super.onContextItemSelected(menuItem);
    
        }
    
    
    }
    

    效果如下: 
    Drawer

    5 Floating Action Button (FAB)

    直接将android.support.design.widget.FloatingActionButton放入布局中即可,例如,要放到右下:

     <android.support.design.widget.FloatingActionButton
                android:id="@+id/fab"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_alignParentBottom="true"
                android:layout_alignParentRight="true"
                android:layout_marginRight="@dimen/activity_horizontal_margin"
                android:layout_marginBottom="@dimen/activity_vertical_margin"
                android:src="@drawable/ic_done" />

    如果需要监听点击,直接通过setOnclickListener即可:

     fab = (FloatingActionButton) findViewById(R.id.fab);
            fab.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    Toast.makeText(MainActivity.this, "您点击了FAB", Toast.LENGTH_SHORT).show();
                }
            });

    FAB

    6 Snackbar

    一般情况下,如果你想给用户一个简短的响应反馈,我们会选择使用Toast,现在我们有了另一个选择啦:Snackbar

    看看如何使用

    public void onClick(View v) {
    
        View.OnClickListener onClickListener = new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Toast.makeText(MainActivity.this,
                        "您点击了Snackbar中的确定", Toast.LENGTH_SHORT).show();
            }
        };
    
        Snackbar sb = Snackbar.make(v,
                "在这里是Snackbar显示内容",
                Snackbar.LENGTH_LONG);
    
        //添加点击"按钮"-->"确定"及其对应的点击事件
        sb.setAction("确定", onClickListener);
        //设置"确定"的颜色
        sb.setActionTextColor(Color.RED);
    
        //设置显示消息的文字颜色
        View view = sb.getView();
        ((TextView) view.findViewById(R.id.snackbar_text)).setTextColor(Color.GREEN);
    
        //设置背景颜色
        view.setBackgroundColor(Color.GRAY);
        //设置透明度
        view.setAlpha(0.5f);
    
        //设置位置,Snackbar本质是一个LinearLayout
        ViewGroup.LayoutParams lp = view.getLayoutParams();
        LinearLayout.LayoutParams llp = new LinearLayout.LayoutParams(lp.width, lp.height);
        llp.gravity = Gravity.TOP;
    
        view.setLayoutParams(llp);
    
        //显示
        sb.show();
    
    }
    

    看看效果:

    SnackBar

    7 TabLayout

    先看布局文件:

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        tools:context="com.hc.materialdesign.MainActivity">
    
    
        <android.support.design.widget.TabLayout
            android:id="@+id/tablayout"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="?attr/colorPrimary"
            android:theme="@style/ThemeOverlay.AppCompat.Dark"
            app:tabGravity="center"
            app:tabMode="fixed" />
    
        <android.support.v4.view.ViewPager
            android:id="@+id/viewpager"
            android:layout_width="match_parent"
            android:layout_height="0dp"
            android:layout_weight="1" />
    
    </LinearLayout>

    注意到,TabLayout中有两个陌生的属性

    • app:tabMode:可以取如下两个值, 
      • fixed:表示Tab不能滚动
      • scrollable:表示Tab可以滚动,此时不管tabGravity取何值,都是按照从左到右排过去,即相当于app:tabGravity="left"(当然了,实际中没有left这个值,只是我们可以这么去理解)
    • app:tabGravity:可以取如下两个值, 
      • fill:当tabMode取fixed时(即tab不能滚动时),tab的所有子标签填充tab的宽度
      • center:当tabMode去fixed时,tab中所有子标签居中显示。

    为了有更加直观的理解,看几张图片:

    app:tabMode="scrollable"

    scrollable

    app:tabMode="fixed"且 app:tabGravity="center"

    center

    app:tabMode=fixed且 app:tabGravity="fill"

    fill

    好了,接下来看看Activity里面具体代码:

    public class MainActivity extends AppCompatActivity {
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            //初始化ViewPager及其适配器
            MyPagerAdapter adapter = new MyPagerAdapter(getSupportFragmentManager());
            ViewPager viewPager = (ViewPager) findViewById(R.id.viewpager);
            //将ViewPager与适配器关联
            viewPager.setAdapter(adapter);
            //TabLayout
            TabLayout tabLayout = (TabLayout) findViewById(R.id.tablayout);
    
            //将ViewPager与TabLayout关联
            tabLayout.setupWithViewPager(viewPager);
    
            //设置指示器的颜色
            tabLayout.setSelectedTabIndicatorColor(Color.GREEN);
        }
    
        static class MyPagerAdapter extends FragmentStatePagerAdapter {
    
            public MyPagerAdapter(FragmentManager fm) {
                super(fm);
            }
    
            @Override
            public Fragment getItem(int position) {
                return MyFragment.newInstance(position);
            }
    
            @Override
            public int getCount() {
                return 3;
            }
    
            @Override
            public CharSequence getPageTitle(int position) {
                return "Tab " + position;
            }
        }
    }

    其中MyFragment很简单,只是用于产生一个简单的Fragment:

    public class MyFragment extends Fragment {
        private static final String TAB_POSITION = "tab_position";
    
        public MyFragment() {
    
        }
    
        public static MyFragment newInstance(int tabPosition) {
            MyFragment fragment = new MyFragment();
            Bundle args = new Bundle();
            args.putInt(TAB_POSITION, tabPosition);
            fragment.setArguments(args);
            return fragment;
        }
    
        @Nullable
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
            Bundle args = getArguments();
            int tabPosition = args.getInt(TAB_POSITION);
            TextView tv = new TextView(getActivity());
            tv.setGravity(Gravity.CENTER);
            tv.setText("Text in Tab #" + tabPosition);
            return tv;
        }
    }
    
    

    运行效果前面已经贴出来了,这里就不再复制显示了。

    8 TextInputLayout

    TextInputLayout主要是用在登录注册方面。

    先看看效果:

    Floating Labels for EditText

    老规矩,从布局文件开始:

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        android:padding="@dimen/activity_vertical_margin"
        tools:context="com.hc.materialdesign.MainActivity">
    
    
        <android.support.design.widget.TextInputLayout
            android:id="@+id/userName"
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
    
            <EditText
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:hint="用户名"
                android:inputType="textEmailAddress"
       />
    
        </android.support.design.widget.TextInputLayout>
    
        <android.support.design.widget.TextInputLayout
            android:id="@+id/email"
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
    
            <EditText
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:hint="邮箱"
                android:inputType="textEmailAddress" />
    
        </android.support.design.widget.TextInputLayout>
    
        <Button
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:onClick="login"
            android:text="注册" />
    </LinearLayout>
    

    可以看到,其实就是将我们平时用的Edit控件放入到android.support.design.widget.TextInputLayout里面,并且里面只能放一个Edit,否则会报错。这点让我不太满意,但是可是是在实现上放入多个Edit不太好控制吧。

    再看MainActivity对输入框数据的验证:

    public class MainActivity extends AppCompatActivity {
        TextInputLayout userNameWrapper;
        TextInputLayout emailWrapper;
        String emailFormate = "^(\w)+(\.\w+)*@(\w)+((\.\w+)+)$";
    
        private Pattern pattern = Pattern.compile(emailFormate);
    
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            userNameWrapper = (TextInputLayout) findViewById(R.id.userName);
            emailWrapper = (TextInputLayout) findViewById(R.id.email);
    
    
        }
    
        private boolean checkUserName() {
            String userName = userNameWrapper.getEditText().getText().toString();
            if (userName.trim().equals(""))
                return false;
            else
                return true;
        }
    
        private boolean checkEmail() {
            String email = emailWrapper.getEditText().getText().toString();
            Matcher matcher = pattern.matcher(email);
            return matcher.matches();
        }
    
        public void login(View v) {
            View view = getCurrentFocus();
    
            if (view != null) {
                ((InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE)).
                        hideSoftInputFromWindow(view.getWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);
            }
            if (!checkUserName()) {
    
                userNameWrapper.setError("用户名不正确!");
    
            } else {
                userNameWrapper.setError("");
                if (!checkEmail()) {
                    emailWrapper.setError("邮箱格式不正确!");
    
                } else {
                    emailWrapper.setError("");
                }
            }
    
    
        }
    }
    

    如果数据是错误的,我们只需通过setError函数来显示即可!

    最后,可能你以及注意到,界面中,用到了各种颜色。也就是说,里面的颜色我们是可以定制的,在你的style文件里面添加部分item即可:

    <resources>
    
        <!-- Base application theme. -->
        <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
            <!-- Customize your theme here. -->
            <item name="colorPrimary">@color/colorPrimary</item>
            <item name="colorPrimaryDark">@color/colorPrimaryDark</item>
    
    
            <!-- Label color in TRUE state and bar color FALSE and TRUE State -->
            <item name="colorAccent">#00ff00</item>
            <item name="colorControlNormal">#00ffff</item>
            <item name="colorControlActivated">#ff00ff</item>
            <item name="android:textColorHint">#00ffff</item>
            <item name="textColorError">#ff0000</item>
        </style>
    
    </resources>
  • 相关阅读:
    Delphi Class of 类引用
    Class-reference types 类引用类型--快要失传的技术
    最简单的TabHost
    修改一些IntelliJ IDEA 11的设置,使Eclipse的使用者更容易上手(转)
    uva 10494
    uva748
    uva 465
    高精度
    uva 694
    uva414
  • 原文地址:https://www.cnblogs.com/GeChuangGuang/p/5703406.html
Copyright © 2011-2022 走看看