'iPhone App'에 해당되는 글 54건

  1. 2011.07.28 [iphone] modalviewcontroller의 parentviewcontroller 에서 reload하기
  2. 2011.07.27 [iphone] IB 를 이용해서 Custom TableViewCell 만들기
  3. 2011.07.27 [iphone] Instruments를 이용해서 메모리 체크를 하자
  4. 2011.07.27 [iphone] 예전에 올린 XML Parsing 소스 Upgrade
  5. 2011.07.26 [iphone] exc_bad_access 에러 났을때 Xcode4에서 활용법
  6. 2011.07.26 [iphone] ModelViewController를 사용해서 뷰위에 뷰를 올려보자
  7. 2011.07.25 [iphone] UIViewController안에 UITableView Insert하기
  8. 2011.07.25 [iphone] UIScrollView 이용하기
  9. 2011.07.22 [iphone] WCF Rest Service로 HttpRequest하는법과 한글 인코딩
  10. 2011.07.22 [iphone] tableview에서 cell을 표시할때 KeyValue쓰지 않고 표시하기
  11. 2011.07.21 [Iphone] NSXMLParser를 이용하여 Xml을 파싱해보자.
  12. 2011.07.19 [iphone] navigationItemButton 추가하는법
  13. 2011.07.18 [iphone] NSMutableArray may not respond to ObjectForKey란 에러메세지
  14. 2011.07.18 [iphone] UITabbarController에서 탭을 선택했을때 항상 Reload, Refresh하기
  15. 2011.07.14 [iphone] string append하기
  16. 2011.07.14 [iphone] Singletone Class만들기
  17. 2011.07.13 [iphone] UITableView에 Data를 넣어보자.
  18. 2011.07.12 [xcode] 간단하게 UITableView를 써보자.
  19. 2011.06.23 [object-c] 컬렉션 사용하기 NSValue NSMutableArray 를 이용
  20. 2011.06.17 [xcode] 아이폰에서 버튼 이벤트 발생시키기 2
  21. 2011.01.07 google docs와 아이패드를 이용하여 Todo List 활용
  22. 2010.09.13 몽키3 결제 했는데 꼭 해지하자. 적어도 11월 10일
  23. 2010.09.07 아이폰 받았을시 확인해봐야할것
  24. 2010.08.17 아이폰4 예약 하기
iPhone App2011. 7. 28. 13:48

내가 하고 싶엇던것은 글쓰기 댓글달기 창을 modal 뷰로 띄우고 저장하면 창이 없어지면서 tableview가 refresh되기를 원했었다.

아직 잘모르겠따

http://stackoverflow.com/questions/2412688/uiviewcontroller-parentviewcontroller-access-properties

여기랑

상위view에서 하위view 만들때 delegate를 이용하자

self.downViewController = [[DownViewController alloc]

initWithNibName:@"DownView" bundle:nil];

self.downViewController.delegate = self;

...

하위view에서 상위view의 Controller사용

[delegate presentModalViewController:self.downTwoViewController animated:YES];

이래 하면 delegate가 상위view의 Controller가 됨  

이걸 참조해보자.

http://liebus.tistory.com/entry/상위-view-의-Controller를-사용하고자-할때

---------------------------------------------------------------------------------------------------

새롭게 해보자.

목적: child navigation 메뉴에서 Save를 눌렀을때 parent navgationViewControoler의 Table을 Reload 하는 메소드를 호출하는것

일단 팝업이나 네비게이션 된 자식 헤더에

@property (nonatomic,retain) HugeBoardViewController *hugeboardViewController;


이렇게 parentController를 추가하고


저장버튼에

hugeboardViewController = [self.navigationController.viewControllers objectAtIndex:0];

hugeboardViewController ReloadBoardData];


이렇게 구현했다.

Posted by 동동(이재동)
iPhone App2011. 7. 27. 17:18

일단 UITableViewCell Class를 하나 만들고 Empty Xib 파일도 만든다.

201107271711.jpg

일단 뷰에 UITableViewCell을 추가하고

그뒤 저렇게 Files'Owner에서 class를 UIViewController로 바꾼다.

이번에는 UITableViewCell에 가서


201107271715.jpg

이렇게 바꾸고


201107271716.jpg

identifer도 바꾼다. 바꾸면 이렇게 된다.


201107271716.jpg

자 이제 클래스 파일을 수정하자

헤더파일이다

#import <UIKit/UIKit.h>


#define HugeBoardCellIdentifier @"HugeBoardCellIdentifier"


@interface HugeBoardCell : UITableViewCell {

IBOutlet UILabel *titleLabel;

IBOutlet UILabel *idxLabel;

}


@property (nonatomic,retain) IBOutlet UILabel *titleLabel;

@property (nonatomic,retain) IBOutlet UILabel *idxLabel;

+ (id)cellWithNib;


@end


딴건 중요하지 않고 cellWithNib이 중요하다
실제 구현부에

+ (id)cellWithNib

{

HugeBoardCell *cell;

UIViewController *controller = [[UIViewController alloc] initWithNibName:@"HugeBoardCell" bundle:nil];

cell = (HugeBoardCell *)controller.view;

[controller release];

return cell;

}


이렇게 추가한다.

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

  HugeBoardCell *cell = (HugeBoardCell *)[tableView dequeueReusableCellWithIdentifier:HugeBoardCellIdentifier];

  

if (cell == nil) {   

cell = [HugeBoardCell cellWithNib];   

}

HugeBoardData* hd = [boardData objectAtIndex:indexPath.row];

cell.titleLabel.text = [NSString stringWithFormat:@"%@", hd.title];

cell.idxLabel.text= [NSString stringWithFormat:@"%@ : ", hd.idx];


