【android】如何實現猿題庫題目的排版


最近我們的產品來了個新的模塊,類似猿題庫一樣,給學生做題提高成績的。

要求如下:

1:支持單選、多選、填空題

2:支持圖片文字混排

3:輸入框有交互,排版精致美觀

4:為了體驗優化,不能使用網頁實現效果

花了兩個禮拜開發優化,效果看起來達到了猿題庫那種圖文、輸入框混排的效果,截圖如下:

  

 

因涉及到公司的核心業務,就不分享源碼了,講解下大概實現步驟

1:圖片文字混排

系統的TextView通過ImageGetter就可以原生實現對文本img標簽的支持,從而達到圖文混排的效果。

Html.fromHtml(text, asyncImageGetter, null);

具體實現步驟請參考Github上的一個庫https://github.com/zzhoujay/RichText

 

2:輸入框混排

如何實現一個自己的TextView,請參考此篇博客http://blog.csdn.net/yellowcath/article/details/27527275

下面是我具體的實現步驟,請在步驟1圖文混排源碼基礎上進行閱讀。

 

最后的UI結構應該是這樣子的,用輸入框蓋在透明的占位圖上,達到了輸入框混排的效果。

--容器

   --圖文混排TextView

   --輸入框A

   --輸入框B

   --輸入框C

 

2.0:根據題目答案數量,生成對應數量的輸入框,添加到容器中,設置為不可見

2.1:題目中的輸入框標記,通過正則表達式使用圖片Img標簽代替,src設置為:Input標簽+輸入框對應答案ID+該輸入框對應答案文字長度

2.2:在ImageGetter中,發現當前圖片包含Input標簽,則使用一個透明的占位圖代替,寬度為畫筆的文本尺寸*答案長度

2.3:參考本步驟開始給出的代碼地址,稍微加工下就可以拿來實現自己的TextView,用於逐行繪制時,獲取當前的寬度和高度。

2.4:在onDraw事件里,遇到當前繪制的Span是圖片類型,且src包含Input標簽的,獲取當前的高度和左邊距,通過下面代碼獲取圖片的寬度。

imgSpan.getDrawable().getBounds().width()

2.5:用步驟4取到的數據,設置MarginLeft和MarginTop,還有寬度,通過輸入框對應答案ID來找到2.0對應的輸入框,刷新其位置和寬度

 

 

3:細節優化

1:填空題的行高比選擇題的要大,為了防止兩行文本框擠在一起。

2:輸入框UI有很多狀態:做題狀態:未獲取焦點沒值、未獲取焦點有值、獲取焦點;校對答案: 答案正確、答案錯誤

3:輸入框超過答案的長度,使用省略號...截取掉超過的文本。

4:圖片、輸入框長度最長為一行,超過圖片等比縮放。

5:圖片添加緩存,加載中給占位圖,加載失敗點擊重試(文本框里的圖片是可以響應點擊事件的,詳情參考步驟1的源碼)

6:某行有大圖的情況下,文本、輸入框垂直居中顯示;反之如果圖片是小圖(數理化公式類型),則垂直居中顯示

7:使用FragmentStatePagerAdapter 代替 FragmentPagerAdapter作為大批量內容頁的適配器。

8:在開始答題的時候,我們已經獲取到了此次所需的題目和答案數據,正則匹配出里面的圖片url,在后台提前下載好到內存中。

后記

一開始遇到圖文輸入框混排,不能用WebView,立刻百度

結果這個需求願意分享的人很少,無奈之下只能自己一步一坑解決了。

 

下載猿題庫的apk包,反編譯,結果看花眼了也跟蹤不到題庫的相關代碼。

倒是在開啟了布局邊界之后,在仔細觀察猿題庫的題目時,發現填空題很多地方,繪制是重疊的,得出其原理是設置輸入框位置來實現的結論。

還好有上面兩個開源的作品,在次基礎上進行開發,有思路多了。

 

比較奇怪的是,猿題庫ViewPager頻繁切換的時候,是會有延遲的。

我們這個一旦打開就立刻呈現在用戶面前,圖片加載完成之后,再刷新占位圖,個人覺得這樣過程要好點。

歡迎大家一起交流,有啥疑問的請留言。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM