之前的項(xiàng)目中有個(gè)需求:將一個(gè)比較長(zhǎng)的列表頁(yè)(用的UITableView)截圖然后分享到微信托呕。貼出實(shí)現(xiàn)方法:
- (UIImage *)captureScrollView:(UIScrollView *)scrollView {
UIImage* image = nil;
UIGraphicsBeginImageContext(scrollView.contentSize);
{
CGSize s = scrollView.contentSize;
//第一個(gè)參數(shù)表示區(qū)域大小槽地。第二個(gè)參數(shù)表示是否是非透明的。如果需要顯示半透明效果苔严,需要傳NO笛臣,否則傳YES。第三個(gè)參數(shù)就是屏幕密度了涵妥,關(guān)鍵就是第三個(gè)參數(shù)。
UIGraphicsBeginImageContextWithOptions(s, NO, [UIScreen mainScreen].scale);
CGPoint savedContentOffset = scrollView.contentOffset;
CGRect savedFrame = scrollView.frame;
scrollView.contentOffset = CGPointZero;
scrollView.frame = CGRectMake(0, 0, SCREEN_WIDTH, scrollView.contentSize.height);
[scrollView.layer renderInContext: UIGraphicsGetCurrentContext()];
image = UIGraphicsGetImageFromCurrentImageContext();
scrollView.contentOffset = savedContentOffset;
scrollView.frame = savedFrame;
}
UIGraphicsEndImageContext();
if (image != nil) {
return image;
}
return nil;
}
所截的圖如下:
這個(gè)方法能順利將tableView截成長(zhǎng)圖坡锡,但是突然有天需求變了:
手續(xù)費(fèi)那一欄不能分享出去蓬网,What?
然后我的思路是截兩次鹉勒,第一次把手續(xù)費(fèi)以上的部分截下來(lái)帆锋,第二次把手續(xù)費(fèi)以下的部分截出來(lái),然后兩張圖片合成一張圖片禽额。思路有了锯厢,操起鍵盤就是一梭子代碼:
/**
Description 從圖片中按指定的位置大小截取圖片的一部分
@param image 原始的圖片
@param rect 要截取的區(qū)域
@return 截取出的圖片
*/
- (UIImage *)imageFromImage:(UIImage *)image inRect:(CGRect)rect{
CGImageRef sourceImageRef = [image CGImage];//將UIImage轉(zhuǎn)換成CGImageRef
/**以下為錯(cuò)誤寫法*/
CGImageRef newImageRef = CGImageCreateWithImageInRect(sourceImageRef, CGRectMake(rect.origin.x, rect.origin.y, rect.size.width, rect.size.height));//按照給定的矩形區(qū)域進(jìn)行剪裁
UIImage *newImage = [UIImage imageWithCGImage:newImageRef];//將CGImageRef轉(zhuǎn)換成UIImage
return newImage;//返回剪裁后的圖片
}
/**
Description 圖片上下拼接
@param topImage 上圖片
@param bottomImage 下圖片
@return 拼接后的圖片
*/
- (UIImage *)composeImgWithTopImage:(UIImage *)topImage bottomImage:(UIImage *)bottomImage {
if (bottomImage == nil) {
return topImage;
}
CGFloat topImageH = topImage.size.height;
CGFloat topImageW = topImage.size.width;
CGFloat bottomImageH = bottomImage.size.height;
CGFloat bottomImageW = bottomImage.size.width;
CGFloat totalHeight = SCREEN_WIDTH*topImageH/topImageW + SCREEN_WIDTH*bottomImageH/bottomImageW;
CGSize offScreenSize = CGSizeMake(SCREEN_WIDTH, totalHeight);
UIGraphicsBeginImageContextWithOptions(offScreenSize, NO, [UIScreen mainScreen].scale);
CGRect rectTop = CGRectMake(0, 0, SCREEN_WIDTH, SCREEN_WIDTH*topImageH/topImageW);
[topImage drawInRect:rectTop];
CGRect rectBottom = CGRectMake(0, SCREEN_WIDTH*topImageH/topImageW, SCREEN_WIDTH, SCREEN_WIDTH*bottomImageH/bottomImageW);
[bottomImage drawInRect:rectBottom];
UIImage* imagez = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return imagez;
}
然后我兩次調(diào)用截圖傳的rect是
CGRect headerClipRect = CGRectMake(0, 0, image.size.width, [self.tableView rectForSection:2].origin.y);
CGRect footerClipRect = CGRectMake(0, [self.tableView rectForSection:3].origin.y, image.size.width, self.tableView.contentSize.height - [self.tableView rectForSection:3].origin.y);
準(zhǔn)備就緒,來(lái)看看截出來(lái)的圖是什么樣子的:
image.png
what脯倒,我到底哪里錯(cuò)了实辑?一臉驚恐
然后反復(fù)查找發(fā)現(xiàn)- (UIImage *)captureScrollView:(UIScrollView *)scrollView
這個(gè)方法截出的長(zhǎng)圖的大小并不是傳入的scrollView
的contentSize,而是長(zhǎng)寬各自乘以手機(jī)分辨率[UIScreen mainScreen].scale
藻丢,所以對(duì)長(zhǎng)圖進(jìn)行切割的時(shí)候剪撬,按照給定的矩形區(qū)域進(jìn)行剪裁應(yīng)該這樣傳值
CGImageRef newImageRef = CGImageCreateWithImageInRect(sourceImageRef, CGRectMake(rect.origin.x*[UIScreen mainScreen].scale, rect.origin.y*[UIScreen mainScreen].scale, rect.size.width*[UIScreen mainScreen].scale, rect.size.height*[UIScreen mainScreen].scale));//按照給定的矩形區(qū)域進(jìn)行剪裁
最后的截圖合成之后應(yīng)該是這樣的:
image.png