關於小程序項目結構,框架介紹,組件說明等,請查看微信小程序官方文檔,關於以下貼出來的代碼部分我只是截取了一些片段,方便說明問題,如果需要查看完整源代碼,可以在我的項目庫中下載:
https://e.coding.net/dwBurning/ReallyWantToApi.git
https://e.coding.net/dwBurning/LazyOrders.git
睡一覺醒來,看到微信公眾號推送的一篇雞湯文,叫做《不會,我可以學!!!》深受鼓舞,回顧這些年,每天忙於業務開發,留給自己的學習時間並不多,一直很仰慕那些大牛們,夢想着自己有一天也能成為同樣牛逼的人物,無奈只是一個普普通通的碼農,但是夢想總是要有的,萬一哪天實現了呢?
言歸正傳,還是回到小程序的話題上,隨着Vue這兩年的火爆,前后端完全分離的設計模式已經深入人心了,微信小程序就是該模式下的典型應用,至於該模式有什么優勢,我就不說了,隨便搜一下都能檢索出來大量的文章,那么接下來的篇幅,就介紹一下小程序的前端代碼。
前后端完全分離,按理一定會涉及到http請求跨域的問題,但是小程序通過wx.request發起請求的時候,並未涉及到跨域,為何?其實想想也知道,wx.request肯定不是通過ajax直接發請求到你的服務器的,而是先把請求交給微信的服務端,然后再由微信的服務端轉發請求到你的服務器,每一個請求都在微信服務端做了中轉,當然這個是小程序正式發布上線后的實現,那么,本地開發的時候是怎么解決這個問題的呢?
本地開發的時候,我搭建的http站點都是直接在本地跑的,也沒有固定IP,用微信小程序的開發工具照樣能拿到請求的數據,且沒有跨域,這就要研究一下這個開發工具了,打開微信小程序開發工具的安裝目錄,你會發現里邊有一個node.exe的文件,啟動開發工具的時候,在進程中能找到node.exe的進程,關於這個進程的描述,寫的很清楚,Node.js;JavaScript服務端到這里真相已經明了。
解決了跨域的問題,我們來看看首頁的前端代碼,如下圖所示,首頁分為三個部分,上邊的輪播,左邊導航,右邊菜單
輪播是微信小程序提供的組件swiper,直接拿示例代碼,改一改就是了
<!-- swiper 輪播圖片 --> <view class="top"> <swiper class="swiper" indicator-dots="true" autoplay="true" interval="5000" duration="1000"> <block wx:for="{{movies}}" wx:for-index="index"> <swiper-item> <image src="{{item.url}}" class="slide-image" mode="aspectFill" /> </swiper-item> </block> </swiper> </view>
/** * 頁面的初始數據 */ data: { movies: [{ url: app.globalData.url + '?fileName=1.jpg' }, { url: app.globalData.url + '?fileName=2.jpg' }, { url: app.globalData.url + '?fileName=3.jpg' } ], navLeftItems: [], navRightItems: [], curNav: 1, curIndex: 0 },
左邊導航是菜單的分類,右邊顯示了這個分類下的菜單明細,這個就涉及到我們的實體設計了,通過我們的swagger界面接口測試http://localhost:8089/api/Category,可以拿到接口的數據,下面我先貼出來,只關注前端的同學或者沒有.Net開發環境的同學,可以直接在JS文件中貼上去,就可以預覽到效果了。
此段的重點就在數組下標的綁定:data-index="{{index}}",
每一次點擊通過JQuery獲取到這個index:index = parseInt(e.target.dataset.index),
然后右邊就綁定這個數組下標對應得數據:<block wx:for="{{navRightItems[curIndex].Menus}}">

{ "Code": 0, "Message": "Success", "Context": [ { "CategoryId": 1, "CategoryName": "經濟快餐", "Menus": [ { "MenuId": 1, "CategoryId": 1, "MenuName": "腐竹炒肉", "ImgPath": "http://localhost:8089/api/lazyorders?fileName=11.jpg", "Price": 15 }, { "MenuId": 2, "CategoryId": 1, "MenuName": "芹菜香干", "ImgPath": "http://localhost:8089/api/lazyorders?fileName=12.jpg", "Price": 14 }, { "MenuId": 3, "CategoryId": 1, "MenuName": "農家小炒肉", "ImgPath": "http://localhost:8089/api/lazyorders?fileName=13.jpg", "Price": 18 }, { "MenuId": 4, "CategoryId": 1, "MenuName": "青瓜炒蛋", "ImgPath": "http://localhost:8089/api/lazyorders?fileName=14.jpg", "Price": 14 } ] }, { "CategoryId": 2, "CategoryName": "精美小炒", "Menus": [ { "MenuId": 5, "CategoryId": 2, "MenuName": "茄子煲", "ImgPath": "http://localhost:8089/api/lazyorders?fileName=25.jpg", "Price": 28 }, { "MenuId": 6, "CategoryId": 2, "MenuName": "小龍蝦", "ImgPath": "http://localhost:8089/api/lazyorders?fileName=26.jpg", "Price": 88 } ] } ] }
/** * 生命周期函數--監聽頁面加載 */ onLoad: function(options) { var _this = this; util.checkSession(); wx.request({ url: app.globalData.urlCategory, success: function(res) { _this.setData({ navLeftItems: res.data.Context, navRightItems: res.data.Context }) } }) }, //事件處理函數 switchRightTab: function(e) { // 獲取item項的id,和數組的下標值 let id = e.target.dataset.id, index = parseInt(e.target.dataset.index); // 把點擊到的某一項,設為當前index this.setData({ curNav: id, curIndex: index }) },
<!--左側欄--> <view class="nav_left"> <block wx:for="{{navLeftItems}}"> <view class="nav_left_items {{curNav == item.CategoryId ? 'active' : ''}}" bindtap="switchRightTab" data-index="{{index}}" data-id="{{item.CategoryId}}"> {{item.CategoryName}} </view> </block> </view> <!--右側欄--> <view class="nav_right"> <scroll-view scroll-y="true" style="height: 100%"> <block wx:for="{{navRightItems[curIndex].Menus}}"> <view class="nav_right_items"> <navigator url="details/details?menuId={{item.MenuId}}"> <image class='nav_right_items_image' src="{{item.ImgPath}}"></image> </navigator> <text>{{item.MenuName}}</text> <text class='price_text'>{{item.Price}}元/份</text> <navigator url="details/details?menuId={{item.MenuId}}"> <image class='add_image' src='/images/add.png'></image> </navigator> </view> </block> </scroll-view> </view>
前端的設計就完成了,當然還有CSS相關的代碼,因為有完整的源代碼,這里就不貼了,貼一下對應的C#實體類吧!

/// <summary> /// 分類 /// </summary> public class Category { /// <summary> /// 主鍵ID /// </summary> public int CategoryId { get; set; } /// <summary> /// 分類 類別名 /// </summary> public string CategoryName { get; set; } /// <summary> /// 該類別下的菜單 /// </summary> public List<Menu> Menus { get; set; } } /// <summary> /// 菜單表 /// </summary> public class Menu { /// <summary> /// 菜單ID /// </summary> public int MenuId { get; set; } /// <summary> /// 類別ID /// </summary> public int CategoryId { get; set; } /// <summary> /// 菜單名 /// </summary> public string MenuName { get; set; } /// <summary> /// 對應的圖片路徑 /// </summary> public string ImgPath { get; set; } /// <summary> /// 單價 /// </summary> public decimal Price { get; set; } }