iOS 高仿 QQ、微信效果的图片浏览器(支持原图和缩略图、多种手势、CocoaPods)

2016-10-11 10:14:17 +08:00
 CoderKo1o

PYPhotoBrowser (star 800+)

GitHub地址:https://github.com/iphone5solo/PYPhotoBrowser

效果图

哪些 app 使用 PYPhotoBrowser (陆续更新)

香脉 汕医移动办公

支持哪些状态

支持哪些布局

支持哪些手势

什么地方用到这个框架

依赖哪些第三方框架

PYPhotoBrowser 框架的主要类

PYPhotosView (快速使用)



@interface PYPhotosView : UIScrollView

/** 代理 */
@property (nonatomic, weak) id<PYPhotosViewDelegate> delegate;

/** 网络图片模型数组 */
@property (nonatomic, copy) NSArray *photos;
/** 网络图片地址数组(缩略图) */
@property (nonatomic, copy) NSArray *thumbnailUrls;
/** 网络图片地址数组(原图) */
@property (nonatomic, copy) NSArray *originalUrls;
/** 本地相册图片数组(默认最多为九张,当传入图片数组长度超过九张时,取前九张) */
@property (nonatomic, strong) NSMutableArray *images;

/** 所有图片的状态(默认为已发布状态) */
@property (nonatomic, assign) PYPhotosViewState photosState;
/** 图片布局(默认为流水布局) */
@property (nonatomic, assign) PYPhotosViewLayoutType layoutType;
/** 图片分页指示类型(默认为 pageControll 。当图片超过九张,改为 label 显示) */
@property (nonatomic, assign) PYPhotosViewPageType pageType;

/** 图片间距(默认为 5 ) */
@property (nonatomic, assign) CGFloat photoMargin;
/** 图片的宽 (默认为 70) */
@property (nonatomic, assign) CGFloat photoWidth;
/** 图片的高 (默认为 70) */
@property (nonatomic, assign) CGFloat photoHeight;

/** 每行最多个数(默认为 3 ), 当图片布局为线性布局时,此设置失效 */
@property (nonatomic, assign) NSInteger photosMaxCol;
/** 当图片上传前,最多上传的张数,默认为 9 */
@property (nonatomic, assign) NSInteger imagesMaxCountWhenWillCompose;

/** 快速创建 photosView 对象 */
+ (instancetype)photosView;
/** photos : 保存图片链接的数组 */
+ (instancetype)photosViewWithThumbnailUrls:(NSArray *)thumbnailUrls originalUrls:(NSArray *)originalUrls;
/** images : 存储本地图片的数组 */
+ (instancetype)photosViewWithImages:(NSMutableArray *)images;

/**
 * thumbnailUrls : 保存图片(缩略图)链接的数组
 * originalUrls : 保存图片(原图)链接的数组
 * type : 布局类型(默认为流水布局)
 */
+ (instancetype)photosViewWithThumbnailUrls:(NSArray *)thumbnailUrls originalUrls:(NSArray *)originalUrls layoutType:(PYPhotosViewLayoutType)type;

/** 
 * thumbnailUrls : 保存图片(缩略图)链接的数组
 * originalUrls : 保存图片(原图)链接的数组
 * maxCol : 每行最多显示图片的个数
 */
+ (instancetype)photosViewWithThumbnailUrls:(NSArray *)thumbnailUrls originalUrls:(NSArray *)originalUrls photosMaxCol:(NSInteger)maxCol;

/** 根据图片个数和图片状态自动计算出 PYPhontosView 的 size */
- (CGSize)sizeWithPhotoCount:(NSInteger)count photosState:(NSInteger)state;

/**
 * 刷新图片(未发布)
 * images : 新的图片数组
 */
- (void)reloadDataWithImages:(NSMutableArray *)images;

@end


PYPhotoBrowseView (自定义)


@protocol PYPhotoBrowseViewDelegate <NSObject>

@optional

/**
 * 图片浏览将要显示时调用
 */
- (void)photoBrowseView:(PYPhotoBrowseView *)photoBrowseView willShowWithImages:(NSArray *)images index:(NSInteger)index;
/**
 * 图片浏览已经显示时调用
 */
- (void)photoBrowseView:(PYPhotoBrowseView *)photoBrowseView didShowWithImages:(NSArray *)images index:(NSInteger)index;
/**
 * 图片浏览将要隐藏时调用
 */
- (void)photoBrowseView:(PYPhotoBrowseView *)photoBrowseView willHiddenWithImages:(NSArray *)images index:(NSInteger)index;
/**
 * 图片浏览已经隐藏时调用
 */
