iOS通过手势滑动改变屏幕声音和亮度和播放进度【类bilibili界面操作】

嗨呀,这个礼拜尽把时间花在坑爹的外包项目上了,第一次做了一个功能相对完善的播放器,播放器是基于百度的云播放SDK,然后我把控制器这块的主要功能全都实现,这里单独写一下关于利用手势去控制音量亮度和播放进度的问题。

先把展示的一些属性定义好

@interface PlayerControlVC () <UIGestureRecognizerDelegate>
{
    CGPoint _currentPoint;
    float _systemVolume; // 系统声音大小
    BOOL _isComplate;// 播放完成
    BOOL _isGes;// 滑动手势只执行一次
    MPVolumeView *sysVolumeView ;// 不显示系统音量提示
    
    UIImageView *blightView;// 明暗提示图
    UIImageView *voiceView; // 音量提示图
    UIImageView *seekView; // 快进快退提示图
    UIProgressView *blightPtogress; // 明暗提示
    UIProgressView *volumeProgress; // 音量提示
    
    float _origional; // 原始数据
}

// 是否正在拖拽
@property (nonatomic, assign) BOOL progressDragging;

@property (strong, nonatomic) MPMusicPlayerController *mpc;

这里的

UIProgressView *blightPtogress; // 明暗提示

UIProgressView *volumeProgress; // 音量提示

表示的是音量和亮度的刻度

然后在viewdidload的时候把这些需要实现的元素实现,以及在viewDidLayoutSubviews的时候把几个需要居中显示的元素居中

- (void)viewDidLoad {
    [super viewDidLoad];
    
    [self optimizationView].progressView = self.slider;
    
    UIImage *blightImage = [UIImage imageNamed:@"blight"];
    UIImage *voiceImage = [UIImage imageNamed:@"volume"];
    
    blightView = [[UIImageView alloc] initWithFrame:CGRectMake(0, 0, 150, 150)];
    blightView.image = blightImage;
    blightView.alpha=0.0;
    blightView.backgroundColor = [UIColor clearColor];
    [self.view addSubview:blightView];
    
    voiceView = [[UIImageView alloc] initWithFrame:CGRectMake(0, 0, 150, 150)];
    voiceView.image = voiceImage;
    voiceView.alpha=0.0;
    voiceView.backgroundColor = [UIColor clearColor];
    [self.view addSubview:voiceView];
    
    seekView = [[UIImageView alloc]initWithFrame:CGRectMake(0, 0, 50, 50)];
    seekView.image = [UIImage imageNamed:@"icon_backoff"];
    seekView.alpha = 0.0;
    [self.view addSubview:seekView];
    
    blightPtogress = [[UIProgressView alloc] initWithFrame:CGRectMake(20,blightView.frame.size.height-20,blightView.frame.size.width-40,20)];
    blightPtogress.backgroundColor = [UIColor clearColor];
    blightPtogress.trackTintColor = [UIColor blackColor];
    blightPtogress.progressTintColor = [UIColor whiteColor];
    blightPtogress.progress = 0.5f;
    // 改变进度条的粗细
    blightPtogress.transform = CGAffineTransformMakeScale(1.0f,2.0f);
    blightPtogress.progressViewStyle = UIProgressViewStyleBar;
    [blightView addSubview:blightPtogress];
    
    volumeProgress = [[UIProgressView alloc] initWithFrame:CGRectMake(20,blightView.frame.size.height-20,blightView.frame.size.width-40,20)];
    volumeProgress.backgroundColor = [UIColor clearColor];
    volumeProgress.trackTintColor = [UIColor blackColor];
    volumeProgress.progress = 0.5f;
    volumeProgress.transform = CGAffineTransformMakeScale(1.0f,2.0f);
    volumeProgress.progressViewStyle= UIProgressViewStyleBar;
    volumeProgress.progressTintColor = [UIColor whiteColor];
    [voiceView addSubview:volumeProgress];
    
    // 添加滑动手势
    UIPanGestureRecognizer *panGesture = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(panGestureDown:)];
    panGesture.delegate = self;
    [self.view addGestureRecognizer:panGesture];
    
    self.mpc = [MPMusicPlayerController applicationMusicPlayer];
    
    // 隐藏系统音量显示
    sysVolumeView=[MPVolumeView new];
    sysVolumeView.frame = CGRectMake(-1000, -1000, 0, 0);
    [self.view addSubview:sysVolumeView];
}

