iOS的圖片拉伸與拼接

問題描述

對于如下圖片,類似于聊天軟件的氣泡背景圖片,在布局時要在圖片中添加文案:


1.原有圖片userGuide_dottedline.png

需要實現(xiàn)的功能時,圖片的高度隨著文案的行數(shù)增加而增加,但是對于去泡的邊緣虛線部分,不能出現(xiàn)拉伸的情況。

解決方案

1.首先想到的是自己去截取中間的部分進行重復(fù)平鋪,而在截取時需要注意的是,進行重復(fù)平鋪的中間部分在和上下部分進行拼接時可能存在不均勻的情況,所以截取需要平鋪的部分就要稍微注意些。


2.實現(xiàn)思路示意

實現(xiàn)代碼如下:

#pragma mark - 截取當前image對象rect區(qū)域內(nèi)的圖像,height為文本高度
- (UIImage *)extendImageWithImage:(UIImage *)image withHeight:(CGFloat)height {
    CGFloat screenScale = [UIScreen mainScreen].scale;
    
    // 20 / 212 是userGuide_dottedline 3倍圖的高度(212px)以及想要重復(fù)的部分高度(20px)的比例
    CGFloat upperPartHeight = (image.size.height * 97 / 212) * screenScale;
    CGRect upperPartRect = CGRectMake(0, 0, image.size.width * screenScale, upperPartHeight);
    UIImage *upperPartImage = [self subImageWithImage:image inRect:upperPartRect];
    
    CGFloat middlePartHeight = (image.size.height * 20 / 212) * screenScale;
    CGRect middlePartaRect = CGRectMake(0, upperPartHeight, image.size.width * screenScale, middlePartHeight);
    UIImage *middlePartImage = [self subImageWithImage:image inRect:middlePartaRect];
    
    CGFloat bottomPartHeight = (image.size.height * 95 / 212) * screenScale;
    CGRect bottomPartaRect = CGRectMake(0, upperPartHeight + middlePartHeight, image.size.width * screenScale, bottomPartHeight);
    UIImage *bottomPartImage = [self subImageWithImage:image inRect:bottomPartaRect];
    
    NSInteger repeatTimes = (int)ceilf((height + middlePartHeight - image.size.height)* screenScale / middlePartHeight);
    UIImage *mergedImage = [self mergeImage:upperPartImage withImage:middlePartImage];
    
    for (NSInteger index = 0; index < repeatTimes; index ++) {
        mergedImage = [self mergeImage:mergedImage withImage:middlePartImage];
    }
    
    mergedImage = [self mergeImage:mergedImage withImage:bottomPartImage];
    mergedImage = [self scaledImageWithImage:mergedImage withScale:(1/screenScale)];
    
    return mergedImage;
}

// 截取指定image對象rect區(qū)域內(nèi)的圖像
- (UIImage *)subImageWithImage:(UIImage *)image inRect:(CGRect)subAreaRect {
    CGImageRef subAreaImageRef = CGImageCreateWithImageInRect(image.CGImage, subAreaRect);
    
    UIImage *subAreaImage = [UIImage imageWithCGImage:subAreaImageRef];
    
    CGImageRelease(subAreaImageRef);
    
    return subAreaImage;
}

// 將兩個圖片合并成一張圖片
- (UIImage*)mergeImage:(UIImage*)firstImage withImage:(UIImage*)secondImage
{
    CGImageRef firstImageRef = firstImage.CGImage;
    CGFloat firstWidth = CGImageGetWidth(firstImageRef);
    CGFloat firstHeight = CGImageGetHeight(firstImageRef);
    
    CGImageRef secondImageRef = secondImage.CGImage;
    CGFloat secondWidth = CGImageGetWidth(secondImageRef);
    CGFloat secondHeight = CGImageGetHeight(secondImageRef);
    
    CGSize mergedSize = CGSizeMake(MAX(firstWidth, secondWidth), firstHeight + secondHeight);
    UIGraphicsBeginImageContext(mergedSize);
    [firstImage drawInRect:CGRectMake(0, 0, firstWidth, firstHeight)];
    [secondImage drawInRect:CGRectMake(0, firstHeight, secondWidth, secondHeight)];
    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    return image;
}

// 等比縮放圖片
- (UIImage *)scaledImageWithImage:(UIImage *)image withScale:(CGFloat)scale {
    CGSize scaledSize = CGSizeMake(image.size.width*scale, image.size.height*scale);
    UIGraphicsBeginImageContext(scaledSize);
    [image drawInRect:CGRectMake(0, 0, scaledSize.width, scaledSize.height)];
    UIImage *scaledImage = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    
    return scaledImage;
}

2.通過查文檔,發(fā)現(xiàn)蘋果有現(xiàn)有方法resizableImageWithCapInsets:可以實現(xiàn)該功能,一行代碼解決問題[??]
參考如下簡書,寫的非常詳細:
http://www.itdecent.cn/p/a577023677c1
http://www.itdecent.cn/p/c9cbbdaa9b02

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容