231

如何将 iPhone 设置为振动一次?

例如,当玩家失去生命或游戏结束时,iPhone 应该会振动。

4

12 回答 12

406

来自“ iPhone 教程:检查 iOS 设备功能的更好方法”:

有两个看似相似的函数带有一个参数kSystemSoundID_Vibrate

1) AudioServicesPlayAlertSound(kSystemSoundID_Vibrate);
2) AudioServicesPlaySystemSound(kSystemSoundID_Vibrate);

这两个功能都会震动 iPhone。但是,当您在不支持振动的设备上使用第一个功能时,它会发出哔声。另一方面,第二个功能在不受支持的设备上没有任何作用。因此,如果您要连续振动设备,就像常识所说的警报一样,请使用功能 2。

AudioToolbox.framework首先,在 Build Phases中将 AudioToolbox 框架添加到您的目标。

然后,导入这个头文件:

#import <AudioToolbox/AudioServices.h>
于 2011-01-18T14:11:41.103 回答
46

斯威夫特 2.0+

AudioToolbox 现在将 呈现kSystemSoundID_Vibrate为一种SystemSoundID类型,因此代码为:

import AudioToolbox.AudioServices

AudioServicesPlaySystemSound(kSystemSoundID_Vibrate)
AudioServicesPlayAlertSound(kSystemSoundID_Vibrate)

而不是必须通过额外的演员步骤

(@Dov 的道具)

原始答案(Swift 1.x)

而且,这就是你在Swift上的做法(以防你遇到和我一样的麻烦)

链接AudioToolbox.framework(转到您的项目,选择您的目标,构建阶段,将二进制文件与库链接,在此处添加库)

一旦完成:

import AudioToolbox.AudioServices

// Use either of these
AudioServicesPlaySystemSound(SystemSoundID(kSystemSoundID_Vibrate))
AudioServicesPlayAlertSound(SystemSoundID(kSystemSoundID_Vibrate))