- (void)photoBrowseView:(PYPhotoBrowseView *)photoBrowseView didHiddenWithImages:(NSArray *)images index:(NSInteger)index;
/**
 * 图片单击时调用
 */
- (void)photoBrowseView:(PYPhotoBrowseView *)photoBrowseView didSingleClickedImage:(UIImage *)image index:(NSInteger)index;
/**
 * 图片长按时调用
 */
- (void)photoBrowseView:(PYPhotoBrowseView *)photoBrowseView didLongPressImage:(UIImage *)image index:(NSInteger)index;

@end

@protocol PYPhotoBrowseViewDataSource <NSObject>

@required
/** 返回将要浏览的图片( UIImage )数组 */
- (NSArray *)imagesForBrowse;

@optional
/** 返回默认显示图片的索引(默认为 0) */
- (NSInteger)currentIndex;

/** 默认显示图片相对于主窗口的位置 */
- (CGRect)frameFormWindow;

/** 消失回到相对于住窗口的指定位置 */
- (CGRect)frameToWindow;

@end


@interface PYPhotoBrowseView  : UIWindow <PYPhotoViewDelegate>

/** 代理 */
@property (nonatomic, weak) id<PYPhotoBrowseViewDelegate> delegate;
/** 数据源代理 */
@property (nonatomic, weak) id<PYPhotoBrowseViewDataSource> dataSource;

/** 用来浏览的图片( UIImage )数组 */
@property (nonatomic, copy) NSArray *images;


/** 用来浏览的图片链接( NSString )数组*/
@property (nonatomic, copy) NSArray *imagesURL;

/** 用来浏览的图片的控件( UIImageView )数组 */
@property (nonatomic, copy) NSArray *sourceImgageViews;

/** 用来记录当前下标 */
@property (nonatomic, assign) NSInteger currentIndex;

/**
 * 浏览图片
 */
- (void)show;

/**
 * 隐藏
 */
- (void)hidden;

@end

如何使用 PYPhotoBrowser

具体使用(详情见示例程序 PYPhotosViewExample )


    // 1. 创建缩略图图片链接数组
    NSMutableArray *thumbnailImageUrls = [NSMutableArray array];
    // 添加图片(缩略图)链接
    [thumbnailImageUrls addObject:@"http://ww3.sinaimg.cn/thumbnail/006ka0Iygw1f6bqm7zukpj30g60kzdi2.jpg"];
    [thumbnailImageUrls addObject:@"http://ww1.sinaimg.cn/thumbnail/61b69811gw1f6bqb1bfd2j20b4095dfy.jpg"];
    [thumbnailImageUrls addObject:@"http://ww1.sinaimg.cn/thumbnail/54477ddfgw1f6bqkbanqoj20ku0rsn4d.jpg"];
    [thumbnailImageUrls addObject:@"http://ww4.sinaimg.cn/thumbnail/006ka0Iygw1f6b8gpwr2tj30bc0bqmyz.jpg"];
    [thumbnailImageUrls addObject:@"http://ww2.sinaimg.cn/thumbnail/9c2b5f31jw1f6bqtinmpyj20dw0ae76e.jpg"];
    [thumbnailImageUrls addObject:@"http://ww1.sinaimg.cn/thumbnail/536e7093jw1f6bqdj3lpjj20va134ana.jpg"];
    [thumbnailImageUrls addObject:@"http://ww1.sinaimg.cn/thumbnail/75b1a75fjw1f6bqn35ij6j20ck0g8jtf.jpg"];
    [thumbnailImageUrls addObject:@"http://ww2.sinaimg.cn/thumbnail/005NFHyQgw1f6bn8bha0eg308w0gib2d.gif"];
    [thumbnailImageUrls addObject:@"http://ww1.sinaimg.cn/thumbnail/86afb21egw1f6bq3lq0itj20gg0c2myt.jpg"];
    
    // 1.2 创建原图图片链接数组
    NSMutableArray *originalImageUrls = [NSMutableArray array];
    // 添加图片(原图)链接
    [originalImageUrls addObject:@"http://ww3.sinaimg.cn/large/006ka0Iygw1f6bqm7zukpj30g60kzdi2.jpg"];
    [originalImageUrls addObject:@"http://ww1.sinaimg.cn/large/61b69811gw1f6bqb1bfd2j20b4095dfy.jpg"];
    [originalImageUrls addObject:@"http://ww1.sinaimg.cn/large/54477ddfgw1f6bqkbanqoj20ku0rsn4d.jpg"];
    [originalImageUrls addObject:@"http://ww4.sinaimg.cn/large/006ka0Iygw1f6b8gpwr2tj30bc0bqmyz.jpg"];
    [originalImageUrls addObject:@"http://ww2.sinaimg.cn/large/9c2b5f31jw1f6bqtinmpyj20dw0ae76e.jpg"];
    [originalImageUrls addObject:@"http://ww1.sinaimg.cn/large/536e7093jw1f6bqdj3lpjj20va134ana.jpg"];
    [originalImageUrls addObject:@"http://ww1.sinaimg.cn/large/75b1a75fjw1f6bqn35ij6j20ck0g8jtf.jpg"];
    [originalImageUrls addObject:@"http://ww2.sinaimg.cn/large/005NFHyQgw1f6bn8bha0eg308w0gib2d.gif"];
    [originalImageUrls addObject:@"http://ww1.sinaimg.cn/large/86afb21egw1f6bq3lq0itj20gg0c2myt.jpg"];
  
  // 2. 创建一个 photosView
  PYPhotosView *photosView = [PYPhotosView photosViewWithThumbnailUrls:thumbnailImageUrls originalUrls:originalImageUrls];
  
  // 3. 添加 photosView
  [self.view addSubview:photosView];
  
    
    // 1. 创建本地图片数组
    NSMutableArray *imagesM = [NSMutableArray array];
    for (int i = 0; i < arc4random_uniform(4) + 1; i++) {
        [imagesM addObject:[UIImage imageNamed:[NSString stringWithFormat:@"%02d", i + 1]]];
    }
    
    // 2.1 设置本地图片
  	PYPhotosView *photosView = [PYPhotosView photosViewWithImages:imagesM];
    
    // 3. 设置代理
    photosView.delegate = self;
    
    // 4. 添加 photosView
    [self.view addSubview:photosView];


    // 1. 创建 photoBroseView 对象
    PYPhotoBrowseView *photoBroseView = [[PYPhotoBrowseView alloc] init];
    
    // 2.1 设置图片源(UIImageView)数组
    photoBroseView.sourceImgageViews = imageViews;
    // 2.2 设置初始化图片下标(即当前点击第几张图片)
    photoBroseView.currentIndex = 2;
    
    // 3.显示(浏览)
    [photoBroseView show];

