I making a simple soundboard and I'm trying to make my button make a sound when pressed, but when I run the simulator nothing plays. This is my code -
ViewController.m
#import "ViewController.h"
#interface ViewController ()
#end
#implementation ViewController
-(IBAction)sound1 {
CFBundleRef mainBundle = CFBundleGetMainBundle();
CFURLRef soundFileURLRef;
soundFileURLRef = CFBundleCopyResourceURL(mainBundle, (CFStringRef) #"sound1", CFSTR("wav"), NULL);
UInt32 soundID;
AudioServicesCreateSystemSoundID(soundFileURLRef, &soundID);
AudioServicesPlaySystemSound(soundID);
}
ViewController.h
#import <UIKit/UIKit.h>
#import <AudioToolbox/AudioToolbox.h>
#interface ViewController : UIViewController
-(IBAction)sound1;
#end
and also how to I link up the button up with the sound??
First, don't use wav as it takes up too much memory, mp3 is better. Second this has got nothing to do with Xcode 6. Third you may have not imported the AudioToolBox file in your linked frameworks and Libraries.
Do this in the .h file
#import <UIKit/UIKit.h>
#import <AudioToolbox/AudioToolbox.h>
#interface ViewController : UIViewController
{
IBOutlet UIButton *SoundButton;
}
#end
Do This is the .m file
-(IBAction)Sound:(id)sender
{
NSLog("Button is pressed");
NSString *over = #"sound1";
SystemSoundID soundID;
NSString *soundPath = [[NSBundle mainBundle] pathForResource:over ofType:#"wav"];
NSURL *soundUrl = [NSURL fileURLWithPath:soundPath];
AudioServicesCreateSystemSoundID ((__bridge CFURLRef)soundUrl, &soundID);
AudioServicesPlaySystemSound(soundID);
}
-(void)viewDidLoad
{
[super viewDidLoad];
SoundButton = [UIButton buttonWithType:UIButtonTypeCustom];
SoundButton.frame = CGRectMake(X cord, Y cord, width, height);
[SoundButton addTarget:self action:#selector(Sound:) forControlEvents:UIControlEventTouchUpInside];
}
I advise you to learn and how to use Xcode and Objective-C / Swift before asking questions such as these.
Related
I have an AVPlayer that plays audio from a mono AVAsset, doing some processing via an audio processing tap along the way. How can I convert this asset to stereo before reaching the tap? The second channel can be empty or a copy of the first channel (it’ll get filled up manually in the tap).
I've tried converting the mono to stereo within the tap, but apparently we have no control over the ASBD or AudioBufferList structure once we're inside the tap. I've also done offline conversion, but this presents big obstacles (can be quite slow, not suitable for web streaming).
Here is the barebones (but complete) code which you can use with any mono audio file. You'll see that by the time it hits the processing tap, there’s just the one channel available instead of the desired two channels. To use the code, you just need to add the MediaPlayer and TapProcessor classes below to a blank Single View Application, use the following ViewController code in place of the default code, and add in your own mono audio file to your project. Thanks for reading.
MediaPlayer.h
#import <Foundation/Foundation.h>
#interface MediaPlayer : NSObject
#end
MediaPlayer.m
#import "MediaPlayer.h"
#import "TapProcessor.h"
#import <AVFoundation/AVFoundation.h>
#interface MediaPlayer()
#property (nonatomic, strong) AVAsset *asset;
#property (nonatomic, strong) AVPlayer *player;
#property (nonatomic, strong) TapProcessor *audioTapProcessor;
#end
#implementation MediaPlayer
- (id)init {
if (self = [super init]){
NSString *path = [[NSBundle mainBundle] pathForResource:#"MonoSource"
ofType:#"mp3"];
[self loadFileWithPath:path];
}
return self;
}
-(void)loadFileWithPath:(NSString*)path{
NSURL *fileURL = [NSURL fileURLWithPath:path];
NSDictionary *options = [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:YES]
forKey:AVURLAssetPreferPreciseDurationAndTimingKey];
self.asset = [AVURLAsset URLAssetWithURL:fileURL options:options];
[self.asset loadValuesAsynchronouslyForKeys:#[#"tracks"] completionHandler:^{
dispatch_async(dispatch_get_main_queue(), ^{
AVKeyValueStatus status = [self.asset statusOfValueForKey:#"tracks" error:nil];
switch (status) {
case AVKeyValueStatusLoaded:
[self setupPlayer];
break;
default:
break;
}
});
}];
}
- (void) setupPlayer{
AVPlayerItem *item = [AVPlayerItem playerItemWithAsset:self.asset];
AVAssetTrack *audioTrack = [[self.asset tracksWithMediaType:AVMediaTypeAudio] objectAtIndex:0];
[self printInfoForTrack:audioTrack];
TapProcessor *newProcessor = [[TapProcessor alloc] initWithTrack:audioTrack];
AVAudioMix *audioMix = [newProcessor audioMix];
item.audioMix = audioMix;
self.player = [AVPlayer playerWithPlayerItem:item];
[self.player play];
}
-(void) printInfoForTrack:(AVAssetTrack*)track{
CMAudioFormatDescriptionRef item = (__bridge CMAudioFormatDescriptionRef)[track.formatDescriptions objectAtIndex:0];
const AudioStreamBasicDescription* desc = CMAudioFormatDescriptionGetStreamBasicDescription(item);
NSLog(#"Number of track channels: %d", desc->mChannelsPerFrame);
}
#end
TapProcessor.h
#import <Foundation/Foundation.h>
#import <AVFoundation/AVFoundation.h>
#interface TapProcessor : NSObject
- (id)initWithTrack:(AVAssetTrack *)track;
#property (readonly, nonatomic) AVAssetTrack *track;
#property (readonly, nonatomic) AVAudioMix *audioMix;
#end
TapProcessor.m
#import "TapProcessor.h"
// TAP CALLBACKS
static void tap_InitCallback(MTAudioProcessingTapRef tap,
void *clientInfo,
void **tapStorageOut){
}
static void tap_FinalizeCallback(MTAudioProcessingTapRef tap){
}
static void tap_PrepareCallback(MTAudioProcessingTapRef tap,
CMItemCount maxFrames,
const AudioStreamBasicDescription *processingFormat){
NSLog(#"Number of tap channels: %d", processingFormat->mChannelsPerFrame);
}
static void tap_UnprepareCallback(MTAudioProcessingTapRef tap){
}
static void tap_ProcessCallback(MTAudioProcessingTapRef tap,
CMItemCount numberFrames,
MTAudioProcessingTapFlags flags,
AudioBufferList *bufferListInOut,
CMItemCount *numberFramesOut,
MTAudioProcessingTapFlags *flagsOut){
MTAudioProcessingTapGetSourceAudio(tap, numberFrames, bufferListInOut, NULL, NULL, NULL);
*numberFramesOut = numberFrames;
}
#implementation TapProcessor
- (id)initWithTrack:(AVAssetTrack *)track{
self = [super init];
if (self){
_track = track;
}
return self;
}
#synthesize audioMix = _audioMix;
- (AVAudioMix *)audioMix {
if (!_audioMix){
AVMutableAudioMix *audioMix = [AVMutableAudioMix audioMix];
if (audioMix){
AVMutableAudioMixInputParameters *audioMixInputParameters = [AVMutableAudioMixInputParameters audioMixInputParametersWithTrack:self.track];
if (audioMixInputParameters) {
MTAudioProcessingTapCallbacks callbacks;
callbacks.version = kMTAudioProcessingTapCallbacksVersion_0;
callbacks.clientInfo = (__bridge void *)self,
callbacks.init = tap_InitCallback;
callbacks.finalize = tap_FinalizeCallback;
callbacks.prepare = tap_PrepareCallback;
callbacks.unprepare = tap_UnprepareCallback;
callbacks.process = tap_ProcessCallback;
MTAudioProcessingTapRef audioProcessingTap;
if (noErr == MTAudioProcessingTapCreate(kCFAllocatorDefault,
&callbacks,
kMTAudioProcessingTapCreationFlag_PreEffects,
&audioProcessingTap)){
audioMixInputParameters.audioTapProcessor = audioProcessingTap;
CFRelease(audioProcessingTap);
audioMix.inputParameters = #[audioMixInputParameters];
_audioMix = audioMix;
}
}
}
}
return _audioMix;
}
#end
ViewController.h
#import <UIKit/UIKit.h>
#interface ViewController : UIViewController
#end
ViewController.m
#import "ViewController.h"
#import "MediaPlayer.h"
#interface ViewController ()
#property (nonatomic,strong) MediaPlayer *mediaPlayer;
#end
#implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
self.mediaPlayer = [[MediaPlayer alloc] init];
}
#end
I have this code to get the audio inside my project and supposed to play audio:
#import "ViewController.h"
#import <AudioToolbox/AudioServices.h>
#implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
[self playAudio];
}
- (void)playAudio {
[self playSound:#"Splash" :#"wav"];
}
- (void)playSound :(NSString *)fName :(NSString *) ext{
SystemSoundID audioEffect;
NSString *path = [[NSBundle mainBundle] pathForResource : fName ofType :ext];
if ([[NSFileManager defaultManager] fileExistsAtPath : path]) {
NSURL *pathURL = [NSURL fileURLWithPath: path];
AudioServicesCreateSystemSoundID((__bridge CFURLRef) pathURL, &audioEffect);
AudioServicesPlaySystemSound(audioEffect);
}
else {
NSLog(#"error, file not found: %#", path);
}
}
#end
I'm using iOS 8 with iPhone 4s simulator, and this code doesn't work and I not hear the audio, why?
I tried iPhone app.In this app I need to import all songs into table-view when I click on import button.I don't know how to import songs dynamically.Please tell me what are the Frameworks to be used.
But i have played Locally saved songs like code:-
using this two Frameworks `AVFoundation.framework,MediaPlayer.framework
#import "ViewController.h"
#import <MediaPlayer/MediaPlayer.h>
#import <AVFoundation/AVFoundation.h>
#interface ViewController ()
#property (nonatomic, strong) AVAudioPlayer *audioPlayer;
- (IBAction)playSound:(id)sender;
#end
#implementation ViewController
- (void)viewDidLoad
{
[super viewDidLoad];
NSBundle *mainBundle = [NSBundle mainBundle];
NSString *filePath = [mainBundle pathForResource:#"drum" ofType:#"mp3"];
NSData *fileData = [NSData dataWithContentsOfFile:filePath];
NSError *error = nil;
self.audioPlayer = [[AVAudioPlayer alloc] initWithData:fileData
error:&error];
[self.audioPlayer prepareToPlay];
self.audioPlayer.numberOfLoops = -1;
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (IBAction)playSound:(id)sender {
[self.audioPlayer play];
UIView *wrapperView = [[UIView alloc] initWithFrame:CGRectMake(20, 120, 260, 20)];
wrapperView.backgroundColor = [UIColor clearColor];
[self.view addSubview:wrapperView];
MPVolumeView *volumeView = [[MPVolumeView alloc] initWithFrame: wrapperView.bounds];
[wrapperView addSubview:volumeView];
}
#end
Output for this code is songs played locally but I need when I click play button it should import 10 songs in tableView and then songs mush be played.
Please give me any idea.
Thanks in advanced.
I can get both iPhone and iPad to load the same HTML file, however I would like to load a more optimized page based on which device the program is loading on.
ViewController.h:
#import <UIKit/UIKit.h>
#interface ViewController : UIViewController
#property (strong, nonatomic) IBOutlet UIWebView *webView;
#end
ViewController.m:
#import "ViewController.h"
#interface ViewController ()
#end
#implementation ViewController
- (void)viewDidLoad
{
NSURL *url = [[NSBundle mainBundle] URLForResource:#"index" withExtension:#"html"];
NSString *html = [NSString stringWithContentsOfURL:url encoding:NSUTF8StringEncoding error:nil];
NSString *path = [[NSBundle mainBundle] bundlePath];
NSURL *baseURL = [NSURL fileURLWithPath:path];
[_webView loadHTMLString:html baseURL:baseURL];
// disable scrolling
_webView.scrollView.scrollEnabled = NO;
_webView.scrollView.bounces = NO;
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#end
I have tried to create a new outlet, but I seem to be running into overlapping code.
How can I load different HTML files for iPad and iPhone with a universal build?
Just use one web view. All you need is two different HTML files.
Then you code can be something like:
NSURL *url;
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPhone) {
url = [[NSBundle mainBundle] URLForResource:#"index-iphone" withExtension:#"html"];
} else {
url = [[NSBundle mainBundle] URLForResource:#"index-ipad" withExtension:#"html"];
}
This assumes you have both an index-iphone.html and a index-ipad.html file in your app bundle.
I have this error:
"No visible #interface for 'NSBundle declares the selector'pathforresource: of type" .
#import "ViewController.h"
#interface ViewController ()
#end
#implementation ViewController
#synthesize WebView1;
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
NSString *localFilePath = [[NSBundle mainBundle] pathForResoursce:#"www/index" ofType:#"html"] ;
NSURLRequest *localRequest = [NSURLRequest requestWithURL:
[NSURL fileURLWithPath:localFilePath]] ;
[WebView1 loadRequest:localRequest] ;
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#end
#import <UIKit/UIKit.h>
#import "ViewController.h"
#interface ViewController : UIViewController
#property (nonatomic,retain) IBOutlet UIWebView *WebView1;
#end
Check the name of the function because you misspelled:
NSString *localFilePath = [[NSBundle mainBundle] pathForResoursce:#"www/index" ofType:#"html"] ;
should be :
NSString *localFilePath = [[NSBundle mainBundle] pathForResource:#"www/index" ofType:#"html"] ;
And then check the name of the html file . It might be index.html.
If you have difficulties in finding the problem you said pathForResoursce: instead of pathForResource: