標籤:
對於這個話題 我想到
1 第一個解決方案就是使用 webView 比較經典
把所有複雜工作都交給控制項本身去處理了, 但是好像好多需要自訂的地方 沒法從 webView獲得響應回調 :(估計也可以實現 也比較複雜,而且 這個需要對 html編碼進行分析理解剝離等)
2 富文本方式 核心架構 coretext
圖文混排 一點問題都沒有 關鍵是怎麼對 靶心圖表片 或者連結 進行觸發響應
要點:
(1)首先要封裝的要相對獨立 拓展也方便 首當其衝就是 和服務端約定的 資料模型 CoreTextModel 要敲定:
我們約定是 一段文字中間用 "[1]" 做標記 [我是圖片id] ,同時傳一個圖片 和相應標題文字 "圖片數組" 圖片數組元素中主鍵就是這個圖片id .
我們開發過程中是預設一張圖片 點擊這個圖 展示解釋 所以 直接知道這張圖片大小 進行繪製, 如果是網狀圖片 那麼就應該預留這張圖片的大小 因為 繪製如果 不知道大小 線性繪製過程 就會卡在這 如果預知大小 那麼就會繼續往下繪製, 變成非同步
所以圖片大小(寬高) 當然 也是這個圖片數組元素 作為資料模型中的.屬性元素而存在
如果是連結呢?? 所以 [1] 也可以認為是 [我是連結的id] 然後模型中有個參數 區分 當前 需要插入的是圖片 還是 連結 或者其他需求 然後進行枚舉判斷
那麼有幾種枚舉 就要有幾個資料結構 比如這裡 就有coreTextImageData && coreTextLinkData 和 繪製的過程 就需要 有幾種可變數組 枚舉的過程 分別進行add
(2)其次 繪製
首先來說 繪製 就是 直接動用底層CoreText
繪製圖片\連結 都是動用底層 我現在的能力 是 調用\理解\修改\拓展 還不能自如的 寫任意 自己想寫東西 我想 也許當我到了這種程度 才能成為 大神吧 哈哈 路漫漫修遠兮 吾將上下求索
1,遍曆資料模型 CoreTextModel 數組 對 文本 夾雜"[1]"的重新組織
2,最終得到的富文本NSMutableAttributedString *result 都會通過 result.length 知道當前的圖片/連結coreTextImageData/ coreTextLinkData的起始位置.
3,繪製 draw
a,繪製圖片 (1)CTRunDelegateCallbacks callbacks;建立記憶體儲存空間(怎麼使用 百度 一大堆) (2) 使用0xFFFC作為空白的預留位置 拼入 add 在result裡
b,繪製連結 或者是一段連續子串 觸發 給他指定顏色 底線 大小等 同樣 也add在result裡
c,最終得到的 result 通過 建立CTFramesetterRef執行個體 獲得 獲得要緩制的地區的高度 再將產生好的CTFrameRef執行個體
ctFrame 和計算好的緩制高度height儲存到CoreTextData執行個體中,最後返回CoreTextData執行個體(CoreTextData 這個結構體裡面至少有ctFrame,height,result, coreTextImageData , coreTextLinkData )
ctFrame 這個 相當於 OC中 的 CGFrame , 但是成鏡像且上下顛倒
盜個圖:
CGFrame
Core Text CTFrameRef
所以如果觸發點擊事件 那麼 還需要把這個繪製座標 轉成UI座標
4,那麼 現在 得到的result
在指定點擊的UIView 要使用iPhone重繪機制drawRect 觸發方法[self setNeedsDisplay] 調用- (void)drawRect:(CGRect)rect
就可展示出 這個視圖了.
- (void)drawRect:(CGRect)rect{ [super drawRect:rect]; if (self.data == nil) {//self.data 是 CoreTextData return; } CGContextRef context = UIGraphicsGetCurrentContext(); CGContextSetTextMatrix(context, CGAffineTransformIdentity); CGContextTranslateCTM(context, 0, self.bounds.size.height); CGContextScaleCTM(context, 1.0, -1.0); CTFrameDraw(self.data.ctFrame, context);
//對所有指定位置的圖片填充 for (CoreTextImageData * imageData in self.data.imageArray) { UIImage *image = [UIImage imageNamed:imageData.name]; if (image) { CGContextDrawImage(context, imageData.imagePosition, image.CGImage); } }
}
(4)觸發點擊事件
原理: 觸發點擊UIView 通過 UIGestureRecognizer * tapRecognizer.
點擊事件中 可以獲得 CGPoint point = [recognizer locationInView:self]; 點擊焦點 . 那麼 判斷 這個 點擊焦點 是不是 圖 或者 是不是可觸發的連結 或者字串 就可以了
a,遍曆 self.data.imageArray 判斷 是否存在滿足條件 如果滿足 則 用 通知post 去觸發點擊響應
我使用了一個參數 focusRect 把焦點地區放大 一圈 防止 圖片 太小點擊 不上 這個是我開發過程中 需要也是必要的 大家用不用 看心情
連結 就舉一反三吧 網上講解也一大堆 目的達到了
好的連結參考
http://blog.csdn.net/sinat_27706697/article/details/46286717 http://blog.csdn.net/sinat_27706697/article/details/46299953 http://ju.outofmemory.cn/entry/53649 https://github.com/kobe1941/HFCoreTextDemo //唐https://github.com/tangqiaoboy/iOS-Pro
下一篇 接著講 觸發彈出 一個對話方塊的邏輯
iOS 圖文混排 連結 可點擊