#import <UIKit/UIKit.h>
@interface ImageFlowLayout : NSObject
@property (nonatomic, assign) CGFloat fixedHeight; // 固定图片高度
@property (nonatomic, assign) CGFloat horizontalSpacing; // 水平间距
@property (nonatomic, assign) CGFloat verticalSpacing; // 垂直间距
@property (nonatomic, assign) CGFloat containerWidth; // 容器宽度
// 布局完成回调,返回所有图片视图数组和最终容器所需高度
typedef void(^LayoutCompletionBlock)(NSArray<UIImageView *> *imageViews, CGFloat containerHeight);
// 主要布局方法
- (void)layoutWithImageUrls:(NSArray<NSString *> *)imageUrls
completion:(LayoutCompletionBlock)completion;
@end
#import "ImageFlowLayout.h"
@implementation ImageFlowLayout
- (instancetype)init {
self = [super init];
if (self) {
// 默认值设置
_fixedHeight = 24;
_horizontalSpacing = 8;
_verticalSpacing = 8;
}
return self;
}
- (void)layoutWithImageUrls:(NSArray<NSString *> *)imageUrls
completion:(LayoutCompletionBlock)completion {
if (imageUrls.count == 0) {
if (completion) {
completion(@[], 0);
}
return;
}
NSMutableArray *imageInfoArray = [NSMutableArray array];
__block NSInteger loadedCount = 0;
NSInteger totalCount = imageUrls.count;
// 创建并加载所有图片
for (NSString *url in imageUrls) {
UIImageView *imageView = [[UIImageView alloc] init];
imageView.contentMode = UIViewContentModeScaleAspectFit;
NSMutableDictionary *info = [NSMutableDictionary dictionary];
info[@"imageView"] = imageView;
[imageInfoArray addObject:info];
[imageView sd_setImageWithURL:[NSURL URLWithString:url] completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, NSURL *imageURL) {
if (image) {
// 计算等比例宽度
CGFloat aspectRatio = image.size.width / image.size.height;
info[@"width"] = @(self.fixedHeight * aspectRatio);
} else {
// 加载失败时使用默认宽度
info[@"width"] = @(self.fixedHeight);
}
loadedCount++;
if (loadedCount == totalCount) {
// 所有图片加载完成,进行布局
[self performLayoutWithImageInfo:imageInfoArray completion:completion];
}
}];
}
}
- (void)performLayoutWithImageInfo:(NSArray *)imageInfoArray
completion:(LayoutCompletionBlock)completion {
CGFloat currentX = 0;
CGFloat currentY = 0;
NSMutableArray *imageViews = [NSMutableArray array];
for (NSDictionary *info in imageInfoArray) {
UIImageView *imageView = info[@"imageView"];
CGFloat imageWidth = [info[@"width"] floatValue];
// 检查是否需要换行
if (currentX + imageWidth > self.containerWidth) {
currentX = 0;
currentY += self.fixedHeight + self.verticalSpacing;
}
// 设置图片位置
imageView.frame = CGRectMake(currentX, currentY, imageWidth, self.fixedHeight);
[imageViews addObject:imageView];
currentX += imageWidth + self.horizontalSpacing;
}
// 计算最终容器高度
CGFloat containerHeight = currentY + self.fixedHeight;
if (completion) {
completion(imageViews, containerHeight);
}
}
@end
// 在需要使用的地方
ImageFlowLayout *layout = [[ImageFlowLayout alloc] init];
layout.containerWidth = self.containerView.frame.size.width;
layout.fixedHeight = 24; // 可选,默认就是24
layout.horizontalSpacing = 8; // 可选,默认就是8
layout.verticalSpacing = 8; // 可选,默认就是8
[layout layoutWithImageUrls:imageUrls completion:^(NSArray<UIImageView *> *imageViews, CGFloat containerHeight) {
// 更新容器高度
self.containerHeightConstraint.constant = containerHeight;
// 添加图片视图到容器
for (UIImageView *imageView in imageViews) {
[self.containerView addSubview:imageView];
}
[self layoutIfNeeded];
}];
发表回复