俗气的事情是,SystemSoundID它基本上是 a 的typealias(花哨的 swift typedefUInt32,而 thekSystemSoundID_Vibrate是常规的Int。编译器会为您尝试从InttoUInt32转换时出现错误,但该错误显示为“无法转换为 SystemSoundID”,这令人困惑。为什么苹果不让它成为一个 Swift 枚举超出了我的范围。

@aponomarenko 的详细信息,我的回答只是针对那里的 Swifters。

于 2014-09-29T07:38:11.483 回答
35

一个简单的方法是使用音频服务:

#import <AudioToolbox/AudioToolbox.h> 
...    
AudioServicesPlaySystemSound(kSystemSoundID_Vibrate);
于 2011-01-18T14:08:15.593 回答
33

对于以某种方式关闭振动的设备,我遇到了很大的麻烦,但无论如何我们都需要它工作,因为它对我们的应用程序功能至关重要,而且由于它只是记录方法调用的整数,它会通过验证。所以我在这里尝试了一些有据可查的声音:TUNER88/iOSSystemSoundsLibrary

然后我偶然发现了 1352,无论静音开关或设备上的设置如何,它都能正常工作(Settings->vibrate on ring, vibrate on silent)

- (void)vibratePhone;
{
     if([[UIDevice currentDevice].model isEqualToString:@"iPhone"])
     {
         AudioServicesPlaySystemSound (1352); //works ALWAYS as of this post
     }
     else
     {
          // Not an iPhone, so doesn't have vibrate
          // play the less annoying tick noise or one of your own
          AudioServicesPlayAlertSound (1105);
     }
}
于 2014-04-03T16:41:43.040 回答
26

重要提示:未来弃用警报。

iOS 9.0开始,API函数描述为:

AudioServicesPlaySystemSound(inSystemSoundID: SystemSoundID)
AudioServicesPlayAlertSound(inSystemSoundID: SystemSoundID)

包括以下注释:

This function will be deprecated in a future release.
Use AudioServicesPlayAlertSoundWithCompletion or  
AudioServicesPlaySystemSoundWithCompletion instead.

正确的方法是使用以下两种方法中的任何一种:

AudioServicesPlayAlertSoundWithCompletion(kSystemSoundID_Vibrate, nil)

或者

AudioServicesPlayAlertSoundWithCompletion(kSystemSoundID_Vibrate) {
 //your callback code when the vibration is done (it may not vibrate in iPod, but this callback will be always called)
}

记得import AVFoundation

于 2015-10-08T19:34:00.820 回答
10

对于 iPhone 7/7 Plus 或更新版本,请使用这三个 Haptic 反馈 API。

可用的 API

对于通知:

let generator = UINotificationFeedbackGenerator()
generator.notificationOccured(style: .error)

可用的样式是.error.success.warning。每个人都有自己独特的感觉。
文档

一个具体的UIFeedbackGenerator子类,它创建触觉来传达成功、失败和警告。

对于简单的振动:

let generator = UIImpactFeedbackGenerator(style: .medium)
generator.impactOccured()

可用的样式是.heavy.medium.light。这些是具有不同“硬度”程度的简单振动。
文档

UIFeedbackGenerator创建触觉以模拟物理影响的具体子类

当用户选择一个项目时

let generator = UISelectionFeedbackGenerator()
generator.selectionChanged()

这是所有触觉中最不引人注目的,因此最适合触觉不应该接管应用程序体验的情况。
文档

UIFeedbackGenerator创建触觉以指示选择更改的具体子类。

笔记

使用这些 API 时有几件事值得记住。

注A

您实际上并没有创建触觉。请求系统生成触觉。系统将根据以下情况做出决定:

  • 如果设备上的触觉是可能的(在这种情况下它是否有触觉引擎)
  • 应用程序是否可以录制音频(在录制过程中不会产生触觉以防止不必要的干扰)
  • 是否在系统设置中启用触觉。

因此,如果不可能,系统将默默地忽略您对触觉的请求。如果这是由于设备不受支持,您可以尝试以下操作:

func haptic() {
    // Get whether the device can generate haptics or not
    // If feedbackSupportLevel is nil, will assign 0
    let feedbackSupportLevel = UIDevice.current.value(forKey: "_feedbackSupportLevel") as? Int ?? 0

    switch feedbackSupportLevel { 
    case 2:
        // 2 means the device has a Taptic Engine
        // Put Taptic Engine code here, using the APIs explained above

    case 1: 
    // 1 means no Taptic Engine, but will support AudioToolbox
    // AudioToolbox code from the myriad of other answers!

    default: // 0
        // No haptic support
        // Do something else, like a beeping noise or LED flash instead of haptics
    }

替换switch-case语句中的注释,此触觉生成代码将可移植到其他 iOS 设备。它将产生最高水平的触觉。

注B

  • 由于生成触觉是硬件级别的任务,因此在调用触觉生成代码与实际发生之间可能存在延迟。出于这个原因,Taptic Engine API 都有一个prepare()方法,可以让它处于准备状态。使用您的 Game Over 示例:您可能知道游戏即将结束,因为用户的 HP 非常低,或者附近有危险的怪物。
  • 如果您在几秒钟内没有产生触觉,触觉引擎将回到空闲状态(以节省电池寿命)


在这种情况下,准备 Taptic Engine 将创造更高质量、更灵敏的体验。

例如,假设您的应用程序使用平移手势识别器来更改世界的可见部分。您希望在用户 360 度“看”时生成触觉。这是您可以使用的方法prepare()

@IBAction func userChangedViewablePortionOfWorld(_ gesture: UIPanGestureRecogniser!) {

    haptic = UIImpactFeedbackGenerator(style: .heavy)

    switch gesture.state {
        case .began:
            // The user started dragging the screen.
            haptic.prepare()

        case .changed:
            // The user trying to 'look' in another direction
            // Code to change viewable portion of the virtual world

            if virtualWorldViewpointDegreeMiddle = 360.0 { 
                haptic.impactOccured()
            }
        
        default:
            break

} 
于 2019-05-02T10:17:16.193 回答
5

在我的旅行中,我发现如果您在录制音频时尝试以下任一操作,即使启用了设备也不会振动。

1) AudioServicesPlayAlertSound(kSystemSoundID_Vibrate);
2) AudioServicesPlaySystemSound(kSystemSoundID_Vibrate);

我的方法是在测量设备运动的特定时间调用的。我不得不停止录音,然后在振动发生后重新开始。

它看起来像这样。

-(void)vibrate {
    [recorder stop];
    AudioServicesPlaySystemSound (kSystemSoundID_Vibrate);
    [recorder start];
}

recorder是一个 AVRecorder 实例。

希望这可以帮助以前遇到同样问题的其他人。

于 2013-11-19T23:54:58.333 回答
5

如果您使用 Xamarin (monotouch) 框架,只需调用

SystemSound.Vibrate.PlayAlertSound()
于 2013-10-29T09:10:54.613 回答
5

在 iOS 10 和较新的 iPhone 上,您还可以使用触觉 API。这种触觉反馈比 AudioToolbox API 更柔和。

对于您的 GAME OVER 场景,重的 UI 影响反馈应该是合适的。

UIImpactFeedbackGenerator(style: .heavy).impactOccurred()

您可以使用其他触觉反馈样式

于 2018-04-30T02:53:05.350 回答
1

在斯威夫特:

import AVFoundation
...
AudioServicesPlaySystemSound(SystemSoundID(kSystemSoundID_Vibrate))
于 2015-08-07T08:44:33.457 回答
0

就我而言,我使用的是 AVCaptureSession。AudioToolbox 处于项目的构建阶段,已导入但仍无法正常工作。为了使它起作用,我在振动之前停止了会话,然后继续。

#import <AudioToolbox/AudioToolbox.h>
...
@property (nonatomic) AVCaptureSession *session;
...
- (void)vibratePhone;
{
  [self.session stopRunning];
     NSLog(@"vibratePhone %@",@"here");
    if([[UIDevice currentDevice].model isEqualToString:@"iPhone"])
    {
        AudioServicesPlaySystemSound (kSystemSoundID_Vibrate); 
    }
    else
    {
        AudioServicesPlayAlertSound (kSystemSoundID_Vibrate);
    }
  [self.session startRunning];
}
于 2015-07-01T10:47:29.360 回答
-5

您可以使用

1) AudioServicesPlayAlertSound(kSystemSoundID_Vibrate);

适用于 iPhone 和一些较新的 iPod。

2) AudioServicesPlaySystemSound(kSystemSoundID_Vibrate);

适用于 iPad。

于 2015-03-30T11:36:03.997 回答