スレッドからコールバック関数を使ってみた

2013.07.06 Saturday 14:34
0
    画面から通信処理などの非同期処理をスレッドで動かして、処理が終われば画面を更新するプログラムを探していました。

    ググり方が悪いのか、思った処理が引っかからなかったので、いろんなサイトを参考にして、自分で書いてみました。



    まずは、NSObjectを継承した非同期処理をするAsyncUtilというクラスを作りました。

    非同期処理の代わりに、とりあえず5秒スリープし、それが終わればコールバックメソッドを呼び出す形です。
    コールバックメソッドの呼び出しにNSInvocationを使ってみました。


    @interface AsyncUtil : NSObject
    {
        NSInvocation *m_invocation;
    }
    
    -(void) setCallbackFunc:(id)callbackInstance selector:(SEL)callbackSelector;
    -(void) startThread;
    
    @end
    


    #import "AsyncUtil.h"
    
    @implementation AsyncUtil
    
    
    // スレッドの起動処理
    -(void) startThread
    {
        
        [self performSelectorInBackground:@selector(runThread:) withObject:nil];
    
    }
    
    
    // スレッドの内容
    -(void) runThread:(NSObject*)param
    {
        NSLog(@"Thread Start");
    
        
        // スレッド内での処理の代わりに5秒スリープ
        [NSThread sleepForTimeInterval:5.0f];
        
    
        // メインスレッドでコールバック関数を呼び出す
        dispatch_async(dispatch_get_main_queue(), ^{
            NSString *errCode = @"none";
            
            [m_invocation setArgument:&errCode atIndex:2];
            [m_invocation invoke];
        });
    
        NSLog(@"Thread End");
    }
    
    
    // コールバックをセット
    -(void) setCallbackFunc:(id)callbackInstance selector:(SEL)callbackSelector {
        
        // コールバックの情報をセットする
        if (callbackInstance && callbackSelector) {
            NSMethodSignature *sig = 
                    [callbackInstance methodSignatureForSelector:callbackSelector];
    
            m_invocation = [NSInvocation invocationWithMethodSignature:sig];
            [m_invocation setSelector:callbackSelector];
            [m_invocation setTarget:callbackInstance];
            
        }
    }
    
    @end
    



    次は呼び出し側です。

    UIViewControllerを継承して、適当に画面を作りました。

    
    - (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
    {
        self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
        if (self) {
            m_AsyncUtil = [[AsyncUtil alloc] init];
        }
        return self;
    }
    
    - (void)viewDidLoad
    {
        [super viewDidLoad];
        
        // コールバックメソッドのセット
        [m_AsyncUtil setCallbackFunc:self selector:@selector(callbackFunc:)];
        // スレッド開始
        [m_AsyncUtil startThread];
        
    }
    
    - (void)didReceiveMemoryWarning
    {
        [super didReceiveMemoryWarning];
    }
    
    // コールバック用のメソッド
    -(void)callbackFunc:(NSString *)error {
        NSLog(@"callbackFunc is called");
        NSLog(@"error : %@", error);
    }
    
    


    [実行結果]

    Thread Start
    Thread End
    callbackFunc is called
    error : none



    一応思った通りの処理ができました。
    スレッドの結果も返せるで、これで使えるかなぁという感じです。

    とりあえず実装してみようと思います。
    category:スレッド関連 | by:こもcomments(0) | - | -

    Calender
      12345
    6789101112
    13141516171819
    20212223242526
    2728293031  
    << August 2017 >>
    Sponsored Link
    Selected entry
    Category
    Archives
    Recent comment
    • NSUnknownKeyExceptionが出た時の回避方法
      itotake
    • 画面を縦方向に固定にする
      iphone 画面 固定
    • NSUnknownKeyExceptionが出た時の回避方法
    • NSUnknownKeyExceptionが出た時の回避方法
      atsushi
    • NSUnknownKeyExceptionが出た時の回避方法
      kanejun
    • UITableViewCellに置いたボタンのイベント処理
      こも
    • UITableViewCellに置いたボタンのイベント処理
      かつお
    • NSUnknownKeyExceptionが出た時の回避方法
      こも
    • NSUnknownKeyExceptionが出た時の回避方法
       
    • iOS7のベータ版を入れてみた
      こも
    Sponsored Link
    Link
    Profile
    Search
    Others
    Mobile
    qrcode
    Powered
    無料ブログ作成サービス JUGEM