自定义 photosView

通过设置 photosView 的对象属性值即可修改

// 设置布局为线性布局
photosView.layoutType = PYPhotosViewLayoutTypeLine;

// 设置指示类型为文本指示
photosView.pageType = PYPhotosViewPageTypeLabel;
// 设置图片间距为 10
photosView.photoMargin = 10;
// 设置图片的宽( width )
photosView.photoWidth = 100;
// 设置图片的高( height )
photosView.photoHeight = 60;
// 设置图片最多列数
photosView.photosMaxCol = 6;
// 设置图片最多上传的张数
photosView.imagesMaxCountWhenWillCompose = 15;

期待

3518 次点击
所在节点    分享创造
11 条回复
eddiechen
2016-10-11 10:41:34 +08:00
支持一个~~~~~~~~~~
sobigfish
2016-10-11 11:47:40 +08:00
图片浏览依赖框架
呃,-。- 那么多啊,只是浏览例子里依赖了它们 3 个?还是核心源代码里就有耦合
CoderKo1o
2016-10-11 21:21:51 +08:00
@sobigfish 主要是 SDWebImage 其他两个一个是用于显示加载进度、一个是用于提示。
CoderKo1o
2016-10-11 21:24:27 +08:00
@eddiechen 谢谢支持!
sobigfish
2016-10-11 21:31:45 +08:00
@CoderKo1o 是啊, 开源不是尽量少依赖么 SDWebImage 更是多操了一份心,他们也许有其他的方案呢,比如喵神的 kingfisher
sobigfish
2016-10-11 21:43:10 +08:00
issues/5 他们不是真的想用 afn 他们想你把整个 app 写给他们
真心不用什么都给他们做了
CoderKo1o
2016-10-11 22:37:38 +08:00
@sobigfish 为了使用简单。 满足更多用户的需求,可用根据需求选择是否依赖框架。 需要的再导入、每一个依赖都是有理由存在的。 而且依赖的框架也是主流框架,大部分相关图片 app 都会依赖的。
sobigfish
2016-10-11 22:42:01 +08:00
要完整功能是的-。- 我也只是在吹毛求疵而已 不要在意
CoderKo1o
2016-10-12 12:39:12 +08:00
@sobigfish 没事!有反馈还是最好的!
champage
2016-10-14 15:39:25 +08:00
恩 发现你的头像跟我微信里的用了同一个
CoderKo1o
2016-10-14 17:49:47 +08:00
@champage 都是喜欢 Alan Walker

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/311805

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX