本項目是通力基金的商業級項目,聲明:在此僅用于交流學習。該項目主要有三個主要功能模塊:1、基金模塊:包括基金的查詢、展示等功能;2、賬戶模塊:包括登錄、充值、提現、收藏等功能;3、輔助模塊:消息中心、幫助、意見反饋等。
項目運行首先會有一個閃屏頁,然后進入的是一個新手引導頁(只顯示一次),可以向右滑動,共4頁圖片,當滑到最后一張時,圖片中會有一個進入的按鈕,點擊這個按鈕進可以進入到App的主頁。?
主頁中:下面是4個導航,根據用戶點擊的不同,會切換至不同的界面。
ok,我們現在開始來分享一下這個軟件的實現過程。新手引導頁的話很簡單,很多人都做過。總之就是使用一個viewPager來實現,使用一個pagerAdapter來填充viewpager的內容,如果直接繼承pagerAdapter這個抽象類,需要重寫getCount()、isViewFromObject()、destroyItem()、instantiateItem()等4個方法才可以為viewpager填充內容。我以前的博客中詳細介紹了新手引導頁的開發,傳送門:[http://blog.csdn.net/sdksdk0/article/details/50043843?](http://blog.csdn.net/sdksdk0/article/details/50043843)? ? ?[點擊打開鏈接](http://blog.csdn.net/sdksdk0/article/details/50043843)。所以這里就不再重復寫了。
下面來分享一個這個主界面的設計,首先使用的是一個非常經典的方法:TabHost。TabHost允許將多個控件放在同一個區域內,然后通過點擊按鈕來替換,這樣就不用調用FragmentManager來進行替換的操作。
下面來看一下這個主界面的布局文件:
~~~
<?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">
<TabHost
android:id="@android:id/tabhost"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:visibility="visible">
<RelativeLayout
android:id="@+id/content_view"
android:layout_width="match_parent"
android:layout_height="match_parent">
<FrameLayout
android:id="@android:id/tabcontent"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_above="@+id/bottom_view">
<fragment
android:id="@+id/jijin_view"
android:name="com.zhilinghui.fund.fragment.JijinFragment"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<fragment
android:id="@+id/member_view"
android:name="com.zhilinghui.fund.fragment.MemberFragment"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<RelativeLayout
android:id="@+id/fs_view"
android:layout_width="match_parent"
android:layout_height="match_parent">
<fragment
android:name="com.zhilinghui.fund.fragment.FSFragment"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</RelativeLayout>
<fragment
android:id="@+id/settings_view"
android:name="com.zhilinghui.fund.fragment.SettingsFragment"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</FrameLayout>
<RelativeLayout
android:id="@+id/bottom_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:background="@drawable/tab_bar_bg"
android:gravity="center_vertical">
<TabWidget
android:id="@android:id/tabs"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<ImageView
android:id="@+id/tab_selected"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:adjustViewBounds="true"
android:background="@drawable/tab_scroll"
android:contentDescription="@null"
android:visibility="gone" />
<ImageView
android:id="@+id/notice_logo"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_marginRight="12dp"
android:layout_marginTop="10dp"
android:adjustViewBounds="true"
android:background="@drawable/notice_logo"
android:contentDescription="@null"
android:visibility="gone" />
</RelativeLayout>
</RelativeLayout>
</TabHost>
<RelativeLayout
android:id="@+id/index_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/transparent"
android:orientation="vertical">
<android.support.v4.view.ViewPager
android:id="@+id/viewpager_index"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<com.zhilinghui.fund.widget.PageControlView
android:id="@+id/pageControlView_index"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:layout_marginBottom="30dp" />
</RelativeLayout>
~~~
在Activity中要找到這些按鈕:
~~~
setContentView(R.layout.a_main);
bottom_view = (RelativeLayout) findViewById(R.id.bottom_view);
mTabHost = (TabHost) findViewById(android.R.id.tabhost);
mTabs = (TabWidget) findViewById(android.R.id.tabs);
mTabs.setDividerDrawable(null);
~~~
從上面的布局文件中,我們可以看到,這個TabHost里面是加了圖片和文字的,這樣看起來會更加美觀一點,添加圖片的方法如下:
~~~
tab01 = (LinearLayout) LayoutInflater.from(this).inflate(R.layout.item_tab_view, null);
tab01.setBackgroundResource(R.drawable.tab_jijin_drawable);
tab02 = (LinearLayout) LayoutInflater.from(this).inflate(R.layout.item_tab_view, null);
tab02.setBackgroundResource(R.drawable.tab_member_drawable);
tab03 = (LinearLayout) LayoutInflater.from(this).inflate(R.layout.item_tab_view, null);
tab03.setBackgroundResource(R.drawable.tab_fs_drawable);
tab04 = (LinearLayout) LayoutInflater.from(this).inflate(R.layout.item_tab_view, null);
tab04.setBackgroundResource(R.drawable.tab_settings_drawable);
mTabHost.addTab(mTabHost.newTabSpec("0")
.setIndicator(tab01)
.setContent(R.id.jijin_view));
mTabHost.addTab(mTabHost.newTabSpec("1")
.setIndicator(tab02)
.setContent(R.id.member_view));
mTabHost.addTab(mTabHost.newTabSpec("2")
.setIndicator(tab03)
.setContent(R.id.fs_view));
mTabHost.addTab(mTabHost.newTabSpec("3")
.setIndicator(tab04)
.setContent(R.id.settings_view));
mTabHost.setCurrentTab(0); //設當前 Tab 為 0
~~~
添加點擊事件:
~~~
mTabHost.setOnTabChangedListener(mOnTabChangeListener);
~~~
設置適配器:
~~~
// 導航欄適配器
adapter = new NavigatePagerAdapter(this, ids, mIndexOverListener, page_control);
viewpager.setAdapter(adapter);
viewpager.setOnPageChangeListener(mOnPageChangeListener);
~~~
(因為我虛擬機的分辨率沒設置好,貌似圖片有點失真了)

在第一頁中上面那個可以滑動的自然也是一個viewpager了,下面就是一個listview第一個頁面還具有下列刷新(包括上下箭頭和時間)和加載更多的功能。基金是有一個后臺的,從服務器傳輸數據顯示在這個輪播條上面。下面的數據條目也是一樣,因為這里沒有過多的圖片,所以不需要設置圖片緩存(而某些項目的listview條目中有圖片的話,我們就應該要考慮增加圖片緩存功能了,從而避免太耗用戶流量或內存溢出等問題)。當我們點擊這個基金進去的時候,例如第一個“活期通力寶",就會跳轉到另一個界面,這里詳細的描述了該基金的信息,例如基金經理、基金代碼、收益率、同類排名等內容,然后還會加上一個折線圖,從而更加清晰的描述這個項目,給用戶帶來更好的體驗。還有就是當數據與后臺傳輸的時候,在這個界面還會有一個圓圈在轉動,若網絡無法連接,則會有一個我們自定義好了的提示界面,說網絡無法連接。(在這里不提供公司的后臺接口,所以這里的數據虛擬化了顯示)。
~~~
@Override
public void onRefresh() {
mController.execute(new UIAsyncTask(getFavHandler, mDatabaseAdapter, BaseHandlerUI.REQUEST_GET_FAV));
}
@Override
public void onLoadMore() {
onLoad();
}
private void onLoad() {
mListView.stopRefresh();
mListView.stopLoadMore();
}
~~~
~~~
@SuppressLint("SetJavaScriptEnabled")
private void loadUrl() {
showProgressDialog(context, context.getString(R.string.dlg_loading));
thread = new Thread(new Runnable() {
@SuppressWarnings("deprecation")
@Override
public void run() {
webview.getSettings().setJavaScriptEnabled(true);
// webview.getSettings().setPluginsEnabled(true);
webview.getSettings().setSupportZoom(true);
webview.getSettings().setBuiltInZoomControls(true);
//加載url前,設置圖片阻塞
webview.getSettings().setBlockNetworkImage(true);
webview.loadUrl(bean.url);
MyWebViewClient myWebView = new MyWebViewClient();
webview.setWebViewClient(myWebView);
}
});
thread.start();
}
~~~
全部基金listview的適配:
~~~
@SuppressLint("ResourceAsColor")
public class Text_Adapter
extends BaseAdapter {
List<FundTitleBean> items = new ArrayList<FundTitleBean>();
private LayoutInflater mInflater;
private OnClickListener mOnClick;
Context context;
private boolean left = true;
public Text_Adapter(Context context, List<FundTitleBean> items,
OnClickListener mOnClick, boolean left) {
super();
this.context = context;
this.mInflater = LayoutInflater.from(context);
this.items = items;
this.mOnClick = mOnClick;
this.left = left;
}
@Override
public int getCount() {
return items.size();
}
@Override
public Object getItem(int position) {
return position;
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder; // ViewHolder 是內部類, 只有一個成員(name) TextView
if (convertView == null) {
holder = new ViewHolder();
convertView = mInflater.inflate(R.layout.item_list_txt_view, null);
holder.name = (TextView) convertView
.findViewById(R.id.name); // 這里的 name 是一個 TextView
convertView.setTag(holder);
} else {
holder = (ViewHolder) convertView.getTag(); //getTag 返回: 一個 Object 引用
}
holder.name.setOnClickListener(mOnClick);
holder.name.setTag(position);
holder.name.setText(items.get(position).name);
if (items.get(position).isSelected) {
if (left) {
convertView.setBackgroundResource(R.drawable.choose_s_left);
} else {
convertView.setBackgroundResource(R.drawable.choose_s_right);
}
} else {
convertView.setBackgroundResource(R.drawable.choose_list_selector);
}
return convertView;
}
private class ViewHolder {
TextView name;
}
}
~~~
無網絡時的錯誤提示Activity代碼:
~~~
public void initView() {
title = (TextView) findViewById(R.id.title_txt);
title.setText(getString(R.string.dlg_net_err));
left_btn = (TextView) findViewById(R.id.left_btn);
left_btn.setVisibility(View.VISIBLE);
left_btn.setOnClickListener(this);
left_btn.setVisibility(View.VISIBLE);
right_btn = (TextView) findViewById(R.id.right_btn);
right_btn.setVisibility(View.GONE);
}
~~~
說到這里,還需要分享一個知識就是關于Application的使用:在很多大型項目中都會有
~~~
Application和Actovotu,Service一樣是android框架的一個系統組件,當android程序啟動時系統會創建一個 application對象,用來
* 存儲系統的一些信息。通常我們是不需要指定一個Application的,這時系統會自動幫我們創建,如果需要創建自己 的Application,也很簡
* 單創建一個類繼承 Application并在manifest的application標簽中進行注冊(只需要給Application標簽增加個name屬性把自己
* 的 Application的名字定入即可)。
* android系統會為每個程序運行時創建一個Application類的對象且僅創建一個,所以Application可以說是單例 (singleton)模式的一個類.且
* application對象的生命周期是整個程序中最長的,它的生命周期就等于這個程序的生命周期。因為它是全局 的單例的,所以在不同的Activity,Service中
* 獲得的對象都是同一個對象。所以通過Application來進行一些,數據傳遞,數據共享 等,數據緩存等操作。
* <p/>
* 二.程序的入口
* Android使用Google Dalvik VM,相對于傳統Java VM而言有著很大的不同,在Sun的Java體系中入口點和標準c語言一樣是main(),
* 而每個Android程序都包含著一個Application實例,一個Application實例中有多個Activity、 Service、ContentProvider或
* Broadcast Receiver。
* 其實在android.app.Application這個包的onCreate才是真正的Android入口點,只不過大多數開發者無需重寫該類。
* <p/>
* 第一步、寫一個全局的單例模式的MyApplication繼承自Application 重寫onCreate
* 第二步、配置全局的Context
* <application
android:name="com.zhilinghui.fund.app.GFFApp"></application>
~~~
ok,今天主要是分享了一下這個商業級基金項目的導航設置和第一個界面(主界面)的設計與功能介紹。下一次將分享”個人中心“、”交易界面"、“幫助中心”的設計與實現,當然,在下一篇博客中我會貼出這個項目的源碼哦!今天的就暫不提供源碼,歡迎關注!
### 記住:下一次博客會貼出整個項目的源碼。可免費下載使用!歡迎關注!
- 前言
- 內存溢出的解決方案
- 安卓消息推送解決方案
- 語言識別和聊天機器人的實現
- 抽屜效果的實現(DrawerLayout和SlidingMenu的對比)
- 植物大戰僵尸經典開發步驟
- 屏幕適配全攻略
- 安卓圖像處理入門教程
- android開發常用工具箱
- java基礎知識總結
- 剖析軟件外包項目
- java基礎知識——網絡編程、IO流
- 安卓性能優化手冊
- 電商活動中刮刮卡的實現
- Android系統的安全設計與架構
- AsnycTask的內部的實現機制
- Android應用UI設計流程
- 數據結構與算法,每日一道
- html5全解析
- 深入解讀XML解析
- 新聞客戶端案例開發
- 細說Http協議
- win10+ubuntu雙系統安裝方案
- 隨機驗證碼實現案例
- 動態數組的實現案例
- 猜拳游戲案例
- 商業級項目——基金客戶端的架構設計與開發(上)