播放系统声音而不导入自己的声音

问题描述 投票:43回答:9

是否可以在不导入自己的声音的情况下播放现有的系统声音?

iphone objective-c ios
9个回答
39
投票

此代码播放苹果系统声音“Tock.aiff”..我相信你可以使用它播放不同的系统声音

NSString *path = [[NSBundle bundleWithIdentifier:@"com.apple.UIKit"] pathForResource:@"Tock" ofType:@"aiff"];
SystemSoundID soundID;
AudioServicesCreateSystemSoundID((CFURLRef)[NSURL fileURLWithPath:path], &soundID);
AudioServicesPlaySystemSound(soundID);
AudioServicesDisposeSystemSoundID(soundID);

请参阅this线程

Apple's documentation on System sounds

https://developer.apple.com/documentation/audiotoolbox/system_sound_services


51
投票

我发现这个systemSoundID列表对于直接访问声音ID非常有用。 http://iphonedevwiki.net/index.php/AudioServices

例如,播放按键音响。

#define systemSoundID    1104
AudioServicesPlaySystemSound (systemSoundID);

您还需要在项目中添加AudioToolbox框架,并将#include <AudioToolbox.h>添加到.m或.h文件中。


26
投票

您可以将此用于所有默认系统音频。

例如,对于tap声音用户:

AudioServicesPlaySystemSound(1104);

对于正面声音,请使用:

 AudioServicesPlaySystemSound(1054);

并且,负面声音使用此:

 AudioServicesPlaySystemSound(1053);

完整列表,你可以看到here


16
投票

所有系统声音列表:iOSSystemSoundsLibrary

您可以播放所有这些声音:

AudioServicesPlaySystemSound (systemSoundID);

6
投票

改编自@ yannc2021

http://iphonedevwiki.net/index.php/AudioServices

如果你想在Swift中使用系统声音

// import this
import AVFoundation

// add this method
required init(coder aDecoder: NSCoder) {
    super.init(coder: aDecoder)
}

// declared system sound here
let systemSoundID: SystemSoundID = 1104

// to play sound
AudioServicesPlaySystemSound (systemSoundID)

4
投票

对于swift,你可以看看complete list of system sounds and ringtones的例子。

编辑:好的,这是这个例子中最重要的代码片段:

    ///The directories where sound files are located.
    let rootSoundDirectories: [String] = ["/Library/Ringtones", "/System/Library/Audio/UISounds"]

    ///Array to hold directories when we find them.
    var directories: [String] = []

    ///Tuple to hold directories and an array of file names within.
    var soundFiles: [(directory: String, files: [String])] = []

    //Starting with the "/Library/Ringtones" & "/System/Library/Audio/UISounds" directories, it looks for other sub-directories just one level lower and saves their relative path in directories array.
    //- URLs: All of the contents of the directory (files and sub-directories).
    func getDirectories() {
        let fileManager: NSFileManager = NSFileManager()
        for directory in rootSoundDirectories {
            let directoryURL: NSURL = NSURL(fileURLWithPath: "\(directory)", isDirectory: true)

            do {
                if let URLs: [NSURL] = try fileManager.contentsOfDirectoryAtURL(directoryURL, includingPropertiesForKeys: [NSURLIsDirectoryKey], options: NSDirectoryEnumerationOptions()) {
                    var urlIsaDirectory: ObjCBool = ObjCBool(false)
                    for url in URLs {
                        if fileManager.fileExistsAtPath(url.path!, isDirectory: &urlIsaDirectory) {
                            if urlIsaDirectory {
                                let directory: String = "\(url.relativePath!)"
                                let files: [String] = []
                                let newSoundFile: (directory: String, files: [String]) = (directory, files)
                                directories.append("\(directory)")
                                soundFiles.append(newSoundFile)
                            }
                        }
                    }
                }
            } catch {
                debugPrint("\(error)")
            }
        }
    }

    //For each directory, it looks at each item (file or directory) and only appends the sound files to the soundfiles[i]files array.
    //- URLs: All of the contents of the directory (files and sub-directories).
        func loadSoundFiles() {
            for i in 0...directories.count-1 {
                let fileManager: NSFileManager = NSFileManager()
                let directoryURL: NSURL = NSURL(fileURLWithPath: directories[i], isDirectory: true)

                do {
                    if let URLs: [NSURL] = try fileManager.contentsOfDirectoryAtURL(directoryURL, includingPropertiesForKeys: [NSURLIsDirectoryKey], options: NSDirectoryEnumerationOptions()) {
                        var urlIsaDirectory: ObjCBool = ObjCBool(false)
                        for url in URLs {
                            if fileManager.fileExistsAtPath(url.path!, isDirectory: &urlIsaDirectory) {
                                if !urlIsaDirectory {
                                    soundFiles[i].files.append("\(url.lastPathComponent!)")
                                }
                            }
                        }
                    }
                } catch {
                    debugPrint("\(error)")
                }
            }
        }

