APICloud AVM多端開發 | 企業app開發解析:案例展現、加盟申請功能源碼

本項目中前端採用 APICloud AVM 多端開發技術進行企業app開發,要點包括 TabLayout 佈局、swiper 輪播圖、rich-text 富文本、scroll-view 滾動視圖、下拉刷新等。前端

項目後端則是使用的 APICloud 數據雲 3.0 自定義雲函數來構建的。node

使用APICloud 多端技術進行企業app開發,實現一套代碼多端運行,支持編譯成 Android & iOS App 以及微信小程序。項目源碼在 https://github.com/apicloudcom/company-display 倉庫的 widget 目錄下。git


使用步驟:github

  1. 使用 APICloud Studio 3 做爲開發工具。
  2. 下載本項目源碼。
  3. 在開發工具中新建項目,並將本源碼導入新建的項目中,注意更新,config.xml 中的 appid 爲你項目的 appid。
  4. 使用 AppLoader 進行真機同步調試預覽。
  5. 或者提交項目源碼,併爲當前項目雲編譯自定義 Loader 進行真機同步調試預覽。
  6. 雲編譯 生成 Android & iOS App以及微信小程序源碼包。

若是以前未接觸過 APICloud 開發,建議先了解一個簡單項目的初始化、預覽、調試和打包等操做,請參考APICloud 多端開發快速上手教程web


網絡請求接口封裝

在 utils/model.js 中,爲每個網絡請求接口封裝了對應方法,如首頁獲取輪播圖接口 Model.getbannersList,這些方法最終會調用 Model.request 方法,在 Model.request 方法中對整個項目的請求進行統一管理,包括處理傳入參數、拼裝請求 url、設置請求頭等,最後調用 api.ajax 方法發起請求。ajax

使用示例:json

// 經過 import 引入
import {Model} from "../../utils/model.js"

// 調用 Model 對象方法
Model.getbannersList({}, (res) => {});

TabBar 和導航欄的實現

首頁使用了 TabLayout 佈局來實現 TabBar 和導航欄,在 config.xml 裏面配置 content 字段,值爲 json 文件路徑,在 json 文件中配置 TabBar、導航欄和頁面信息。小程序

// config.xml
<content src="config.json" />

config.json 文件內容以下,設置了 navigationBar 的背景色和標題文字顏色,設置了 tabBar 每項的 icon 和文字,以及每項對應的頁面。後端

{
  "name": "root",
  "hideNavigationBar": false,
  "navigationBar": {
    "background": "#fff",
    "color": "#000",
    "hideBackButton": true
  },
  "tabBar": {
    "scrollEnabled": false,
    "background": "#fff",
    "shadow": "#f1f1f1",
    "color": "#5e5e5e",
    "selectedColor": "#333333",
    "preload": 0,
    "frames": [{
      "name": "page1",
      "url": "pages/index/index.stml",
      "title": "首頁"
    }, {
      "name": "page2",
      "url": "pages/case/case.stml",
      "title": "案例"
    }, {
      "name": "page3",
      "url": "pages/join/join.stml",
      "title": "加盟代理"
    }],
    "list": [{
      "iconPath": "images/toolbar/home@no_selected.png",
      "selectedIconPath": "images/toolbar/home@selected.png",
      "text": "首頁"
    }, {
      "iconPath": "images/toolbar/case@no_selected.png",
      "selectedIconPath": "images/toolbar/case@selected.png",
      "text": "案例"
    }, {
      "iconPath": "images/toolbar/join@no_selected.png",
      "selectedIconPath": "images/toolbar/join@selected.png",
      "text": "加盟代理"
    }]
  }
}

從上面的企業app開發效果圖中咱們能夠看到」加盟代理「頁面隱藏了導航欄,而其它頁面沒有隱藏。」加盟代理「頁面路徑爲 pages/join/join.stml,咱們參照微信小程序的語法,在同目錄下放置了 join.json 文件,在裏面配置 navigationStyle 字段爲 custom。微信小程序

