欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Android 新闻界面模拟ListView和ViewPager的应用

程序员文章站 2024-03-06 17:43:44
模拟新闻 app 的界面 1)写 listview 之前先写布局:  这里有两种 item 的布局:

模拟新闻 app 的界面

Android 新闻界面模拟ListView和ViewPager的应用

1)写 listview 之前先写布局:

 这里有两种 item 的布局:

<?xml version="1.0" encoding="utf-8"?>
<relativelayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="match_parent"
  android:layout_height="100dp"
  android:padding="10dp">


  <imageview
    android:layout_width="100dp"
    android:layout_height="60dp"
    android:id="@+id/imageview"
    android:background="@mipmap/ic_launcher"
    android:layout_centervertical="true"
    android:layout_alignparentright="true" />

  <textview
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="new text"
    android:id="@+id/tv_title"
    android:maxlines="3"
    android:layout_marginright="10dp"
    android:layout_alignparenttop="true"
    android:layout_alignparentleft="true"
    android:layout_toleftof="@+id/imageview" />

  <textview
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:textappearance="?android:attr/textappearancesmall"
    android:text="small text"
    android:id="@+id/tv_time"
    android:layout_alignparentbottom="true"
    android:layout_alignparentleft="true"/>
</relativelayout>

activity_item
<?xml version="1.0" encoding="utf-8"?>
<relativelayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:padding="10dp">

  <textview
    android:id="@+id/tv_title"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:text="@string/app_name"
    android:singleline="true"/>

  <linearlayout
    android:id="@+id/line1"
    android:layout_width="match_parent"
    android:layout_height="60dp"
    android:layout_below="@id/tv_title"
    android:layout_margintop="10dp">

    <imageview
      android:id="@+id/imageview1"
      android:layout_width="100dp"
      android:layout_height="60dp"
      android:layout_weight="1"
      android:layout_marginright="10dp"
      android:background="@mipmap/ic_launcher" />

    <imageview
      android:id="@+id/imageview2"
      android:layout_width="100dp"
      android:layout_height="60dp"
      android:layout_weight="1"
      android:layout_marginright="10dp"
      android:background="@mipmap/ic_launcher" />

    <imageview
      android:id="@+id/imageview3"
      android:layout_width="100dp"
      android:layout_height="60dp"
      android:layout_weight="1"
      android:background="@mipmap/ic_launcher" />
  </linearlayout>

  <textview
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:textappearance="?android:attr/textappearancesmall"
    android:text="small text"
    android:id="@+id/tv_time"
    android:layout_below="@id/line1"
    android:layout_alignparentleft="true"/>


</relativelayout>

activity_item2

第一种是单张图片,第二种是三张图片。

在 listview 添加的头部布局, 用 viewpager 实现滑动的效果:

<?xml version="1.0" encoding="utf-8"?>
<relativelayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="match_parent"
  android:layout_height="match_parent">

  <android.support.v4.view.viewpager
    android:id="@+id/vp"
    android:layout_width="match_parent"
    android:layout_height="200dp" />

  <textview
    android:id="@+id/tv_msg"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_centerhorizontal="true"
    android:layout_marginbottom="5dp"
    android:layout_alignbottom="@+id/vp"
    android:textcolor="#ddd"
    android:text="吴建明和中国外交"
    android:singleline="true" />

</relativelayout>

activity_item_header

最后是 listview 的布局;

<?xml version="1.0" encoding="utf-8"?>
<relativelayout 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:padding="10dp"
  tools:context="com.dragon.android.baseadapter.mainactivity">

  <listview
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:scrollbars="none"
    android:dividerheight="1dp"
    android:divider="#ccc"
    android:id="@+id/listview"/>
</relativelayout>

activity_main

2)listview 中要显示的数据这里先自己设定,不进行网络请求。

<?xml version="1.0" encoding="utf-8"?>
<resources>

  <string-array name="titles">
    <item>那些被捕上岸的不寻常的大鱼,往往成为大家关注的焦点。一种奇观和一段足以津津乐道的传奇经历。</item>
    <item>自2008年正式推出,杭州公共自行车在国内外圈粉无数,它超越了一道风景、一张名片的定义,成为杭州的生活方式。</item>
    <item>奥运历史上,像美国队单独重赛这样荒诞的场面也不时出现。</item>
    <item>在巴西里约奥运赛场上,菲尔普斯身上“神秘的东方红圈”走红。</item>
    <item>里约奥运会正式启幕,为国出征的运动员激战正酣。而在奥运赛场之外,一大波隐藏的民间运动高手也蠢蠢欲动。</item>
    <item>6月30日以来,第四轮强降雨给湖北造成严重损失。</item>
    <item>查阅世界上城市地下排水系统中的佼佼者,可以发现,那些真正的良心下水道,即使多年过去,仍在发挥效用。</item>
  </string-array>

  <string-array name="msgs">
    <item>吴建明和中国外交</item>
    <item>同性恋酒吧:是天堂也是地狱</item>
    <item>那些年,我们这样过端午</item>
    <item>马英九8年:从万人迷到受气包</item>
    <item>朝鲜外宣里的幸福平壤</item>
  </string-array>

</resources>

arrays

图片资源可以*添加

3)自定义适配器继承 baseadapter:

package com.dragon.android.baseadapter;

import android.content.context;
import android.view.layoutinflater;
import android.view.view;
import android.view.viewgroup;
import android.widget.baseadapter;
import android.widget.imageview;
import android.widget.textview;

import java.text.simpledateformat;
import java.util.date;
import java.util.list;
import java.util.locale;

/**
 * created by auser on 2016/9/8.
 */
public class myadapter extends baseadapter {

  private final context context;
  private list<data> mdata;

  public myadapter(context context, list<data> data) {
    this.mdata = data;
    this.context = context;
  }

  /**
   * @return item 的数量
   */
  @override
  public int getcount() {
    return mdata == null ? 0 : mdata.size();
  }

  /**
   * @param position
   * @param convertview <重点: 得到每个 item 将要显示的视图
   * @param parent
   * @return
   */
  @override
  public view getview(int position, view convertview, viewgroup parent) {
    view view;
    data data = getitem(position);
    if (position % 3 == 0) {
      view = layoutinflater.from(context).inflate(r.layout.acyivity_item_2, parent, false);
      imageview imageview1 = (imageview) view.findviewbyid(r.id.imageview1);
      imageview imageview2 = (imageview) view.findviewbyid(r.id.imageview2);
      imageview imageview3 = (imageview) view.findviewbyid(r.id.imageview3);
      imageview1.setimageresource(data.getimgresid()[0]);
      imageview2.setimageresource(data.getimgresid()[1]);
      imageview3.setimageresource(data.getimgresid()[2]);

    } else {
      view = layoutinflater.from(context).inflate(r.layout.activity_item, parent, false);
      imageview imageview = (imageview) view.findviewbyid(r.id.imageview);
      imageview.setimageresource(data.getimgresid()[0]);
    }
    textview tv_title = (textview) view.findviewbyid(r.id.tv_title);
    tv_title.settext(data.gettitle());

    textview tv_time = (textview) view.findviewbyid(r.id.tv_time);
    string time = new simpledateformat("hh:mm", locale.china).format(new date(data.gettime()));
    tv_time.settext(time);
    return view;
  }

  /**
   * 给开发者自己实现,一般用来的二道当前 position 位置的 数据
   * 当 item 可以在屏幕显示的时候,会调用 getview 且传递显示的 item 的位置
   *
   * @param position 新显示的 item 的位置
   * @return
   */
  @override
  public data getitem(int position) {
    // log.d("tag", position + "");
    return mdata.get(position);
  }

  /**
   * @param position 当用户设置了 listview 的item 的点击时间的时候,将此值作为 第四个参数 传递
   * @return
   */
  @override
  public long getitemid(int position) {
    return 10086;
  }

}

myadapter

4)因为头部布局使用 viewpager 实现,所以要添加自定义的适配器继承 pageradapter:

package com.dragon.android.baseadapter;

import android.support.v4.view.pageradapter;
import android.view.view;
import android.view.viewgroup;
import android.widget.imageview;

import java.util.list;

/**
 * created by auser on 2016/9/8.
 */
class mypageradapter extends pageradapter {

  private list<imageview> mlist;

  public mypageradapter(list<imageview> mlist) {
    this.mlist = mlist;
  }

  /**
   * 决定viewpager中能够显示几个子视图
   * @return 可滑动的边界
   */
  @override
  public int getcount() {

    // 2的31次方-1
    // mlist.size=5:0--4
    // position:0---9
    // 0%5=0,4%5=4,
    // 5%5=0,6%5=1....9%5=4
    return integer.max_value;
  }

  /**
   * 产生item.container:容器.--->viewpager
   * @param container
   * @param position
   * @return
   */
  @override
  public object instantiateitem(viewgroup container, int position) {
    // 将imageview添加到viewpager容器中.
    container.addview(mlist.get(position % mlist.size()));

    return mlist.get(position % mlist.size());
  }

  /**
   * 判断当前的view是否是第一次产生的.
   * @param view
   * @param obj
   * @return
   */
  @override
  public boolean isviewfromobject(view view, object obj) {

    return view == obj;
  }

  /**
   * 移除一个item
   * @param container
   * @param position
   * @param object
   */
  @override
  public void destroyitem(viewgroup container, int position, object object) {
    // 从容器中移除视图
    container.removeview(mlist.get(position % mlist.size()));
  }

}