该示例在表视图中显示系统声音文件。声音播放如下所示:

override func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
        //Play the sound
        let directory: String = soundFiles[indexPath.section].directory
        let fileName: String = soundFiles[indexPath.section].files[indexPath.row]
        let fileURL: NSURL = NSURL(fileURLWithPath: "\(directory)/\(fileName)")
        do {
            model.audioPlayer = try AVAudioPlayer(contentsOfURL: fileURL)
            model.audioPlayer.play()
        } catch {
            debugPrint("\(error)")
        }
    }

model.audioPlayer只是AVAudioPlayer的一个例子:

///Audio player responsible for playing sound files.
var audioPlayer: AVAudioPlayer = AVAudioPlayer()

4
投票

斯威夫特4 +

注意:仅在真实设备上试用:

import AVKit
AudioServicesPlaySystemSound(1007);

或者您可以尝试使用URL作为 -

let url = URL(fileURLWithPath: "/System/Library/Audio/UISounds/payment_success.caf")
var soundID: SystemSoundID = 0
AudioServicesCreateSystemSoundID(url as CFURL, &soundID)
AudioServicesPlaySystemSound(soundID);

https://github.com/klaas/SwiftySystemSounds/blob/master/README.md


1
投票

这种仅可可解决方案使用现有的音频文件来播放声音。此方法可用于播放任何声音文件。必须将AVFoundation.framework添加到您的框架中。您将必须定义或删除我使用的宏,这些宏是自我解释的。

我在AVAudioPlayer中添加了一个类别,如下所示:

AVAudioPlayer + .H

 #import <AVFoundation/AVAudioPlayer.h>

@interface AVAudioPlayer ( CapSpecs )
+ (AVAudioPlayer*) click;
+ (AVAudioPlayer*) tink;
+ (AVAudioPlayer*) tock;
+ (AVAudioPlayer*) withResourceName: (NSString*) aName;
@end

AVAudioPlayer + .M

 #import "AVAudioPlayer+.h"

@implementation AVAudioPlayer ( CapSpecs )
+ (AVAudioPlayer*) click {
    StaticReturn ( [AVAudioPlayer withResourceName: @"iPod Click"] );
}
+ (AVAudioPlayer*) tink {
    StaticReturn ( [AVAudioPlayer withResourceName: @"Tink"] );
}
+ (AVAudioPlayer*) tock {
    StaticReturn ( [AVAudioPlayer withResourceName: @"Tock"] );
}
+ (AVAudioPlayer*) withResourceName: (NSString*) aName {
    NSBundle* zBundle = [NSBundle bundleWithIdentifier: @"com.apple.UIKit"];
    NSURL* zURL = [zBundle URLForResource: aName withExtension: @"aiff"];
    (void) RaiseIfNil ( nil, zURL, ([SWF @"URL for %@",aName]) );
    NSError* zError = nil;
    AVAudioPlayer* zAudio = [[AVAudioPlayer alloc] initWithContentsOfURL: zURL error: &zError];
    RaiseError ( nil, zError, @"AVAudioPlayer init error" );

#ifdef DEBUG
    //  Apple records the console dump which occurs as a bug in the iOS simulator
    //  all of the following commented code causes the BS console dump to be hidden
    int zOldConsole = dup(STDERR_FILENO);   // record the old console
    freopen("/dev/null", "a+", stderr); // send console output to nowhere
    (void)[zAudio prepareToPlay];       // create the BS dump
    fflush(stderr);             // flush the console output
    dup2(zOldConsole, STDERR_FILENO);   // restore the console output
#endif

    return zAudio;
}
@end

0
投票

对于斯威夫特

import AVFoundation

func play(sound: String) {
        var soundID: SystemSoundID = SystemSoundID()
        let mainBundle = CFBundleGetMainBundle()
        if let ref = CFBundleCopyResourceURL(mainBundle, sound as CFString, nil, nil) {
            AudioServicesCreateSystemSoundID(ref, &soundID);
            AudioServicesPlaySystemSound(soundID);
        }
}

@Krishnabhadra的实施

© www.soinside.com 2019 - 2024. All rights reserved.