{
  "navigationBarTitleText": "加盟代理",
  "backgroundColor": "#FFFFFF",
  "navigationStyle":"custom"
}

在首頁 index.stml 的 apiready 方法裏面則監聽了 tabBar 每項的點擊事件,在 App 端,咱們須要在點擊事件裏面動態設置頁面顯示、隱藏導航欄。

// index.stml
api.addEventListener({
	name:'tabitembtn'
}, function(ret){
	var hideNavigationBar = ret.index == 2;
	api.setTabLayoutAttr({
		hideNavigationBar: hideNavigationBar,
		animated: false
	});
	api.setTabBarAttr({
		index: ret.index
	});
});

首頁輪播圖

首頁路徑爲 pages/index/index.stml,裏面輪播圖使用 swiper 組件實現,使用 v-for 指令循環 swiper-item,bannersList 爲定義的數組類型的屬性,在首頁的 apiready 方法裏面,咱們經過調用 getbannersList 方法發起網絡請求,獲取輪播圖片列表數據後賦值給 bannersList 屬性。這裏監聽了 swiper-item 的 click 事件,點擊後須要跳轉到詳情頁面。

<view style={'height:'+swiperHeight+'px;'} class="swiper-box">
	<swiper class="swiper" autoplay indicator-dots indicator-color="rgba(255,255,255,0.2)" indicator-active-color="rgba(51,51,51,1)">
		<swiper-item v-for="(item_,index_) in bannersList" data-index={index_} onclick="bindBanner">
			<image src={item_.image} class="banner-image" mode="aspectFill"></image>
		</swiper-item>
	</swiper>
</view>

輪播圖的寬度跟隨屏幕寬度變化,高度則經過計算屬性 swiperHeight 來動態計算獲得。

computed:{
	swiperHeight(){
		return api.winWidth*0.42;
	}
}

rich-text 富文本的使用

APICloud這個企業app開發項目是信息展現類型,運營人員會在管理後臺直接編輯提交富文本信息,所以在項目中不少地方使用了 rich-text 來展現信息,好比在首頁中,產品展現和關於信息部分就是使用的 rich-text,若是沒爲 rich-text 設置高度,其高度就爲裏面內容的高度。

<view class="goods">
	<rich-text v-if={{product_description}} nodes={product_description} />
</view>
<view class="about">
	<rich-text v-if={{about_us}} nodes={about_us} />
</view>

rich-text 用於展現 HTML String 片斷,在從服務器獲取到 HTML String 後,咱們調用 $util.fitRichText 方法處理了一下 HTML String,在 fitRichText 方法中爲 img 標籤加了最大寬度的限制,以防止圖片寬度過大致使顯示溢出。

// util.js
fitRichText(richtext, width){
   var str = `<img style="max-width:${width}px;"`;
   var result = richtext.replace(/\<img/gi, str);
   return result;
}

下拉刷新、滾動到底部加載更多

在」案例「頁面(pages/case/case.stml),經過 scroll-view 實現了案例列表展現,同時實現了下拉刷新、滾動到底部加載更多功能。

<scroll-view class="main" scroll-y enable-back-to-top refresher-enabled refresher-triggered={refresherTriggered} onrefresherrefresh={this.onrefresherrefresh} onscrolltolower={this.onscrolltolower}>
	<view>
		<view class="item" data-id={item.id} onclick={this.openCaseInfo} v-for="(item, index) in caseList">
			<image src={item.cover_img} class="item-img"></image>
			<text class="item-title">{{item.title}}</text>
		</view>
	</view>
   <view class="footer">
       <text class="loadDesc">{loadStateDesc}</text>
   </view>
</scroll-view>

