AVFoundation
框架提供了播放音訊和視訊的工具,使用 AVFoundation 基本能滿足我們的大部分的播放需求。
AVPlayer
提供了音量調節的功能,但是 這種調節屬於 APP 級別的控制,是獨立於系統音量,調節大小不會影響系統音量。但是有時候我們需要調節系統音量,以免如果系統音量過小,APP 調節音量的效果並不明顯。
使用MPVolumeView
調節系統音量
MPVolumeView
是Media Player Framework
中的一個UI元件,直接包含了對系統音量和Airplay
裝置的音訊映象路由的控制功能。其中包含一個MPVolumeSlider
的subview
用來控制音量。這個MPVolumeSlider
是一個私有類,我們無法手動建立此類,但這個類是UISlider
的子類。MPVolumeView
的使用很簡單,只需要將其加入到一個父檢視中,給予父檢視合適的大小,再建立MPVolumeView示例,將其加入到父檢視中即可,蘋果官方的文件中有示例程式碼可以參考。
但是使用 MPVolumeView
有個缺點就是 UI 不能自定義,顯示出來的效果始終是系統的樣式。而且不能新增手勢控制
自定義音量提示
要獲取系統的音量 需要使用
#import <MediaPlayer/MPVolumeView.h>
複製程式碼
/**
音量的 view
把系統的音量的 view 的 frame 設定到根本看不見的地方,這樣就不會覆蓋自定義的 提示 view
*/
- (MPVolumeView *)volumeView {
if (_volumeView == nil) {
// 如果要顯示音量的 view 可在這裡設定,預設只調整音量,沒有顯示View
_volumeView = [[MPVolumeView alloc] initWithFrame:CGRectMake(-20, -20, 10, 10)];
_volumeView.hidden = NO;
[self addSubview:_volumeView];
}
return _volumeView;
}
/**
音量 slider
@return slider
*/
- (UISlider *)volumeSlider {
if (_volumeSlider== nil) {
for (UIView *subView in [self.volumeView subviews]) {
if ([subView.class.description isEqualToString:@"MPVolumeSlider"]) {
_volumeSlider = (UISlider*)subView;
break;
}
}
}
return _volumeSlider;
}
複製程式碼
把 volumeView
的 frame 放到螢幕以外的地方,這樣就不會看到系統的音量提示,而且不影響其他的操作(這個是不能隱藏的,設定 hidden
無效)
volumeSlider.value
就是當前獲取到的系統的音量
然後在當前播放的 view 上新增滑動手勢,監聽手勢的滑動方向和範圍來改變 volumeSlider.value
就是改變了 系統的音量
手勢控制
- (void)addPanGestureRecoginizer {
self.panGesture = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(controlVolumeAndLigint:)];
[self addGestureRecognizer:self.panGesture];
}
複製程式碼
- (void)controlVolumeAndLigint:(UIPanGestureRecognizer *)gesture {
// 獲取手勢位置
CGPoint locationPoint = [gesture locationInView:self];
// 獲取手勢速度
CGPoint speed = [gesture velocityInView:self];
switch (gesture.state) {
case UIGestureRecognizerStateBegan:
{
self.isPanOnView = YES;
CGFloat x = fabs(speed.x);
CGFloat y = fabs(speed.y);
if (x < y) {
self.panDirection = LiveAVPLayerPanDirectionVerticalModed;
// 開始滑動的時候,狀態改為正在控制音量
if (locationPoint.x > self.bounds.size.width / 2) {
}else {
// 狀態改為顯示亮度調節
}
}
}
break;
case UIGestureRecognizerStateChanged:
{
switch (self.panDirection) {
case LiveAVPLayerPanDirectionVerticalModed:
{
// 音量或者亮度調整
[self verticalMoved:speed.y];
}
break;
case LiveAVPLayerPanDirectionHorizontalMoved:
{
// 水平移動 暫時不做進度調整
}
break;
default:
break;
}
}
break;
case UIGestureRecognizerStateEnded:
{
[self hiddenHintView];
}
break;
default:
break;
}
}
複製程式碼
在這裡根據滑動的距離計算需要修改的數值
hintView
是我自定義的提示 view,可以根據型別顯示不同的圖片,根據數值顯示 百分比
這裡就可以根據自己的需求去自定義了
- (void)verticalMoved:(CGFloat)value {
//該value為手指的滑動速度,一般最快速度值不會超過10000,保證在0-1之間,往下滑為正,往上滑為負 所以用 “-=”
value = value / 1000;
if (self.isVolume) {
[self.volumeSlider setValue:(self.volumeSlider.value - value) animated:NO];
if (self.volumeSlider.value > 1.0f) {
[self.volumeSlider setValue:1 animated:NO];
}
else if (self.volumeSlider.value < 0.0f) {
[self.volumeSlider setValue:0 animated:NO];
}
[self.volumeSlider sendActionsForControlEvents:UIControlEventTouchUpInside];
self.hintView.types = volumType;
[self.hintView tinkerUp:self.volumeSlider.value With:0.0];
}
else {
[UIScreen mainScreen].brightness -= value;
if ([UIScreen mainScreen].brightness > 1.0f) {
[UIScreen mainScreen].brightness = 1.0f;
}
else if ([UIScreen mainScreen].brightness < 0.0f) {
[UIScreen mainScreen].brightness = 0.0f;
}
self.hintView.types = lightType;
[self.hintView tinkerUp:[UIScreen mainScreen].brightness With:0.0];
}
}
複製程式碼
[UIScreen mainScreen].brightness = 1.0f;
[UIScreen mainScreen].brightness 是系統的亮度,建議在退出播放的時候恢復調整之前的亮度