'Flex'에 해당되는 글 8건

  1. 2009/08/25 kineticroad Flash player 메모리 관리 Tip
  2. 2009/04/19 kineticroad URLStream 사용기
  3. 2009/04/19 kineticroad 오랜만의 블로깅? AIR File.ApplicationDirectory 접근하기.
  4. 2009/01/14 kineticroad AIR Examples
  5. 2008/11/22 kineticroad Flex에서 DeepLinking하기 (1)
  6. 2008/09/16 kineticroad DateChooser 클래스의 비밀 (1)
  7. 2008/02/08 kineticroad Flex로 만든 Naver Open API를 이용한 책 검색 (2)
  8. 2008/01/27 kineticroad Flex로 만든 네이버 Open Api - 책검색

Flash player 의 오랜 과제였던 메모리 관리 문제는 어떤 프로젝트를 진행하던지 간에 언제나 이슈로 대두 되었다.
특히나 Flex 내에서 모듈을 load하고 unload하는 과전에 있어서 메모리의 계속된 증가는
결국 사용자 PC의 브라우져가 과도한 메모리 점유로 인해 온갖 문제들을 야기 시켰는데
그것은 종국에 가서 클라이언트의 불만으로 이어지고
그런 불만을 해소하기 위해서 System.gc() 메서드나 LocalConnection 을 통한
강제 garbage collection을 해주고자 하였으나 근본적인 해결책은 되지 못했다.

한편 사람들은 메모리 문제에 대해서 removeListener를 통해 리스너를 삭제하는 방법들을
메모리 점유나 퍼포먼스에 대한 해결책으로 제시하고 있지만
문제는 무한이 늘어나는 인스턴스의 해결은 어찌 하느냐가 관건이었다.

전번 프로젝트를 통해 메모리를 줄여나가는 방법들에 대해서 여러가지로 연구하고
별의 별 방법들을 사용했고 시도했었다.
iframe을 통한 flash player의 브라우져 refresh는 Adobe사에서 권장하는 방법이었으나
다수의 Application의 생성이 불가피하고 rich internet 시장에 맞지 않는 작업들이라
클라이언트의 클래임을 설득하기 위한 회의는 연일 지속되어야만 했다.
게다가 refresh로 인해 Application의 다운로드 속도가 만족되어지지 않을 경우
RSL 방식이니 뭐니 하면서 Application 자체의 용량을 줄이기 위해 전쟁을 해야하는 상황들과 직면해야한다는 사실에는
변함이 없었다.
(그로인한 컴파일러 옵션값 조정에 몇 시간, 혹은 몇일의 시간을 날려먹었는지 모른다.)

프로젝트를 진행함에 있어서 가장 중요한것은 맨 마지막 산출물이 얼마나 rich한 작업이었는 지를
따지기 이전에 메모리의 양을 어찌 조절하느냐가 관건이 되었다.
앞뒤가 거꾸로 돌아가는 것이 아닌가 싶을정도로 고민과 번뇌로 코드를 들여다 봐야했고
메모리 점유율을 낮추기 위해 그리고 왜 낮춰지지 않는가에 대한 고민을 헤아릴 수 없이 해야만 했으며
생머리던 내 머리칼은 어찌나 쥐어뜯었는지 곱슬머리가 되어버렸다면 얼마나 많은 고민을 했을지 예상했으리라

그렇다면 왜 Flash player는 메모리를 낮추지 않을까?
왜 Flash player는 unload된 모듈에 대한 객체들을 지워주지 않을까에 대해 이해에 도움이 되기 위해서는
일단 Flash player 자체는 우리의 생각보다 멍청한 프로그램이고 뭐가 필요한 객체인지 아닌지에 대한
이해가 떨어지기 때문이라고 생각하면 속이 좀 편안해 질거다.

