AJ分享,必须精品

:一效果

如果直接设置会有拉伸等等的状况,这里主要介绍图片显示的一些细节

二:代码

代码实现其实很简单,微博当中用了一个photos来存放九宫格这些图片,然后用了一个photo类来做每个photo,并且在上面显示gif等的样式,很多很多小技巧,直接上代码

九宫格根据行列设置等算法,不难

  1. #import "HWStatusPhotosView.h"
  2. #import "HWPhoto.h"
  3. #import "HWStatusPhotoView.h"
  4. #define HWStatusPhotoWH 70
  5. #define HWStatusPhotoMargin 10
  6. #define HWStatusPhotoMaxCol(count) ((count==4)?2:3)
  7. @implementation HWStatusPhotosView // 9
  8. - (id)initWithFrame:(CGRect)frame
  9. {
  10. self = [super initWithFrame:frame];
  11. if (self) {
  12. }
  13. return self;
  14. }
  15. - (void)setPhotos:(NSArray *)photos
  16. {
  17. _photos = photos;
  18. int photosCount = photos.count;
  19. // 创建足够数量的图片控件
  20. // 这里的self.subviews.count不要单独赋值给其他变量
  21. while (self.subviews.count < photosCount) {
  22. HWStatusPhotoView *photoView = [[HWStatusPhotoView alloc] init];
  23. [self addSubview:photoView];
  24. }
  25. // 遍历所有的图片控件,设置图片
  26. for (int i = 0; i<self.subviews.count; i++) {
  27. HWStatusPhotoView *photoView = self.subviews[i];
  28. if (i < photosCount) { // 显示
  29. photoView.photo = photos[i];
  30. photoView.hidden = NO;
  31. } else { // 隐藏
  32. photoView.hidden = YES;
  33. }
  34. }
  35. }
  36. - (void)layoutSubviews
  37. {
  38. [super layoutSubviews];
  39. // 设置图片的尺寸和位置
  40. int photosCount = self.photos.count;
  41. int maxCol = HWStatusPhotoMaxCol(photosCount);
  42. for (int i = 0; i<photosCount; i++) {
  43. HWStatusPhotoView *photoView = self.subviews[i];
  44. int col = i % maxCol;
  45. photoView.x = col * (HWStatusPhotoWH + HWStatusPhotoMargin);
  46. int row = i / maxCol;
  47. photoView.y = row * (HWStatusPhotoWH + HWStatusPhotoMargin);
  48. photoView.width = HWStatusPhotoWH;
  49. photoView.height = HWStatusPhotoWH;
  50. }
  51. }
  52. + (CGSize)sizeWithCount:(int)count
  53. {
  54. // 最大列数(一行最多有多少列)
  55. int maxCols = HWStatusPhotoMaxCol(count);
  56. int cols = (count >= maxCols)? maxCols : count;
  57. CGFloat photosW = cols * HWStatusPhotoWH + (cols - 1) * HWStatusPhotoMargin;
  58. // 行数
  59. int rows = (count + maxCols - 1) / maxCols;
  60. CGFloat photosH = rows * HWStatusPhotoWH + (rows - 1) * HWStatusPhotoMargin;
  61. return CGSizeMake(photosW, photosH);
  62. }
  63. @end

photo的代码

  1. #import "HWStatusPhotoView.h"
  2. #import "HWPhoto.h"
  3. #import "UIImageView+WebCache.h"
  4. @interface HWStatusPhotoView()
  5. @property (nonatomic, weak) UIImageView *gifView;
  6. @end
  7. @implementation HWStatusPhotoView
  8. - (UIImageView *)gifView
  9. {
  10. if (!_gifView) {
  11. UIImage *image = [UIImage imageNamed:@"timeline_image_gif"];
  12. UIImageView *gifView = [[UIImageView alloc] initWithImage:image];
  13. [self addSubview:gifView];
  14. self.gifView = gifView;
  15. }
  16. return _gifView;
  17. }
  18. - (id)initWithFrame:(CGRect)frame
  19. {
  20. self = [super initWithFrame:frame];
  21. if (self) {
  22. // 内容模式
  23. self.contentMode = UIViewContentModeScaleAspectFill;
  24. // 超出边框的内容都剪掉
  25. self.clipsToBounds = YES;
  26. }
  27. return self;
  28. }
  29. - (void)setPhoto:(HWPhoto *)photo
  30. {
  31. _photo = photo;
  32. // 设置图片
  33. [self sd_setImageWithURL:[NSURL URLWithString:photo.thumbnail_pic] placeholderImage:[UIImage imageNamed:@"timeline_image_placeholder"]];
  34. // 显示\隐藏gif控件
  35. // 判断是够以gif或者GIF结尾
  36. self.gifView.hidden = ![photo.thumbnail_pic.lowercaseString hasSuffix:@"gif"];
  37. }
  38. - (void)layoutSubviews
  39. {
  40. [super layoutSubviews];
  41. self.gifView.x = self.width - self.gifView.width;
  42. self.gifView.y = self.height - self.gifView.height;
  43. }
  44. @end

