8

嗯,这是我有史以来的第一篇文章——在这个网站、个人博客和 iPhoneDevSDK 论坛之间,我总是能够自己解决问题。我已经为 iOS 开发了大约五个月,从未在 Google 之外寻求帮助。但这一次,我被困住了。

我已经成功地在我的应用程序中实现了 Matt Galagher 的 AudioStream 类(必须删除链接,因为 SO 假定我的帖子是垃圾邮件),我很高兴地报告它运行良好。我在一个视图控制器中使用它,它实际上是 TabBar 应用程序中父视图的子视图。事实上,我的实现与Matt 示例中的实现并没有太大区别——我只是更改了一些 UI 元素。

到目前为止,viewDidDisappear当用户切换到另一个选项卡时,我一直在使用停止流媒体。但最近我决定,只要应用程序正在运行,就可以让音频流播放,无论顶部是什么视图。这是一个非常简单的更改,现在无论我在应用程序的哪个位置,我的音频流都会继续播放。

以下是视图控制器的工作原理:

  1. 我有一个播放按钮和一个停止按钮放在同一个位置,停止按钮隐藏。
  2. 当用户按下播放按钮时,播放按钮隐藏,显示 UIActivityIndi​​catorView (`[streamer isWaiting]`)
  3. 当流开始播放时(`[streamer isPlaying]`),`UIActivityIndi​​catorView` 被隐藏,并出现一个停止按钮
  4. 此外,在“[streamer isPlaying]”时,我在导航提示中显示经过的时间 (mm:ss),它每秒更新一次

上述所有工作每次都完美无缺。如果我离开视图(通过弹出到父视图或导航到另一个选项卡),音频将继续播放,这正是我想要的。但是当我返回视图时,UI 看起来好像我还没有启动它(播放按钮可见,导航提示被隐藏)。如果我按下播放按钮,我会听到第二个流与第一个流同时播放。

updateProgress似乎已经停止(因为不再self.navigationItem.prompt可见),我猜它playbackStateChanged是“死的”(不知道如何描述它)。

我花了几个小时筛选 AudioStreamer 类,试图弄清楚如何保持对流的控制,但我已经筋疲力尽了。我希望有人能告诉我我错过了什么。

正如我之前所说,我的视图控制器与示例几乎相同(请参阅上面的超链接,因为 SO 仍然假设我是垃圾邮件发送者),只有一些与 UI 相关的更改。

我想简短的问题是这样的:有没有人能够实现 AudioSTreamer 类,弹出它的视图,然后回来查看经过的时间或停止流?

编辑:下面是我实现 AudioStreamer 的视图控制器

。H

#import <UIKit/UIKit.h>
#import <QuartzCore/CoreAnimation.h>
#import <MediaPlayer/MediaPlayer.h>
#import <CFNetwork/CFNetwork.h>

@class AudioStreamer;


@interface RadioViewController : UIViewController
{
    IBOutlet UIButton *playButton;
    IBOutlet UIButton *stopButton;
    IBOutlet UIActivityIndicatorView *waitIndicator;

    AudioStreamer *streamer;
    NSTimer *progressUpdateTimer;

    BOOL shouldAutoStop;
}

- (IBAction)play;
- (IBAction)stop;

- (void)createStreamer;
- (void)destroyStreamer;
- (void)updateProgress:(NSTimer *)aNotification;
- (void)checkWiFi;

@end

.m

#import "AudioStreamer.h"
#import "ServerCheck.h"
#import "RadioViewController.h"

@implementation RadioViewController


- (void)viewDidLoad
{
    [[self navigationItem] setTitle:@"WXK33 162.550"];

    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(checkWiFi) name:UIApplicationDidBecomeActiveNotification object:nil];

    [super viewDidLoad];
}

- (void)viewDidAppear:(BOOL)animated
{   
    [self performSelector:@selector(checkWiFi)];

    [super viewDidAppear:animated];
}

- (void)viewDidDisappear:(BOOL)animated
{
    //[self performSelector:@selector(stop)];

    [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationDidBecomeActiveNotification object:nil];

    [super viewDidDisappear:animated];
}