실제 사용하는부분에 이렇게 사용했다 ,
Posted by 동동(이재동)
iPhone App2011. 7. 27. 11:35

일단 xcode 4를 위주로 설명하겠다.

지금까지 메모리 관리가 엉망이었다. 메모리 관리를 철저하게 하지 안흐면

계속 사용할때마다 메모리를 먹기때문에 나중에 문제가 생긴다.

그래서 코딩후 항상 체크하는 습관을 가지면 좋다.

일단 prouct의 profile을 클릭한다 단축키가 더 편하다 커맨드+I

201107271128.jpg  

Leaks를 선택한다.

그러면 시뮬레이터가 뜨고 막 이리저리 사용해본다.


201107271132.jpg

그러면 이렇게 뜨는데 snapshot interval이 기본은 10으로 되어있는데 좀더 세밀하게 관찰하기 위해서 좀더 줄인다 나는 5정도로 했다.

그리고 leaks를 클릭 해서 보면 저렇게 메모리 관련 오류가 나온다 그쪽에서 responsible Library를 클릭하면 프로젝트 별로 죽 뜨는데

그쪽에서 현재 자기가 진행하는 프로젝트 이름만 보면 된다.

그뒤 더블 클릭하면 오류가 난 코드가 있는쪽으로 바로간다. 그쪽에서 혹시 메모리관리를 잘못했는지 확인해보자.

Posted by 동동(이재동)
iPhone App2011. 7. 27. 11:19

저번에 XML에 파싱 부분을 올렸었다 소스를 올렸지만 그렇게 되면 메모리 관리가 제대로 안돼서 다시 만들었다.

일단 지난 번 코드를 보자

-(NSMutableArray*) parseContent:(NSURL*) url

{

NSXMLParser* xmlParser = [[NSXMLParser alloc] initWithContentsOfURL:url];

[xmlParser setDelegate:self];

  

_hugeBoardDataArray =[NSMutableArray arrayWithCapacity:1024];

_elementStack = [NSMutableArray arrayWithCapacity:1024];

[xmlParser parse];

return _hugeBoardDataArray;

}

@end

보면 엉망이다 일단 arrayWithCapacity를 마땅히 쓸필요가 없고 _hugeBoardDataArray와 ElementStack을

- (id) init

{

if((self = [super init]) != nil)

{

_hugeBoardDataArray = [[NSMutableArray alloc] init];

_elementStack = [[NSMutableArray alloc] init];

}

  

return self;

}

생성자에서 이렇게 처리 하였다.


그리고 이부분은

-(NSMutableArray*) parseContent:(NSURL*) url

{

NSXMLParser* xmlParser = [[NSXMLParser alloc] initWithContentsOfURL:url];

[xmlParser setDelegate:self];

[xmlParser parse];

[xmlParser release];

  

return [NSMutableArray arrayWithArray:_hugeBoardDataArray];

}

이렇게 고쳤다.

return 부분이 포인트다 무언가를 리턴할때 꼭 autoRelase로 만들어서 리턴해야 한다는 것을 깨달았다.

arraywitharray를 쓴이유다 만약 그냥 _hugeBoardDataArray를 리턴하게 되면 release를 해줘야 하는 타입임으로

저렇게 넣어서 했다.


그리고 data쪽도 new로 받았었는데

- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qualifiedName attributes:(NSDictionary *)attributeDict

{

if([elementName isEqualToString:@”HugeBoardInfo”] == TRUE)

{

HugeBoardData *data = [[HugeBoardData alloc] init];

[_elementStack addObject:data];

[data release];

}

else if([elementName isEqualToString:@”idx”] || [elementName isEqualToString:@”Name”] || [elementName isEqualToString:@”Title”] || [elementName isEqualToString:@”Description” ] || [elementName isEqualToString:@”Date”])

{

NSString *element = [NSString stringWithString:elementName];

[_elementStack addObject:element];

}

}

저렇게 alloc로 받도록 수정하였다.


마지막으로

-(void) dealloc

{

[super dealloc];

[_hugeBoardDataArray release];

[_elementStack release];

}

이렇게 메모리 해제는 꼭 해줘야 한다.




Posted by 동동(이재동)
iPhone App2011. 7. 26. 16:13

product창을 클릭후 Edit Scheme를 클릭



201107261612.jpg

이렇게 app에 가서 Arguments에 간후 NSZombieEnabled와 NSDebugEnabled를 YES로 하면

메모리 오류가 날시 어디서 에러가 났는지 알려준다.

참고한곳 http://mellang.tistory.com/12

Posted by 동동(이재동)
iPhone App2011. 7. 26. 14:17

네이버 카페 어플 이나 기타 글쓰는 어플 보면 네비게이션 보다는 ModelView를 이용해서 현재 뷰위에 뷰를 띄우는 방식을

이용을 많이 사용했다.

그래서 나도 리플을 다는곳에 그냥 ModelView를 이용해 보았다.

너무 쉬웠다. 애플이 참 sdk를 잘만들었구나 싶은 생각이 들었다.

-(void)WriteReply{

ReplyEditView* replyEditView = [[[ReplyEditView alloc]init] initWithNibName:@"ReplyEditView" bundle:nil];

[self presentModalViewController:replyEditView animated:YES];

[replyEditView release];

}


그냥 이부분만 넣으면 된다.

[self presentModalViewController:replyEditView animated:YES];


그럼 닫고 싶을때는 어떻게?


-(void)cancel

{

[self dismissModalViewControllerAnimated:YES];

}



참고한곳 : http://blog.daum.net/urilove0314/8033115

Posted by 동동(이재동)
iPhone App2011. 7. 25. 18:31

대부분 책들은 UIViewController를 만들지 않고 바로 UITableViewController를 바로 상속받아서 사용하였다.

지금은 UIBiewController 에 여러 컨트롤들과 함께 UITableView를 Insert하는 형식으로 만들어보자.

일단 xib view에 TableView를 하나 만들어서 넣자

@interface DetailView : UIViewController <UITableViewDelegate,UITableViewDataSource>{

   IBOutlet UITableView *descriptionTableView;  

NSMutableArray *data;

}


그뒤 UITableViewDelegate,UITableViewDataSource 프로토콜을 이용하자


- (void)viewDidLoad

{

[super viewDidLoad];

descriptionTableView.delegate = self;

descriptionTableView.dataSource = self;

}


viewdidload에 이렇게 추가하고


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


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


필수 2개 델리게이트를 구현하면 된다 끝~


참고한곳 : http://iwoohaha.tistory.com/156





Posted by 동동(이재동)
iPhone App2011. 7. 25. 18:23

iphone에서 이용하기 위해서는 일단 xib에 UIScrollVier

201107251821.jpg

이런식으로 넣고

ViewDIDLoad에

- (void)viewDidLoad

{

[super viewDidLoad];

// Do any additional setup after loading the view from its nib.

  

descriptionTextView.text = hugeBoardData.description;

  

  

   scrollview.frame = CGRectMake(0, 0, 320, 460);

scrollview.contentSize = CGSizeMake(320, 800);


이렇게 rect를 만든다.그러면 화면이 스크롤이 된다.
참고한곳 : http://www.roseindia.net/tutorial/iphone/tutorial/iphone/UIScrollView-Example-iPhone.html
Posted by 동동(이재동)
iPhone App2011. 7. 22. 18:51

일단 내가 하고 싶었던것은 GET방식의 URL을 HttpRequest 를 해서 WCF에 전송하게 한뒤 글을 쓰게 만드는것이 목표였다.

일단 헤더에 NSMutableData를 만들고

-(void) save{

responseData = [NSMutableData new];

NSString *serviceURL = [NSString stringWithFormat:@"http://192.168.10.3:9090/hugeboardservice/write?name=%@&title=%@&description=%@",

[self encodeString:nameTextField.text],

[self encodeString:titleTextField.text],

[self encodeString:descriptionTextView.text]];


NSURL *url = [NSURL URLWithString:serviceURL];

NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:60.0];

  

[request setHTTPMethod:@"GET"];

  

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

[self.navigationController popViewControllerAnimated:YES];

}


이렇게 했다 저기 위에 보면 NSURLConnectino을 delegate 받았다.


그래서 추가적으로 4개의 델리게이트 메소드를 만들었다.


- (void) connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response {

[responseData setLength:0];

}


- (void) connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {

[responseData appendData:data];

}


- (void) connectionDidFinishLoading:(NSURLConnection *)connection {

[connection release];

  

NSString* responseString = [[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding];

NSLog(@"the html from google was %@", responseString);

  

[responseString release];

}


-(void) connection:(NSURLConnection *)connection didFailWithError:(NSError *)error {

NSLog(@"something very bad happened here");

}


참고한곳은 http://toranbillups.com/blog/archive/2011/04/10/Writing-your-first-http-request-in-objective-c


여기이다.

하지만 이렇게 하다보니 문제가 생겼다 한글을 파라미터로 하면 오류가 났던것이다. 아마 인코딩을 안해서 그렇다고 생각해서


//한글떄문에 엔코딩하기 위해서 만든 메소드

-(NSString *)encodeString: (NSString*) unencodedString{

NSString *temp = (NSString *)CFURLCreateStringByAddingPercentEscapes(

NULL,

(CFStringRef)unencodedString,

NULL,

(CFStringRef)@"!*'();:@&=+$,/?%#[]",

kCFStringEncodingUTF8 );

  

return temp;

}


이런 메소드를 추가로 만들었다
만드는데 참고한 사이트는
http://simonwoodside.com/weblog/2009/4/22/how_to_really_url_encode/


***추가***

save를 하고 뒤로 가기 위해서 save메소드에 

[self.navigationController popViewControllerAnimated:YES];

이걸 넣었는데

여기에 넣는게 아니라 

- (void) connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response { [responseData setLength:0]; [self.navigationController popViewControllerAnimated:YES]; }

이쪽에 넣는것이 맞다. 한마디로 작업이 완료가 되면 뒤로 넘어가야지 바로 넘어가면 안되는것이다.

참고 : http://www.pcraft.kr/101


Posted by 동동(이재동)
iPhone App2011. 7. 22. 15:28

이것참... 역시 책으로 공부하면 안되는것이다.

책에서 tableview에 내용을 넣을때 array에 넣고 안에 딕션널리 컬렉션류를 넣어서 항상 forkey를 이용하게 했었다.

그래서 이번에 xml을 파싱하여 tableview로 보여줬어야 했는데 NSObject 클래스로 만들어서 안에 있는 내용을 보여줄려고 해서

key를 쓸려니까 잘안되었다.

말로는 설명이 힘드니 직접 코드를 보자..

@interface HugeBoardData : NSObject {

NSString* _idx;

NSString* _name;

NSString* _title;

NSString* _description;

NSString* _date;

}


@property(nonatomic,retain) NSString* idx;

@property(nonatomic,retain) NSString* name;

@property(nonatomic,retain) NSString* title;

@property(nonatomic,retain) NSString* description;

@property(nonatomic,retain) NSString* date;

이런 데이터 구조를 가진 object class가 있다 여기에 데이터를 집어넣고

HugeBoardData *data = (HugeBoardData*)parentElement;

if([element isEqualToString:@"idx"])

{

data.idx = trimmedValue;

}

else if([element isEqualToString:@"Name"])

{

data.name = trimmedValue;

}

else if([element isEqualToString:@"Title"])

{

data.title = trimmedValue;

}

else if([element isEqualToString:@"Description"])

{

data.description = trimmedValue;

}

else if([element isEqualToString:@"Date"])

{

data.date = trimmedValue;

}

이런식으로 집어넣고 tableiew delegate에서

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

  

static NSString *CellIdentifier = @"Cell";

  

//UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];

UITableViewCell *cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier] autorelease];

  