ActionScript에는 강한참조, 약한참조 가 있다는 사실은 조금만 공부해도 알 수 있는 내용이고
addEventListener 메서드로 이벤트를 등록할 때 useWeakReference 옵션 값을 true로 해줘서
약한참조로 만들어주면 gc가 돌때 등록된 이벤트를 같이 삭제한다고 이야기는 들었으나
이 약한참조라는게 어느 순간 목적 객체를 놓치는 경우가 종종 발생하여 문제는 계속해서 발생하게 된다.
(그 놈의 원인모를 문제는 다 여기서 나오는 거더라)

그렇다면 그냥 removeEventListener를 습관화 하는게 가장 좋은 방법이다.
묻지도 말고 따지지도 말고 그냥 무조건 remove시키는게 제일인것으로 결론이 났다.
그리고 가장 큰 문제인 ArrayCollection 의 강한참조가 문제다.

ArrayCollection은 정말 답이없는 객체다.
dataProvider로 DataGird 같은 List 객체나 Chart 객체에 Binding을 걸면 그것또한 낭패.
왜냐하면 ArrayCollection을 List 객체나 Chart객체 내부에선 dataProvider로 참조걸린 객체가 있다면
모듈 삭제시 인스턴스를 삭제 하지 않기때문이다.

한마디로 DataGrid가 삭제되도 내부의 데이터 값 자체는 삭제하지 못한다는 것이다.
이런 낭패가!
이벤트도 다 지웠겠다 UI객체들도 삭제했으니 당연히 메모리는 다시 원상 복구 되겠지!
하고 믿어 의심치 않고 있는 마당에 이런 뒤통수 맞는 경우가;;
Binding이라는게 쓸때는 참 편하고 좋다가도 이런 이유때문에 객체가 그대로 살아서 내 목을 조이고 있다고
생각하면 정말 믿는 도끼에 발등을 찍히는 기분이다.

그래서 UI객체가 삭제되는 시점을 틈타 FlexEvent.REMOVE 이벤트 발생시 객체들을 아래와 같이 삭제한다.


<mx:Script>
<![CDATA[
import mx.collections.ArrayCollection;
import mx.events.FlexEvent;

[Bindable]
private var tempAC:ArrayCollection;

override protected function createChildren():void
{
super.createChildren();
addEventListener(FlexEvent.CREATION_COMPLETE, creationCompleteHanlder);
}

private function creationCompleteHandler(evnet:FlexEvent):void
{
removeEventListener(FlexEvent.CREATION_COMPLETE, creationCompleteHandler);


tempAC = new ArrayCollection([
{data1:"temp1", data2:"temp1"},
{data1:"temp2", data2:"temp2"},
{data1:"temp3", data2:"temp3"},
]);

addEventListener(FlexEvent.REMOVE, removeHandler);
}

private function removeHandler(event:FlexEvent):void
{
removeEventListener(FlexEvent.REMOVE, removeHandler);

Object(dg.dataProvider).removeAll();
tempAC.removeAll();

removeAllChildren();
}
]]>

<mx:DataGrid id="dg" dataProvider="{tempAC}">
<mx:columns>
<mx:DataGridColumn headerText="sample1" dataField="data1" />
<mx:DataGridColumn headerText="sample2" dataField="data2" />
</mx:columns>
</mx:DataGrid>



removeHandler부분을 잘보면 ArrayCollection 객체에 null로 삭제하는 것이 아니라 removeAll() 메서드로 삭제하고 있고 모든 이벤트 들은 사용이 종료되었을 때 그때 그때 삭제해주는 버릇이 중요하다.
그래야 쓸데없는 인스턴스를 줄일 수 있고 나중에 클라이언트와의 언쟁을 조금이라도 줄일 수 있게 되니 서로 간에 스트레스 없이 좋게좋게 끝낼 수 있을 것이다.

2009/08/25 12:41 2009/08/25 12:41

URLStream 사용기

Flex 2009/04/19 02:55
프로젝트를 진행하다가 몇가지 이슈사항이 발생했다.
AIR로 웹에 있는 파일에 접근해 FileReference 클래스 이용없이 맞바로 로컬에 파일을 생성해야하는 이슈였는데
이부분은 URLStream클래스로 간단하게 해결할 수 있었다.

private const HOST_NAME:String = "http://www.kineticroad.com/blog";

private var urlStream:URLStream;

private function urlStreamTest():void
{
urlStream = new URLStream();
urlStream.endian = Endian.LITTLE_ENDIAN;
var request:URLRequest = new URLRequest(HOST_NAME + "test.xml");
addEventListeners();
urlStream.load(request);
}

private function addEventListeners():void
{
urlStream.addEventListener(Event.COMPLETE, completeHandler);
urlStream.addEventListener(IOErrorEvent.IO_ERROR, ioErrorHandler);
urlStream.addEventListener(SecurityErrorEvent.SECURITY_ERROR, securityErrorHandler);
urlStream.addEventListener(ProgressEvent.PROGRESS, progressHandler);
}

private function removeEventListeners():void
{
urlStream.removeEventListener(Event.COMPLETE, completeHandler);
urlStream.removeEventListener(IOErrorEvent.IO_ERROR, ioErrorHandler);
urlStream.removeEventListener(SecurityErrorEvent.SECURITY_ERROR, securityErrorHandler);
urlStream.removeEventListener(ProgressEvent.PROGRESS, progressHandler);
}

private function completeHandler(event:Event):void
{
var remoteData:
var clientFile = new File('D:/test.xml');
var clientStream:FileStream = new FileStream();
clientStream.open(clientFile, FileMode.WRITE);

while(urlStream.bytesAvailable)
{
var value:int = urlStream.readByte();
clientStream.writeByte(value);
}

clientStream.close();
urlStream.close();
}

private function ioErrorHandler(event:IOErrorEvent):void
{
trace("IOError / " + event.type);
}

private function securityErrorHandler(event:SecurityErrorEvent):void
{
trace("Security Error / " + event.sandboxType);
}

private function progressHandler(event:ProgressEvent):void
{
var percent:Number;
percent = Math.round((bytesLoaded * 100) / bytesTotal);
trace(percent + "% complete");
}


아주 간단한 만든 샘플인데 일단 서버의 파일에 접근해서 readByte로 읽어온다. 읽어온 value를 미리 선언해 뒀던 클라이언트 파일에 writeByte로 작성에 넣는 작업을 수행하게 되어있다.
아주 간단하게 구성되어있는 이 소스를 기반으로 여러가지 작업을 할 수 있게 되었는데
대표적으로 모듈단위의 AIR 업데이트를 수행하는 것이나 서버의 이미지 파일을 지정된 위치에
지정한 이름으로 저장할 수 있게 하는 FileReference.browse() 메서드 기능을 구현할 수도 있다.
잘만 만들면 FTP 비슷한 프로그램을 만드는 것도 가능할 것이다.
2009/04/19 02:55 2009/04/19 02:55
그동안 완전히 블로깅을 손놓고 있었다.
그도 그럴게 프로젝트다 뭐다 해서 좀 정신이 없었기 때문이기도 하고
시험준비를 하느라고(요새 대학교는 중간고사 시즌이란다;;; 덜덜) 새벽까지 수업듣고 자느라
정신을 챙길래야 챙길만한 여유가 없었기 때문인데 오늘은 AIR 에대한 내용으로 블로깅을 해볼까 한다.

AIR를 처음 만진게 1.0 처음 런칭했을 때였는데(코드명 아폴로로 불렸을 때는 존재를 잘 몰랐었다;;; 아 둔탱이)
그당시 개발을 EditPlus로 하느라 AIR가 어떤식으로 Compile하고 실행하는지 Developer Guide를
하나하나 해석해가며 눈물을 삼겼었던 적이 있었다.(흑.. 추억하고 싶지 않다는;;;)

그때 만들었던게 FXUG Lite였다. FXUG(Flex User Group)는 회사에서 만든 비영리 커뮤니케이션으로
Full Flex로 개발되어 MDI로 구성된 UI를 선보였었다.(개발하는데 무려 3개월이나 걸리긴 했지만;;)
아무튼 FXUG Lite의 기능중 극히 작은 기능이긴 하지만 사용자가 동적으로 화면의 구성을 바꿀 수 있게
마련한 옵션 메뉴가 있었다. 이것은 사용자가 사용자 정보 xml 파일을 읽어봐 수정하고 다시 쓰는 작업을
하게끔 되어있는데 그 때 크게 발생한 이슈가 사용자의 ApplicationDirectory에 있는 파일을 수정하거나
쓸 수가 없었다는 것이다.
보통 프로그램을 설치하게 되면 ApplicationDirectory가 Program Files 디렉토리로 설치가 되는데
그 부분을 Flie.ApplicationDirectory 속성으로 접근해 파일을 다시 쓰게 되면 Security Error를 띄우도록 AIR의 보안정책으로 명시 되어있다.
이를 어찌할까 하다 구글링으로 찾은 꽁수는 어느 중국인의 블로깅을 보고 힌트를 얻었었다.
(한자들 앞에서 무력했었던 끔찍한 기억 작렬 ㅠㅠ)

해결한 방법은 다음과 같다.

var tempFile:File = File.applicationDirectory.resolvePath("test.xml");
tempFile = new File(tempFile.nativePath);

일단 tempFile로 선언된 File 객체에 test.xml 파일에 접근한다. applicationDirectory에 있는 파일에 접근해 정보를 읽는건 보안정책에 어긋나는건 아니니 일단 접근을 하고 새로 File 객체를 생성한다. 물론 instance를 늘리지 않고 기존에 사용했던 tempFile를 다시 생성하는데 이때 아까 접근했던 test.xml 파일의 nativePath 경로를 인자로 넘겨준다.

이 방법을 이용하면 test.xml 파일을 찾아서 쓰거나 수정할 수가 있는데 이유인즉슨 이렇게 해석될 수 있다.
보안정책상 파일에 applicationDirectory에 속해있는 파일을 수정하거나 쓰는건 안된다. 다시 이야기하면 File 객체로 접근만 하지않으면 된다는 이야기.
그래서 잔머리를 굴린방법이 nativePath다.
applicationDirectory에 접근하긴 했으나 String으로 접근하게 되면 보안정책상 하자가 없다는 이야기다.
Adobe에서는 이런 정책을 수정해서 접근 할 수 없게 하겠다....라고 이야기 했다고는 하나(들리는 풍문에 의하면)
"Adobe가 귀찮아서 안하지 않을까?"라고 조심스럽게 추측하고 있다.(사실 믿고 있다. Adobe)