- (void)createStreamer
{
    if ([ServerCheck serverReachable:@"audiostream.wunderground.com"])
    {
        if (streamer)
        {
            return;
        }

        [self destroyStreamer];

        NSURL *url = [NSURL URLWithString:@"http://audiostream.wunderground.com/MaffooClock/San_Angelo.mp3"];
        streamer = [[AudioStreamer alloc] initWithURL:url];

        progressUpdateTimer = [NSTimer scheduledTimerWithTimeInterval:1.0 target:self selector:@selector(updateProgress:) userInfo:nil repeats:YES];

        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(playbackStateChanged:) name:ASStatusChangedNotification object:streamer];

    }
    else
    {
        [[self navigationController] popViewControllerAnimated:YES];
    }
}

- (IBAction)play
{
    [self createStreamer];
    [waitIndicator startAnimating];
    [streamer start];

    [[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:YES];
}

- (IBAction)stop
{
    self.navigationItem.prompt = nil;
    [streamer stop];

    [[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:NO];
}


- (void)playbackStateChanged:(NSNotification *)aNotification
{
    if ([streamer isWaiting])
    {
        [playButton setHidden:YES];
        [stopButton setHidden:YES];
        [waitIndicator startAnimating];
    }
    else if ([streamer isPlaying])
    {   
        [playButton setHidden:YES];
        [stopButton setHidden:NO];
        [waitIndicator stopAnimating];

        [[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:YES];
    }
    else if ([streamer isIdle])
    {
        [self destroyStreamer];

        [playButton setHidden:NO];
        [stopButton setHidden:YES];
        [waitIndicator stopAnimating];
    }
}


- (void)updateProgress:(NSTimer *)updatedTimer
{
    if (streamer.bitRate > 0.0)
    {
        double progress = streamer.progress;

        double minutes = floor(progress/60);
        double seconds = trunc(progress - (minutes * 60));

        self.navigationItem.prompt = [NSString stringWithFormat:@"Elapsed: %02.0f:%02.0f",minutes,seconds];;

        if (shouldAutoStop && progress > 600)
            [self performSelector:@selector(stop)];
    }
    else
    {
        self.navigationItem.prompt = nil;
    }
}

- (void) checkWiFi
{
    if (![ServerCheck wifiAvailable])
    {
        LogInfo(@"No Wi-Fi");

        NSString * messageTitle = @"Notice";
        NSString * messageText = @"It appears that you do not have an active Wi-Fi connection.  Listening to streaming audio via cellular data may incurr additional data charges.  Streaming will automatically stop after 10 minutes.";

        UIAlertView *errorAlert = [[UIAlertView alloc] initWithTitle:messageTitle message:messageText delegate:self cancelButtonTitle:@"Dismiss" otherButtonTitles:nil];

        [errorAlert show];
        [errorAlert release];

        shouldAutoStop = YES;
    }
    else
        shouldAutoStop = NO;    
}


- (void)destroyStreamer
{
    if (streamer)
    {
        [[NSNotificationCenter defaultCenter] removeObserver:self name:ASStatusChangedNotification object:streamer];
        [progressUpdateTimer invalidate];
        progressUpdateTimer = nil;

        [streamer stop];
        [streamer release], streamer = nil;
    }
}


- (void)dealloc
{
    [self destroyStreamer];
    if (progressUpdateTimer)
    {
        [progressUpdateTimer invalidate], progressUpdateTimer = nil;
    }
    [super dealloc];
}

@end
4

1 回答 1

0

事实证明,我只需要重新考虑我是如何分配和推送视图的。“更多”选项卡显示表视图,每个单元格表示选择该单元格时将被按下的子视图。我将这个视图更改为在里面分配所有子视图viewDidLoad,然后简单地执行里面的推送didSelectRowAtIndexPath,然后释放里面的子视图dealloc

这完美地解决了我的问题。感谢 Jason Coco 让球滚动起来。

于 2011-01-20T15:20:55.977 回答