美女图片採集器 (源代码+解析)

前言:

有一段时间没写博客了, "持之以恒"徽章都暗了, 实在不该。 前一段确实比較忙, ...小小地给自己的懒找个借口吧。

大二即将结束, 学习iOS也有一段时间了。今天抽点时间, 开源一个前几天刚上传的App里面的一个功能, RT, 美女图片採集器。 ? 美女.. 相信没有人不喜欢吧, 基于此, 这个小Demo应运而生。

注:?

本文正在參加博客大赛。 假设认为对你有所帮助, 还望帮忙投下票。 多谢。

?

投票链接:?http://vote.blog.csdn.net/Article/Details?articleid=37825177 (投票button在最下方)

效果演示:

看到这里, 假设还有兴趣学习的话, 能够先到我的git中下载源代码, 然后配合着源代码看我以下的解析。相信, 会让你有所收获的。

git下载链接:?BeautyPickDemo.git

涉及内容:

  1. 百度图片API的使用
  2. JSON格式数据解析
  3. 图片异步下载 + 离线缓存
  4. 图片基本操作(缩放, 删除, 加入, 保存到本地)
  5. 下拉刷新, 上提载入
  6. 幻灯片放映
  7. 自己定义后台显示图片

源代码解析:

一。百度图片API的使用

首先, 我们知道百度是没有对外开放图片API的, 可是我们能够通过谷歌浏览器来捕捉到訪问过程中它调用的API。有兴趣的, 能够了解下谷歌浏览器Network选项的使用, 也能够參考下这篇文章:?百度图片api

这里, 我们主要介绍怎样使用就可以。

1.百度图片通用API:

http://image.baidu.com/i?

tn=resultjsonavstar&ie=utf-8&word=刘德华&pn=0&rn=60
说明:
返回格式为json
word为查询的内容
pn为第几页
rn为一页返回的图片数量
用法:大家在浏览器地址栏输入上述地址,回车就可以看到返回的图片地址

2.百度图片分类API (我们使用的就是这个)

http://image.baidu.com/channel/listjson?pn=0&rn=30&tag1=美女&tag2=所有&ie=utf8
http://image.baidu.com/channel/listjson?

pn=0&rn=30&tag1=美女&tag2=所有&ftags=校花&ie=utf8

至于其它的, 按照这种方法都能获取到. 就不反复说明了。

至于怎样调用API, 涉及到网络编程。

开源的ASI类库做的比較好(尽管挺老的一个东西了, 也有一段时间没更新了, 可是能满足我们需求)。

从源代码中, 能够找到 网络请求ASI目录。里面有须要的文件

1。导入这里的文件

2。导入必须的框架, 包含:

SystemConfiguration.framework
MobileCoreServices.framework
CFNetwork.framework
libz.dylib

3。调用API (參见 主界面-->picVC)

@property (nonatomic,strong) ASIHTTPRequest *testRequest;
NSString* urlString = [NSString stringWithFormat:@"http://image.baidu.com/channel/listjson?pn=%d&rn=10&tag1=美女&tag2=%@", nowPage, [chooseArr objectAtIndex:nowChoose]];