- (void)viewDidLayoutSubviews {
    [super viewDidLayoutSubviews];
    blightView.center = self.view.center;
    voiceView.center = self.view.center;
    seekView.center = self.view.center;
}

// 添加滑动手势
UIPanGestureRecognizer *panGesture = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(panGestureDown:)];
panGesture.delegate = self;
[self.view addGestureRecognizer:panGesture];

UIPanGestureRecognizer指的是手指的拖动,与他相对于的还有相面几个手势api

  • tap:轻触
  • long press:在一点上长按
  • pinch:两个指头捏或者放的操作
  • pan:手指的拖动
  • swipe:手指在屏幕上很快的滑动
  • rotation:手指反向操作

这里就先不过多赘述了。

最后是关于整个panGestureDown的实现,这个也是整个方法的关键我们分步来解释
想要获取用户的动作,首先你要先获得用户点击的第一个点,同时还要注意不要和原来的UISliber发生冲突,下面的_currentPoint就是你第一个点。


#pragma mark - 手势代理 解决手势冲突问题,不要忘记添加代理delegate

-(BOOL)gestureRecognizer:(UIGestureRecognizer*)gestureRecognizer shouldReceiveTouch:(UITouch*)touch{
    
    // NSLog(@"touch.view=====%@",touch.view);
    if([touch.view isKindOfClass:[UISlider class]]){
        return NO;
    }else{
        return YES;
    }
}
-(void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{
    
    _currentPoint = [[touches anyObject] locationInView:self.view];
}

下面的代码全都是写在panGestureDown我这里分段描述

-(void)panGestureDown:(UIPanGestureRecognizer*)sender

    CGFloat sliberWith;
    if (FullScreen) {
        sliberWith = SCREEN_WIDTH;
    } else {
        sliberWith = SCREEN_HEIGHT;
    }
    
    CGPoint point = [sender locationInView:self.view];// 上下控制点
    CGPoint tranPoint = [sender translationInView:self.view];//播放进度
    typedef NS_ENUM(NSUInteger, UIPanGestureRecognizerDirection) {
        UIPanGestureRecognizerDirectionUndefined,
        UIPanGestureRecognizerDirectionUp,
        UIPanGestureRecognizerDirectionDown,
        UIPanGestureRecognizerDirectionLeft,
        UIPanGestureRecognizerDirectionRight
    };

sliberWith是用来判断用户的屏幕到底是取手机的宽度还是高度的,通过fullscreen来判断,至于fullscreen是怎么来的,大家自己通过具体情况添加就好。
然后是关于控制点point和进度tranPoint的获取;
再自己定义5个状态来表示你需要的4个手势,

最后是4个手势以及UIGestureRecognizerStateEndedUIGestureRecognizerStateEnded代表用户把手指移开屏幕时的动作,在这个时候你就可以对这个动作做最后的行动了。


    static UIPanGestureRecognizerDirection direction = UIPanGestureRecognizerDirectionUndefined;
    switch (sender.state) {
        case UIGestureRecognizerStateBegan: {
            _origional = self.slider.value;// 记录开始滑动位置
            if (direction == UIPanGestureRecognizerDirectionUndefined) {
                CGPoint velocity = [sender velocityInView:self.view];
                BOOL isVerticalGesture = fabs(velocity.y) > fabs(velocity.x);
                if (isVerticalGesture) {
                    if(!FullScreen){
                        return;// 只有横屏才可以调节音量和亮度
                    }
                    if (velocity.y > 0) {
                        direction = UIPanGestureRecognizerDirectionDown;
                    } else {
                        direction = UIPanGestureRecognizerDirectionUp;
                    }
                }
                else {
                    if (velocity.x > 0) {
                        direction = UIPanGestureRecognizerDirectionRight;
                    } else {
                        direction = UIPanGestureRecognizerDirectionLeft;
                    }
                }
            }
            break;
        }
        case UIGestureRecognizerStateChanged: {
            
            switch (direction) {
                case UIPanGestureRecognizerDirectionUp: {
                    
                    float dy = point.y - _currentPoint.y;
                    int index = (int)dy;
                    // 左侧 上下改变亮度
                    if (_currentPoint.x < self.view.frame.size.width / 2) {
                        blightView.alpha = 1.0f;
                        if(index >0){
                            [UIScreen mainScreen].brightness = [UIScreen mainScreen].brightness - 0.01;
                        } else {
                            [UIScreen mainScreen].brightness = [UIScreen mainScreen].brightness + 0.01;
                        }
                        blightPtogress.progress =[UIScreen mainScreen].brightness;
                    } else {// 右侧上下改变声音
                        voiceView.alpha = 1.0f;
                        if (index > 0) {
                            [self setVolumeDown];
                        }else{
                            [self setVolumeUp];
                        }
                        volumeProgress.progress = _systemVolume;
                    }
                    break;
                }
                case UIPanGestureRecognizerDirectionDown: {
                    float dy = point.y - _currentPoint.y;
                    int index = (int)dy;
                    // 左侧 上下改变亮度
                    if (_currentPoint.x <self.view.frame.size.width/2) {
                        blightView.alpha = 1.0f;
                        if (index > 0) {
                            [UIScreen mainScreen].brightness = [UIScreen mainScreen].brightness - 0.01;
                        } else {
                            [UIScreen mainScreen].brightness = [UIScreen mainScreen].brightness + 0.01;
                        }
                        blightPtogress.progress = [UIScreen mainScreen].brightness;
                    } else {
                        // 右侧上下改变声音
                        voiceView.alpha =1.0f;
                        if (index > 0) {
                            [self setVolumeDown];
                        }else{
                            [self setVolumeUp];
                        }
                        volumeProgress.progress = _systemVolume;
                    }
                    break;
                }
                case UIPanGestureRecognizerDirectionLeft: {
                    if (_isGes ==NO) {
                        NSLog(@"Left");
                        _isGes =YES;
                        self.progressDragging = YES;
                    }
                    if (FullScreen) {
                        seekView.alpha = 1.0f;
                        seekView.image = [UIImage imageNamed:@"icon_backoff"];
                    }
                    // 手势滑动控制 快进进度
                    if (tranPoint.x / sliberWith +_origional <= 0) {
                        self.slider.value = 0.0f;
                    } else {
                        self.slider.value = (tranPoint.x/sliberWith) * 100 + _origional;
                    }
                    break;
                }
                case UIPanGestureRecognizerDirectionRight: {
                    if (_isGes == NO) {
                        NSLog(@"Right");
                        _isGes = YES;
                        self.progressDragging = YES;
                    }
                    if (FullScreen) {
                        seekView.alpha = 1.0f;
                        seekView.image = [UIImage imageNamed:@"icon_forward"];
                    }
                    if (tranPoint.x/sliberWith +_origional <=0 ) {
                        self.slider.value = 0.0f;
                    } else {
                        self.slider.value = (tranPoint.x / sliberWith) * 100 +_origional;
                    }
                    break;
                }
                default: {
                    break;
                }
            }
            break;
        }
        case UIGestureRecognizerStateEnded: {
            _isGes =NO;
            NSLog(@"end");
            _origional = self.slider.value;// 记录结束滑动位置
            direction = UIPanGestureRecognizerDirectionUndefined;
            [self updateIdleTime];
            [self.delegate seek:self.slider.value];
            [UIView animateWithDuration:0.5f animations:^{
                blightView.alpha = 0.0f;
                voiceView.alpha = 0.0f;
                seekView.alpha = 0.0f;
            }];
            break;
        }
        default:
            break;
    }

最后再把音量的两个方法加上

-(void)setVolumeUp
{
    _systemVolume = _systemVolume+0.01;
    NSLog(@"%f",_systemVolume);
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
    self.mpc.volume = _systemVolume;
#pragma GCC diagnostic pop
}
-(void)setVolumeDown{
    
    _systemVolume = _systemVolume-0.01;
    NSLog(@"%f",_systemVolume);
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
    self.mpc.volume = _systemVolume;
#pragma GCC diagnostic pop
}

这里直接用self.mpc.volume比再去写一套MPVolumeView要方便的多。

这次内容主要参考的是天明天这篇博客

总得来说其实并没有很多的知识点,主要是关于UIPanGestureRecognizer的具体应用,也算学到了很多。不过这次项目是真的紧,揪心啊- -明明应该是少说要20天完成的工作,硬是让我们7个工作日搞定,嗨呀,只能被迫从百度云播放现有的SDK Demo基础上进行修改了,还好值得庆幸的是我改出来了,阿弥陀佛

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 217,907评论 6 506
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,987评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,298评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,586评论 1 293
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,633评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,488评论 1 302
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,275评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,176评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,619评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,819评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,932评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,655评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,265评论 3 329
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,871评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,994评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,095评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,884评论 2 354

推荐阅读更多精彩内容