三:注意地方

显示\隐藏gif控件

  1. // 判断是够以gif或者GIF结尾
  2. self.gifView.hidden = ![photo.thumbnail_pic.lowercaseString hasSuffix:@"gif"];

字符串分类根据字符串字体和最大宽度来得到所占据的高度宽度

  1. /**
  2. * 根据字符串字体和最大宽度来得到所占据的高度宽度
  3. *
  4. * @param font 字体
  5. * @param maxW 最大宽度
  6. *
  7. * @return 长宽size
  8. */
  9. - (CGSize)sizeWithFont:(UIFont *)font maxW:(CGFloat)maxW
  10. {
  11. NSMutableDictionary *attrs = [NSMutableDictionary dictionary];
  12. attrs[NSFontAttributeName] = font;
  13. CGSize maxSize = CGSizeMake(maxW, MAXFLOAT);
  14. return [self boundingRectWithSize:maxSize options:NSStringDrawingUsesLineFragmentOrigin attributes:attrs context:nil].size;
  15. }
  16. /**
  17. * 在宽度为最大值时候根据字体得到宽高
  18. *
  19. * @param font 字体
  20. *
  21. * @return 长宽size
  22. */
  23. - (CGSize)sizeWithFont:(UIFont *)font
  24. {
  25. return [self sizeWithFont:font maxW:MAXFLOAT];
  26. }

UIImageView图片设置

  1. /**
  2. UIViewContentModeScaleToFill : 图片拉伸至填充整个UIImageView(图片可能会变形)
  3. UIViewContentModeScaleAspectFit : 图片拉伸至完全显示在UIImageView里面为止(图片不会变形)
  4. UIViewContentModeScaleAspectFill :
  5. 图片拉伸至 图片的宽度等于UIImageView的宽度 或者 图片的高度等于UIImageView的高度 为止
  6. UIViewContentModeRedraw : 调用了setNeedsDisplay方法时,就会将图片重新渲染
  7. UIViewContentModeCenter : 居中显示
  8. UIViewContentModeTop,
  9. UIViewContentModeBottom,
  10. UIViewContentModeLeft,
  11. UIViewContentModeRight,
  12. UIViewContentModeTopLeft,
  13. UIViewContentModeTopRight,
  14. UIViewContentModeBottomLeft,
  15. UIViewContentModeBottomRight,
  16. 经验规律:
  17. 1.凡是带有Scale单词的,图片都会拉伸
  18. 2.凡是带有Aspect单词的,图片都会保持原来的宽高比,图片不会变形
  19. */
  20. // 内容模式self(imageView对象)
  21. self.contentMode = UIViewContentModeScaleAspectFill;
  22. // 超出边框的内容都剪掉
  23. self.clipsToBounds = YES;