下拉刷新使用了 scroll-view 默認的下拉刷新樣式,使用 refresher-enabled 字段來開啓下拉刷新,爲 refresher-triggered 字段綁定了 refresherTriggered 屬性來控制下拉刷新狀態,須要注意的是,在刷新的事件回調方法裏面,咱們須要主動設置 refresherTriggered 的值爲 true,在數據加載完成後再設置爲 false,這樣綁定的值有變化,刷新狀態才能通知到原生裏面。

onrefresherrefresh(){
	this.data.refresherTriggered = true;
	this.loadData(false);
}

滾動到底部監聽了 scroll-view 的 scrolltolower 事件,在滾動到底部後自動加載更多數據,加載更多和下拉刷新都是調用 loadData 方法請求數據,經過 loadMore 參數來進行區分,作分頁請求處理。

loadData(loadMore) {
	if (this.data.loading) {
		return;
	}
	this.data.loading = true;
	var that = this;
	var limit = 10;
	var skip = loadMore?that.data.skip+1:1;
	let params = {
		data:{
			values:{
				status: 1,
				skip: skip,
				limit: limit
			}
		}
	}
	Model.getCasesList(params, (res) => {
		if (res && res.status == 0) {
			let items = res.data.items;
			that.data.haveMoreData = items.length == limit;
			if (loadMore) {
				that.data.caseList = that.data.caseList.concat(items);
			} else {
				that.data.caseList = items;
			}
			that.data.skip = skip;
		} else {
			that.data.haveMoreData = false;
		}
		that.data.loading = false;
		that.data.refresherTriggered = false;
	});
}

scroll-view 滾動到指定元素

在」加盟代理「頁面(pages/join/join.stml),最外層是一個 scroll-view,裏面有分類列表、分類內容兩項,點擊分類列表裏面某項後會自動滾動到對應的分類內容處,讓分類內容可見。

<scroll-view class="main" scroll-y scroll-into-view={viewId} scroll-with-animation enable-back-to-top refresher-enabled refresher-threshold="90" refresher-triggered={refresherTriggered} onrefresherrefresh={this.onrefresherrefresh}>
	<!-- 分類列表 -->
	<view class="cate">
		<view class="cate-item" v-for="(item,index) in list" data-id={item.id} onclick="onitemclick">
			<image src={item.image} class="cate-img"></image>
			<text class="cate-word">{item.title}</text>
		</view>
	</view>
	<!-- 分類內容 -->
	<view class="content">
		<view class="content-item" v-for="(item,index) in list" id={'content'+item.id}>
			<text class="content-title">{item.title}</text>
			<rich-text nodes={item.content} />
		</view>
	</view>
</scroll-view>

滾動到指定視圖經過 scroll-view 的 scroll-into-view 屬性實現,這裏綁定了 viewId 屬性,在分類列表項的點擊事件 onitemclick 裏面,改變 viewId 屬性的值,這個值是分類內容裏面某項的 id,這樣就實現了滾動到指定視圖。

onitemclick(e) {
	var id = e.currentTarget.dataset.id;
	this.data.viewId = 'content' + id;
	this.data.viewId = null;
}

平臺差別化處理

在多端開發中,不免會遇到不一樣平臺差別化的地方,須要在運行期間作判斷處理,爲此在 utils/util.js 中封裝了 isApp 方法,裏面經過 api.platform 屬性判斷當前運行環境。

// util.js
isApp(){
   if (api.platform && api.platform == 'app') {
       return true;
   }
   return false;
}

例如在 pages/web/web.stml 中,咱們使用 v-if、v-else 指令,經過區分平臺使用不一樣的組件來加載 web 連接。

<view class="main">
	<frame v-if="$util.isApp()" class="web-view" name="web" url={api.pageParam.link}></frame>
	<web-view v-else class="web-view" src={api.pageParam.link}></web-view>
</view>

本文只是簡單介紹了用APICloud AVM多端工具進行企業app開發須要注意的問題,想要熟練掌握開發技巧,仍是須要開發者本身經過源碼不斷實踐哦!

相關文章
相關標籤/搜索