if (cell == nil) {

cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];

}


HugeBoardData* hd = [data objectAtIndex:indexPath.row];

  

cell.textLabel.text = [NSString stringWithFormat:@"%@. %@", hd.idx, hd.title];

cell.detailTextLabel.text = [NSString stringWithFormat:@"%@", hd.name];


return cell;

}


이렇게

HugeBoardData* hd = [data objectAtIndex:indexPath.row];

하고 하나씩 꺼내 쓰면 된다 그러면 원하는 idx,title,name등을 골라서 뽑아 쓰면 된다.

막상 인터넷에도 없고 책에는 다 딕셔널리로 되어 있어서 상당히 헷갈렸던 부분이다.

앞으로 array안에 꼭 데이터를 저렇게 넣고 빼서 써야겠다 어찌보면 간단한건데 헷갈렸던것이다.


Posted by 동동(이재동)
iPhone App2011. 7. 21. 18:15

아이폰에서 XML을 파싱하기 위해서는 여러가지 방법이 있다.

라이브러리를 이용하는 방법(touchXML,KISSXML등등)과 NSXMLParser를 이용하는 방법이 있다.

아이폰이 아닌 그냥 맥개발에서는 NSXMLDocument가 있어서 편하게 쓸수 있다고 하는데 아무튼.. 그냥 힘든방법으로 가자.

c#으로 개발했을때는 시리얼라이즈가 있어서 클래스만 만들면 자동으로 xml을 만들고 파싱하고 아주 편했다.

하지만 Iphone Objective-C는........ㅠ.ㅠ

일단 WCF Rest서비스를 만들어서 DB내용을 XML로 동적으로 뿌려주기 위한 서비스를 만들었다.

그래서 파싱할 xml은 이렇다.

<ArrayOfHugeBoardInfo xmlns="http://schemas.datacontract.org/2004/07/HugeBoardService" xmlns:i="http://www.w3.org/2001/XMLSchema-instance">

<HugeBoardInfo>

<Date>2010-02-02T00:00:00</Date>

<Description>hi</Description>

<Name>leejaedong</Name>

<Title>hi</Title>

<idx>1</idx>

</HugeBoardInfo>

일단 이 데이터를 저장할 클래스부터 만들자 C#이랑 비슷하다 여기까지는

@interface HugeBoardData : NSObject {

NSString* _idx;

NSString* _name;

NSString* _title;

NSString* _description;

NSString* _date;

}


@property(copy) NSString* idx;

@property(copy) NSString* name;

@property(copy) NSString* title;

@property(copy) NSString* description;

@property(copy) NSString* date;



@end

헤더에 이렇게 넣고

@implementation HugeBoardData

@synthesize idx= _idx;

@synthesize name= _name;

@synthesize title= _title;

@synthesize description = _description;

@synthesize date= _date;

@end


구현부에 구현을 하자

그다음 일단 Xml을 파싱을 전문적으로 하는 class를 만들자.

@interface HugeBoardXmlParser : NSObject<NSXMLParserDelegate> {

NSXMLParser *parser;

NSMutableArray *_hugeBoardDataArray;

NSMutableArray *_elementStack;

}


@property (nonatomic,retain) NSXMLParser *parser;

-(NSMutableArray*)parseContent: (NSURL*) url;

@end


이름을 HugeBoardXmlParser라 만들고 NSXMLParser 델리게이트를 참조 하였다.그리고 XML을 parser할 NSXMLParser와 xml파일의 모든 데이터를 저장할 hugeboardDataArray그리고 elementStack이라고 해서 한줄한줄 읽을때마다 저장해서 이게 어떤 노드에 있고 어떤값지를 임시로 저장해놓는 array이다

#import "HugeBoardXmlParser.h"

#import "HugeBoardData.h"


@implementation HugeBoardXmlParser


@synthesize parser;


- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qualifiedName attributes:(NSDictionary *)attributeDict

{

if([elementName isEqualToString:@"HugeBoardInfo"] == TRUE)

{

HugeBoardData *data = [HugeBoardData new];

[_elementStack addObject:data];

}

else if([elementName isEqualToString:@"idx"] || [elementName isEqualToString:@"Name"] || [elementName isEqualToString:@"Title"] || [elementName isEqualToString:@"Description" ] || [elementName isEqualToString:@"Date"])

{

NSString *element = [NSString stringWithString:elementName];

[_elementStack addObject:element];

}

}


- (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName

{

if([elementName isEqualToString:@"HugeBoardInfo"] == TRUE)

{

HugeBoardData *data =(HugeBoardData*)[_elementStack lastObject];

[_hugeBoardDataArray addObject:data];

[_elementStack removeLastObject];

}

else if([elementName isEqualToString:@"idx"] || [elementName isEqualToString:@"Name"] || [elementName isEqualToString:@"Title"] || [elementName isEqualToString:@"Description" ] || [elementName isEqualToString:@"Date"])

{

[_elementStack removeLastObject];

}

  

}


- (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string

{

//trim 쓰자면 이걸 쓰고 안하면 그냥 string 값을 넣어도 된다.

NSCharacterSet *characterSet = [NSCharacterSet whitespaceAndNewlineCharacterSet];

NSString *trimmedValue = [string stringByTrimmingCharactersInSet:characterSet];

if([trimmedValue length] == 0)

{

return;

}

  

id element = [_elementStack lastObject];

if([element isKindOfClass:[NSString class]])

{

NSUInteger count = [_elementStack count];

NSUInteger index = count -2;

id parentElement = [_elementStack objectAtIndex:index];


HugeBoardData *data = (HugeBoardData*)parentElement;

if([element isEqualToString:@"idx"])

{

data.idx = trimmedValue;

}

else if([element isEqualToString:@"Name"])

{

data.name = trimmedValue;

}

else if([element isEqualToString:@"Title"])

{

data.title = trimmedValue;

}

else if([element isEqualToString:@"Description"])

{

data.description = trimmedValue;

}

else if([element isEqualToString:@"Date"])

{

data.date = trimmedValue;

}

}

}

-(NSMutableArray*) parseContent:(NSURL*) url

{

NSXMLParser* xmlParser = [[NSXMLParser alloc] initWithContentsOfURL:url];

[xmlParser setDelegate:self];

  

_hugeBoardDataArray =[NSMutableArray arrayWithCapacity:1024];

_elementStack = [NSMutableArray arrayWithCapacity:1024];

[xmlParser parse];

return _hugeBoardDataArray;

}

@end


이것은 구현부이다.
하나씩 알아보자.일단 파싱을 하기 위해서 필요한 3가지 델리게이트가 있다.첫째 이부분이다.

- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qualifiedName attributes:(NSDictionary *)attributeDict

{

if([elementName isEqualToString:@"HugeBoardInfo"] == TRUE)

{

HugeBoardData *data = [HugeBoardData new];

[_elementStack addObject:data];

}

else if([elementName isEqualToString:@"idx"] || [elementName isEqualToString:@"Name"] || [elementName isEqualToString:@"Title"] || [elementName isEqualToString:@"Description" ] || [elementName isEqualToString:@"Date"])

{

NSString *element = [NSString stringWithString:elementName];

[_elementStack addObject:element];

}

}

초반 엘리먼트를 읽는다. 우린 이것을 일단 모두 저장한다. 어디에? elementStack에

그다음 호출되는것은 이거다

- (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string

{

//trim 쓰자면 이걸 쓰고 안하면 그냥 string 값을 넣어도 된다.

NSCharacterSet *characterSet = [NSCharacterSet whitespaceAndNewlineCharacterSet];

NSString *trimmedValue = [string stringByTrimmingCharactersInSet:characterSet];

if([trimmedValue length] == 0)

{

return;

}

  

id element = [_elementStack lastObject];

if([element isKindOfClass:[NSString class]])

{

NSUInteger count = [_elementStack count];

NSUInteger index = count -2;

id parentElement = [_elementStack objectAtIndex:index];


HugeBoardData *data = (HugeBoardData*)parentElement;

if([element isEqualToString:@"idx"])

{

data.idx = trimmedValue;

}

else if([element isEqualToString:@"Name"])

{

data.name = trimmedValue;

}

else if([element isEqualToString:@"Title"])

{

data.title = trimmedValue;

}

else if([element isEqualToString:@"Description"])

{

data.description = trimmedValue;

}

else if([element isEqualToString:@"Date"])

{

data.date = trimmedValue;

}

}

}


실제 Value값을 여기서 얻을수가 있는데 아까 처음에 _elementStack에 저장했던 값을 분석해서 HugeBoardData라는 아까 만든 저장형 클래스에 담는다. trimmedValiue대신에 string을 넣어도 된다.
마지막으로 호출되는것은 이것이다.

- (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName

{

if([elementName isEqualToString:@"HugeBoardInfo"] == TRUE)

{

HugeBoardData *data =(HugeBoardData*)[_elementStack lastObject];

[_hugeBoardDataArray addObject:data];

[_elementStack removeLastObject];

}

else if([elementName isEqualToString:@"idx"] || [elementName isEqualToString:@"Name"] || [elementName isEqualToString:@"Title"] || [elementName isEqualToString:@"Description" ] || [elementName isEqualToString:@"Date"])

{

[_elementStack removeLastObject];

}

}


여기서하는것은 아까 foundCharacters에서 저장한 HugeBoardData를 _HugeBoardDataArray에 저장한다. 여기까지가 한텀이 끝난것이다. 이제 아마 같은 방식으로 계속 한텀한텀씩 저장해서 모든 xml데이터를 _hugeBoardDataArray에 저장할것이다.한텀이 끝났으면 다음텀을 위해서 _elementStack을 삭제한다. 이렇게 3개의 델리게이트 메소드가 계속 호출되면서 반복된다.
이제 이 모든기능을 작동되게 만드는 외부에서 호출 당하는 메소드를 보자

-(NSMutableArray*) parseContent:(NSURL*) url

{

NSXMLParser* xmlParser = [[NSXMLParser alloc] initWithContentsOfURL:url];

[xmlParser setDelegate:self];

  

_hugeBoardDataArray =[NSMutableArray arrayWithCapacity:1024];

_elementStack = [NSMutableArray arrayWithCapacity:1024];

[xmlParser parse];

return _hugeBoardDataArray;

}


여기보면 xmlParser를 작동되게 하고 모든 xmlData를 포함하는 _hugeBoardDataArray를 리턴한다.
그래서 외부에서 사용할려면

NSURL *XMLURL =[NSURL URLWithString:@"http://192.168.10.3:9090/hugeboardService/getboardinfo"];

HugeBoardXmlParser* parser = [[HugeBoardXmlParser alloc] init];

NSMutableArray *hugeboardArr = [parser parseContent:XMLURL];


이렇게 하면 된다. 그럼 hugeBoardArr에 모든 데이터가 저장될것이다.



참고 한 사이트 : http://kiipos.delimount.net/1084

Posted by 동동(이재동)
iPhone App2011. 7. 19. 16:26

viewdidload에 이런식으로 추가하고


action쪽에 onadd를 등록했다.


- (void)viewDidLoad

{

[super viewDidLoad];

  

UIBarButtonItem* toAdd=[[UIBarButtonItem alloc] initWithTitle:@"음식 추가" style:UIBarButtonItemStylePlain target:self action:@selector(onAdd)];

self.navigationItem.rightBarButtonItem = toAdd;

   [toAdd release];

.

.

}

그리고 이렇게 아까 action에 쓴 onAdd 메소드를 구현하면 된다.

- (void)onAdd

{

NSLog(@"hi");

}

Posted by 동동(이재동)
iPhone App2011. 7. 18. 14:58

코딩을 하다보니 이런 경고가 계속 떠서 짜증났다.

이런 경고를 없애기 위해서 인터넷 찾아보니

for문 in을 쓸때(c#에서는 foreach) NSmutableArray 컬렉션으로

   for(NSMutableArray *item in afd.foodData)

{

NSNumber *calrorie = [NSNumber numberWithInt:[[item objectForKey:@"calrorie"] intValue]];

count = [NSNumber numberWithInt:[count intValue]+[calrorie intValue]];

NSString *name = [NSString stringWithString:[item objectForKey:@"name"]];

[totalName appendFormat:@"%@ (%d) Cal \n",name,[calrorie intValue]];

}


이런식으로 하니 경고가 발생했다 그래서

   for(NSMutableDictionary *item in afd.foodData)

{

NSNumber *calrorie = [NSNumber numberWithInt:[[item objectForKey:@"calrorie"] intValue]];

count = [NSNumber numberWithInt:[count intValue]+[calrorie intValue]];

NSString *name = [NSString stringWithString:[item objectForKey:@"name"]];

[totalName appendFormat:@"%@ (%d) Cal \n",name,[calrorie intValue]];

}


이렇게 수정하니 경고가 사라졌다.
참고 : http://stackoverflow.com/questions/6196688/how-to-resolve-nsmutablearray-may-not-respond-to-objectforkey
Posted by 동동(이재동)
iPhone App2011. 7. 18. 13:39

샘플로 칼로리 계산기를 만들면서 Tab을 클릭하면 항상 새로운 데이터를 다시 로드하는 것을 하고 싶었다.

인터넷 찾아보니

- (void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController {

NSLog(@"didSelectViewController : %@",viewController);

}


이런 delegate를 사용하란다. 이것을 호출하기 위해서 헤더에 프로토콜을 추가하고 이렇게

interface CalrorieCalAppDelegate : NSObject <UIApplicationDelegate,UITabBarControllerDelegate> {


IBOutlet UITabBarController *tabBar;

}


이 delegate를 꼭 추가해준다 구현부에
[self.tabBar setDelegate:self];
추가한 곳은 아래와 같다.    

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions

{

// Override point for customization after application launch.

//self.window.rootViewController = self.viewController;

self.window.rootViewController = self.tabBar;

[self.tabBar setDelegate:self];

[self.window makeKeyAndVisible];

return YES;

}



하지만 이것보다 더 좋은 방법이 있다. 바로


-(void) viewWillAppear:(BOOL)animated


이걸 이용한 방법이다. view에서 override 해서 쓴다.

tab을 읽기전에 항상 호출된다.


자 이곳에서 refresh를 해주자.


-(void) viewWillAppear:(BOOL)animated

{

AteFoodData* afd = [AteFoodData sharedSingletonClass];

count = [[NSNumber alloc] init];

NSMutableString *totalName = [NSMutableString stringWithString:@"음식 이름\n\n"];

for(NSArray *item in afd.foodData)

{

NSNumber *calrorie = [NSNumber numberWithInt:[[item objectForKey:@"calrorie"] intValue]];

count = [NSNumber numberWithInt:[count intValue]+[calrorie intValue]];

NSString *name = [NSString stringWithString:[item objectForKey:@"name"]];

[totalName appendFormat:@"%@ (%d) Cal \n",name,[calrorie intValue]];

}

  

resultTextView.text = [NSString stringWithFormat:totalName];

resultLabel.text = [NSString stringWithFormat:@"당신이 섭취한 칼로리는? (%d칼로리)",[count intValue]];

}


이렇게 하면 탭을 눌렀을때 항상 값을 읽어온다.
여담이지만 여기서 메모리 에러가 나서 고생했었는데 count를 전역변수로 해서 쓰는데 header에서 NSNumber로 해서정의했지만
count = [[NSNumber alloc] init];

이렇게 count를 초기화를 안해줘서 메모리 에러가 났었다. 항상 초기화를 해주자.!!






Posted by 동동(이재동)
iPhone App2011. 7. 14. 17:07

스트링을 append할때

NSString에 stringAppendingString인가 를 쓰니까 안붙어져서

NSMutableString을 쓰니까 잘 된다.

NSString *name = [NSString stringWithString:[item objectForKey:@"name"]];

[totalName appendFormat:@"%@ "name];


이런식으로
appendFormat을 이용하자
그리고 줄 바꿀려면 \n 을 이용하면 된다.
Posted by 동동(이재동)
iPhone App2011. 7. 14. 11:29

요즘 다이어트 시대를 맞이해 연습차 칼로리 계산기를 만들어 보았다.

근데 칼로리를 지속적으로 저장해야 하는데 c# 같은경우는 그냥 static class 하나 만들어서 저장을 했는데

objective c에서도 있었다.

// SingletonClass.h

#import <Foundation/Foundation.h>

@interface SingletonClass : NSObject

{

}

+ (SingletonClass *)sharedSingletonClass;

@end

일단 이렇게 헤더 class를 만들고

// SingletonClass.m

#import "SingletonClass.h"

@implementation SingletonClass

+ (SingletonClass *)sharedSingletonClass

{

   static SingletonClass *singletonClass = nil;

  

   if(singletonClass == nil)

   {

   @synchronized(self)

   {

   if(singletonClass == nil)

   {

   singletonClass = [[self alloc] init];

   }

   }

   }

  

   return singletonClass;

}

@end

구현부에 이렇게 하면 된다.

사용은

SingletonClass *s = [SingletonClass sharedSingletonClass];

이렇게 하면 된다.

이렇게 하면 클래스 인스턴스를 한번만 생성되어서 어디서나 클래스를 만들어도

스태틱한 class가 되는것이다.

참고 : http://b4you.net/blog/210

Posted by 동동(이재동)
iPhone App2011. 7. 13. 11:10

값을 넣는대는 프로퍼티를 이용해서 값을 return 해주는방법과

- (void)viewDidLoad

{

[super viewDidLoad];

if (data==nil) {

data = [[[NSMutableArray alloc] init ]retain];

[data addObject:[NSDictionary dictionaryWithObjects:[NSArray arrayWithObjects:@"핫식스",[NSNumber numberWithInt:7000], nil] forKeys:KEYS]];

}

}


이렇게 view가 로드되고 넣어주는 방법이 있다.


내생각에는 후자가 메모리 관리상 나을것 같다.


그뒤에 row를 보여주는곳에는


- (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];

   }

  


cell.textLabel.text = [NSString stringWithFormat:@"%@ (%d칼로리)",

[[data objectAtIndex:indexPath.row] objectForKey:@"name"],

   [[[data objectAtIndex:indexPath.row] objectForKey:@"price"] intValue]];

  


return cell;

}



이렇게 하자.


Posted by 동동(이재동)
iPhone App2011. 7. 12. 18:07

맥은 참 나를 힘들게하는거 같다.

이번에 xcode 4를 깔았는데 이게 더 나은거 같다. 이건 중요하지 않고

일단 xib 에서 tableView를 하나 만들고.. 기존에 View가 있으면 지우고 만든다.

그다음에 오른쪽 버튼으로 연결후

헤더에서

#import <UIKit/UIKit.h>


@interface CalrorieCalViewController : UITableViewController {

NSMutableArray *data;

}


@property (nonatomic, retain) NSMutableArray* data;

@end


이런식으로 바꾼다.


그뒤에


-(NSMutableArray*) data {

if (data==nil) {

data = [[NSMutableArray alloc] init];

[data addObject:[NSMutableDictionary dictionaryWithObject:@"핫식스" forKey:@"name"]];

[data addObject:[NSMutableDictionary dictionaryWithObject:@"NF소나타" forKey:@"name"]];

  

}

return data;

}


이렇게 data를 만들고


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


return [self.data 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];

}

  

cell.textLabel.text = [[self.data objectAtIndex:indexPath.row] objectForKey:@"name"];

return cell;

}


이렇게 row를 돌면서 데이터를 뿌려준다.
마지막으로

- (void)viewDidUnload

{

[super viewDidUnload];

self.data = nil;

// Release any retained subviews of the main view.

// e.g. self.myOutlet = nil;

}


이렇게 해제하자


Posted by 동동(이재동)
iPhone App2011. 6. 23. 15:02

반 구조체 같은 경우 컬렉션에 넣을수 없다.

예를 들면 NSRect같은것은 바로 array에 addObject로 넣으면 안들어가기때문에 NSValue로 한번 감싸서 넣어준다.

물론 숫자 int,float등도 바로 넣을수 없기떄문에 NSNumber로 한번 감싸서 넣어준다.

NSMutableArray *mutableArray= [NSMutableArray arrayWithCapacity:2];

NSRect rect = NSMakeRect (1, 2, 30, 40);

NSValue *value;

value = [NSValue valueWithBytes:&rect objCType: @encode(NSRect)];

[mutableArray addObject: value];

NSValue *value2; NSRect rect2;

value2 = [mutableArray objectAtIndex: 0];

[value2 getValue: &rect2];

NSLog(@"Data %f %f",rect2.size.width,rect2.size.height); 

Posted by 동동(이재동)
iPhone App2011. 6. 17. 14:34

음 이것저것 해보았지만 역시 잘 정리된 사이트가 별로 없었다.

 

자 내가 한번 해보자.

 

이번 목표는 버튼을 클릭했을 때 웹 페이지를 띄우는 것과 Label Text를 변경하는 것이다.

 

일단 난 돈이 없어서 xcode 3.2로 했다. xcode4 빨리 받아야 될텐데

 

일단 하는법은 View-based Application으로 프로젝트를 하나 만든후

 

확장자가 xib가 되어있는 것을 더블 클릭한다. 그러면 View가 뜰것이다.

 

여기서 Label이랑 Button을 하나씩 추가 한다.

 

자 이제 ViewController.h 헤더 파일에서 label과 button을 설정한다.

 

#import <UIKit/UIKit.h>
 
@interface TestHelloWorldViewController : UIViewController {
    IBOutlet UILabel  *myLabel;        
}
@property (nonatomic,retain) IBOutlet UILabel *myLabel;
 
-(IBAction) onGotoTest;
@end

 

인터페이스에 IBoutlet UILabel 에 myLabel이라는 것을 하나 설정하고

@property로 똑같이 하나 잡는다.

 

Label은 이걸로 끝~

 

버튼은 더 간단하다

-(IBAction) onGotoTest로 버튼 이벤트? Action을 정한다.

 

자 코딩을 마쳤으면 다시 View로 돌아가자 View로 돌아가서 헤더에서 만든것을 연결해보자.

 

xib를 클릭하여 view를 보고 일단 내가 만든 버튼에서 오른쪽 버튼을 누르면 Rounded Rect Button이라는 팝업창이 하나 뜬다. 여기서 우리는 터치를할것이니 Touch Up inside에 옆에 동그라미를 마우스로 끌어서 File’s Owner에 집어 넣자

그럼 아까 내가 헤더에서 만든 onGotoTest Button Action을 선택할수 있다. 그러면  끝이다.

 

이번에는 라벨을 컨트롤 하기 위해서 label에서 오른쪽 버튼을 누른후 new referenciong Outlet 옆에 있는 동그라미를 끌어서 file's Owner에 집어 넣는다. 그러면 다시 헤더에서 만들었던 myLabel이 보일것이다 선택하면 두개의 연결은 끝~

 

자이제 실제로 Controller.m에 직접 코딩을 해보자.

 

@synthesize myLabel;
 
-(IBAction)onGotoTest{
    //NSURL *url = [NSURL URLWithString:@"http://www.naver.com"];
//    [[UIApplication sharedApplication] openURL:url];
    myLabel.text=@"jaedong";
     
}

 

@synthesize로 myLabel을 정의 한후

onGotoTest이벤트가 발생하면 즉 버튼이 클릭되면 myLabel 의 Text를 바꾸 었다.

 

흠… 쓰다보니 기초지식이 너무 없네… 일단 object-c부터 파야겠다.

 

아무튼 20분만에 첫 예제 프로그램을 만들어서 기쁘다…!!

 

참고: http://iphoneappsmaker.tistory.com/713

Posted by 동동(이재동)
iPhone App2011. 1. 7. 13:02

google docs를 이용해서 편리하게 아이패드와 동기화를 해보자.

 

일단 내가 하고 싶었던 일은 내컴퓨터에서 적은 ToDO나 메모를 아이패드에서 실시간으로 보고 싶었다.

 

그래서 EverNote나 어썸 노트를 써보았지만 구글 독스에서 저장한후 꼭 어플의 동기화 버튼을

 

눌러야만 동기화가 되었다

 

하지만 내가 원하는건 구글 독스에서 저장했을때 아이패드를 건드리지 않고 자동으로 refresh 되어서 아이패드에

 

출력하기를 원했다…

 

일단 나는 웹에서 작업하기가 느려서 MS Office와 연동을 해서 사용했다.

 

참고한곳은 여기이며

 

http://pakcw.cafe24.com/1170

 

사용한 프로그램은

 

OffiSync 프로그램이였다.(http://www.offisync.com/download.html)

 

이걸 설치하면 구글 docs와 오피스가 실시간 싱크 된다 굉장이 유용한 프로그램이다.

 

자 이제 내컴퓨터에 준비는 끝났다….

 

아이패드에서 docs.google.com 들어가자 어라? 모바일 버전이다.

 

모바일 버전에서는 일단 EDIT를 할수가 없었고 실시간으로 내컴퓨터에서 쓰는 내용을 동기화 하지 않았다.(당근 수정이 안되기떄문인듯) pc버전으로 웹페이지를 보면 되긴하지만 너무 느림

 

그래서 인터넷 검색결과 구글독스 환경설정에 가서 언어를 영어로 설정하면 EdIT 버튼이 생긴다고 하여서

 

해보니 생겼다….

 

자 이제 내컴퓨터에서 글을 작성하고 아이패드 웹 브라우저에서 편하게 실시간 동기활로 글을 볼수 있게 되었다.

 

이로써 아이패드 활용도가 더 높아지는것인가?

Posted by 동동(이재동)
iPhone App2010. 9. 13. 18:06

몽키3 결제를 했다...


일단 컴퓨터에서도 노래를 무제한 들을수 있으며 아이폰에는 다운도 가능하기때문이며


또 한달 들으면 한달은 무료란다...


하지만 결제가 자동결제여야만 한달이 무료였다.


지금이 9월 13일이니까 적어도 11월 10일까지는 꼭 해지를 안하면 까먹고 계속 돈 4500원이 나갈것이다.


까먹지 말고 꼭하자...


결제 하고 나니까 피해사례가 떳다.


결제나간다고 말을 안했다는것이다. 피해본사람이 많은듯


http://cafe.naver.com/appleiphone/596498


Posted by 동동(이재동)
iPhone App2010. 9. 7. 11:24
Posted by 동동(이재동)
iPhone App2010. 8. 17. 09:26

뜨아 힘들다 ㅋㅋ 내일이 드디어 아이폰4 예약하는 날이다

새벽 5시에 일어나서 준비를 해야 한다 광클을... 6시에 예약하니까 근데 기차표도 예약 하는날이 겹쳐서 ㅋㅋ

일단 미리 대리점 위치를 검색해 놨다... 우리집 위치랑 이런것도 미리 준비해야겠다.

메모장에 바로 기입할수 있도록 (복사 & 붙여넣기) 주소랑 전화번호 통장 번호 등등을 미리 써놔야겠다.

미리 적어야할  양식폼 샘플

http://db.blueweb.co.kr/formmail/Newformmail.html?dataname=ranger2xx0

우리집에서 가까운 대리점 리스트~

그리고  브라우저 크기는 100%로 만들어 놓고 팝업창 허용으로 바꿀껏


주식회사케이픽 퍼스트 신림정 1577-3940 서울 관악구 신림동 1640-44번지 <--젤가까움

팝세븐 서울 관악구 신림동 1422-10번지

새벽 텔레콤 서울관악구 신림동 1641-50번지


일단 가까운 리스트를 뽑아 놓았다...

이제 광클많이 살길이다 오늘은 일찍 자야겠다 ㅋㅋ

아이폰4 가 손에 들어온다~

Posted by 동동(이재동)