AJ学IOS 之微博项目实战(10)微博cell中图片的显示以及各种填充模式简介的更多相关文章

  1. AJ学IOS 之微博项目实战(1)微博主框架-子控制器的添加

    AJ分享,必须精品 一:简单介绍 这是新浪微博的iOS端项目,来自于黑马的一个实战项目. 主要分成五大模块,本次全部运用纯代码实现,其中会用到很多前面学过得内容,如果有的地方有重复的知识点,说明这个知 ...

  2. AJ学IOS 之微博项目实战(2)微博主框架-自定义导航控制器NavigationController

    AJ分享,必须精品 一:添加导航控制器 上一篇博客完成了对底部的TabBar的设置,这一章我们完成自定义导航控制器(NYNavigationController). 为啥要做自定义呢,因为为了更好地封 ...

  3. 猫猫学iOS 之微博项目实战(2)微博主框架-自己定义导航控制器NavigationController

    猫猫分享,必须精品 原创文章,欢迎转载.转载请注明:翟乃玉的博客 地址:http://blog.csdn.net/u013357243?viewmode=contents 一:加入导航控制器 上一篇博 ...

  4. AJ学IOS 之微博项目实战(5)微博自定义搜索框searchBar

    AJ分享,必须精品 一:效果 用UITextField简单定义一个搜索框 二:调用: 调用的代码,很简单,直接init就可以,以后加功能自己添加就行了. - (void)viewDidLoad { [ ...

  5. AJ学IOS 之微博项目实战(9)微博模型之时间相关重要操作,判断刚刚,昨天,今年等等

    AJ分享,必须精品 一:效果 二:实现代码 /** 1.今年 1> 今天 * 1分内: 刚刚 * 1分~59分内:xx分钟前 * 大于60分钟:xx小时前 2> 昨天 * 昨天 xx:xx ...

  6. AJ学IOS 之微博项目实战(4)微博自定义tabBar中间的添加按钮

    AJ分享,必须精品 一:效果图 自定义tabBar实现最下面中间的添加按钮 二:思路 首先在自己的tabBarController中把系统的tabBar设置成自己的tabBar(NYTabBar),这 ...

  7. AJ学IOS 之微博项目实战(3)微博主框架-UIImage防止iOS7之后自动渲染_定义分类

    AJ分享,必须精品 一:效果对比 当我们设置tabBarController的tabBarItem.image的时候,默认情况下会出现图片变成蓝色的效果,这是因为ios7之后会对图片自动渲染成蓝色 代 ...

  8. 猫猫学iOS 之微博项目实战(5)微博自己定义搜索框searchBar

    猫猫分享.必须精品 原创文章.欢迎转载. 转载请注明:翟乃玉的博客 地址:http://blog.csdn.net/u013357243 一:效果 用UITextField简单定义一个搜索框 二:调用 ...

  9. AJ学IOS 之微博项目实战(8)用AFNetworking和SDWebImage简单加载微博数据

    AJ分享,必须精品 一:效果 没有图文混排,也没有复杂的UI,仅仅是简单的显示出微博数据,主要介绍AFNetworking和SDWebImage的简单用法 二:加载数据AFNetworking AFN ...

随机推荐

  1. Red Team 工具集之网络钓鱼和水坑攻击

    来自:信安之路(微信号:xazlsec),作者:myh0st 参考项目:https://github.com/infosecn1nja/Red-Teaming-Toolkit 上图是一个 Red Te ...

  2. django中基于python3.6使用容联发送短信

    一. Django基于python3.6使用容联发送短信流程 容联官方的python支持2.7版本,当我们python解释器采用3版本时,需要修改容联接口中的一些参数及方法. 首先去容联官网注册账号, ...

  3. hdu1242 又又又是逃离迷宫(bfs模板题)

    题目链接:http://icpc.njust.edu.cn/Problem/Hdu/1242/ 这次的迷宫是有守卫的,杀死一个守卫需要花费1个单位的时间,所以以走的步数为深度,在每一层进行搜索,由于走 ...

  4. 第十六周Java实验作业

    实验十六  线程技术 实验时间 2017-12-8 1.实验目的与要求 (1) 掌握线程概念: 多线程是进程执行过程中产生的多条执行线索,线程是比进程执行更小的单位. 线程不能独立存在,必须存在于进程 ...

  5. 自定义上下文菜单,contextmenu事件

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  6. arcgis server建完站点之后修改默认6080端口号

    1.首先找到arcgis server的安装路径,找到server.xml文件,修改其中一处的6080端口为你想更改的端口号,例如8888.具体操作如下图所示: 默认的安装路径为:D:\Program ...

  7. 【Pytest01】全网最全最新的Pytest框架快速入门

    一.Pytest简介pytest是一个非常成熟的全功能的Python测试框架,主要有一下几个特点:1.简单灵活,容易上手,支持参数化2.能够支持简单的单元测试和复杂的功能测试,还可以用来做seleni ...

  8. 【译】Java SE 14 Hotspot 虚拟机垃圾回收调优指南

    原文链接:HotSpot Virtual Machine Garbage Collection Tuning Guide,基于Java SE 14. 本文主要包括以下内容: 优化目标与策略(Ergon ...

  9. elasticesearch搜索返回高亮关键字

    pre_tags 前缀标签 post_tags 后缀标签 tags_schema 设置为styled可以使用内置高亮样式 require_field_match 多字段高亮需要设置为false 使用h ...

  10. async和await是如何实现异步编程?

    目录 异步编程样例 样例解析 浅谈Promise如何实现异步执行 参考 1.异步编程样例 样例: // 等待执行函数 function sleep(timeout) { return new Prom ...