하지만 이 방법으로도 어려운 난제가 있는데 Vista 이후의 Window는 위의 방법으로도 파일을 쓸 수가 없다.
그 이유는 AIR 의 보안정책에는 하자가 없지만 운영체제 상의 보안정책때문인데 이는 관리자 모드로 프로그램을 실행하게 되면 파일을 쓸 수가 있다.(AIR 자체로는 이를 해결할 방법이 없다;;;
운영체제가 막겠다는데 이겨낼 방법이 있을 수가 없지 않은가;;;
아 물론 XP 사용자는 해당사항이 없다.
2009/04/19 01:45 2009/04/19 01:45

AIR Examples

Flex 2009/01/14 13:50
http://airexamples.com/

오랜만에 열이아빠님 블로그를 놀러갔더니 AIR Examples라는 제목의 포스트가 있어서 봤더니
AIR Example 이라는 AIR의 예제소스를 만드는 블로그를 찾을 수 있게 되었다.

사용자 삽입 이미지
AIR 업무를 곧잘 맡는 나로써는 유용한 사이트가 아닐까.
이런 예제들을 담은 사이트들이 점점더 많아졌으면 좋겠당

우왕굳~

ps : 열이아빠님의 포스트는 http://koko8829.tistory.com/?page=4 이곳으로.
2009/01/14 13:50 2009/01/14 13:50

프로젝트를 하다가 가끔씩 마주치는 이슈가 있는데
그것은 바로 DeepLinking 기능이다.
Flex에서 최종산출물이 swf로 떨어지기 때문에 JSP와 같이 GET 방식의 주소를 통해 정해진 인자를 주소로 보내면 특정 페이지로 바로 접근하는 방법을 찾던도중 DeepLinking이란 기능을 알게 되었다.
물론 이것은 JSP 처럼 별다른 연산 없이 바로 접근 할 수 있는게 아니라 그저 Flex가 내부적으로 브라우져 주소입력창에 어떤 내용을 넣었는지 확인 할 수 있는 그런 기능일 뿐이다.
그래도 이것이 어딘가 싶어서
연구를 하다가 또 놀라운 사실을 접하게 되었는데 알고 보니 Flex의 단독기능이 아니라 JavaScript와 SWF 상호간의 ExternalInterface를 이용한 콤비네이션이었을 뿐이었고 나처럼 빌더를 쓰지않고 EditPlus로 개발하는 사람으로써는 그런 JavaScript를 구축하는데 꽤나 시간이 많이 소요된다는 점에서 조금 실망하지 않을 수 없었다.
그래서 나는 이 방법을 피하고 싶어 꽤나 요리조리 피해 클라이언트 들에게 이렇게 하면 어떻겠냐 저렇게 하면 어떻겠냐라고 하다가 이번엔 좀 제대로 걸려서 천상 이 DeepLinkg을 만들어야할 상황에 온김에 포스팅도 같이 고고.

아무튼 일단 빌더로 구축된 Flex 산출물 중에 history라는 디렉토리가 자동으로 생성된다는 사실을 알고 있을텐데 그 안에 보면 history.js 파일이 있다.
그 안에 보면 BrowserHistory = (funtion() { .......}) 하는 형식으로 짜여진 함수를 볼 수 있을 것이다.
그 안에 있는 내용이 DeepLinking과 관련 된 내용들이다.
(사실 Javascript는 문외한이라 잘 모르지만 통밥으로 느낄 수 있다!!)

뭐... 잘 살펴보면 "#" 이라는 구분자로 주소와 파라미터를 구분 한다는 것도 알 수 있고
그 파라미터를 Flex에서 가져갈 수 있게끔 리턴도 해준다.

일단 이런 내용은 빌더로 프로젝트를 하나 구축하면 자동으로 생성되므로 확인 할 필요가 없다.
Javascript는 알아서 만들어주니 걱정은 덜고 Flex에서 코딩을 어찌할지가 문제로구나.

이런 예제 소스는 여기저기 많다.
http://www.flexlive.net/?p=84 여기서는 샘플코드를 다운로드 해줄 수 있게 해준다.
http://labs.adobe.com/wiki/index.php/fl ··· _linking 여기는 Adobe Lab

Google에서 이것저것 검색하면 많이 나오므로 걱정하지말고 두드려라 그럼 열릴것이니.

자. 그렇다면 어떤 어떤 클래스를 import를 해야하는지 알아보자.

DeepLinking을 하려면 IBrowserManager 와 BrowserManager 두개의 클래스가 필요하다.
IBrowserManager를 주로 사용하는데 이 클래스는 결국 인터페이스 클래스이므로 Construct를 하기위해서는 BrowserManager.getInstance() 메서드가 필요하다.

var browserManager:IBrowserManager = BrowserManager.getInstance();

이런식으로 Construct를 해준다.
그럼 이제 주소표시줄의 내용을 가져오고 싶은데 그렇게 하려면 이벤트리스너를 등록해줘야한다.
BrowserChangeEvent 클래스가 있는데 여기에서 URL_CHANGE 이벤트를 받을 수 있게 해주면
주소표시줄에 # 이하의 파라미터가 있으면 이벤트가 발생하게 된다.(없으면 발생하지 않는다.)

그래서 간단하게 개념 정리를 하자면 이렇다.
Application이 initialize하게 되면 IBrowserManager를 Construct를 시키고
BrowserChangeEvent.URL_CHANGE 이벤트를 등록한다.

이벤트가 발생하면 파라미터값이 있는 것이므로 이벤트 핸들러에서 파라미터 값에 맞는 액션을 취해주면 된다.

결국 Flex소스 자체에는 큰 액션이 없다.
JavaScript가 하는 일을 그저 BrowserManager가 받아서 처리 해주는 일 뿐이다.
간단하게 소스를 짜면 아래와 같은 로직이 될것이다.

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx=http://www.adobe.com/2006/mxml initialize="initializeHandler()">
<mx:Script>
        <![CDATA[
        import mx.controls.Alert;
        import mx.managers.IBrowserManager;
        import mx.managers.BrowserManager;
        import mx.events.BrowserChangeEvent;

        private var browser:IBrowserManager;

        private function initializeHandler():void
        {
            // IBrowserManager 생성
            browser = BrowserManager.getInstnace();
            browser.addEventListener(BrowserChangeEvent.URL_CHANGE, urlChangeHandler);
        }
       
        private function urlChangeHandler(event:BrowserChangeEvent):void
        {
            Alert.show("파라미터 : " + browser.fragment);
        }
        ]]>
</mx:Script>
</mx:Application>

간단하게 이런식으로 파라미터를 받아와 DeepLinking 할 수 있게 코딩을 할 수 있다.
하지만 프로젝트 초반에 이런 기획이 없이 개발에 들어가면 나중에 소스를 죄다 뜯어 고쳐야할 소지가 짙으므로
미리 이런 기능이 필요한지, 아닌지에 대하여 논의를 하고 설계를 해야할 것이다.
물론 이런 반쪽뿐인 DeepLinking 기능이지만 그래도 이만하면 Flex도 할만큼 한게 아닐는지;;

2008/11/22 14:23 2008/11/22 14:23
Flex에 보면 DateChooser라는 클래스가 있다.
사실 이런 DateChooser는 Style을 마음대로 먹이기가 꽤 까다로운데
이번에 프로젝트를 하면서 재밌는 사실을 알아냈다.

DateChooser에서는 년도와 월을 선택해주는 기능 외에 다른 기능이 포함되어 있지 않다는 사실.

DateChooser에서 구현되었을 줄 알았던 달력부분은
사실 다른 클래스에서 가져와 기능을 하고 있다는 사실을 알아냈다.
그 클래스의 이름은 CalendarLayout이라는 클래스인데 그 클래스는 livedocs 에도 나와있지 않아 확장 컨포넌트를 사용할 줄 모르는 사람은 알아내기가 꽤 곤란하다.
이 클래스는 DateChooser 에서 달력 부분을 표시하는 기능을 하고 있고
이 클래스에는 displayedMonth, displayedYear과 같은 프로퍼티가 구현되어 있어
DateChooser와 똑같이 사용하면 된다.

참, 스타일도 거의 비슷하게 먹는데 DateChooser에만 있는 객체들에 대한 스타일 외에
달력에만 적용되는 스타일은 동일하게 적용된다.
아래는 CalendarLayout 클래스를 이용해 컨포넌트를 만든 화면.

p.s 프로젝트에 사용되는 화면이라 CalendarLayout을 확장해 만들었으니 이해해주삼

사용자 삽입 이미지


2008/09/16 17:40 2008/09/16 17:40
자.. 오랜 잠수 끝에 만든 책검색 서비스다.
사실 개발 기간은 4일.. ㅎㄷㄷ
디자인도 신경 하나도 안쓰고 그냥 쇼핑몰 기능을 조금 넣어봤던걸까나..
프로그래밍이라는 것도 하나도 모르고
회사에서 조금씩 배우면서 만든거라 굉장히 허접스럽다는.. 어허허

간단히 원리를 말하자면 이렇다.
검색어를 담아내는 하나의 기억장소가 필요하고
그 검색어와 API를 이용하기 위한 Key 값을 조합해서 쿼리를 네이버 책검색 서비스로 던져준다.
그러면 네이버 쪽에서 다시 값을 날려주는데
그 값의 형태는 XML 형태.
XML을 다시 이 쪽에서 VO(Value Object)로 변환시켜서
배열에 집어넣는다.
Flex 2.0 부터는 ArrayCollection이라는게 만들어져서 꽤 간단하게 짤 수 있었다.
이 ArrayCollection 은 mx.collections.ArrayCollection 클래스 소속인데
이게 좋은건 데이터가 바뀔 때 마다 dataProvide해 줄 필요가 없다는 것이다.
VO데이터를 Array에 넣게 되면 Object 형태로 들어가는데 Object 내부의 일부분이 수정되거나 변경되어도
기존의 Array는 그런 사실을 provide되는 Object에게 알려주지 않는데 이 ArrayCollection은
뭐가 어떻게 바뀌었는지 알려준다. 이전에 했더 CRUD 맛보기 프로그램을 짤 때도 잘 이용했다.
사실 처리할 데이터가 몇건 안될 때는 그냥 Array를 통째로 dataProvide 해버리면 되는데
만약 몇 만건이상의 데이터 베이스를 처리할 경우가 생기면
그 처리시간이 만만치 않게 걸린다는 것이다. 그런 점에서 ArrayCollection은 유용한 도구가 될 수 있다.
ArrayCollection 이야기를 하다보니 본론에서 조금(?) 벗어나 버렸다.

뭐 아무튼
이렇게 처리한 VO데이터를 DataGrid와 TileList를 ViewStack을 이용하여 검색된 결과를 보여준다.
보여준 데이터는 ItemRenderer를 이용해서 이미지와 HTML 텍스트들을 처리했다.
보고 있는 아이템중 상세정보를 보고 싶은 아이템을 클릭하게 되면
일련의 처리과정 후에 아랫쪽에 보여지게 된다.
기존의 검색된 데이터에서 누락된 데이터들을 볼 수 있게 되고 이 때 좀 더 상세한 내용을 보고 싶은 아이템은
상세정보를 볼 수 있는 아이콘이 있어서 바로 네이버로 가서 확인할 수 있게끔 링크를 걸어두었고
장바구니 버튼을 클릭하면 오른쪽에 있는 장바구니 화면에 들어가게 된다.
장바구니 버튼을 여러번 누르면 아이템이 계속 장바구니에 담겨지는게 아니라 NumbericStepper의 숫자가 올라가게 된다.
그러다 구매하기 싫은 아이템은 체크박스에 체크를 하고 삭제버튼을 누르면 삭제가 된다.
편의를 위해 전체선택도 가능하게 했다.
이렇게 이야기만 하면 크게 감흥이 안올 것 같고(사실 직접봐도 큰 감흥은 없다..-_-;;)
한 번 보시라.

클릭하세염~

2008/02/08 21:42 2008/02/08 21:42

Flex를 통해 3일만에 만든게 게시판이었다.
물론 데이터베이스를 이용한 것은 아니였지만 기본적인 CRUD를 구현하기 위해서
이틀동안 머리를 쥐어짜야했다.(그것이 가능했던건 물론 회사였기 때문이 아니었을까..-_-;;)
어쟀든 며칠동안 작업하고 Open Api라는 것에 대한 이해가 전혀 없었던 나로써는
조금은 벅찬(?)걸 만들었다. 물론 완성은 아니지만..

Flex 네이버 Open Api를 통해 만든 책검색 서비스!!

일단 현재는 책을 검색해서 상위 6권의 보여주는 정도다.
이제 더 작업해야하는건

1. 선택된 책들에 대한 상세정보를 보여줘야한다.
2. 책을 6권이 아닌 검색된 전체 내역을 보여줘야한다. - 페이징 기능
(네이버 open Api 서비스의 한계때문에 1000건이상 결과가 나오더라도
 1000번째 이상 상세정보를 받아올 수 없다.)
3. 상세정보를 보고 구입을 원하게 되면 실제 구매 페이지로 링크를 걸어줘야 한다.

지금 디자인은 OSX를 모티브로 했다.
http://www.scalenine.com 에서 받아왔고 사용하지 않는 기능은 삭제시켰다.
완성되면 만드는 과정을 찬찬히 살펴보도록 하자.

2008/01/27 22:59 2008/01/27 22:59