mypageradapter

这里面要注意如何实现 viewpager 滑动时的循环效果 --- 即设置一个非常大的边界,循环显示。

5)需要一个容器来存放要展示的数据,这里封装一个 data 类

package com.dragon.android.baseadapter;

import java.util.arrays;

/**
 * created by auser on 2016/9/8.
 */
public class data {

  private int[] imgresid;
  private string title;
  private long time;

  @override
  public string tostring() {
    return "data{" +
        "imgresid=" + arrays.tostring(imgresid) +
        ", title='" + title + '\'' +
        ", time=" + time +
        '}';
  }

  public data() {
  }

  public data(string title, int[] imgresid, long time) {
    this.imgresid = imgresid;
    this.title = title;
    this.time = time;
  }

  public int[] getimgresid() {
    return imgresid;
  }

  public void setimgresid(int[] imgresid) {
    this.imgresid = imgresid;
  }

  public string gettitle() {
    return title;
  }

  public void settitle(string title) {
    this.title = title;
  }

  public long gettime() {
    return time;
  }

  public void settime(long time) {
    this.time = time;
  }
}

data

6)最后在 mainactivity 中对 listview 和 viewpager 配置适配器(同时实现文本随 viewpager 的滑动同步改变)

package com.dragon.android.baseadapter;

import android.os.bundle;
import android.support.v4.view.viewpager;
import android.support.v7.app.appcompatactivity;
import android.view.view;
import android.widget.imageview;
import android.widget.listview;
import android.widget.textview;

import java.util.arraylist;
import java.util.list;

public class mainactivity extends appcompatactivity {

  private listview listview;
  private list<data> mdata;
  private list<imageview> mlist;
  private viewpager mvp;
  private textview mtv;

  private int[] imgresids = {r.mipmap.c1, r.mipmap.c2, r.mipmap.c3,
      r.mipmap.c4, r.mipmap.c5, r.mipmap.c6, r.mipmap.c7, r.mipmap.c8,
      r.mipmap.c9, r.mipmap.c10, r.mipmap.c11, r.mipmap.c12, r.mipmap.c13};

  private int[] imageheaderids = {r.mipmap.a1,r.mipmap.a2,r.mipmap.a3,r.mipmap.a4,r.mipmap.a5};

  @override
  protected void oncreate(bundle savedinstancestate) {
    super.oncreate(savedinstancestate);
    setcontentview(r.layout.activity_main);

    listview = (listview) findviewbyid(r.id.listview);
    string[] stringarray = getresources().getstringarray(r.array.titles);

    mdata = new arraylist<>();
    initdata(stringarray);

    addheader();

    myadapter myadapter = new myadapter(this, mdata);
    listview.setadapter(myadapter);
  }

  /**
   * 添加头部布局 viewpager
   */
  private void addheader() {
    view view = getlayoutinflater().from(this).inflate(r.layout.activity_item_header, listview, false);
    listview.addheaderview(view);

    mvp = (viewpager) view.findviewbyid(r.id.vp);
    mtv = (textview) view.findviewbyid(r.id.tv_msg);
    string[] msgs = getresources().getstringarray(r.array.msgs);

    // 创建数据源.存放头部布局要展示的视图
    mlist = new arraylist<imageview>();
    for (int i = 0; i < imageheaderids.length; i++) {
      imageview iv = new imageview(this);
      iv.setbackgroundresource(imageheaderids[i]);
      mlist.add(iv);
    }
    mypageradapter adapter = new mypageradapter(mlist);
    mvp.setadapter(adapter);

    // 设置viewpager当前是第几个视图
    mvp.setcurrentitem(1000 * mlist.size());

    // mvp.setonpagechangelistener(listener);
    mvp.addonpagechangelistener(new viewpager.simpleonpagechangelistener() {

      @override
      public void onpageselected(int position) {
        string[] msgs = getresources().getstringarray(r.array.msgs);

        // 让标题随着viewpager的切换而切换
        mtv.settext(msgs[position % mlist.size()]);
      }
    });
  }

  /**
   * 创建数据源
   * @param stringarray
   */
  private void initdata(string[] stringarray) {
    int j = 0;
    for (int i = 0; i < stringarray.length; i++) {
      long l = system.currenttimemillis();
      if (i % 3 == 0) {
        mdata.add(new data(stringarray[i], new int[]{imgresids[j++], imgresids[j++], imgresids[j++]}, l + 1000000 * i));
      } else {
        mdata.add(new data(stringarray[i], new int[]{imgresids[j++]}, l + 1000000 * i));
      }
    }
  }
}

以上就是新闻界面的模拟示例,有需要的朋友可以看一下,谢谢大家对本站的支持!