urlString = [urlString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
NSURL *url = [NSURL URLWithString:urlString];
testRequest = [ASIHTTPRequest requestWithURL:url];
[testRequest setDelegate:self];
[testRequest startAsynchronous];

就可以正常调用API。

至于怎样处理返回的数据, 以下再详细讲。

二。

JSON格式数据解析

一般的数据格式有XMLJSON, 这里由于调用百度图片API返回的数据格式是JSON, 所以我们仅仅要解析JSON就可以。

调用API成功后, 它会自己主动运行这个函数

#pragma mark - 载入数据完成
- (void)requestFinished:(ASIHTTPRequest *)request

我们仅仅须要在这里解析数据, 使用数据就可以。

这种方法返回的数据是二进制格式的NSData, 我们须要手动转为UTF8编码。能够这样获取:

//当以二进制读取返回内容时用这种方法
    NSData *responseData = [request responseData];
    NSString *responseString = [[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding];

接下去就是奇妙的时候了, 对于这种一个字符串, 假设直接打印, 你可能会看得云里雾里的, json格式而且没有又一次排列。

可是我们能够使用JsonKit来直接解析。(文件在json解析目录中)

仅仅需这样一条语句就可以:

self.testDic = [responseString objectFromJSONString];

打印解析后的数据例如以下:

至于须要哪些, 直接取就好了。比方. 我们这里须要获取到图片的标题. url, 宽度, 高度

NSMutableDictionary *nowDic = [[NSMutableDictionary alloc]init];
[nowDic setObject:[[array objectAtIndex:i]objectForKey:@"image_url"] forKey:@"image_url"];
[nowDic setObject:[[array objectAtIndex:i]objectForKey:@"image_width"] forKey:@"image_width"];
[nowDic setObject:[[array objectAtIndex:i]objectForKey:@"image_height"] forKey:@"image_height"];
[nowDic setObject:[[array objectAtIndex:i]objectForKey:@"desc"] forKey:@"desc"];

[picArray addObject:nowDic];

三。图片异步下载+离线缓存

这里提一下SDWebImage, 我们将会使用它来实现。

详细使用參见:SDWebImage 笔记

在解析完json数据后, 我们会获取到图片相应的url。

我们能够通过訪问url获取图片。?

- (void)setImageWithURL:(NSURL *)url placeholderImage:(UIImage *)placeholder;

这是SDWebImage给我们提供的一个函数. 通过调用它, 我们能够实现异步下载和离线缓存。

用法:

UIImageView *imageView = [[UIImageView alloc]initWithFrame:CGRectMake(SPACE / 2 , SPACE / 2 , width, height)];
NSURL *url = [NSURL URLWithString:imageInfo.thumbURL];
[imageView setImageWithURL:url placeholderImage:nil];
imageView.backgroundColor = [UIColor palePurpleColor];
[self addSubview:imageView];

异步下载,离线缓存效果:(离线缓存能够到应用沙盒中查看)



watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvaGl0d2h5bHo=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/Center" />

四。

图片基本操作(缩放, 删除, 加入, 保存到本地)

这里涉及的主要是一些常规操作, 包含缩放, 删除, 加入, 保存到本地等。

至于删除, 通常是长按删除, 仅仅要在图片上加上长按手势响应就可以。然后弹出一个对话框, 提示用户是否删除。确定删除后, 从沙盒中清除缓存就可以。

加入手势方法:

//长按
UILongPressGestureRecognizer *longRecognizer;
longRecognizer = [[UILongPressGestureRecognizer alloc]initWithTarget:self action:@selector(handleSingleLongFrom:)];
[self addGestureRecognizer:longRecognizer];

从视图和沙盒中删除

        //从当前视图中删除
        [testArr removeObject:data];
        //刷新数据
        __weak picVC *blockSelf = self;
        [blockSelf.waterView refreshView:testArr];
        [blockSelf.waterView.infiniteScrollingView stopAnimating];

        //从沙盒中删除
        //打开沙盒
        NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
        NSString *documentsDirectory = [paths objectAtIndex:0];
        NSString * namePath = [documentsDirectory stringByAppendingPathComponent:[NSString stringWithFormat:@"savedPicInfo_%d.plist",nowChoose]];
        NSMutableArray *picArray = [[NSMutableArray alloc] initWithContentsOfFile:namePath];

        for (int i=0; i<[picArray count]; i++)
        {
            if ([[[picArray objectAtIndex:i]objectForKey:@"image_url"] isEqualToString:data.thumbURL])
            {
                [picArray removeObjectAtIndex:i];
                break;
            }
        }
        [picArray writeToFile:namePath atomically:YES];

至于缩放, 首先要弹出一个全屏显示的视图。

像这样:

//单击, 显示大图
-(void)showImage:(ImageInfo*)data
{
    NSURL *url = [NSURL URLWithString:data.thumbURL];
    [clickImage setImageWithURL:url placeholderImage:nil];
    TGRImageViewController *viewController = [[TGRImageViewController alloc] initWithImage:clickImage.image setImageInfo:data];
    viewController.transitioningDelegate = self;
    [self presentViewController:viewController animated:YES completion:nil];
}

本质就是调用presentViewController:viewController。

当然。我们能够给新视图的显示加上动画效果, 例如以下:

#pragma mark - UIViewControllerTransitioningDelegate methods
- (id<UIViewControllerAnimatedTransitioning>)animationControllerForPresentedController:(UIViewController *)presented presentingController:(UIViewController *)presenting sourceController:(UIViewController *)source
{
    if ([presented isKindOfClass:TGRImageViewController.class]) {
        return [[TGRImageZoomAnimationController alloc] initWithReferenceImageView:clickImage];
    }
    return nil;
}

- (id<UIViewControllerAnimatedTransitioning>)animationControllerForDismissedController:(UIViewController *)dismissed {
    if ([dismissed isKindOfClass:TGRImageViewController.class]) {
        return [[TGRImageZoomAnimationController alloc] initWithReferenceImageView:clickImage];
    }
    return nil;
}

然后, 在新视图中, 加入点击移除, 长按弹出新操作, 双指移动缩放手势就可以。

详细实现例如以下:

#pragma mark - Private methods

- (void)longPress:(UITapGestureRecognizer *)tapGestureRecognizer
{

    if(tapGestureRecognizer.state == UIGestureRecognizerStateBegan)
    {
        [self popupActionSheet];
    }
}

- (IBAction)handleSingleTap:(UITapGestureRecognizer *)tapGestureRecognizer {
    [self dismissViewControllerAnimated:YES completion:nil];
}

- (IBAction)handleDoubleTap:(UITapGestureRecognizer *)tapGestureRecognizer {
    if (self.scrollView.zoomScale == self.scrollView.minimumZoomScale) {
        // Zoom in
        CGPoint center = [tapGestureRecognizer locationInView:self.scrollView];
        CGSize size = CGSizeMake(self.scrollView.bounds.size.width / self.scrollView.maximumZoomScale,
                                 self.scrollView.bounds.size.height / self.scrollView.maximumZoomScale);
        CGRect rect = CGRectMake(center.x - (size.width / 2.0), center.y - (size.height / 2.0), size.width, size.height);
        [self.scrollView zoomToRect:rect animated:YES];
    }
    else {
        // Zoom out
        [self.scrollView zoomToRect:self.scrollView.bounds animated:YES];
    }
}

五。

下拉刷新, 上提载入

这个功能详细在浏览图片的时候使用。 代码在picVC中。

可是由于我之前专门写过一篇这种博客。 就不再反复了。

详细能够看这里:?iOS开发-ios7下拉刷新,上提载入高速集成

六。幻灯片放映

顾名思义, 就是能够自己主动播放收藏过的美女图片.. ?

这里的原理是利用UIView的动画, 不断切换显示图片和显示效果。

切换效果例如以下:

    _transitionOptions= @[[NSNumber numberWithInteger:UIViewAnimationOptionTransitionFlipFromLeft],
                          [NSNumber numberWithInteger:UIViewAnimationOptionTransitionFlipFromRight],
                          [NSNumber numberWithInteger:UIViewAnimationOptionTransitionCurlUp],
                          [NSNumber numberWithInteger:UIViewAnimationOptionTransitionCurlDown],
                          [NSNumber numberWithInteger:UIViewAnimationOptionTransitionCrossDissolve],
                          [NSNumber numberWithInteger:UIViewAnimationOptionTransitionFlipFromTop],
                          [NSNumber numberWithInteger:UIViewAnimationCurveEaseIn],
                          [NSNumber numberWithInteger:UIViewAnimationCurveEaseOut],
                          [NSNumber numberWithInteger:UIViewAnimationCurveLinear],
                          [NSNumber numberWithInteger:UIViewAnimationOptionAllowAnimatedContent],
                          [NSNumber numberWithInteger:UIViewAnimationOptionOverrideInheritedCurve],
                          [NSNumber numberWithInteger:UIViewAnimationOptionTransitionFlipFromTop],
                          [NSNumber numberWithInteger:UIViewAnimationOptionTransitionFlipFromBottom]];

然后切换图片的时候, 实现例如以下代码就可以。

?(详细參见PhotoStackView)

-(void)reloadData {

    if (!self.dataSource) {
        //exit if data source has not been set up yet
        self.photoViews = nil;
        return;
    }

    NSInteger numberOfPhotos = [self.dataSource numberOfPhotosInPhotoStackView:self];
    NSInteger topPhotoIndex  = [self indexOfTopPhoto]; // Keeping track of current photo‘s top index so that it remains on top if new photos are added

    if(numberOfPhotos > 0) {

        NSMutableArray *photoViewsMutable   = [[NSMutableArray alloc] initWithCapacity:numberOfPhotos];
        UIImage *borderImage                = [self.borderImage resizableImageWithCapInsets:UIEdgeInsetsMake(self.borderWidth, self.borderWidth, self.borderWidth, self.borderWidth)];

        for (NSUInteger index = 0; index < numberOfPhotos; index++) {

            UIImage *image = [self.dataSource photoStackView:self photoForIndex:index];
            CGSize imageSize = image.size;
            if([self.dataSource respondsToSelector:@selector(photoStackView:photoSizeForIndex:)]){
                imageSize = [self.dataSource photoStackView:self photoSizeForIndex:index];
            }
            UIImageView *photoImageView     = [[UIImageView alloc] initWithFrame:(CGRect){CGPointZero, imageSize}];
            photoImageView.image            = image;
            UIView *view                    = [[UIView alloc] initWithFrame:photoImageView.frame];
            view.layer.rasterizationScale   = [[UIScreen mainScreen] scale];
            view.layer.shouldRasterize      = YES; // rasterize the view for faster drawing and smooth edges

            if (self.showBorder) {

                // Add the background image
                if (borderImage) {
                    // If there is a border image, we need to add a background image view, and add some padding around the photo for the border

                    CGRect photoFrame                = photoImageView.frame;
                    photoFrame.origin                = CGPointMake(self.borderWidth, self.borderWidth);
                    photoImageView.frame             = photoFrame;

                    view.frame                       = CGRectMake(0, 0, photoImageView.frame.size.width+(self.borderWidth*2), photoImageView.frame.size.height+(self.borderWidth*2));
                    UIImageView *backgroundImageView = [[UIImageView alloc] initWithFrame:view.frame];
                    backgroundImageView.image        = borderImage;

                    [view addSubview:backgroundImageView];
                } else {
                    // if there is no boarder image draw one with the CALayer
                    view.layer.borderWidth        = self.borderWidth;
                    view.layer.borderColor        = [[UIColor whiteColor] CGColor];
                    view.layer.shadowOffset       = CGSizeMake(0, 0);
                    view.layer.shadowOpacity      = 0.5;
                }
            }

            [view addSubview:photoImageView];

            view.tag    = index;
            view.center = CGPointMake(CGRectGetMidX(self.bounds), CGRectGetMidY(self.bounds));

            [photoViewsMutable addObject:view];

        }

        // Photo views are added to subview in the photoView setter
        self.photoViews = photoViewsMutable; photoViewsMutable = nil;
        [self goToPhotoAtIndex:topPhotoIndex];

    }

}

七。自己定义后台显示图片

这个功能就是演示效果里面, 当应用切换到后台后, 我们双击home键后显示后台程序时候, 该应用的显示效果。

比方.. ?有时候我们浏览的图片尺度比較大.. 然后切到后台的时候, 就希望把它隐藏起来.. ?

这就涉及到了Background Fetch的应用。

之前也写过一篇博客专门介绍。 这里就不反复了。

详细參见:?iOS开发-自己定义后台显示图片(iOS7-Background Fetch的应用)

好了。 到这里最终是介绍的几乎相同了。

当然。 我这里的解析都比較概括, 列举的都是几个关键代码段。

更加详细的还是须要自己去看代码。 凝视也写了, 预计没什么问题。 假设有问题, 欢迎联系我。

一口气写了3个小时的博客... ?累的够呛的。也希望, 能对你有所帮助。


本文正在參加博客大赛。

假设认为对你有所帮助, 还望帮忙投下票。

多谢。?

投票链接:?http://vote.blog.csdn.net/Article/Details?

articleid=37825177 (投票button在最下方)

学习的路上, 与君共勉。

原文地址:https://www.cnblogs.com/ldxsuanfa/p/10799968.html

时间: 2024-11-08 13:16:04

美女图片採集器 (源代码+解析)的相关文章

金蝶盘点机条码数据採集器PDA,WIFI已经连接,可是PDA应用程序还是网络初始化不成功?

PDA任务栏里显示了小电脑.小电脑也是绿色的,为什么PDA还是网络初始化不成功呢? 1.须要检查下server的[PDA后台服务程序]是否打开?假设没有打开请打开[PDA后台服务程序]. 2.须要检查PDA应用程序的[网络设置]是否设置的server的IP地址.也就是serverIP地址是否设置正确,须要检查下serverIP地址是否有变动. 3.以上两步都对了.还不通,那么我们就须要在PDA上使用ping程序,ping一下server.看PDA的网络是否跟server相通.详细Ping的操作步

防止站点数据被採集——成佩涛黑客

本文主要应对与web端数据的防採集(接口数据加密方面) 一般採集器(採集程序)在对web数据进行採集时.无非是通过解析特定链接请求后返回的内容,然后获取实用的内容.那么我们该怎样去防止这样的现象呢? 网上已经有一些经常使用的方法了,比方说: 1.通过限制IP地址单位时间的訪问次数来进行拦截(不可持续性解决方式) 2.屏蔽ip(个人认为这种方法基本没什么有用性) 3.利用js加密网页内容(这样的方法,加密效果还是不错的,可是不利于(SEO)搜索引擎优化) 4.站点随机採用不同模版以及html採用随

美女图片采集器 (源码+解析)

前言: 有一段时间没写博客了, "持之以恒"徽章都暗了, 实在不该. 前一段确实比较忙, ...小小地给自己的懒找个借口吧. 大二即将结束, 学习iOS也有一段时间了.今天抽点时间, 开源一个前几天刚上传的App里面的一个功能, RT, 美女图片采集器.   美女.. 相信没有人不喜欢吧, 基于此, 这个小Demo应运而生. 效果演示: 看到这里, 如果还有兴趣学习的话, 可以先到我的git中下载源码, 然后配合着源码看我下面的解析.相信, 会让你有所收获的. git下载链接: Bea

Python实战:美女图片下载器,海量图片任你下载

Python应用现在如火如荼,应用范围很广.因其效率高开发迅速的优势,快速进入编程语言排行榜前几名.本系列文章致力于可以全面系统的介绍Python语言开发知识和相关知识总结.希望大家能够快速入门并学习Python这门语言. 本文是在前一部分Python基础之上Python实战:Python爬虫学习教程,获取电影排行榜,再次升级的Python网页爬虫实战课程. 1.项目概述. 利用XPath和requests模块进行网页抓取与分析,达到网页图片下载的效果. 抓爬图片地址:http://www.2c

自己动手写美女图片下载器

前言:看到标题可能会有人觉得似曾相识,没错,这篇博文的来源正是根据杨中科老师的<百度美女图片下载器开发教程.Net版>.因为我也观看了该教程,觉得很好玩,于是乎想自己独立完成一次,作为对之前基础学习内容的回顾和运用.以博文的形式和大家分享整个开发过程主要是想借此机会来重新整理下思路.锻炼下自己的表达能力.您如果对下面要用到知识点很熟悉,可忽略此文. 一.主要技术 Winform常用控件的基本使用 HttpWebRequest请求其他网站内容 Newtonsoft.Json.dll组件解析JSO

Scrapy爬取美女图片第三集 代理ip(上) (原创)

首先说一声,让大家久等了.本来打算520那天进行更新的,可是一细想,也只有我这样的单身狗还在做科研,大家可能没心思看更新的文章,所以就拖到了今天.不过忙了521,522这一天半,我把数据库也添加进来了,修复了一些bug(现在肯定有人会说果然是单身狗). 好了,废话不多说,咱们进入今天的主题.上两篇 Scrapy爬取美女图片 的文章,咱们讲解了scrapy的用法.可是就在最近,有热心的朋友对我说之前的程序无法爬取到图片,我猜应该是煎蛋网加入了反爬虫机制.所以今天讲解的就是突破反爬虫机制的上篇 代理

python学习(24) 使用Xpath解析并抓取美女图片

Xpath最初用来处理XML解析,同样适用于HTML文档处理.相比正则表达式更方便一些 Xpath基本规则 nodename 表示选取nodename 节点的所有子节点 / 表示当前节点的直接子节点 // 表示当前节点的子节点和孙子节点 . 表示当前节点 .. 当前节点的父节点 @ 选取属性 下面举例使用下 text = ''' <div class="bus_vtem"> <a href="https://www.aisinei.org/thread-17

【源代码】基于Android和蓝牙的单片机温度採集系统

如需转载请标明出处:http://blog.csdn.net/itas109 QQ技术交流群:129518033 STC89C52单片机通过HC-06蓝牙模块与Android手机通信实例- 基于Android和蓝牙的单片机温度採集系统 整个project下载:http://download.csdn.net/detail/itas109/7539057 当中包含. 1.下位机电路原理图 2.下位机採集温度.控制发送.自己主动纠错代码 3.Android端接收温度并显示代码 文件截图 这个是我当年

自己动手写工具:百度图片批量下载器

开篇:在某些场景下,我们想要对百度图片搜出来的东东进行保存,但是一个一个得下载保存不仅耗时而且费劲,有木有一种方法能够简化我们的工作量呢,让我们在离线模式下也能爽爽地浏览大量的美图呢?于是,我们想到了使用网络抓取去帮我们去下载图片,并且保存到我们设定的文件夹中,现在我们就来看看如何来设计开发一个这样的图片批量下载器. 一.关于网络抓取与爬虫 网络蜘蛛的主要作用是从Internet上不停地下载网络资源.它的基本实现思想就是通过一个或多个入口网址来获取更多的URL,然后通过对这些URL所指向的网络资