6개월 전쯤 오랫만에 iOS 프로젝트를 하게되어 Xcode 새 버전을 다운로드 받고 실행해 보았다. 오래 안봤더니 생소한 인터페이스빌더의 모습에 겁을 먹고 인터페이스빌더를 사용하지 않고 개발하기로 했다. 그러다 근래가 되어서야 지인으로부터 스토리보드란 것이 있다는 이야기를 들었다. 오랫동안 손을 놓고 있었던 스모킹 카운터의 업그레이드 버전은 사용법도 익힐 겸 스토리보드를 사용해서 만들기로 했다.

'신기하게 잘 만들었구나'하며 이것저것 해보면서 만들다가 오늘 문득 타겟을 iOS 4.3으로 해도 되는지 테스트 해보기 위해 아무 생각없이 타겟을 iOS 4.3으로 수정하고 빌드를 해보았다. 'Storyboards are unavailable on iOS 4.3 and prior'란 오류가 났다. 안되는 구나 하고 다시 5.0으로 변경한 후 빌드를 하는데 또 같은 오류가 난다. Xcode를 종료하고 클린을 한후에 다시 빌드를 했는데 결과는 같다. 검색을 해보니 나만 그런 것은 아닌 것 같고... 하지만 검색해서 얻은 해결법들이 나의 경우에는 해결되지 않았다. 설마 프로젝트를 다시 만들어야 하는 것은 아닌지 Xcode 초보자로서 참으로 난감한 일이다. 그러던 중 늘 그렇듯이 소발에 쥐잡기로 빌드는 되었다.

1. 프로젝트 Deployment Target이 5.0인지 확인.
2. 스토리보드 속성중 Document Versioning에서 Deployment가 iOS 5인지와 Development가 Xcode 4.2인지 확인. 
3. 파인더에서 *.storyboard 파일을 다른 곳으로 이동(언어별로 되어 있으면 모두 이동).
4. Xcode 종료
5. *.storyboard 파일을 기존의 디렉토리로 다시 이동.
6. Xcode 재실행 후 클린
7. 빌드


Xcode 버전은 4.2.1이며 용기가 없어 확인해 보기 위해 다시 재현하지는 못했다. Xcode 버그인지 아니면 일반적인 방법이 있는데 삽질인지는 모르겠다. 

iOS 2010.04.09 15:56
어제 애플에서 아이폰 OS 4에 관련된 내용들을 발표했습니다. 직접 보지는 못하고 애플 사이트에서 iPhone OS 4 Event 키노트를 보았습니다.

예전 같으면 SDK 베타부터 다운로드 받아 설치했을 것 같은데 이제는 업무로 Xcode를 사용하다 보니 베타 버젼은 설치를 기피하게 되네요. 그런 변명도 있고 제가 가진 OS X가 10.5라 더이상 업그레이드를 할 수 없는 상태이기도 합니다. 맥북이라 느리기도 하고 조만간 아이맥을 구입해야 할 것 같습니다. 이젠 더 이상 손을 놓고 기다리기 힘들게 되었습니다.

맥의 OS X도 마찬가지지만 이번 아이폰 OS의 업그레이드 내용을 보면 'OS 업그레이드는 이렇게 하는 것이다'라는 전형적인 모범답안을 보여주고 있는 것 같습니다. 1.0부터 모든 버젼의  업그레이드를 이미 다 계획해 놓은 듯이 보여질 정도로 단계적으로 업그레이드를 해갈때 마다 완성형에 가까운 모습으로 가고 있는 것 같습니다.

이번 업그레이드도 많은 변경이 있지만 키노트에서는 아래와 같이 7가지 주요 기능을 위주로 설명하고 있습니다. 간단한 내용은 아래와 같습니다.

1. 멀티태스킹
오랫동안 논란이 되어왔던 멀티태스킹이 드디어 아이폰에서도 가능하게 되었습니다. 멀티태스킹은 하드웨어의 성능때문에 아이폰 3GS와 3세대 터치에서만 가능합니다.

2. 폴더
폴더를 만들어 비슷한 어플을 그룹화시켜 저장할 수 있습니다. 이로인해 기존 180개에서 2,160개까지 어플을 저장할 수 있게 되었습니다. 배경화면도 사용자가 지정한 이미지로 설정할 수 있게되었습니다.

3. 메일
메일함이 통합되고 메일을 스레드로 볼 수 있게 되었습니다. 또한 성능이 개선되고 첨부파일을 서드파티 어플에서 열어 볼 수 있습니다.

4. 아이북
아이패드에서 보았던 아이북이 아이폰에도 추가되었습니다.

5. 엔터프라이즈
데이터 보안이 강화되고 SSL VPN을 지원합니다. 데이터 보안 API는 일반 개발자들도 사용할 수 있습니다.  그리고 인하우스 앱들은 네트워크를 사용해 설치할 수 있습니다.

6. 게임센터
게임센터가 추가되었습니다. 친구를 초대하고 대전상대를 찾고 스코어가 기록됩니다.

7. 아이애드
iAd란 어플리케이션에서의 광고를 지원합니다. 이익의 60%가 어플리케이션 개발자에게 지급됩니다.

가장 큰 변경사항은 멀티태스킹입니다. 이로인해 어플리케이션이 백그라운드로 실행될 수 있기때문에 이와 관련된 메소드들이 많이 추가되었습니다. 백그라운드로 전환되어 대기상태가 될때는 OpenGL ES 메소드를 호출한다거나 네트워크을 사용하지 말아야하며 주소록 같은 시스템 리소스도 해제해야합니다. 많은 메모리를 사용하고 있다면 이역시 해제해야합니다.

만약 메모리와 같은 시스템 리소스가 부족하면 백그라운드에서 실행중인 어플리케이션이 먼저 제거대상이됩니다. 또한 시스템이 어플리케이션이 백그라운드로 전환될 때 메인윈도우를 캡쳐해 놓고 전환시 사용하기 때문에 패스워드같이 민감한 정보는 해당윈도우에서 삭제하길 권장하고 있습니다. 그리고 사용자 설정이 변경될 때 어플이 대응할 수 있도록 필요하다면 관련 통보 메시지를 처리해야 합니다. 이와함께 백그라운드에서 실행되는 어플들이 알려야할 내용이 있을때 사용할 수 있도록 위해 로컬 노티피케이션도 추가되었습니다.

Game Kit에는 게임센터를 지원하는 메소드들이 추가되었습니다. 애플에서 제공하는 서버와 서비스를 이용하여 사용자들의 점수를 저장할 수 있고 사용자들은 특정 사용자를 초대하거나 다른 사용자들을 선택할 수 있습니다.

이외에 어플리케이션에서도 SMS를 보내고 파일을 공유하고 PDF를 생성하고 사용자 폰트를 사용할 수 있는등 많은 기능과 서비스들이 추가되고 변경되었습니다. 애플에서 제공하는 iPhone OS 4 beta API Diffs란 문서를 참조하시면 4.0 SDK에서 추가된 내용들을 확인하실 수있습니다.

현재 애플의 기세는 MS, 구글, 아도비, 닌텐도, 소니등 모든 IT 업체들과 적이되어 홀홀 단신으로 싸울려는 모습으로 보여지기도 합니다. 이런 자신감은 수많은 어플리케이션을 올리며 든든히 뒤에는 바쳐주는 개발사와 개발자가 있기 때문이 아닌가라는 생각도 듭니다.

이번 SDK 4.0에서 추가된 많은 서비스와 API를 이용하여 지금과는 또다른 독특하고 재미있는 어플들이 많이 나올 것 같다는 생각이 듭니다.

'iOS' 카테고리의 다른 글

아이폰 OS 4  (8) 2010.04.09
NSXMLParser로 RSS 읽어오기  (21) 2009.08.05
인터페이스빌더 Table View Cell 사용하기  (0) 2009.06.25
cocos2d 개발환경 설정  (24) 2009.04.13
iPhone SDK 3.0 beta 2  (4) 2009.04.05
UITableView의 메모리 누수 현상  (4) 2009.02.05

1. 빌드시 시뮬레이터 판별

#if !TARGET_IPHONE_SIMULATOR
pickerController.sourceType = UIImagePickerControllerSourceTypeCamera;
#endif
TARGET_IPHONE_SIMULATOR로 실제 아이폰에서만 실행되는 코드를 따로 관리할 수 있습니다.

2. 하위 View 검색

NSArray *subViewList = [searchBar subviews];
for (UIView *view in subViewList) {
    if ([view isKindOfClass:[UITextField class]]) {
        [(UITextField *)view setReturnKeyType:UIReturnKeyDone];
    }   
}
UIView의 subviews와 isKindOfClass를 사용하여 하위의 특정 뷰를 찾아내어 설정을 변경할 수 있습니다. UISearchBar에서 UITextField를 찾아내어 키보드의 Search 버튼의 텍스트를 Done으로 변경하는 예입니다.

- (void) setSubViewsClearColor: (UIView*)theView {
   NSArray *subViewList = theView.subviews;
   for (UIView *view in subViewList) {
       [view setBackgroundColor:[UIColor clearColor]];
       [self setSubViewsClearColor:view];
   }
}
하위 View를 모두 찾아 배경을 투명한 속성으로 변경하는 예입니다.
초기화 하는 곳에서 [self setSubViewsClearColor:self]; 와 같이 호출하여 사용합니다.
 
 
3. 사용자 데이터 저장

userLevel = [[NSUserDefaults standardUserDefaults] integerForKey:@"user_level"];
[[NSUserDefaults standardUserDefaults] setInteger:g_userLevel forKey:@"user_level"];
옵션등의 간단한 설정은 데이터베이스나 파일을 이용하는대신 NSUserDeraults를 사용하면 간단하게 저장하고 불러올 수 있습니다.

4. Rect와 Point
좌표로 많이 사용되는 Rectd와 Point에서 자주 사용되는 함수와 상수입니다.

CGRect  CGRectMake(CGFloat x, CGFloat y, CGFloat width, CGFloat height);
x, y, width, height로 설정된 CGRect를 반환합니다.

CGRectZero
0, 0 좌표와 0, 0 크기를 가진 CGRect 상수입니다.

CGPointMake(CGFloat x, CGFloat y);
x, y로 설정된 CGPoint를 반환합니다.

CGPointZero
0, 0 좌표를 가진 CGPoint 상수입니다.

bool CGRectContainsPoint(CGRect rect, CGPoint point);
rect 사각형에 point가 속해있는지 여부를 반환합니다.

bool CGRectContainsRect(CGRect rect1, CGRect rect2);
rect1 사각형에 rect2 사각형이 속해있는지 여부를 반환합니다.

bool CGRectIntersectsRect (CGRect rect1,  CGRect rect2);
rect1과 rect2가 교차하는지 여부를 반환합니다.


5. Path

NSString *bundlePath = [[NSBundle mainBundle] bundlePath];
어플리케이션 번들 디렉토리를 반환합니다.

NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
번들에 포함된 파일들은 읽기만 가능하고 쓰기가 불가능합니다. 디비와 같이 변경이 필요한 경우에는 위와같이 어플리케이션의 도큐먼트 폴더를 구해와 도큐먼트 폴더로 복사 생성해 놓고 작업합니다.


6. URL

NSURL *url = [NSURL URLWithString:@"http://www.cocoadev.co.kr"];
[[UIApplication sharedApplication] openURL:url];
지정된 웹주소를 사파리에서 오픈합니다.

NSURL *url = [NSURL URLWithString:@"mailto:abc@def.com"];
[[UIApplication sharedApplication] openURL:url];         
받는사람이 설정되어 메일 프로그램의 새로운 메시지가 실행됩니다.

NSURL *url = [NSURL URLWithString:@"tel:02-111-2222"];
[[UIApplication sharedApplication] openURL:url];
지정된 번호로 전화를 겁니다.


아이폰 3.0 SDK 부터는 accelerometer를 사용하지 않고도 UIResponder에 추가된 motion 이벤트 처리 메소드를 구현함으로써 간단하게 사용자의 흔들기 동작을 체크할 수 있습니다. 저도 처음 사용해 보면서 간단한 내용들을 정리해 보았습니다.

1. First responder 되기
사용자의 흔들기 이벤트를 처리할 ViewController는 그 자신이 First responder가 되어야 합니다. becomFirstResponder 메소드를 호출하고 canBecomeFirstResponder 메소드에서 YES를 반환합니다.

  1. - (void)viewDidAppear:(BOOL)animated {
  2.     [super viewDidAppear:animated];
  3.     [self becomeFirstResponder];
  4. }
  5.  
  6. - (BOOL)canBecomeFirstResponder {
  7.     return YES;
  8. }

viewDidAppear는 코드에서 서브뷰로 추가될 때만 호출됩니다. IB에서 바로 Window에 View를 추가하였으면 awakeFromNib등의 메소드에서 becomFirstResponder를 호출하셔야 합니다.

2. motion 메소드 구현
이후로는 간단합니다. 사용자의 흔들기가 시작되면 해당 motionBegan이 호출되고 종료될 때 motionEnded가 호출됩니다. 지나치게 많이 흔들거나 하여 유효하지 않은 흔들기로 판단될 때는 motionCancelled가 호출됩니다.

  1. - (void)motionBegan:(UIEventSubtype)motion withEvent:(UIEvent *)event {
  2.     NSLog(@"Shaking start");
  3. }
  4.  
  5. - (void)motionEnded:(UIEventSubtype)motion withEvent:(UIEvent *)event {
  6.     NSLog(@"Shaking end");
  7. }
  8.  
  9. - (void)motionCancelled:(UIEventSubtype)motion withEvent:(UIEvent *)event {
  10.     NSLog(@"Shaking cancel");  
  11. }
  12.  

motionEnded 메소드에 사용자의 흔들기가 끝난 후 실행할 코드를 추가하면, 간단하게 흔들기를 지원할 수 있습니다.


이전에 포스팅한 "NSXMLParser로 RSS 읽어오기"와 유사한 방법으로 구글 날씨 RSS를 가져오는 것을 만들어 보았습니다. 그런데 한글이 깨져나와 확인해 보니 문자셋이 euc-kr이었습니다. 문자셋을 확인하는 방법은 URLConnection의 델리게이트 메소드에서 확인할 수 있습니다.
  1. - (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response {
  2.     NSLog(@"Encoding: %@", [response textEncodingName]);
  3. }

전송이 끝난 후에 아래와 같이 NSData를 euc-kr을 utf-8로 변환하여 사용할 수 있습니다. 변경된 data를 NSXMLParser의 initWithData의 인자로 사용하면 됩니다.
  1. - (void)connectionDidFinishLoading:(NSURLConnection *)connection {
  2.     NSString *str = [[NSString alloc] initWithData:receiveData encoding:0x80000000 + kCFStringEncodingDOSKorean];
  3.     NSData *data = [str dataUsingEncoding:NSUTF8StringEncoding];
  4.    
  5.     NSXMLParser *parser = [[NSXMLParser alloc] initWithData:data];
  6. .
  7. .
  8. .
  9. }

한가지 이상한 점은 웹브라우저에서 확인하면 같은 URL이지만 utf-8로 넘어 옵니다. 아마 서버에서 헤더를 검사에서 각각 다른 인코딩으로 넘겨주는 것이 아닌가 하는 생각이 듭니다. 헤더의 항목들을 변경해서 보았는데 User-Agent를 설정해서 보내보니 euc-kr이 아닌 utf-8로 넘어 왔습니다.
  1.     NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"http://www.google.com/ig/api?weather=seoul"]];
  2.      
  3.     [request addValue:@"Mozilla/5.0 (Macintosh; U; Intel Mac OS X 10.5; ko; rv:1.9.1.2) Gecko/20090729 Firefox/3.5.2" forHTTPHeaderField:@"User-Agent"];
  4.  
  5.     xmlConnection = [[NSURLConnection alloc]
  6.                      initWithRequest:request
  7.                      delegate:self];


구글의 날씨 API에서는 이와 같이 User-Agent를 보내면 utf-8로 보내기때문에 위와같이 인코딩의 변환이 필요하지 않습니다. 아마 예측가능한 User-Agent는 utf-8로 보내고 그외에는 euc-kr로 보내는 것 같습니다. 이는 영문도 마찬가지이며 http://www.google.com/ig/api?weather=seoul와 같이 co.kr에서 com으로 변경하면 문자셋이 iso-8859-1로 넘어 옵니다. User-Agent를 추가하면 역시 utf-8로 넘어 옵니다.



이전부터 그냥 복사해서 올렸는데 오늘 보니 아래와 같이 나오는 건 너무 보기가 힘든 것 같아서, 예제코드를  Quick Highlighter를 사용해서 정리해 보았습니다.
    NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"http://www.google.com/ig/api?weather=seoul"]];
     
    [request addValue:@"Mozilla/5.0 (Macintosh; U; Intel Mac OS X 10.5; ko; rv:1.9.1.2) Gecko/20090729 Firefox/3.5.2" forHTTPHeaderField:@"User-Agent"];

    xmlConnection = [[NSURLConnection alloc]
                     initWithRequest:request
                     delegate:self];

보기도 조금 나아지지만 해당 클래스에 대한 애플의 문서로 바로 링크가 되는 것도 좋은 것 같습니다.


RSS를 읽어 오는 간단한 리더기를 만들어 보겠습니다. 맥에서는 NSXMLDocument란 편리한 클래스가 있지만 아이폰 SDK에는 포함되어 있지 않습니다. 그렇기 때문에 NSXMLParser를 사용해서 RSS xml을 읽어오는 간단한 샘플을 만들어 보겠습니다.

인터넷을 통해 데이터를 가져오는 부분은 이전  "NSURLConnection으로 웹페이지 내용 가져오기"란 포스팅을 참고 하시기 바랍니다. 여기서는 파싱하는 부분만 간단히 살펴보겠습니다.


1. NSXMLParser 생성
xml 데이터 파싱은 네트워크로 데이터 수신이 완료된 후 불려지는 connectionDidFinishLoading 메소드에서 아래와 같이 처리합니다.

NSXMLParser *parser = [[NSXMLParser alloc] initWithData:receiveData];

[parser setDelegate:self];
[parser parse];
[parser release];

NSXMLParser 오브젝트를 수신된 데이터가 저장된 NSData 타입의 receiveData를 인자로 초기화를 합니다. setDelegate 메소드로 현재 오브젝트를 NSXMLParser의 딜리케이트로 지정합니다. 지정된 오브젝트는 요소별로 파싱의 시작/종료와 파싱된 스트링을 받을 수 있는 메소드를 구현해야 합니다.

parse 메소드로 파싱이 시작됩니다. 파싱은 자동으로 처리되지 않으며, 각 단계별로 딜리게이트된 메소드를 구현하여 필요와 형식에 맞게 직접 처리해야 합니다.

2. Delegate 메소드 구현
NSXMLParser에는 많은 딜리게이트 메소드가 있지만 가장 중요하고 거의 반드시 구현해야될 메소드는 parser:didStartElement, parser:foundCharacters, parser:didEndElement입니다.

parser:didStartElement로 한 요소의 파싱이 시작됨을 알수 있습니다. parser:foundCharacters로 해당 문자열들이 넘어 옵니다. 토큰 단위로 넘어 오기 때문에 넘어 오는 문자열들을 계속 저장해야 합니다. parser:didEndElement가 실행되면 비로소 한 요소의 파싱이 끝난 것을 알 수 있습니다. 이 메소드에서 해당 요소에 따른 필요한 처리를 합니다.

1) 시작 메소드 구현
- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary *)attributeDict {
    if ([elementName isEqualToString:@"item"])
        elementType = etItem;
   
    [xmlValue setString:@""];
}

두번째 인자인 elementName으로 해당요소의 이름이 전달됩니다. 세번째와 네번째 인자는 네임스페이스와 관련된 uri와 전체이름이 전달됩니다. 만약 해당 xml이 네임스페이스를 사용한다면 이전에 [parser setShouldProcessNamespaces:YES];로 네임스페이스를 처리하도록 설정해야 합니다. NSXMLParser의 shouldProcessANamespace의 기본값은 NO 입니다.

마지막 인자인 attributeDict에는 해당 요소의 속성들이 전달됩니다. 만약 <item lang="ko"> 와 같이 되어 있다면 attributeDict 딕셔너리에 key가 'lang', value가 'ko'로 저장되어 전달됩니다.

여기서는 다른 인자들은 무시하고 item이란 이름의 요소가 시작될때 부터 데이터들을 저장하도록 요소이름이 item인지만 확인합니다. 그리고 xmlValue에 새로운 데이터를 저장하기 위해 이전에 저장된 값들을 초기화합니다.

2) 데이터 저장 메소드 구현
- (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string {
    if (elementType == etItem) {
        [xmlValue appendString:string];
    }
}
토큰별로 넘어오는 문자열을 xmlValue에 저장합니다.

3) 종료 메소드 구현
- (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName {
    if (elementType != etItem)
        return;

    if ([elementName isEqualToString:@"title"]) {
        [currectItem setValue:[NSString stringWithString:xmlValue] forKey:elementName];
    } else if ([elementName isEqualToString:@"link"]) {
        [currectItem setValue:[NSString stringWithString:xmlValue] forKey:elementName];
    } else if ([elementName isEqualToString:@"description"]) {
        [currectItem setValue:[NSString stringWithString:xmlValue] forKey:elementName];
    } else if ([elementName isEqualToString:@"category"]) {
        [currectItem setValue:[NSString stringWithString:xmlValue] forKey:elementName];
    } else if ([elementName isEqualToString:@"pubDate"]) {
        [currectItem setValue:[NSString stringWithString:xmlValue] forKey:elementName];
    } else if ([elementName isEqualToString:@"item"]) {
        [xmlParseData addObject:[NSDictionary dictionaryWithDictionary:currectItem]];
    }
}

한 요소가 끝날때 호출됩니다. 여기서는 RSS의 title, link, description, category, pubData 항목들만 currentItem 딕셔너리에 저장합니다. 한 포스팅의 마지막 요소인 </item>일 경우에는 xmlParseData에 현재 딕셔너리를 추가합니다.

3. 테이블뷰 출력
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
    return 1;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    return [xmlParseData count];
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
   
    static NSString *CellIdentifier = @"Cell";
   
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil) {
        cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
    }
   
    NSDictionary *dict = [xmlParseData objectAtIndex:indexPath.row];
    [[cell textLabel] setText:[dict objectForKey:@"title"]];
   
    return cell;
}

여기서 테이블뷰는 아무 동작을 하지않으며 xmlParseData에 저장된 해당 title만 출력합니다. 빌드 후 실행하면 아래와 같이 해당 RSS의 제목이 출력되는 것을 확인할 수 있습니다.

간단한 RSS 리더기를 구현해 보았습니다. 전체 소스는 아래의 압축파일을 다운로드 받아 확인하실 수 있습니다. 정확하고 자세한 내용은 아이폰 개발자 센터에서 제공하는 Introduction to Event-Driven XML Programming Guide for Cocoa 문서 또는 SeismicXML 샘플코드를 확인하시기 바랍니다.

'iOS' 카테고리의 다른 글

아이폰 OS 4  (8) 2010.04.09
NSXMLParser로 RSS 읽어오기  (21) 2009.08.05
인터페이스빌더 Table View Cell 사용하기  (0) 2009.06.25
cocos2d 개발환경 설정  (24) 2009.04.13
iPhone SDK 3.0 beta 2  (4) 2009.04.05
UITableView의 메모리 누수 현상  (4) 2009.02.05

NSURLConnection을 이용하면 간단하게 해당 웹서버의 html, xml등의 내용을 쉽게 가져올 수 있습니다.

1. 연결
connection = [[NSURLConnection alloc] initWithRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:@"http://www.cocoadev.co.kr/rss]] delegate:self];

[[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:YES];

대상 URL을 인자로 NSURLConnection을 생성합니다. 위는 이 블로그의 rss를 주소로 생성하는 예입니다. delegate는 self로 현제 오브젝트로 지정합니다. delegate로 지정된 오브젝트는 NSURLConnection의 delegate 메소드를 구현하고 메시지를 받을 수 있습니다.

UIApplication의 networkActivityIndicatorVisible을 YES로 하여 데이터 수신 시 좌측과 같이 상단 상태바에 인디케이터가 회전하는 에니메이션으로 사용자에게 데이터 수신중임을 알려줍니다. 기본값은 NO로 되어 있습니다.

2. delegate 메소드 구현
NSURLConnection 생성시 delegate로 지정된 클래스에서는 해당 이벤트 처리 메소드를 구현해야 합니다. 가장 자주 사용되는 delegate 메소드는 데이터 수신, 연결 종료, 오류발생등에 관련된 것들입니다.

1) 데이터 수신
* connection:didReceiveData:
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
   [receiveData appendData:data];
}
데이터가 수신될 때 불려지면 웹서버로 부터 받은 데이터가 NSData 형태로 넘어 옵니다. NSMutableData의 appendData 메소드를 이용하여 수신되는 데이터들을 차례대로 저장합니다.

2) 연결 종료
* connectionDidFinishLoading:
- (void)connectionDidFinishLoading:(NSURLConnection *)connection {
   NSString *str = [[NSString alloc] initWithData:receiveData
encoding: NSUTF8StringEncoding];
   NSLog(@"%@", str);
   [str release];

   [[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:NO];
}
데이터가 모두 수신되어 웹서버와의 연결이 종료되었을 때 호출됩니다. 이곳에서 원하는 작업을 하거나 다른 오브젝트가 처리하도록 할 수 있습니다. 위는 NSData로 저장된 데이터를 NSString으로 변환하여 출력하는 예입니다. xml이라면 NSXMLParser를 사용하여 데이터를 처리할 수 있습니다.

3) 오류 발생
* connection:didFailWithError:
- (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error {
   NSLog(@"Connect error: %@", [error localizedDescription]);   

  [[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:NO];
}
네트워크가 연결되지 않았을 경우등 오류가 발생하였을 때 호출되는 메소드 입니다. 해당 페이지가 없음을 나타내는 404 오류등은 이 메소드가 호출되지 않습니다.


몇일전에 어플을 버젼업 하면서 큰 실수를 했습니다. UITableViewController를 UIViewController로 교체하면서 Edit 버튼을 클릭해도 테이블뷰에서 삭제모드로 변경이 안되는 버그를 확인 못하였습니다. delegate와 datasource 프로토콜의 필요한 메시지들은 다 구현이 되어 있는데 안되더군요.


가능하면 다시 UITableViewController로 돌아 가지 않는 방법을 찾아 보았는데, UIViewController의 setEditing 메소드를 이용하는 방법이 있었습니다. 사용자가 Edit/Done 버튼을 클릭할 때 불려지는 메소드인데 인자로 넘어오는 editing을 참고하면 테이블뷰의 에디트 모드가 UITableViewController일때와 동일하게 동작합니다.

- (void)setEditing:(BOOL)editing animated:(BOOL)animated {

    resultTable.editing = editing;

    [super setEditing:editing animated:animated];

}


조금 더 확인을 해봐야 겠지만 아직까지는 문제가 없는 것 같습니다. 기능도 몇개 없는데 귀찮아서 테스트도 안해보고 올렸다니 제 자신이 한심하네요.


보통 Table View의 Cell은 코드로 만드는 경우가 많습니다. 여기서는 인터페이스빌더에서 Table View Cell을 사용하는 간단한 샘플을 만들어 보겠습니다.





1. 프로젝트 생성과 AppDelegate 변경
Xcode를 실행하고 "New Project"를 클릭하여 "Window-based Application"을 선택하여 프로젝트를 생성합니다. 저는 그냥 IBCell이란 이름으로 프로젝트를 만들었습니다.

1) IBCellAppDelegate.h

@class TableViewController;


@interface IBCellAppDelegate : NSObject <UIApplicationDelegate> {


IBOutlet TableViewController *tableViewController;

    UIWindow *window;

}

2
인터페이스 빌더에서 연결을 위해 tableViewController의 아울렛 변수를 추가합니다.

2) IBCellAppDelegate.m

- (void)applicationDidFinishLaunching:(UIApplication *)application {

  

[window addSubview:[tableViewController view]];

    // Override point for customization after application launch

    [window makeKeyAndVisible];

}


메인 윈도우의 SubView로 tableViewController의 View를 추가합니다.

2. ViewController
1) 생성
UIViewController subclass로 TableViewController란 이름으로 클래스를 생성합니다. SDK 3 부터는 "With XIB for user interface"가 있어 선택할 경우 ViewController 오브젝트와 연결된 별도의 xib를 자동으로 생성하여 줍니다. 여기서는 편의를 위해 선택하지 않았습니다.
* 2009/06/26 추가
오늘 확인해 보니 Objective-C class 선택시에 하단에 Subclass of로 선택할 수 있는 클래스들이 나오네요. 버젼업되면서 왜 줄었나 했더니 여기로 들어 가 있었습니다. 위의 방법말고 아래에서 UITableViewController를 바로 선택하고 사용하시면 됩니다.
 

2) TableViewController.h

#import <UIKit/UIKit.h>



@interface TableViewController : UITableViewController {

IBOutlet UITableViewCell *myCell;

}


- (IBAction)goMyBlog:(id)sender;


@end


부모 클래스를 UIViewController에서 UITableViewController로 변경합니다. 그리고 인터페이스빌더에서 연결을 위해 myCell 아울렛 변수를 추가합니다. 그리고 버튼 클릭시 연결될 goMyBlog 액션 메소드를 선언합니다.

3) TableViewController.m

/* 버튼 클릭시 */

- (IBAction)goMyBlog:(id)sender {

NSURL *url = [NSURL URLWithString:@"http://www.cocoadev.co.kr/"];

[[UIApplication sharedApplication] openURL:url];

}


#pragma mark Table view methods


/* 색션 */

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {

return 1;

}


/* 색션 타이틀 */

- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {

return @"소개";

}


/* */

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {

return myCell;

}


/* 높이 */

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {

return [myCell frame].size.height;

}


버튼 클릭시 실행될 메소드와 tableView의 delegate, datasource 메소드를 구현합니다.



3. 인터페이스 빌더

1) Table View Controller

인터페이스 빌더를 실행하고 라이브러리의 Controlls의 Table View Controller를 MainWindow.xib로 드래그해서 가지고 옵니다. Class를 TableViewController로 지정합니다.



좌측과 같이 Table View의 Style 속성을 Grouped로 지정합니다.



2) Table View Cell

라이브러리에서 Table View Cell을 MainWindow.xib로 드래그해서 가지고 옵니다.




아래와 같이 TableViewController의 myCell 아울렛에 가져온 Table View Cell을 연결합니다.


사용자 삽입 이미지
라이브러리 윈도우에서 Image View, Label, Rounded Rect Button, Text View를 드래그 해서 Table View Cell에 가져다 놓습니다.



Cell의 높이를 늘리고 각각의 컨트롤들을 아래와 같이 배치합니다. 적당한 이미지를 Xcode 좌측의 Groups & Files 아래의 Resources 그룹으로 드래그해서 프로젝트로 가져옵니다. Image View의 Image 속성에서 해당 이미지를 선택합니다. 입력이 되지 않도록 Text View의 Editable 속성의 체크를 해제합니다.
사용자 삽입 이미지

버튼 클릭시 사파리에서 해당 URL로 이동하기 위해 Text View Controller의 goMyBlog IBAction과 연결합니다.


4. 확인
Xcode에서 Build & Go를 클릭하면 시뮬레이터에서 아래와 같이 확인하실 수 있습니다.
SDK 3을 대충 보기만 하고 처음 사용해 보았는데 곳곳에 바뀐 부분이 눈에 뛰네요. SDK 3도 처음이고 오랫만에 포스팅이라 틀린 부분이 있는지도 모르겠습니다.

'iOS' 카테고리의 다른 글

아이폰 OS 4  (8) 2010.04.09
NSXMLParser로 RSS 읽어오기  (21) 2009.08.05
인터페이스빌더 Table View Cell 사용하기  (0) 2009.06.25
cocos2d 개발환경 설정  (24) 2009.04.13
iPhone SDK 3.0 beta 2  (4) 2009.04.05
UITableView의 메모리 누수 현상  (4) 2009.02.05

iOS 2009.04.13 10:59
cocos2d-iphone 는 OpenGL ES를 기반으로 하는 게임, 에니메이션, 데모등을 위한 2D 라이브러리입니다. 기본적인 에니메이션부터 메뉴, 스코어 서버까지 지원하기 때문에 빠른 시간에 편리하게 사용할 수 있습니다. cocos2d-iphone 사이트에서 최신 버젼을 다운로드 받으실 수 있습니다.



1. cocos2d 설정
1) 빌드
다운로드를 받으신 후에 압축을 풀고 Xcode Project 파일을 클릭하여 Xcode를 실행합니다. Active Target을 cocos2d로 하고 Actvie SDK를 Device로 빌드 합니다.


Active SDK를 Simulator로 하고 다시 한번 빌드합니다.


cocos2d는 프로젝트 자체에 여러 샘플소스들을 많이 가지고 있습니다. Target을 해당 데모로 변경하여 실행을 확인해 보실 수 있습니다.

2) 라이브러리 복사
해당 폴더의 빌드 폴더를 보시면 2개의폴더에 각각 libcocos2d.a와 libChipmunk.a가 같이 빌드되어 있습니다.


원하시는 곳에 폴더를 만드시고 이 두 폴더의 파일들을 각각 다른 폴더로 가져다 놓습니다. 저는 /Developer/Library 밑에 Cocos2d란 폴더를 만들고 그 밑에 Device와 Simulator 폴더를 만들어 각각의 라이브러리 파일들을 가져다 놓았습니다.

3) 헤더파일 복사
/Developer/Library/Cocos2d 밑에 헤더파일들을 복사하기 위해 Include 폴더를 새로 만듭니다. Include 폴더의 하위로 Support 폴더를 만듭니다. 다시 cocos2d 폴더로 와서 보시면 하위에 똑 같은 이름의 cocos2d란 폴더가 있습니다. 이 폴더내의 *.h을 위에서 생성한 Include 폴더로 복사합니다. 하위의 Support 폴더내의 *.h 파일도 해당 폴더의 Support 폴더내로 복사합니다. (파인더에서 정렬을 종류로 하시면 헤더파일별로 쉽게 가져 올 수 있습니다.)


그리고 cocos2d 폴더의 external/Chipmunk/src에 있는 *.h 파일도 위와 같이 생성한 Include 폴더로 복사합니다. Chipmunk는 게임등에 사용되는 물리엔진으로 컴파일을 위해 헤더파일이 꼭 필요하며 실제 사용하지 않을 경우에는 라이브러리는 추가하지 않으셔도 됩니다.

4) fps_images.png 복사
cocos2d가 초당 프레임수를 출력할 때 사용하는 이미지를 해당 프로젝트의 Resource 폴더에 복사해 놓으셔야 됩니다. 이 이미지가 없을 경우에는 아래와 같은 실행오류가 발생합니다.


cocos2d 폴더의 Resources/Images에 있는 fps_images.png 파일을 적당한 위치에 복사해 놓습니다.



2. Xcode 설정
Xcode에서 New Project를 클릭하여 iPhone OS/Application의 Window-Based Application으로 프로젝트를 생성합니다. 프로젝트명을 cocos2d App로 입력합니다.

1) Search Paths 설정
좌측과 같이 Groups & Files에서 프로젝트를 우클릭한 후에 Get Info를 클릭하여 Project 정보창을 오픈합니다.

두번째 Build에서 Search Paths항목에서 Header와 Library를 각각 해당 폴더로 입력합니다.

아래와 같이 Header Search Paths, Library Search Paths가 입력되어 있는 것을 확인합니다.

2) cocos2d 라이브러리 링크
Linking 항목중 OPther Linker Flags에 -lcocos2d를 입력합니다.


libcocos2d.a를 드래그 해서 직접 추가하여 사용하셔도 됩니다. 하지만 시뮬레이터와 디바이스의 선택에 따라 각각의 라이브러리 파일이 필요하기 때문에 Active SDK가 변경될 경우에는 매번 파일을 변경해 주어야 합니다.

그렇기 때문에 설정에서 Configuration이 Debug일때는 Library Search Paths를 Simulator로 Release일 때는 Device로 설정합니다. 시뮬레이터로 개발시에는 Debug 모드로 개발하고 실제 기기에서 테스트시나 업로드시에는 Release 모드를 선택하면 해당 라이브러리 파일의 변경없이 편하게 사용하실 수 있습니다.

3) 프레임워크 추가
cocos2d가 사용하는 OpenGL ES, QuartzCore 프레임워크를 추가합니다. 좌측과 같이 cocos2d App 타겟에 우클릭하여 Get Info를 클릭합니다.



General 항목의 좌측 하단에 [+] 버튼을 클릭합니다.
아래와 같이 OpenGLES.framework와 QuartzCore.framework를 선택하고 Add를 클릭합니다.


4) fps_images.png 추가
좌측과 같이 이전에 복사해 두었던 fps_images.png를 Resources 항목으로 드래그해서 가져다 놓습니다.



5) 프로젝트 템플릿 추가
cocos2d를 사용할 때마다 매번 위의 설정을 하는 것은 번거로운 작업입니다. 그렇기 때문에 기본설정된 항목을 템플릿에 추가하여 사용하는 것이 편리합니다. cocos2d App 프로젝트 폴더를  /Library/Application Support/Deveoper/Shared/Xcode/Project Templates/ 밑에 Application 폴더를 만드시고 그 아래에 복사합니다.
이제 새 프로젝트를 선택하면 User Templates/Application에 cocos2d App 항목이 나오며 위에서 cocos2d를 위해 설정된 사항대로 편리하게 사용하실 수 있습니다.

cocos2d에 관한 자세한 내용과 자료는 cocos2d-iphone 사이트에서 확인하실 수 있습니다.

'iOS' 카테고리의 다른 글

NSXMLParser로 RSS 읽어오기  (21) 2009.08.05
인터페이스빌더 Table View Cell 사용하기  (0) 2009.06.25
cocos2d 개발환경 설정  (24) 2009.04.13
iPhone SDK 3.0 beta 2  (4) 2009.04.05
UITableView의 메모리 누수 현상  (4) 2009.02.05
UIView에서 텍스트 출력  (10) 2009.01.13

iOS 2009.04.05 16:59
몇일 전 메일로 아이폰 SDK 3 베타가 나왔다는 소식을 들었는데 이제서야 추가되고 변경된 내용들을 개략적으로 둘러 보았습니다. 중요한 변경사항으로는 블루투스를 공식적으로 지원하며 30핀 독 컨넥터를 이용해 각종 액세서리들과 통신할 수 있는 수단을 제공하는 것과 App 자체내에서 결제를 제공하는 것 같습니다. 그외 각종 API가 추가되고 간단하게 사용할 수 있도록 변경되었습니다.
사용자 삽입 이미지
(이미지 출처: 애플)

애플 아이폰 개발자 센터의 아이폰 OS 3.0 소개 페이지에서 내세우는 6개의 큰 변화된 내용은 아래와 같습니다.

* In App Purchase
어플리케이션 자체내에서 사용자가 결제를 할 수 있는 StoreKit이란 프레임워크가 추가되었습니다. 이를 이용하면 App내에서 컨텐츠나 기능을 추가할 때 사용자로 부터 과금을 할 수가 있습니다. App는 무료로 배포하고 컨텐츠 접근시에만 유료로 결제를 받는 서비스들도 많이 등장할 것 같다는 생각이 듭니다. (델피니님이 댓글로 안된다고 말씀해 주셨네요. 제 착오 였습니다. ^^;;)

* Peer to Peer Connectivity
블루투스를 이용해 페어링 없이 아이폰(터치)간에 연결이 가능합니다. 이를 이용하여 데이터를 주고 받을 수도 있으며, 특별히 음성데이터를 위한 GKVoiceChatService란 서비스도 제공합니다. 연결될 기기를 선택하기 위한 기본적인 UI도 제공합니다.

* Apple Push Notification service
App가 실행되지 않을 때라도 Push Notification Service에 동록된 서버로 부터 메시지를 받을 수 있가 있습니다. App가 실행되지 않을 때 이 메시지를 받게되면 다이알로그박스, 뱃지, 효과음등을 통하여 사용자에게 새로운 데이터나 변경된 내역이 있다는 것을 알려 줍니다. 만약 어플리케이션이 실행중이라면 미리 정의된 메소드에서 이 메시지를 처리할 수 있습니다.

* Maps
구글 모바일 맵 서비스와 연동하는 Map View가 추가되었습니다. 확대, 축소가 가능하며 핀을 사용할 수 있고, 현제 좌표를 주소로 변환해주는 API도 제공합니다. 구글맵의 Open API를 사용하지 않고도 편리하게 관련된 어플리케이션을 만들 수 있습니다.


* Accessories

30핀 독과 블루투스를 통하여 외부 기기들과 통신할 수 있는  악세서리 API를 제공합니다. 아이팟의 악세서리와 이와 연동할 수 있는 App를 이용하여 다양하고 재미있는 악세서리들과 App들이 많이 나올 것으로 기대가 됩니다.

* iPod Library Access

사용자의 아이폰/터치에 있는 음악과 Podcasts, Audio Books, 플레이 리스트에 접근할 수 있는 API를 제공하면, 선택을 위한 기본적인 UI 컨트롤러도 제공합니다.

* 기타
이외에도 Cut, Copy & Paste를 지원하고, App내에서 이메일 발송을 위한 API와 UI를 제공하는 등 많은 변화가 있는 것 같습니다.

그리고 맥의 spotlight와 같은 검색기능이 추가되었습니다. 주소록, 미디어 파일등을 검색하는 용도로 사용하는 것 같습니다.


3.0에서 업그레이드 된 기능들을 이용해 개발사들은 더욱 다양한 수익모델을 만들 수 있을 것 같습니다. 사용자들도 다양한 악세사리들과 이와 연동되는 App를 사용할 수 있다는 것은 환영할 만한 일이라고 생각됩니다. 애플이 아이폰 SDK 업그레이드 로드맵을 장기적인 안목으로 정말 잘 짜놓은 것 같습니다.


TableView 사용시 NSIndexPath에서 불특정하게 Instruments에서 메모리 누수가 감지되고는 합니다. 이전에도 이런 현상을 간혹 보기는 했지만, 혼자서 만들어 본 간단한 샘플이고 Instruments에 익숙하지 안다는 이유로 궁금증을 뒤로 하고 그냥 넘어 갔었습니다.


하지만 이번에 앱스토어에 올릴 어플리케이션을 준비하면서 또 위와 같은 문제를 만났습니다. 이번에는 그냥 넘어 갈 문제가 아니기 때문에 누수를 찾을려고 해보았습니다. 그러나 역시 찾지 못했습니다. 검색을 해보아도 비슷한 경우를 겪은 사람들은 많지만 딱히 해답은 없었습니다.

애플의 SimpleDrillDown이나 UICatalog와 같은 TableView를 사용하는 샘플에서도 이와 같은 누수가 감지됩니다. 애플의 담당자들도 실수를 할 수 있겠지만 이런 UI의 대표적인 샘플에서 정말 문제가 있었다면, 이에 관련된 업데이트가 그동안 있었을 것이라 생각이 됩니다.

또한 실제 디바이스에서 테스트를 하면 위와 같은 누수는 발생하지 않습니다. 이번에 2.2.1로 업그레이되면서 혹시나 해결되었나 했는데 마찬가지였습니다. 애플의 이에대한 공식적인 언급은 못보았지만, 잠정적으로 시뮬레이터의 버그이고 실제로 사용시에는 문제가 없다는 결론을 내렸습니다. 하지만 아직도 제가 무엇을 잘 못한 것은 아닌지 찜찜한 마음은 가시지 않네요. 혹시 원인이나 해결책을 아시는 분이 계신가요?

'iOS' 카테고리의 다른 글

cocos2d 개발환경 설정  (24) 2009.04.13
iPhone SDK 3.0 beta 2  (4) 2009.04.05
UITableView의 메모리 누수 현상  (4) 2009.02.05
UIView에서 텍스트 출력  (10) 2009.01.13
iPhone 어플리케이션 개발을 위한 준비 - 4. 시작하기  (16) 2008.12.22
아이폰 SQLite3 샘플  (6) 2008.11.25

아이폰 SDK의 UIKit에는 문자열의 출력을 위해 NSString에 추가된 메소드들을 제공합니다. 이를 이용해서 UIView의 drawRect에서 직접 문자열을 출력하는 간단한 방법을 알아 보겠습니다. UIKit에 추가된 NSString의 메소드들에 대한 자세한 설명은 iPhone DevCenterNSString UIKit Additions Reference 문서에서 확인하실 수 있습니다.

1. 폰트 설정

폰트는 UIFont를 사용하여 설정할 수 있습니다. iPhone과 터치에서 사용가능한 폰트는 아래의 소스를 이용하여 확인할 수 있습니다.
NSArray* familyArray = [UIFont familyNames];
for (NSString *familyName in familyArray) {
    NSLog(@"- %@", familyName);  
    NSArray *fontArray = [UIFont fontNamesForFamilyName:familyName];
       
    for (NSString *fontName in fontArray) {
        NSLog(@"%@", fontName);
    }  
}

위 소스를 실행하면 아래와 같이 폰트들의 목록이 출력됩니다. 전체목록은 아래의 '모든 폰트 보기'를 클릭하시면 확인하실 수 있습니다.
- Georgia
Georgia-Bold
Georgia
Georgia-BoldItalic
Georgia-Italic

모든 폰트 보기


폰트명을 보면 볼드는 -bold와 이텔릭은 -Italic과 같이 되어 있어 각각의 특징을 알 수 있습니다. 폰트는 일반적으로 UIFont의 아래와 같은 메소드를 사용하여 생성합니다.
+ (UIFont *)fontWithName:(NSString *)fontName size:(CGFloat)fontSize

fontName에는 폰트명을 fontSize에는 크기를 설정하여 UIFont 오브젝트를 생성합니다. 아래는 위의 메소드를 이용하여 19 사이즈의 'Verdana-Bold' 폰트를 생성하는 예입니다.
UIFont *generalFont = [UIFont fontWithName:@"Verdana-Bold" size:19];

한글은 다른 폰트로 설정을 해도 영향을 받지 않는 것 같고 'AppleGothic'만 사용할 수 있는 것 같습니다.
 

2. 컬러 설정

컬러는 UIColor의 'colorWith...' 류의 생성 메소드로 직접 생성할 수 있지만 아래와 같이 미리 지장된 색상을 간편하게 이용할 수도 있습니다.
UIColor *generalColor = [UIColor darkGrayColor];

UIColor에서 지정되어 있는 색상은 아래와 같습니다.
black, darkGray, lightGray, white, gray, red, green, blue, cyan, yellow, magenta, orange,
purple, brown

색상설정은 set을 이용하여 간편하게 적용할 수 있습니다.
[generalColor set]


3. drawAtPoint

지정된 위치에 문자열을 출력하는 간단한 메소드입니다. 반환값은 실제 문자를 출력한 크기입니다.
- (CGSize)drawAtPoint:(CGPoint)point withFont:(UIFont *)font

point에 출력될 위치를 font에 사용될 폰트를 지정합니다.  다소 복잡하지만 아래의 메소드도 많이 사용됩니다.
- (CGSize)drawAtPoint:(CGPoint)point
forWidth:(CGFloat)width
withFont:(UIFont *)font
lineBreakMode:(UILineBreakMode)lineBreakMode

forWith는 문자열이 출력될 너비를 구합니다. fotWidth를 넘어 가는 문자들은 출력되지 않으며, lineBreakMode에 설정된 값에 따라 잘리는 옵션을 선택할 수 있습니다. 옵션은 아래와 같습니다. lineBreakMode의 옵션은 아래와 같습니다.

  • UILineBreakModeWordWrap - 단어 단위
  • UILineBreakModeCharacterWrap - 문자 단위
  • UILineBreakModeClip - 영역
  • UILineBreakModeHeadTruncation - 앞에 '...' 표시
  • UILineBreakModeTailTruncation - 뒤에 '...' 표시
  • UILineBreakModeMiddleTruncation - 중간에 '...' 표시

각 옵션의 결과는 아래의 샘플에서 확인하실 수 있습니다.


4. drawInRect

지정된 영역에 문자를 출력하는 메소드 입니다. 가로정렬이 가능하고 긴 문자열의 경우에는 여러줄에 걸쳐 출력을 할 수 있습니다.
- (CGSize)drawInRect:(CGRect)rect
withFont:(UIFont *)font
lineBreakMode:(UILineBreakMode)lineBreakMode
alignment:(UITextAlignment)alignment

drawAtPoint와 동일하며 alignment의 옵션은 아래와 같습니다.
  • UITextAlignmentLeft - 좌측 정렬
  • UITextAlignmentCenter - 중앙 정렬
  • UITextAlignmentRight - 우측정렬

5. 출력전 크기 구하기

출력전에 미리 출력될 문자열의 크기를 알아 낼 수 있는 'sizeWith...'류의 메소드들을 제공합니다. 출력시 사용하는 font와 width, lineBreakMode과 동일하게 설정하고 호출하면 출력될 텍스트의 실제 크기를 반환합니다.
- (CGSize)sizeWithFont:(UIFont *)font
forWidth:(CGFloat)width
lineBreakMode:(UILineBreakMode)lineBreakMode


drawInRect로 긴 문자열을 여러줄에 출력할 시에는 아래의 메소드를 호출해여 크기를 구해 와야 합니다.
- (CGSize)sizeWithFont:(UIFont *)font
constrainedToSize:(CGSize)size
lineBreakMode:(UILineBreakMode)lineBreakMode


6. 샘플

위의 메소드들을 이용해서 아래와 같이 간단한 예제를 만들어 보겠습니다. drawAtPoint의 breakMode별로 출력하고, 마지막에는 drawInRect를 이용하여 여러행에 걸쳐 출력하도록 하였습니다.
UIView 서브클래스의 drawRect에 아래와 같이 소스를 입력합니다.
- (void)drawRect:(CGRect)rect {
// 시작 x 좌표
#define START_X        10
   
    /* 텍스트 설정 (from wikipedia) */
    NSString *title = @"Tiger";
    NSString *memo = @"The tiger (Panthera tigris) is a member of the Felidae family;" \
                      "the largest of the four big cats";
   
    /* 폰트 설정 */
    UIFont *titleFont = [UIFont fontWithName:@"Arial-BoldItalicMT" size:40];
    UIFont *memoFont = [UIFont fontWithName:@"ArialMT" size:16];
   
    /* 칼라 설정 */
    UIColor *blackColor = [UIColor blackColor];
    UIColor *blueColor = [UIColor blueColor];
    UIColor *redColor = [UIColor redColor];
    UIColor *userColor = [UIColor colorWithRed:0.2 green:0.4 blue:0.2 alpha:0.8];
   
    CGFloat yPosition = 10;
    CGFloat viewWidth = [self bounds].size.width;
    CGSize textSize;
   
    /* 타이틀 출력 */
    [blueColor set];
    textSize = [title drawInRect:CGRectMake(0, yPosition, viewWidth, 30)
                        withFont:titleFont
                   lineBreakMode:UILineBreakModeWordWrap
                       alignment:UITextAlignmentCenter];
    yPosition = (textSize.height + 20);
       
    int mode = 0;   
    NSArray* breakModeArray = [NSArray arrayWithObjects:@"WordWrap",
                               @"CharacterWrap",
                               @"Clip",
                               @"HeadTruncation",
                               @"TailTruncation",
                               @"MiddleTruncation",
                               nil];

    /* breakMode 설정별로 텍스트 출력 */
    [blackColor set];
   
    for (NSString *modeName in breakModeArray) {
        /* 현재 breakMode 출력 */
        [redColor set];
        textSize = [modeName drawAtPoint:CGPointMake(START_X, yPosition)
                                forWidth:viewWidth
                                withFont:memoFont
                           lineBreakMode:UILineBreakModeWordWrap];
        yPosition += textSize.height;
       
        /* 텍스트 출력 */
        [blackColor set];
        textSize = [memo drawAtPoint:CGPointMake(START_X, yPosition)
                            forWidth:viewWidth-80
                            withFont:memoFont
                       lineBreakMode:mode];
        yPosition += (textSize.height + 8);
       
        mode++;
    }
   
    /* drawInRect 타이틀 출력 */
    [redColor set];
    textSize = [@"* drawInRect" drawAtPoint:CGPointMake(START_X, yPosition)
                                   forWidth:viewWidth
                                   withFont:memoFont
                              lineBreakMode:UILineBreakModeWordWrap];
    yPosition += textSize.height;
   
    /* memo를 drawInRect로 출력 */
    [userColor set];
    textSize = [memo drawInRect:CGRectMake(START_X, yPosition, viewWidth-80, 100)
                       withFont:memoFont
                  lineBreakMode:UILineBreakModeWordWrap];
}


iPhone 어플리케이션은 Xcode란 개발툴에서 코코아터치 프레임워크와 Objective-C 언어를 사용하여 개발합니다. 코코아 터치는 맥 OS X의 핵심 프레임워크인 코코아를 기본으로 아이폰/터치라는 모바일 기기의 특성에 맞추어진 iPhone 개발의 기본 API입니다.

그렇기 때문에 아이폰 어플리케이션 개발을 위해 기본적으로 알아야할 사항은 통합개발 환경인 Xcode와 인터페이스 빌더라는 툴의 사용법, Cocoa Touch 프레임워크, Objective-C 크게 세가지입니다. 이번에는 간단히 iPhone OS의 계층구조를 중심으로 iPhone 어플리케이션 제작을 위해 접근하는 방법에 대해서 알아 보겠습니다.

1. iPhone OS 계층 구조
아래의 그림은 애플에서 설명하는 아이폰 OS의 기술 계층입니다. 이에 대한 자세한 내용은 아이폰 개발자 센터iPhone OS Technology Overview란 문서에 잘 정리되어 있습니다.


가장 로우레벨의 Core OS부터 가장 상위단계인 코코아 터치까지의 계층구조입니다. 주로 하단은 API가 C로 제공되며 상위로 올라 오면서 Objective-C로 제공됩니다. 많이 사용되는 로우레벨의 API들은 상위단계에서 쉽고 편하게 사용할 수 있는 프레임워크로 제공됩니다. 간 계층의 간단한 설명은 아래와 같습니다.

1) Core OS
메모리/프로세서 관리, 파일 시스템, 네트워크, 각종 하드웨어 드라이버등, 운영체제 하단의 커널 레벨에서 제공하는 커널 API 입니다. 흔히 이야기하는 시스템 프로그래밍에 관련된 C를 기반으로 한 라이브러리를 제공합니다.

2) Core Services
Core Foundation, CFNetwork, SQLite, POSIX threads와 같은 파일입출력, 저수준 데이터 타입, 소켓등에 관련된 서비스입니다. Core OS 레벨에 비교적 쉽게 접근할 수 있는 API를 제공합며 대부분 C로된 프레임워크를 제공됩니다. 여기서 제공하는 많은 기능들은 상단 코코아터치의 Foundation Framework에서 Objective-C 프레임워크로 제공됩니다.

  • Core Foundation - 배열, 스트링, 날짜, URL, 로우레벨 데이터등 아이폰 어플리케이션을 위한 기본적인 C API를 제공합니다.
  • CFNetwork - BSD 소켓 및 HTTP, FTP 프로토콜등 네트워크에 쉽게 접근할 수 있는 API를 제공하는 프레임워크입니다.
  • Core Location - GPS, 주변검색등에 사용할 수 있는 사용자의 현재 위치(위도, 경도) 정보와 관련된 API를 제공하는 프레임워크입니다.
  • SQLite - 아이폰 어플리케이션에서 쉽게 사용할 수 있는 파일기반의 경량 데이터베이스 입니다. SQLite에 관련된 보다 자세한 내용은 이전 포스팅을 참조해 주세요.
  • XML - XML 파싱을 위한 libXML2 라이브러리를 제공합니다.

이외에 보안, 주소록등에 관련된 서비스를 제공합니다.

3) Media
비디오, 오디오, 2D/3D 그래픽, 에니메이션을 구현할 수 있는 API를 제공합니다. Objective-C 또는 C로된 API를 제공합니다.

  • Quartz - OS X의 벡터를 기반으로 한 그래픽 엔진입니다. 선과 도형을 그리고 이미지, 비트맵, PDF를 출력하고 색상, 위치에 관련된 C로된 API를 Core Graphic 프레임워크를 통해 제공합니다.
  • Core Animation - 각종 에니메이션과 시각효과를 제공하는 Objective-C로된 프레임워크입니다.
  • OpenGL ES - 게임등과 같은 고성능의 2D/3D 그래픽 출력을 위한 OpenGL ES 1.1에 기반한 C 프레임워크입니다. OpenGL ES를 사용한 게임은 이를 지원하는 다양한 모바일 플랫폼에서의 포팅을 쉽게 할 수 있습니다. 자세한 내용은 공식 홈페이지를 참조하시기 바랍니다.
  • Core Audio - 마이크를 통해 녹음하고 음악파일을 출력하고 각종 음향효과를 제공하는 C로된 오디오 관련 프레임워크입니다.
  • OpenAL - OpenGL ES와 유사한 개념의 크로스 플랫폼을 지원하는 게임등을 위한 고성능 3D 오디오 라이브러리입니다. 자세한 내용은 공식 홈페이지를 참조 하시기 바랍니다.
  • 동영상 - mov, mp4, 3gp와 같은 각종 동영상 파일을 출력을 지원합니다. 이는 Objective-C를 기반으로 한 Media Player framework를 이용하여 손쉽게 접근할 수 있습니다.

4) Cocoa Touch
iPhone개발의 기본이 되는 계층으로 Objective-C를 기반으로 한 핵심적인 두개의 프레임워크를 가지고 있습니다. 사용자 인터페이스, 이벤트 처리등과 함께 위에서 언급한 로우레벨의 기술들을 보다 쉽게 사용할 수 있는 프레임워크를 제공합니다.

  • Foundation Framework - 배열, 스트링, 날짜 로우레벨 데이터등에 관련된 클래스를 제공하는 기본적인 프레임워크입니다. 위의 Core Foundation에서 제공하는 기본 API들의 Objective-C 레퍼 클래스를 제공합니다.
  • UIKit Framework -각종 컨트롤, 윈도우등의 UI, 이벤트 처리등 iPhone 어플리케이션의 사용자 인터페이스와 관련된 API를 제공하는 프레임워크입니다.


2. Mac or iPhone
Mac의 Cocoa와 iPhone의 Cocoa touch는 이름에서 부터 알 수 있듯이 매우 비슷합니다. 가장 큰 차이점은 역시 인터페이스에 관련된 부분으로 이와 관련하여 Mac에서는 AppKit이란 프레임워크를 iPhone에서는 UIKit이란 프레임워크를 제공합니다.

Foundation Framework는 거의 유사하지만 아이폰의 특성상 제거 또는 변경된 부분이 있습니다. 아이폰은 코코아 바인딩, Objective-C 2.0의 가비지 컬렉션, 애플스크립트, NSUndoManage등은 지원하지 않습니다.

개인적으론 시간이 충분하다면 맥에서 코코아 프로그래밍으로 시작한 후에 코코아 터치로 넘어가도 큰 어려움은 없을 것 같습니다.


3. C or Objective-C
대표적인 코코아 프로그래밍 서적인 Cocoa Programming for MAC OS X (번역본:코코아 프로그래밍)의 저자 아론 힐리가스는 그의 저서에서 아래와 같이 이야기 했습니다.

"C와 Java/C++같은 객체지향 언어를 알고 있다면 두시간이면 Objective-C를 마스터할 수 있다"

OOP와 프로그래밍 언어에 대한 개념만 있다면 Objective-C를 익히는 것은 쉽다라는 의미인 것 같습니다.

사실 어느 언어나 기본지식만 있으면 언어 자체를 익히는데는 그다지 어려움이 없습니다. 하지만 해당 플랫폼에 대한 지식과 핵심 라이브러리나 프레임워크를 배우는데 더욱 많은 시간을 소비해야 합니다. 아이폰도 Xcode, 인터페이스빌더의 사용법, OS X에서의 프로그래밍에대한 이해와 코코아 API를 배우는데 Objective-C 언어 자체를 배우는 것보다 더 많은 시간이 필요합니다.

1) C의 선행학습이 필요한가?
개발경험이 있으신 분들은 그동안의 경험을 바탕으로 어떻게 공부해야 할지 나름대로 방법이 있을 것입니다. 하지만 처음 시작하시는 분들은 Objective-C가 C를 기반으로 하고 있기 때문에, 반드시 C를 공부한 후에 Objective-C를 공부해야하는 지에 대해 질문을 하시는 분들이 있습니다.

이 부분은 아마 많은 분들이 차이가 있을 것 같습니다. 제 생각은 "반드시 필요하지는 않다" 입니다. Objective-C는 C에서 확장된 슈퍼셋이라고 하지만 Objective-C를 공부하기 위해 반드시 C를 먼저 공부해야 할 필요는 없을 것 같습니다.

C를 이해한 후에 Objective-C를 시작하는 것이 이론상으로도 맞고, 정상적인 방법일 것입니다. 하지만 대부분의 Objective-C 서적이나 메뉴얼에는 기본적인 문법에 대한 설명이 있고, 전문 C 서적보다는 범위가 작습니다. Objective-C를 사용할 수 있을 만큼 최소한의 문법만 알고 시작하는 것이 더 접근이 쉬울 것 같습니다.

아래는 iPhone 어플케이션의 샘플 소스중에 한부분입니다. 기존에 C/C++ 개발자들도 이런 Objective-C의 문법을 처음 보게되면, 이것이 C와 관련이 있고 C에서 확장되었다는 사실이 잘 이해가 가지 않을 것입니다.
 

처음 시작하시는 분이라면 차라리 이런 혼란을 피하고 코코아 어플리케이션을 바로 제작할 수 있는 Objective-C로 시작하는 것도 한 방법이라고 생각됩니다.

2) 접근방법
사실 가장 좋은 것은 아래와 같이 가장 로우레벨단계 부터 이해하고 올라 가는 것이 기초도 탄탄하고 가장 좋은 방법일 것입니다.

  1. 메모리/CPU등 컴퓨터 하드웨어에 대한 이해
  2. OS에 대한 이해
  3. 컴파일러에 대한 이해
  4. C언어
  5. 시스템 프로그래밍
  6. 자료구조/알고리즘
  7. Objective-C
  8. OOP, 디자인 패턴
  9. Cocoa API

위의 단계대로 차례로 지식과 실력을 쌓아서 접근하면 좋겠지만, 당장 아이폰 어플리케이션을 만들고 싶은데 지루하고 많은 시간을 필요로 합니다. 흥미를 잃지 않고 접근하는 방법은 위의 순서와 반대로 접근하는 것입니다.

Objective-C에 대한 메뉴얼을 대충(?) 한번 읽어 보고 바로 책, 웹사이트, 동영상등의 간단한 튜토리얼등을 따라해 보면서 실제 실행되는 모습을 보면 계속 흥미를 유지할 수 있습니다.

그후에 어느정도 감이 생기면 직접 만들고 싶은 어플리케이션을 목표로 잡습니다. 첫 목표는 과한 욕심은 버리고 간단하고 쉬운 어플리케이션 부터 시작합니다. 아무리 간단해도 따라해 보며 만들었던 것과는 달리 원하는 기능을 직접 구현하는 것은 매우 어렵습니다. 자료도 많이 찾아 보아야되고, 다른 샘플 소스에서 복사해 와야 하는 경우도 있고, 관련 커뮤니티를 통해 도움을 받을 수도 있습니다. 관련자료들은 이전의 iPhone 어플리케이션 개발을 위한 준비 - 3. 관련 자료 포스팅을 참고하시기 바랍니다.

우여곡절끝에 만들어 내면 부족한면이나 필요한 부분이 무엇인지 조금씩 보이게 될 것 입니다. 필요에 의해 공부를 하다보면 아마 위의 순서를 거슬러 올라 접근하게 되는 경우가 많을 것 같습니다. 그러면 차차 복잡하고 어려운 어플리케이션을 만들 수 있을 것입니다.

막상 처음 시작하게 되면 알아야 할 것은 많고 답답한 마음만 드실 것입니다. 하지만 안타깝게도 왕도는 없습니다. 흥미와 열정을 유지하면서 차근차근 해 나가다 보면 어느새 바라는 어플리케이션을 만들수 있는 날이 눈앞에 와있을 것 입니다.

간혹 주위에 개발경험이 전혀 없는 분들로 부터 "무엇부터 시작해야 아이폰 어플리케이션을 만들 수 있냐?"는 질문을 들으면서 이와 관련해서 간단히 포스팅을 해보아야 겠다고 생각했습니다.

정리는 해보았는데 역시 어렵네요. 제가 봐도 이상한 용어들만 난무하고 설명도 중구난방이고, 개발을 처음 하시는 분들이 보면 잘 이해가 안가실 것 같다는 생각이 듭니다.

* 관련링크
iPhone 어플리케이션 개발을 위한 준비 - 1. 하드웨어
iPhone 어플리케이션 개발을 위한 준비 - 2. 소프트웨어
iPhone 어플리케이션 개발을 위한 준비 - 3. 관련 자료
iPhone 어플리케이션 개발을 위한 준비 - 4. 시작하기

iOS 2008.11.25 14:18
SQLite는 경량화된 DB로 맥과 아이폰/아이팟 터치에 기본적으로 내장되어 편리하게 사용할 수 있습니다. 자세한 내용은 SQLite 공식 홈페이지와 아래의 문서들을 참조하시면 도움이 되실 것입니다.


이와함께 애플의 iPhoneDev Center SQLite Book List란 샘플을 보시면, 아이폰 SDK에서 사용하는 방법이 잘 나와있습니다. SQLite의 개발자인 Richard Hipp이 구글 테크토크에서 직접 SQLite에 대해서 설명하는 'An Introducion to SQLite'란 동영상도 참고하면 좋습니다.



아래는 제가 SQLite를 테스트 해보기 위해 만들어 본 간단한 샘플코드입니다. 아이폰에서 사용자로 부터 입력을 받은 후에 SQLite DB에 저장하는 간단한 샘플입니다. DB를 오픈하는 부분과 SELECT, INSERT하는 부분만 참고하시면 쉽게 사용하실 수 있습니다.

* SQLiteTestAppDelegate.h
#import <UIKit/UIKit.h>
#import <sqlite3.h>

@interface SQLiteTestAppDelegate : NSObject <UIApplicationDelegate> {
    UIWindow *window;
    sqlite3 *db;
    NSMutableArray *dataList;

    IBOutlet UITextField *newString;
    IBOutlet UITableView *dataTable;
}

@property (nonatomic, retain) IBOutlet UIWindow *window;

- (void)updateDataList;

- (IBAction)addRow:(id)sender;
   
@end


SQLiteTestAppDelegate.m
#import "SQLiteTestAppDelegate.h"

@implementation SQLiteTestAppDelegate

@synthesize window;

- (void)applicationDidFinishLaunching:(UIApplication *)application {   

    // Override point for customization after application launch
    [window makeKeyAndVisible];
   
    /* 어플리케이션 패스를 구한다. */    
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentsDirectory = [paths objectAtIndex:0];
    NSString *path = [documentsDirectory stringByAppendingPathComponent:@"mydata.db"];
       
    /* 데이터베이스를 오픈한다 */
    if(sqlite3_open([path UTF8String], &db) == SQLITE_OK) {
        char *error = NULL;
        const char* query = "SELECT count(*) from mytable";
       
        /* mytable을 쿼리해보고 오류가 있으면 mytable을 생성한다. */
        if (sqlite3_exec(db, query, NULL, 0, &error) != SQLITE_OK) {
            sqlite3_free(error);
           
            /* 테이블 생성 */
            if (sqlite3_exec(db, "CREATE TABLE mytable ('name' CHAR(16))", NULL, 0, &error) != SQLITE_OK) {
                NSLog(@"TABLE CREATE ERROR: %s", error);
                sqlite3_free(error);
            }   
        }
    } else {
        /* DB 오픈 에러 */
        sqlite3_close(db);
        db = NULL;
       
        NSLog(@"DB OPEN ERROR: '%s'", sqlite3_errmsg(db));   
    }
   
    dataList = [[NSMutableArray alloc] initWithCapacity:100];
   
    [self updateDataList];
}

- (void)applicationWillTerminate:(UIApplication *)application {
    if (db) {
        sqlite3_close(db);
    }
}

- (void)dealloc {
    [dataList release];
   
    [window release];
    [super dealloc];
}

/** 현재 DB에 있는 데이터를 dataList에 등록 */
- (void)updateDataList {
   
    /* 이전 데이터를 모두 삭제 */
    [dataList removeAllObjects];
   
    const char *query = "SELECT name FROM mytable";
    sqlite3_stmt *statement;
   
    if (sqlite3_prepare_v2(db, query, -1, &statement, NULL) == SQLITE_OK) {
        while (sqlite3_step(statement) == SQLITE_ROW) {
           
            /* dataList에 쿼리결과 등록 */
            NSString* str = [[NSString alloc] initWithUTF8String:(char *)sqlite3_column_text(statement, 0)];
            [dataList addObject:str];
            [str release];
        }
    }
    sqlite3_finalize(statement);

    [dataTable reloadData];
}


#pragma mark IBACTION

- (IBAction)addRow:(id)sender {

    char *error = NULL;
   
    /* 사용자가 입력한 값을 DB에 추가한다 */
    NSString *query = [NSString stringWithFormat:@"INSERT INTO mytable VALUES ('%@')", [newString text]];
    sqlite3_exec(db, [query UTF8String], NULL, 0, &error);
   
    [self updateDataList];
}


#pragma mark TextField Delegate method

- (BOOL)textFieldShouldReturn:(UITextField *)textField {
   
    [textField resignFirstResponder];
    return YES;
}


#pragma mark TableView Delegate method

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
    return 1;
}

- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {
    return @"Table Items";
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    return [dataList count];
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
   
    static NSString *cellIdentifier = @"Cell";
   
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
    if (cell == nil) {
        cell = [[[UITableViewCell alloc] initWithFrame:CGRectZero reuseIdentifier:cellIdentifier] autorelease];
    }
    cell.text = [dataList objectAtIndex:indexPath.row];
   
    return cell;
}

@end


요즘은 어디 나갈 때 핸드폰보다 터치를 더 챙기게 되었습니다. NDS도 있지만 아기자기한 게임들을 기울기와 터치로 즐기는 색다른 재미에, 가족들 사이에서도 터치의 게임이 훨씬 더 인기가 좋습니다. 제가 요즘 터치에서 가장 즐겨하는 게임은 Smallware에서 나온 Sol Free라는 카드게임입니다. (유료지만 무료 버젼도 있습니다.) 화장실에도 들고 갑니다. ^^;;


이전에 윈도우에서도 심심풀이로 많이 했지만, 터치에서는 직접 손으로 카드를 옮기고 넘기는 손맛때문에 한층 재미가 더 한 것 같습니다. 컴퓨터의 마우스로는 이 맛이 느낄 수 없어 재미가 없습니다.

다음으로 Rocking Porket Games에서 나온 Blue Skies란 게임도 간혹 하고 있습니다. 유료게임이지만 무료로된 lite 버젼을 설치하였습니다. 대공과 대지 공격을 하는 헬리콥터를 조정하여 적들을 찾아 파괴하는 게임입니다. 기울여서 방향을 조종하기 때문에 조금 반응이 늦는 감은 있지만, 헬리콥터의 움직임과는 잘 어울리는 것 같습니다.

그리고 오늘 App 스토어에서 또 다른 재미있는 게임을 찾았습니다. 작년 초에 아이맥에서 가끔 하고 저의 다른 블로그에서도 소개했던 3D 슈팅게임인 sauerbraten이 아이폰, 터치용으로 포팅이 되어 sauerbraten의 이전 이름인 Cube란 게임으로 나왔습니다.


위는 터치에서 캡쳐한 게임화면입니다. 터치를 돌리면서 진행 방향을 정하고 아래와 같이 외각을 터치해서 움직이고 총을 쏘고 점프를 할 수 있습니다.


이전에 컴퓨터에서 했던 게임을 똑같이 터치에서 할 수 있다는게 신기하긴 하지만, 컨트롤이 터치에서 제가 하기엔 너무 어려운 것 같습니다. 익숙해지면 좀 나아질지 모르겠습니다. PC용 버젼은 전체소스가 공개되어 있는데 터치용 버젼의 소스는 공개가 되지 않은 것 같습니다.

한번씩 App 스토어를 들어가면 이런 재미있는 공짜 게임들이 많이 올라오니, 사용자 입장에선 참 행복하고 고마운 일입니다. 이제는 초기에 비해서 완성도가 꽤나 높은 게임들이 무료나 lite 버젼으로 많이 올라오고 있는 것 같습니다.

애플은 아이폰 개발자 유니버시티 프로그램을 추가하여 대학생들이 공부를 목적으로 무료로 아이폰 어플리케이션을 사용하고 기기에서 테스트 해 볼 수 있는 지원을 하고 있습니다. 이와 마찬가지로 공개 소프트웨어 개발자에게도 무료 개발자 프로그램 등록과 같은 혜택을 주었으면 좋겠습니다.

iOS 2008.11.22 14:33
오늘 맥을 켜니 아이튠즈와 함께 아이팟 터치 펌웨어도 2.2로 업그레이드 되었습니다. 애플 사이트에서 가져온 아이폰 펌웨어 2.2에서 변경된 내역은 아래와 같습니다.

* Enhancements to Maps
  • Google Street View*
  • Public transit and walking directions
  • Display address of dropped pins
  • Share location via email
* Decrease in call setup failures and dropped calls

* Enhancements to Mail
  • Resolved isolated issues with scheduled fetching of email
  • Improved formatting of wide HTML email
* Podcasts are now available for download in iTunes application (over Wi-Fi and cellular network)

* Improved stability and performance of Safari

* Improved sound quality of Visual Voicemail messages

* Pressing Home button from any Home screen displays the first Home screen

* Preference to turn on/off auto-correction in Keyboard Settings

사파리로 브라우징시에 간혹 튕기는 현상이 있었는데, 사파리의 안정화 부분 정도에만 눈길이 가네요. 캘린더에 TODO 기능과 iCal과의 동기화가 되었으면 좋겠는데, 애플에서 언제쯤 넣어줄지 모르겠습니다.

완료후에 iPhone DevCenter로 가보니 역시 SDK도 동일하게 2.2로 업그레이드 되었습니다. SDK를 새로 설치하니 Xcode도 3.1.1에서 3.1.2로 업그레이드 되었습니다.

IDE나 Core의 버젼이 올라갔지만 펌웨어에 맞추어 2.2로 업그레이된 것을 제외하고는 문서를 읽어보아도, 실행해서 대충 둘러 보아도 눈에 뛰게 변경된 점은 없는 것 같습니다.

3. 관련 자료

* 한글 자료와 영어
아쉽게도 이곳에서 소개하는 대부분의 자료들은 영문으로 되어 있습니다. 아이폰과 관련되어 나온 번역서적은 아직까지는 한권도 없습니다. (준비하고 있다는 이야기는 들었습니다) OS X 코코아 프로그래밍에 관련된 내용인 코코아 프로그래밍이란 책이 유일하게 번역되어 나온 관련 서적입니다.


코코아 프로그래밍
카테고리 컴퓨터/IT
지은이 아론 힐리가스 (인사이트, 2007년)
상세보기

아직까지는 코코아 프로그래밍이 대중화 되지 않아 한글로된 자료가 적지만, 점점 많아질 것으로 보아집니다. 하지만 빠르고 다양한 자료를 얻기 위해서는 영문 자료를 보시는 수 밖에 없습니다. 저도 모자라는 영어로 괴롭지만 자꾸 보다보면서 조금씩 익숙해지고 있습니다. 저같이 영어 공부를 게을리 하신 분들은 따로 영어를 공부하실 필요 없이 영문자료로 공부를 하셔도 좋을 것 같습니다.

* ADC (Apple Developer Connection)
사실 맥/아이폰 프로그래밍에 관한 자료를 구하는 곳은 사실 딱 한 곳, ADC만 알고 있어도 됩니다. 이곳에는 애플에서 제공하는 OS X 개발과 관련된 다양한 문서와 자료, 동영상, 소스코드들이 있습니다. 자료가 방대하지만 이곳을 문지방이 닳도록 드나드시며 근본적인 자료들을 보시는 것이 늦어 보이지만 빠른 길입니다.


1) 관련 사이트
맥/아이폰 개발과 관련된 국내외 사이트들과 블로그들입니다. 국내 사이트들도 아직은 다른 일반적인 개발환경에 비해서 자료와 회원들이 많지는 않습니다. 하지만 비슷한 관심분야를 가진 분들과 교류를 할 수 있고, 궁금하신 점들을 올리고 다른 분들의 의견이나 해답을 들을 수 있습니다. 아무래도 같은 한국어로 이야기하는 것이 명확하고 친근할 것 같습니다.

2.1) 사이트
* 국내

* 국외
  • Apple Developer Connection - 애플에서 제공하는 개발자 지원 서비스입니다.
  • Apple Discutssions - Developer Forum - 애플에서 제공하는 개발자 포럼입니다.
  • iPhone Development Forum - 애플의 아이폰 개발자 포럼이며, 현재는 개발자 프로그램에 등록된 회원만 접근할 수 있습니다.
  • Cocoalab - Become An Xcode란 문서로 유명한 사이트이며 관련 강좌와 소스들을 제공합니다.
  • iPhone Development Centra - 아이폰 개발에 관련된 튜토리얼, 포럼을 제공합니다.
  • iPhoneWebDev - 아이폰용 웹사이트 개발에 관련된 예제, FAQ를 제공합니다.
  • Cocoabuilder.com - Cocoa와 Xcode에 관련된 메일링 리스트를 제공합니다.
  • Apps Amuck - 31개의 아이폰 튜토리얼과 샘플코드를 제공합니다.
  • Cocoa Dev Central - 코코아 튜토리얼과 관련 링크들을 제공합니다.
  • CS 193E - 스텐포드 대학에서 제공하는 코코아 프로그래밍 강좌입니다.
  • CS 193P - 스텐포드 대학에서 제공하는 아이폰 프로그래밍 강좌입니다.

2.2) 블로그

아래는 맥, 아이폰 개발 관련 블로그들입니다. RSS로 등록해 놓으시면 유익하고 재미있는 포스팅들을 편하게 구독하실 수 있습니다.


이외에 Xcode, Cocoa, 맥프로그래밍 관련 국내외 사이트란 포스팅도 참고하세요.

2) 관련 서적
다음은 Cocoa, Objective-C, 맥/아이폰 개발에 관련된 서적들입니다. '코코아 프로그래밍'을 제외하고는 모두 원서이므로 아마존과 같은 외국 사이트 또는 국내의 구매대행 서비스를 하는 온라인 쇼핑몰에서 구입을 하셔야 합니다.

맥에서의 개발이든 아이폰에서의 개발이든 공통적으로 Xcode/인터페이스빌더의 사용법과 Objective-C, 파운데이션 프레임워크에 관해서 알고 있어야 합니다. 그렇기 때문에 당장 시작을 할 수는 없지만, 초반에 기본을 익히는데는 맥 프로그래밍 서적을 보셔도 큰 상관은 없을 것 같습니다.


* 코코아 프로그래밍
- 가격: 22,000원
- 출판: 인사이트
- 역자: 박진형

위에서 언급했던 현재까지 유일한 번역서적입니다. 코코아 프로그래밍에 관한 기본적인 사항을 익히기에 아주 좋은 책이지만, Xcode 2.*를 중심으로 소개하고 있기 때문에, 초보자들이 보기에는 Xcode 3.*을 사용하면서 약간의 차이점 때문에 혼돈되는 부분이 있습니다.


* Cocoa Programming for Mac OS X
가격: $31.49
출판: Addison-Wesley Professional
저자: Aaron Hillegass

아론 힐리가스가 쓴 코코아 프로그래밍의 가장 대표적인 서적입니다. 아이폰이 아닌 맥 프로그래밍에 관한 내용이지만 Xcode, 인터페이스 사용법과 Objective-C등 기본적인 내용을 익히기에 좋은 책입니다. 


* Xcode 3 Unleashed
가격: $26.99
출판 Sams
저자: Fritz Anderson

Step into Xcode의 다음 버젼으로 이전과는 달리 깔끔한 디자인으로 Xcode 3에 맞추어 새로 발간된 책입니다. 위의 아론 책과 유사한 입문서적인데 툴 로서의 Xcode 3 사용법에 치중하였습니다. 칼라로 되어 있기 때문에 보기에 편하고 좋습니다.


* Programming in Objective-C 2.0
가격: $26.69
출판: Addison-Wesley Professional
저자: Stephen G. Kochan

Objective-C 언어에 대한 책입니다. 저는 1.0 버젼을 가지고 있어 정확히 내용은 어떻게 변경되었는지는 모르겠습니다. Objective-C에 대해 체계적으로 공부하기에 좋은 책이며, 책의 절반 가량은 코코아에서 사용하는 파운데이션 프레임워크에 관해 설명하고 있습니다.


* The iPhone Developer's Cookbook
가격: $27.62
출판: Addison-Wesley Professional
저자: Erica Sadun

저도 읽은 적은 없지만 아이폰에서의 개발을 따라 해 볼 수 있는 좋은 책이라고 들었습니다. 쿡북이란 제목처럼 실제로 사용할 수 있는 다양한 소스들을 참조하고 따라해 볼 수 있을 것 같습니다.

(이미지 출처:아마존)

지금은 원서도 많지는 않지만 앞으로는 아이폰 개발에 관련된 책들이 많이 나올 것으로 보입니다. 새로 나온 iPhone, Cocoa 관련 책과 저자들이란 포스팅에서 신간 혹은 새로 나올 관련서적을 확인하실 수 있습니다.

3) 관련 문서
ADC에서는 OS X 개발에 기본이되는 많은 문서들을 제공하고 있습니다. 또한 많은 문서들은 pdf 버젼으로 다운로드 받을 수 있습니다. 자주 참조하는 문서들은 pdf 문서로 다운로드를 받아 편하게 읽어 볼 수 있습니다.

3.1) Getting Started 문서
제목 그대로 애플에서 제공하는 맥/아이폰 개발을 처음 시작하는 입문자를 위한 문서들입니다. 이 문서들은 요점만 제공하기 때문에 내용이 짧아 부담없이 읽어 보실 수 있습니다.

* Mac
ADC의 Gettting Started with Apple Technologies 란 문서를 보시면 맥 OS X 개발을 위한 다양한 자료와 링크를 확인하실 수 있습니다. 또한 세부 항목별로 Getting Started with *와 같은 링크를 제공하기 때문에 관심있는 분야별로 보다 상세하게 확인하실 수 있습니다.

* iPhone
iPhone Dev Center에서는 시작 페이지에서 아래와 같은 문서의 링크를 제공합니다. 각 문서들은 로그인 후에 접근할 수 있습니다.


3.2) Objective-C

3.3) Xcode & Cocoa

  • What's New in Xcode - Xcode 3.0과 3.1에서 업그레이드된 사항들입니다.
  • Xcode Workspace Guide - 툴로서 Xcode 사용법에 관한 메뉴얼입니다.
  • Xcode Overview - Xcode에 대한 간단한 설명과 함께 관련내용에 대한 세부 링크를 제공합니다.
  • Become An Xcoder - 처음 코코아 프로그래밍을 시작하는 사람들을 위한 튜토리얼입니다.
  • Cocoa Fundamentals Guide - 코코아 프레임워크에 관련된 전반적인 내용을 제공합니다.
  • Cocoa Application Tutorial - 간단한 코코아 어플리케이션을 만들어 보는 상세한  튜토리얼을 제공합니다.
  • Foundation Framework Reference - 코코아 프로그래밍을 위한 NS로 시작되는 다양한 파운데이션 프레임워크의 클래스들에 대한 설명 과 기본적인 함수, 데이터타입과 상수들에 대한 문서입니다. Xcode의 도움말에서도 확인하실 수 있으며, 제공하는 클래스들을 둘러 보기에 좋은 문서입니다.
  • Application Kit Framework Reference - AppKit은 위의 파운데이션 프레임워크와 함께 코코아 프로그래밍의 핵심 프레임워크로, 사용자 인터페이스(UI)를 위한 프레임워크입니다. 코코아에서 제공하는 다양한 사용자 UI 클래스들을 볼 수 있는 문서입니다.

3.4) 아이폰
ADC에서 아이폰 개발과 관련된 문서들은 링크는 가능하지만, 로그인 하지 않으면 메인 페이지에서 접근할 수 없는 정책에 따라 링크는 제공하지 않습니다. 하지만 아이폰 관련문서는 많지 않기 때문에 iPhone Dev Center로 로그인 후에 쉽게 찾으실 수 있습니다.

애플의 iPhone DevCenter의 메인화면에서 우측하단을 보면 iPhone Reference Library 색션에서 Required Reading 항목을 보면 아래와 같은 세개의 문서가 있습니다. 애플에서도 권장하는 기본적인 문서인만큼 꼭 읽어 보시는 것이 좋습니다.



이상 맥/아이폰 개발을 위한 자료들과 관련 사이트들을 간단히 알아 보았습니다. 급하게 써내려가서 빠지거나 틀린 내용들이 많이 있을 것 같습니다. 이는 추후에 수정해 나가겠습니다.

다음에는 마지막으로 아이폰 프로그래밍을 시작하는 방법에 대해 주관적인 제 생각을 포스팅 해 보겠습니다.
* 관련링크
iPhone 어플리케이션 개발을 위한 준비 - 1. 하드웨어
iPhone 어플리케이션 개발을 위한 준비 - 2. 소프트웨어
iPhone 어플리케이션 개발을 위한 준비 - 3. 관련 자료
iPhone 어플리케이션 개발을 위한 준비 - 4. 시작하기


2. 소프트웨어
아이폰 어플리케이션을 위해 준비해야될 소프트웨어는 Xcode와 iPhone SDK 입니다. 내용은 조금 길지만 요약하면 ADC 맴버쉽 프로그램에 가입 후에 Xcode와 iPhone SDK를 다운로드 받아 설치하시면 됩니다. 맴버쉽 프로그램 등록, 개발 툴 모두 무료입니다.

1) Xcode 와 iPhone SDK 설치
1.1) ADC 가입
Xcode와 iPhone SDK는 모두 무료로 제공됩니다. 하지만 다운로드 받기 위해서는 ADC (Apple Developer Connection) 멤버쉽 프로그램에 가입하셔야 됩니다. (Xcode는 설치CD에 포함되어 있지만, 최신버젼을 얻기 위해서는 다운로드 받아서 설치하시는 것을 권장합니다.)  ADC는 애플이 제공하는 개발에 관련된 각종 툴, 문서, 샘플코드등을 제공하는 서비스입니다. 현재는 아래와 같이 아이폰과 맥, 두개의 색션으로 분리되어 있습니다.


ADC 회원은 지원범위에 따른 여러 유료회원도 있지만, 무료인 온라인 회원으로 가입하셔도 개발툴과 관련 문서, 샘플코드를 사용할 수 있습니다. ADC회원가입과 Xcode, iPhone SDK 설치에 관한 자세한 내용은 Xcode 3 다운로드 및 설치란 포스팅을 참고 하시기 바랍니다.

1.2) Xcode
Xcode는 애플에서 제공하는 OS X에서 맥/아이폰 어플리케이션 개발을 위한 대표적인 개발툴입니다. GCC를 컴파일러로 사용하는 Xcode는 Objective-C, C/C++, Java, Ruby, Python등의 언어를 지원하며, GUI 어플리케이션뿐만 각종 커멘드라인 유틸리티, 프레임워크, 라이브러리, 드라이버등 맥과 아이폰에서 사용하는 다양한 실행 바이너리를 만들 수 있습니다.


* 인터페이스 빌더
Xcode는 맥과 아이폰의 GUI 디자인을 위한 툴로 인터페이스 빌더(IB)를 제공합니다. IB는 OS X 어플리케이션에서 사용하는 nib 파일을 생성해 줍니다. nib에 대한 자세한 설명은 nib 파일 둘러보기란 포스팅을 참조하시기 바랍니다.
 


1.3) 아이폰 시뮬레이터
Xcode 와 iPhone SDK를 설치하면 아이폰 시뮬레이터를 사용할 수 있습니다. 시뮬레이터는 아이폰이나 아이팟 터치가 없더라도, 맥에서 만든 어플리케이션을 실행할 수 있는 아이폰의 에뮬레이터 입니다. 마우스로 터치 UI를 시연해 볼 수 있으며, 회전도 가능합니다.



2) 아이폰 개발자 프로그램 가입
아이폰 어플리케이션을 개발 후에 배포 및 판매를 위해서는 반드시 아이폰 개발자 프로그램에 가입을 하셔야 됩니다. 스텐다드와 엔터프라이즈 두개의 프로그램이 있으며 각각 $99, $299의 비용이 들어 갑니다. (1년마다 같은 비용으로 자격을 연장하셔야 합니다) 차이점은 개발한 어플리케이션을 App 스토어에 등록을 하여 배포를 하는지 또는 직접 배포를 하는지의 여부입니다.


개발자 프로그램에 가입을 하시면 아이폰/아이팟 터치를 테스트 기기로 등록을 할 수 있습니다. Xcode를 이용해 이 등록된 기기로 어플리케이션을 업로드 하여, 실제로 동작을 테스트 해 볼 수 있습니다.

가입이 완료된 후에는 아이폰 개발자 프로그램 포탈에서 iPhone Developer Program Portal User Guide란 문서를 참조하시면, 추후 등록과정을 쉽게 진행하실 수 있습니다. 아이폰 개발자 프로그램 등록 완료란 포스팅에 등록에 관한 저의 간단한 후기가 있습니다.

* 아이폰 개발자 포럼
개발자 프로그램에 등록하시면 현제 베타로 운영중인 아이폰 개발자 포럼도 이용할 수 있습니다. 아이폰 개발자 포럼은 전세계 아이폰 개발자들의 커뮤니티로 주제별로 다양한 의견을 나누고 질문 또는 답변을 할 수 있습니다. 현재까지는 아이폰 개발과 관련되어 질문을 하고 궁굼한 내용을 검색을 하기에 가장 좋은 곳으로 생각이 됩니다.


아이폰 개발에 필요한 소프트웨어를 간단히 알아 보겠습니다. 다음 포스팅에서는 개발을 위해 필요한 정보, 자료등과 접근하는 방법에 대해서 알아 보겠습니다.
* 관련링크
iPhone 어플리케이션 개발을 위한 준비 - 1. 하드웨어
iPhone 어플리케이션 개발을 위한 준비 - 2. 소프트웨어
iPhone 어플리케이션 개발을 위한 준비 - 3. 관련 자료
iPhone 어플리케이션 개발을 위한 준비 - 4. 시작하기


애플의 App 스토어와 아이폰/아이팟 터치에 관심을 가지시는 분들이 많아지면서, 아이폰 개발을 어떻게 시작 하는지 궁금해 하시는 분들이 계셔서 이에 관해서 포스팅을 해볼려고 합니다. 개발에 관한 직접적이거나 기술적인 이야기 보다는 준비해야 할 것, 관련 사이트/서적등에 대해 간단히 써보겠습니다.

기존에 다른 플랫폼에서 개발경험이 있는 분들은 조금만 자료를 찾아 보시면 쉽게 적응을 할 수 있으시니, 이 글에서는 별다른 도움이나 흥미있는 내용이 없을 것입니다. 이 포스팅은 아래와 같은 분들을 대상으로 합니다.

  • 애플 제품을 사용해 본적이 없으신 분
  • 개발 경험이 없으신 분
  • 아이폰 개발을 시작하시려는 분
 
이번과 다음 포스팅에서는 아이폰 어플리케이션 개발을 위해서는 필요한 하드웨어와 소프트웨어에 대해서 알아 보겠습니다. 설명이 길지만 요점은 아래와 같습니다.
* 필수 사항
  • OS X 10.5* 설치된 Mac
  • ADC 회원 가입
  • Xcode
  • iPhone SDK

* 선택 사항
  • 아이팟 터치 (또는 아이폰)
  • 아이폰 개발자 프로그램 가입

1. 하드웨어
1)  Mac 컴퓨터
아이폰 어플리케이션은 Xcode 3( +  iPhone SDK)를 사용하여 개발합니다. Xcode 3.* 버젼과 iPhone SDK는 OS X 10.5(레오퍼드) 이상에서만 설치하고 사용하실 수 있습니다.

그렇기 때문에 레오퍼드가 설치되어 있는 하드웨어가 필요하고, 공식적으로는 애플에서 판매하는 맥을 구입하셔야 합니다. (해킨토시나 cygwin에서 툴체인을 사용하는 방법은 논외로 하겠습니다.) OS X 10.5 레오퍼드에 대해서는 애플의 개발자를 위한 Leopard 기술이란 문서를 참조하시기 바랍니다.

 
1.1) 사양 비교
한국 애플스토어에서 판매하는 맥의 종류와 가격은 아래와 같습니다. 아쉽게도 요즘 환율로 인하여 최근에 나온 맥들은 이전보다 사양에 비해 가격이 많이 상승했습니다.


제품의 사양 및 평가는 제 경험에 의한 지극히 주관적인 평가입니다. 절대적인 것이 아니니 참고만 하시기 바랍니다.

* 맥미니
맥미니 1.83GHz은 가장 저렴한 맥으로 69만원이며, 현재 판매되는 맥중에서 성능은 가장 낮습니다. 또한 맥미니는 디스플레이와 키보드/마우스가 포함되어 있지 않기 때문에, 추가로 구입을 하거나 미리 준비가 되어 있어야 합니다. 하지만

(저는 집에서 가장 사양이 낮은 맥 미니 1.83GHz를 사용하고 있지만, Xcode에서 아이폰 어플리케이션을 개발하고 시뮬레이터를 실행하는데 전혀 부족함을 느끼지 못했습니다. 하지만 리소르를 많이 사용하는 작업이나 고사양의 3D 게임과 같은경우에는 부족한 점이 느껴질 것 같습니다.)


*
iMac

iMac은 디스플레이와 키보드/마우스가 제품에 포함되어 있기 때문에, 추가비용이 거의 발생하지 않습니다. 가격대 성능비가 가장 우수한 맥입니다. 개인적으론 개발용으로 사용하기에는 iMac이 비용대비로 가장 적당하지 않나 생각됩니다. iMac은 외부 모니터도 사용가능하기 때문에, iMac 디스플레이까지 포함하여 듀얼 모니터로 사용할 수 있습니다. 하지만 별도의 Mini DVI to VGA 또는 Mini DVI to DVI 어댑터를 구입하셔야 합니다.


*
맥북/맥북 프로/맥북 에어

당연한 이야기지만 가장 무난한 것은 맥북, 이동성 위주로 선택하면 에어, 성능 위주로 선택하면 맥북 프로입니다. 컴퓨터를 들고 다녀야 할 일이 없다면 개발이나 다른 용도로도 iMac이 더 나은 것 같습니다. 하지만 맥이 2대가 아니면서 집이외에 사무실/학교 등에서도 맥이 필요할 시에는 가장 좋은 선택으로 생각됩니다.

(저는 사무실에서 이전 세대의 2.4GB 흰색 맥북을 사용하고 있습니다. 구입시에 새로나온 iMac이 듀얼 모니터를 지원하는 것을 모르고, 이동할 일은 없지만 단순히 듀얼로 사용할려고 맥북을 구입했습니다. 제가 게임을 안해서 그런지 개발, 업무 및 일반적인 메인 컴퓨터로 사용시에도 사양이 떨어 진다는 생각은 전혀 들지 않았습니다.)


*
맥 프로

사용은 못 해보았지만 당연히 좋을 것 같습니다. 최저사양의 본체 가격만 315만원이며 맥 프로답게 강력하게 사용할려면 메모리와 하드 용량을 더 추가하면 기하급수적으로 비싸집니다. 능력이 되시는 분들은 당연히 맥 프로가 좋습니다.

(제게 있어서는 꿈의 하드웨어이고 다음 세대 iMac이 나오면 맥북에서 갈아 탈려고 합니다. 그리고 3년 정도 더 사용하다 맥 프로를 써보는 것이 야심찬(?) 저의 계획입니다.)


사양이 좋고 속도가 빠르면 빠를 수록 좋지만 가격을 감안하여 용도, 사용 장소, 휴대 여부등을 고려하여 결정하시면 될 것 같습니다. 위에도 언급하였지만 가장 사양이 낮은 맥미니도 아이폰 어플리케이션 개발을 위해선 무리가 없는 사양으로 생각됩니다.

1.2) 할인 혜택
* 교육 할인
대학생 또는 대학생 자녀를 둔 학부모와 유치원/초/중/고/대학교에 근무하는 교직원들은 교육할인 혜택으로 보다 저렴하게 맥을 구입할 수 있습니다.

* 구제품 할인
애플의 할인 스토어에서 구제품을 구입하는 방법도 있습니다. 애플인증 구제품은 반품제품을 애플에서 다시 수리, 교체하여 테스트 후에 판매하는 제품입니다. 거의(?) 새제품을 할인된 가격에 구입할 수 있습니다. 하지만 재고가 많지 않아 등록되자 마자 빠르게 팔리기 때문에 항상 확인을 해야 합니다.

* 중고 직거래
kmug와 같은 관련 커뮤니티 사이트들의 장터를 이용해 직접 중고 맥을 구입할 수 있습니다. OS X 10.5가 설치되어 있거나 설치가 가능하며 인텔 프로세스를 사용한 맥으로 구입하시면 됩니다.


2) 아이팟 터치
아이폰 어플리케이션은 아이폰과 아이팟 터치에서 실행됩니다. 아쉽게도 아이폰은 현재 우리나라에서 판매되지 않기때문에, 외국에서 따로 구입하지 않는다면 아이팟 터치가 거의 유일한 선택입니다.

아이팟 터치는 현재 2세대 제품이 판매되고 있습니다. 1세대와의 기능상 차이점은 아래와 같습니다. Xcode의 시뮬레이터가 있기 때문에 개발시에 아이팟 터치가 반드시 있어야 하는 것은 아닙니다. 배포를 생각하지 않고 있고 터치가 필요하지 않다면 시뮬레이터로도 개발은 가능합니다.

  • 스피커 내장
  • Nike+ 내장
  • 배터리 사용시간 증가
  • 음량 조절 버튼 추가

아이팟 터치는 저장 용량에 따라 8GB, 16GB, 32GB로 판매되고 있으며, 각각의 가격은 아래와 같습니다.

* 8GB - 280,000원
* 16GB - 370,000원
* 32GB - 489,000원

터치는 위의 용량에서 시스템이 1GB정도를 사용하고 있습니다. 역시 용량이 많을 수록 좋겠지만 사용계획과 가격에 따라 적당한 용량을 선택하시면 됩니다. 저는 8GB이며 몇개의 동영상, 노래 30여곡, 어플리케이션, pdf파일, 그림 파일등을 넣고 다니는데 현재 1GB 정도사용하고 있으며 6GB가 사용가능한 용량으로 남아 있습니다.

아이폰 개발시 필요한 하드웨어에 대해서 간단히 둘러 보았습니다. 다음 포스팅에서는 필요한 소프트웨어와 ADC 멤버 프로그램과 아이폰 개발자 프로그램에 대해서 알아 보겠습니다.
 * 관련링크
iPhone 어플리케이션 개발을 위한 준비 - 1. 하드웨어
iPhone 어플리케이션 개발을 위한 준비 - 2. 소프트웨어
iPhone 어플리케이션 개발을 위한 준비 - 3. 관련 자료
iPhone 어플리케이션 개발을 위한 준비 - 4. 시작하기