美文网首页IOS 超级无敌GPUImage学习【资料】
GPUImage解析(十二) —— 一个简单的实例之添加水印(七

GPUImage解析(十二) —— 一个简单的实例之添加水印(七

作者: 刀客传奇 | 来源:发表于2017-09-14 23:56 被阅读90次

    版本记录

    版本号 时间
    V1.0 2017.09.14

    前言

    GPUImage是直接利用显卡实现视频或者图像处理的技术。感兴趣可以看上面几篇文章。
    1. GPUImage解析(一) —— 基本概览(一)
    2. GPUImage解析(二) —— 基本概览(二)
    3. GPUImage解析(三) —— 基本概览(三)
    4. GPUImage解析(四) —— 安装方法及框架介绍
    5. GPUImage解析(五) —— 框架中的几个基类
    6. GPUImage解析(六) —— 一个简单的实例(一)
    7. GPUImage解析(七) —— 一个简单的实例结合GPUImageVideoCamera(二)
    8. GPUImage解析(八) —— 一个简单的实例之多滤镜视频采集存储(三)
    9. GPUImage解析(九) —— 一个简单的实例之GPUImageTiltShiftFilter滤镜处理(四)
    10. GPUImage解析(十) —— 一个简单的实例之实时更改视频的滤镜值(五)
    11. GPUImage解析(十一) —— 一个简单的实例之视频的叠加混合(六)

    功能要求

    实现视频添加水印的效果。


    功能实现

    下面看示例代码。

    #import "JJGPUWatermarkVC.h"
    #import "GPUImage.h"
    #import <AssetsLibrary/ALAssetsLibrary.h>
    #import "Masonry.h"
    
    #define kWidth [UIScreen mainScreen].bounds.size.width
    #define kHeight [UIScreen mainScreen].bounds.size.height
    
    @interface JJGPUWatermarkVC ()
    
    @property (nonatomic, strong) GPUImageMovie *imageMovie;
    @property (nonatomic, strong) GPUImageOutput <GPUImageInput> *blendFilter;
    @property (nonatomic, strong) GPUImageMovieWriter *movieWriter;
    @property (nonatomic, strong) UILabel *tipLabel;
    @property (nonatomic, strong) GPUImageView *imageView;
    @property (nonatomic, copy) NSString *pathStr;
    @property (nonatomic, strong) NSURL *movieURL;
    
    @end
    
    @implementation JJGPUWatermarkVC
    
    #pragma mark - Override Base Function
    
    - (void)viewDidLoad
    {
        [super viewDidLoad];
        
        [self setupUI];
        
        [self setupConfig];
    }
    
    - (void)viewWillAppear:(BOOL)animated
    {
        [super viewWillAppear:animated];
        
        self.navigationController.navigationBarHidden = YES;
    }
    
    - (void)viewWillDisappear:(BOOL)animated
    {
        [super viewWillDisappear:animated];
        
        self.navigationController.navigationBarHidden = NO;
    }
    
    #pragma mark - Object Private Function
    
    - (void)setupUI
    {
        //实例化GPUImageView
        self.imageView = [[GPUImageView alloc] initWithFrame:self.view.frame];
        [self.view addSubview:self.imageView];
        
        //显示label
        self.tipLabel = [[UILabel alloc] init];
        self.tipLabel.textColor = [UIColor blueColor];
        self.tipLabel.font = [UIFont systemFontOfSize:20.0];
        [self.view addSubview:self.tipLabel];
        
        [self.tipLabel mas_makeConstraints:^(MASConstraintMaker *make) {
            make.centerX.equalTo(self.view);
            make.top.equalTo(self.view).offset(20.0);
        }];
    }
    
    - (void)setupConfig
    {
        //滤镜
        self.blendFilter = [[GPUImageDissolveBlendFilter alloc] init];
        [(GPUImageDissolveBlendFilter *)self.blendFilter setMix:0.5];
        
        //播放
        NSURL *resourceURL = [[NSBundle mainBundle] URLForResource:@"lili" withExtension:@"mp4"];
        AVAsset *asset = [AVAsset assetWithURL:resourceURL];
        
        //实例化GPUImageMovie
        self.imageMovie = [[GPUImageMovie alloc] initWithAsset:asset];
        self.imageMovie.runBenchmark = YES;
        self.imageMovie.playAtActualSpeed = YES;
        
        //水印提示文字
        UILabel *watermarkLabel = [[UILabel alloc] init];
        watermarkLabel.text  = @"水印";
        watermarkLabel.font = [UIFont systemFontOfSize:30.0];
        watermarkLabel.textColor = [UIColor redColor];
        
        //水印图片
        UIView *backView = [[UIView alloc] initWithFrame:self.view.frame];
        backView.backgroundColor = [UIColor clearColor];
        [self.view addSubview:backView];
        
        UIImageView *watermarkImageView = [[UIImageView alloc] init];
        watermarkImageView.image = [UIImage imageNamed:@"light_4"];
        watermarkImageView.center = CGPointMake(kHeight / 2, kWidth / 2);
        
        [backView addSubview:watermarkLabel];
        [backView addSubview:watermarkImageView];
        
        [watermarkImageView mas_makeConstraints:^(MASConstraintMaker *make) {
            make.center.equalTo(backView);
            make.height.equalTo(@(50.0));
            make.width.equalTo(@(50.0));
        }];
    
        [watermarkLabel sizeToFit];
        [watermarkLabel mas_makeConstraints:^(MASConstraintMaker *make) {
            make.center.equalTo(backView);
        }];
    
        //实例化GPUImageUIElement
        GPUImageUIElement *uiElement = [[GPUImageUIElement alloc] initWithView:backView];
    
        //存储相关
        NSString *pathStr = [NSHomeDirectory() stringByAppendingPathComponent:@"Documents/Movie.m4v"];
        unlink([pathStr UTF8String]);
        self.pathStr = pathStr;
        NSURL *movieURL = [NSURL fileURLWithPath:pathStr];
        self.movieURL = movieURL;
        
        //实例化GPUImageMovieWriter
        self.movieWriter = [[GPUImageMovieWriter alloc] initWithMovieURL:movieURL size:CGSizeMake(640.0, 480.0)];
        
        GPUImageFilter *imageFilter = [[GPUImageFilter alloc] init];
        [self.imageMovie addTarget:imageFilter];
        [imageFilter addTarget:self.blendFilter];
        [uiElement addTarget:self.blendFilter];
        
        self.movieWriter.shouldPassthroughAudio = YES;
        [self.imageMovie enableSynchronizedEncodingUsingMovieWriter:self.movieWriter];
        
        //显示
        [self.blendFilter addTarget:self.imageView];
        [self.blendFilter addTarget:self.movieWriter];
        [self.movieWriter startRecording];
        [self.imageMovie startProcessing];
        
        CADisplayLink *displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(displayProgress)];
        [displayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSRunLoopCommonModes];
        displayLink.paused = NO;
        
        [imageFilter setFrameProcessingCompletionBlock:^(GPUImageOutput *output, CMTime time){
            CGRect frame = watermarkImageView.frame;
            frame.origin.x += 0.5;
            frame.origin.y += 0.5;
            watermarkImageView.frame = frame;
            [uiElement updateWithTimestamp:time];
        }];
        
        //存储
        __weak typeof(self) weakSelf = self;
        [self.movieWriter setCompletionBlock:^{
            __strong typeof(self) strongSelf = weakSelf;
            [strongSelf.blendFilter removeTarget:strongSelf.movieWriter];
            [strongSelf.movieWriter finishRecording];
            
            ALAssetsLibrary *library = [[ALAssetsLibrary alloc] init];
            if (UIVideoAtPathIsCompatibleWithSavedPhotosAlbum(strongSelf.pathStr))
            {
                [library writeVideoAtPathToSavedPhotosAlbum:strongSelf.movieURL completionBlock:^(NSURL *assetURL, NSError *error)
                 {
                     dispatch_async(dispatch_get_main_queue(), ^{
                         
                         if (error) {
                             NSLog(@"保存失败");
                         }
                         else {
                             NSLog(@"保存成功");
                         }
                     });
                 }];
            }
        }];
    }
    
    #pragma mark - Action && Notification
    
    - (void)displayProgress
    {
        NSLog(@"self.imageMovie.progress = %f", self.imageMovie.progress);
        self.tipLabel.text = [NSString stringWithFormat:@"Progress = %.2f%%",self.imageMovie.progress * 100];
        [self.tipLabel sizeToFit];
    }
    
    @end
    

    功能效果

    下面我们就给出几个效果图。分别是录制时和存储在相册回放时候的效果。

    后记

    未完,待续~~~

    相关文章

      网友评论

        本文标题:GPUImage解析(十二) —— 一个简单的实例之添加水印(七

        本文链接:https://www.haomeiwen.com/subject/iadjsxtx.html