블로그 이미지
물결(Wave)
하고 싶은 것만 하며 살고 싶다

calendar

        1 2 3
4 5 6 7 8 9 10
11 12 13 14 15 16 17
18 19 20 21 22 23 24
25 26 27 28 29 30  
javascript로 xml 문서를 파싱하려면 꼭 필요한 메서드중 하나가 바로 hasAttributes 입니다.
hasAttributes 는 해당 노드에 정의된 속성(attribute)가 있는지를 확인해 주는 메서드 입니다.

아래와 같은 xml 문서가 있을 경우,
<xml>
    <guest age="20" name="Asrada" />
</xml>

다음과 같이 하면 guest 노드를 획득 할 수 있습니다.
var xmlDoc = document.createXMLDocument("샘플 문서");
xmlDoc


그리고 


IE는 hasAttributes 메서드를 지원하지 않습니다.

하지만 다행스럽게도 attributes 속성(property)은 지원합니다.

결국 크로스 브라우징을 위해서는 hasAttributes 메서드 대신 attributes 속성을 이용해야 합니다.


신고
크리에이티브 커먼즈 라이선스
Creative Commons License
posted by 물결(Wave)
2009.09.16 12:05 Programing/Java
팀내에서 진행하는 프로젝트에 ppt 파일에 포함된 슬라이드를 개별 이미지로 변환해 주는 기능이 필요하여 무료로 제공되는 Apache POI 를 사용해보고 이에 대해 간단히 정리해봅니다.

Apache POI

Apache POI 프로젝트는 Microsoft Format 의 파일들을 엑세스를 지원하는 Java API 라이브러리 입니다. 2009년 9월 16일 현재 3.2 Final 버전과 3.5 beta 6 버전 까지 릴리즈 되었습니다.


POI Components

POI는 MS 오피스의 각 문서 포멧에 대응하는 다양한 컴포넌트를 지원하고 있습니다.


저는 이 중에서 ppt를 위한 컴포넌트인 HSLF를 사용하여 슬라이드를 이미지로 변환하였습니다.
사용법은 무척 간단하고 쉽습니다.

우선 POI 라이브러리를 다운로드 하고 압축을 풀면 3개의 jar 파일을 볼 수 있습니다.(3.2 Final 버전 기준)


HSLF 컴포넌트를 사용하기 위해서는 poi-3.2-FINAL-20081019.jar 와 poi-scratchpad-3.2-FINAL-20081019.jar 파일을 import 해야 합니다.



FileInputStream is = new FileInputStream("slideshow.ppt");
SlideShow ppt = new SlideShow(is);
is.close();
        
Dimension pgsize = ppt.getPageSize();

Slide[] slide = ppt.getSlides();

for (int i = 0; i < slide.length; i++) {
    BufferedImage img
 = new BufferedImage(pgsize.width, pgsize.height, BufferedImage.TYPE_INT_RGB);
    Graphics2D graphics = img.createGraphics();
    
    //clear the drawing area
    graphics.setPaint(Color.white);
    graphics.fill(new Rectangle2D.Float(0, 0, pgsize.width, pgsize.height));

    //render
    slide[i].draw(graphics);

    //save the output
    FileOutputStream out = new FileOutputStream("slide-"  + (i+1) + ".png");
    javax.imageio.ImageIO.write(img, "png", out);
    out.close();
}

아래 이미지는 실제 제가 저 코드를 사용하여 클래스를 작성하고 테스트 해본 결과입니다.
3장짜리 ppt 를 변환하니 3장의 png 파일이 만들어졌습니다.


변환된 이미지를 확인해 보니 텍스트가 약간 뭉개지긴 하지만 썩 괜찮은 결과물이었습니다.

마치며

3.2 Final 버전에서는 아직까지 MS Office 2007의 pptx 포멧을 지원하지 않고 있습니다. 다행이도 현재 pptx 지원을 위해 개발 중이라고 하니 다음 릴리즈에서는 pptx 도 문제없이 변환될 것 같습니다.

아주 간단한 코드만으로 ppt 파일을 이미지 파일로 손쉽게 변환 가능하 POI-HSLF 컴포넌트.
만약 PPT파일 변환 기능때문에 고민중이시라면 저는 주저없이 Apache POI 를 권하고 싶습니다.

신고
크리에이티브 커먼즈 라이선스
Creative Commons License
posted by 물결(Wave)
2008.09.05 13:37 Programing/XUL

Firefox Extension을 배포하기 위해서는 몇 가지 간단한(?) 절차를 거쳐야 합니다.

1.install.rdf 자동 업데이트 설정

install.rdf파일은 익스텐션의 기본 정보를 갖고 있는 파일이고 이 파일을 통해서 브라우저는 새로운 버전이 있는지를 확인 할 수 있게 됩니다.

install.rdf

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<RDF:RDF xmlns="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:RDF="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:em="http://www.mozilla.org/2004/em-rdf#">
    <RDF:Description about="urn:mozilla:install-manifest">
        <em:aboutURL>chrome://myextension/content/about.xul</em:aboutURL>
        <em:creator>작성자</em:creator>
        <em:description>익스텐션 설명</em:description>
        <em:homepageURL>작성자 홈페이지 URL</em:homepageURL>
        <em:iconURL/>
        <em:id>익스텐션 ID(예: asrada@asrada.net)</em:id>
        <em:name>익스텐션 이름</em:name>
        <em:version>0.1.0</em:version>
        <em:updateURL>익스텐션 업데이트를 확인할 URL(예: http://asrada2001.tistory.net/myextension/update.php</em:updateURL>
        <em:type>2</em:type>
        <em:targetApplication>
            <RDF:Description>
                <em:id>{ec8030f7-c20a-464f-9b0e-13a3a9e97384}</em:id>
                <em:maxVersion>2.0.*</em:maxVersion>
                <em:minVersion>1.5</em:minVersion>
            </RDF:Description>
        </em:targetApplication>
    <em:optionsURL/></RDF:Description>
</RDF:RDF>

위와 같이 <updateURL>속성을 써주면 브라우저가 시작될때 자동으로 익스텐션의 업데이트 정보를 확인합니다.

보다 자세한 내용을 원하시는 여기를 보세요.

일단 install.rdf파일을 만들어 두고 update.rdf파일을 만듭니다.

update.rdf 파일은 아래와 같이 간단하게 만들 수 있습니다.

(저는 update.rdf로 통계 값을 확인 하기 위해 php로 작성하였으나 일반 rdf 파일로 작성하셔도 됩니다.)


update.rdf - text/rdf 형태로 전송

<?php
header('Content-Type: text/rdf');

echo <<<heredoc
<?xml version="1.0"?>

<r:RDF xmlns:r="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
       xmlns="http://www.mozilla.org/2004/em-rdf#">

<r:Description about="urn:mozilla:extension:익스텐션 ID(install.rdf 에 있는 것과 동일)">
<updates>
<r:Seq>
<r:li>
    <r:Description>
        <version>0.1.1</version>
        <targetApplication>
            <r:Description>
                <id>{ec8030f7-c20a-464f-9b0e-13a3a9e97384}</id>
                <minVersion>1.5</minVersion>
                <maxVersion>2.0.0.*</maxVersion>
                <updateLink>
새로 업데이트 된 확장기능의 URL(예: http://asrada2001.tistory.com/myextension/new_extension.xpi)</updateLink>
            </r:Description>
        </targetApplication>
    </r:Description>

</r:li>
</r:Seq>
</updates>

<version>상동</version>
<updateLink>상동</updateLink>

</r:Description>
</r:RDF>
heredoc;
?>


Firefox3를 위한 설정

Firefox3부터는 익스텐션 관리에 있어 보안이 한층 두터워 졌습니다.

updateLink가 https 프로토콜을 사용하지 않는다면 무조건 아래의 절차를 밟아야 합니다.


우선 익스텐션 패키지에 대한 updateHash를 얻어야 합니다.

이때 사용되는 해싱알고리즘은 sha1, sha256, sha384 , sha512 중에 아무거나 쓰시면 됩니다.

많이 사용하는 openSSL 을 예로 들어보겠습니다.

openssl sha1 FILE

간단하죠?

명령이 실행되면 콘솔에 해시가 출력됩니다. 이것을 잘 복사 하셔서 update.rdf에 추가하면 됩니다.

이때 주의 하실 점은 아래와 같이 해시 코드 앞에 꼭 해싱 알고리즘을 명시해야 한다는 것입니다.

<em:updateHash>sha1:78fc1d2887eda35b4ad2e3a0b60120ca271ce6e6</em:updateHash>

다음으로 익스텐션의 updateKey를 만들어야 하는데 McCoy라는 툴을 이용하면 자동으로 이루어집니다.

McCoy의 Create버튼을 클릭해서 공개키를 만듭니다. 그리고 Install버튼을 클릭하고 install.rdf 파일을 선택하면 자동으로 install.rdf에 updateKey가 추가됩니다.

그리고 Sign버튼을 클릭해서 update.rdf 파일을 선택합니다. 역시 자동으로 McCoy가 update.rdf파일을 변경해줍니다.

패키지 생성

zip형식으로 압축 -> 확장자를 xpi 로 변경

이제 패키징을 할 차례입니다.

install.rdf를 익스텐션 소스파일의 루트에 넣고 zip 형식으로 압축합니다.

그리고 확장자를 xpi 로 변경해주면 익스텐션 패키지가 완성됩니다.

이제 진짜 배포하는 일만 남았는데 한 가지 아주 간단한 작업이 남았습니다....


Apache httpd.conf 수정

자신의 서버에서 익스텐션을 배포하려면 Apache가 xpi 파일을 허용하도록 아래의 내용을 httpd.conf에 추가해야 합니다.

AddType application/x-xpinstall .xpi

이제 다 됐습니다. 이제 위 설정 파일에서 지정해 준대로 update.rdf파일과 익스텐션 패키지 파일을 두시고 익스텐션 다운로드 링크를 생성해서 배포 하시면 됩니다.

이후 익스텐션을 수정하여 버전업이 이루어지면 위 순서대로 반복하시면 됩니다. 그럼 이전 버전의 익스텐션을 사용하는 브라우저가 시동될 때 자동으로 업데이트 된 익스텐션을 확인하고 사용자에게 알려줍니다.


보다 자세한 정보는 여기에서 확인 하실 수 있습니다.

신고
크리에이티브 커먼즈 라이선스
Creative Commons License

'Programing > XUL' 카테고리의 다른 글

Firefox Extension 배포하기  (0) 2008.09.05
웹페이지를 데스크탑 어플리케이션으로...  (0) 2007.12.02
XUL - Firefox ectention 만들기  (2) 2007.11.16
posted by 물결(Wave)
2008.08.30 00:32 Programing/PHP
PHP보다는 HTML,CSS,Javascript와 씨름하며 지내는 요즘 반갑게도 PHP를 써야하는 작은 프로젝트를 하나 맡았습니다. 근 1년여 동안 멀리했던 PHP인지라 함수들도 가물가물하고 요즈음은 트렌드도 많이 바뀌어서 제법 낯설기도 하지만 그래도 반갑기만 하네요~ :)

마침 메인 PC도 맥으로 갈아탄터라 이것저것 셋팅하는 맛도 있겠거니와 정말정말 오래간만에 php컴파일도 좀 해보고 아파치도 만져볼 생각에 한창 들떴더랍니다. ^^

최근 구매한 iMac 24인치에는 개발에 필요한 기본적인 도구들이 상당히 많이 들어있습니다. 그 중에 아파치와 PHP도 포함되어 있으니 정말 편한 시스템이죠~(물론 자바도 기본으로 설치되어 있답니다~~)


1.준비

우선 Enabling PHP and Apache in Leopard를 참고하시어 php,apache 기본 설정을 확인 하시고 php를 활성화 하는 작업이 선행되어야 합니다. 이 상태로도 기본적인 php개발 환경은 마련이 됩니다. 하지만 프로젝트가 바뀔때마다 매 번 아파치의 DocumentRoot를 변경하고, ftp를 이용해 실서버로 배포하는 작업은 그리 유쾌한 작업은 아니죠. 게다가 이클립스라는 아주 훌륭한 IDE를 쓰면서 말이죠....

(주의: 저는 지금 이클립스를 이용해서 개발 하시는 분들을 위한 포스팅을 하고 있답니다~!!)


2.가상호스트 설정

프로젝트 별 가상호스트를 만들어 줍니다.
편집기로 아피치 가상호스트 설정 파일을 엽니다.

$ sudo vi /private/etc/apache2/extra/httpd-vhosts.co

처음 이 파일을 열면 샘플 가상호스트가 주석으로 둘러싸여 있는데요 그 부분을 복사해서 아래에 붙여 넣습니다.

DocumentRoot를 설정하고 도메인도 설정합니다.
이 가상호스트만의 독립적인 로그가 필요하면 로그 파일에 대한 내용도 작성합니다.
자세한 가이드는 여기를 참고하세요.

<VirtualHost *:80>
    DocumentRoot "/Users/asrada/Documents/workspace/MyProject/trunk/testcase"
    ServerName test.project1.com
    ErrorLog "/private/var/log/apache2/test.project1-error_log"
</VirtualHost>

가상호스트에 도메인을 만들어 주긴 했지만 실제 저 도메인은 등록이 안된 것이죠.
때문에 hosts 파일에 저 도메인에 대한 리다이렉션을 명시해야 합니다.

$ sudo vi /etc/hosts

파일을 열고 맨 아랫줄에 리다이렉션 시킬 ip 와 도메인을 입력하면 됩니다.
가상호스트가 로컬에 있으니 로컬 PC로 리다이렉션 시키면 되겠죠~

127.0.0.1 test.project1.com

이제 브라우저에서 test.project1.com을 입력하면 가상호스트로 설정된 DocumentRoot에 있는 index.html파일이 열리게 됩니다.
프로젝트가 추가되면 가상호스트를 늘려주면 됩니다~~



3. Ant를 이용한 배포

이제 로컬PC에서 프로젝트 소스 파일을 편집하고 테스트도 해 볼 수 있게 되었습니다.
실서버로 배포만 하면 프로젝트를 마무리 할 수 있겠네요~~~:)
자 그럼 FTP클라이언트를 실행하고....이럼 안되겠죠?? ^^
이클립스를 쓰고 있으니 최대한 이클립스안에서 모든걸 해결하도록 해보죠.
이클립스 플러그인중에 Ant라는 아주 유용한 플러그인이 있습니다.
이클립스에서 작업한 소스코드를 FTP프로토콜을 이용해서 별도의 FTP클라이언트 프로그램을 실행할 필요 없이 원하는 곳으로 전송 할 수 있고, 프로젝트 전체를 압축해서 보내고 전송이 완료되면 실서버에 telnet으로 접속해서 전송한 압축파일을 원하는 디렉토리에 풀어주는 일도 가능합니다.
자세한 내용은 여기를 보세요~~

Ant의 기능은 상당히 많지만 이 포스트에서는 Ant의 기본 구조와 간단한 사용방법을 소개하는 정도에서 그치도록 하겠습니다. ^^

1)설정파일 만들기

Ant설정 파일은 xml형태의 파일로 하나의 project 엘리먼트 안에 여러개의 target 엘리먼트로 이루어지는데요, 이 target은 어떤 하나의 행동(task)을 나타냅니다.

<project name="UIRSS_Extension" basedir=".">
 <property file="${basedir}/info.properties" />

 <target name="create.xpi">
  <zip destfile="${extension.root}/${extension.destfile}" basedir="${src.root}" />
 </target>
 
 <target name="compress">
  <tar destfile="${basedir}/${deploy.destfile}" basedir="${extension.root}" compression="gzip" />
 </target>

위의 예제는 실제로 제가 쓰고 있는 Ant설정 파일의 일부입니다.

내용을 보면 UIRSS_Extension이라는 프로젝트 이름을 갖고 있는 Ant설정 파일이라는 것을 알 수 있구요,

2개의 target은 각각 zip으로 특정 파일들을 압축하고 tar로 특정 파일들을 묶는 작업을 수행하도록 설정 되어 있습니다.

보시다시피 target안에 있는 zip이나 tar 요소들은 우리가 잘 알고 있는 그 zip과 tar에 대응하는 요소입니다.

각 target은 독립적으로 실행되며 여러 target을 순차적으로 실행하는 것도 가능합니다.

<target name="deploy" depends="local.compress, sendToServer,server.decompress"/>

위 target을 실행하면 먼저 local.compress라는 target을 실행한 후 sendToServer target을 실행하고 마지막으로 server.decompress target을 실행하게 됩니다. 배치파일과 비슷하죠?? ^^

이렇게 기능적으로 완전히 독립된 여러 target들을 만들어 두고 작업 득성에 맞게 각 target들을 조립해서 하나의 target을 만들어서 사용하면 배포에 들어가는 시간과 노력을 아낄 수 있습니다.:)

2)외부 속성 파일 사용하기

Ant 설정 파일에서는 변수를 지원하는데요, 맨 위 Ant 설정 파일을 자세히 보시면 ${}로 감싸여져있는 변수 형태의 값들이 여기저기 있는데요, 실제로 이것들은 변수의 역할을 합니다. 맨 윗줄 project요소에 있는 basedir속성을 그 아래 property요소에서 ${basedir}로 재사용하고 있죠?

이렇게 project안에서 속성 값을 공유 할 수 있습니다. 또한 여러 속성들을 외부 파일에 작성 해 두고 그 값들을 불러와서 쓸 수 있는데요, 2번째 줄에 있는 property 요소에 이 변수들에 대한 값을 설정하고 있는 외부 설정 파일의 위치를 담고 있는 것을 볼 수 있습니다.

그 외부 설정 파일은 아래와 같은 모양을 하고 있습니다.

src.root = ${basedir}/srcExtension
extension.destfile=uirss.xpi
extension.root = ${basedir}/extension
deploy.destfile=extension.tar.gz
ftp.server=  xxx.xxx.xxx.xxx(실제 ftp의 ip를 입력합니다)
ftp.userid=userid
ftp.port=port
ftp.password=password
telnet.server=${ftp.server}
telnet.userid=${ftp.userid}
telnet.password=${ftp.password}

이 파일에 설정된 변수의 이름을 Ant설정 파일안에서 ${}로 감싸서 재사용 할 수 있는 것이죠.

이런식으로 자신의 프로젝트 배포에 필요한 task들을 묶어서 하나의 xml 파일로 만든 다음 이 xml파일을 이클립스의 Ant  View에 끌어다 놓으면 자동으로 인식을 하게 됩니다.




2번째 그림에서 보이는 개미아이콘이 붙은 항목은 각각의 xml파일이고 project 요소의 name속성 값을 보여줍니다. 이 부분을 더블 크릭하면 디폴트 target의 내용이 실행됩니다. 그 하위 동그라미 아이콘들은 xml파일 안에 있는 각각의 target요소들을 뜻하며 text는 target의 name속성 값입니다.  각 target항목을 더블클릭하면 해당 target의 작업이 실행됩니다.

3.마치며

이렇게 몇 가지 간단한 내용들고 OSX에서 PHP로컬 개발 환경을 구축하는 방법에 대해 소개해 드렸습니다. 하지만 1번을 제외한 2,3번의 내용들은 OSX에만 국한되는 것은 아니니 Apache를 사용하시는, 이클립스를 사용하시는 윈도우 사용자 분들도 그대로 적용하실 수 있습니다.

너무 많은 내용을 하나의 포스트에 짤막하게 담으려다 보니 세밀함이 많이 부족한 포스트가 되고 만것 같습니다.^^;; 게다가 글재주 또한 잼병이라 아는것마저 정확히 전달을 하지 못한 것 같습니다......;;

더 자세한 내용들은 각 사이트에 세세한 문서들이 많으니 참조하시길 바랍니다.

신고
크리에이티브 커먼즈 라이선스
Creative Commons License

'Programing > PHP' 카테고리의 다른 글

[OSX] Eclipse에서 PHP 로컬 개발/테스트 환경 구축하기  (4) 2008.08.30
Enabling PHP and Apache in Leopard  (2) 2008.08.19
WAV파일 분석  (0) 2006.11.10
간단한 소켓통신  (0) 2006.10.13
간단한 대화식 프로그램  (0) 2006.07.24
시스템 모니터링 툴  (0) 2006.07.17
posted by 물결(Wave)
2008.08.19 12:01 Programing/PHP
Mac OS X 10.5 레오파드에는 기본적으로 PHP가 설치 되어있습니다.
하지만 아파치에서 PHP모듈을 활성화 하지 않았기 때문에 PHP를 웹서비스에 이용하기 위해서는 아파치 설정파일에서 PHP모듈을 활성화 해주어야 합니다.
우선 아파치 설정 파일을 찾아야 하는데요.

터미널을 열고 httpd -V 라고 입력하면 아래와 같은 메세지들이 출력됩니다.

사용자 삽입 이미지

하단에 아파치 설정 파일인 httpd.conf 파일의 위치가 나와있죠~

이제 이 파일을 열어 PHP모듈을 활성화 시켜주어야 합니다.

설정파일이 있는 곳으로 디렉토리를 이동한 후 다음과 같이 타이핑합니다.

sudo vi httpd.conf

비밀번호를 입력하고 슬래시(/)를 눌러 "php" 를 찾습니다.

줄 맨 앞에 "#"으로 주석 처리가 되어 있습니다.

사용자 삽입 이미지


주석을 제거하고 저장을 하고 vi를 종료합니다.

이제 PHP의 설정파일을 편집할 차례입니다.
기본 설정대로 쓰고 싶다면 이 과정은 생략해도 됩니다만, 여러가지 이유로 인해서 이 과정 역시 수행하실 것을 권합니다.

콘솔에서 다음과 같이 타이핑 합니다.

php -i | grep ini

그럼 아래와 같은 메세지가 출력됩니다.

사용자 삽입 이미지


맨 윗 줄을 보면 php.ini 파일의 위치가 /etc 라고 나옵니다.

ls -l /etc/php.ini

불행히도 파일을 찾을 수 없다는 메세지가 출력됩니다.

초기 상태에 php.ini 파일은 만들어져 있지 않습니다.

사용자가 php.ini.default 파일을 복사해서 php.ini 파일을 생성해야 하는데요.

php.ini.default 파일은 /private/etc/ 에 있습니다.

콘솔에서 다음과 같이 입력하여 php.ini 파일을 생성해줍니다.

cd /private/etc sudo cp php.ini.default php.ini

이제 vi를 사용하여 php.ini파일을 입맛대로 수정하고 저장하면 모든 설정이 끝납니다.

다시 콘솔에서 php -i | grep ini 를 입력해 보면 아래와 같이 ini 파일이 로드되었음을 알리는 메세지가 출력됩니다.

사용자 삽입 이미지





참고: http://foundationphp.com/tutorials/php_leopard.php
신고
크리에이티브 커먼즈 라이선스
Creative Commons License

'Programing > PHP' 카테고리의 다른 글

[OSX] Eclipse에서 PHP 로컬 개발/테스트 환경 구축하기  (4) 2008.08.30
Enabling PHP and Apache in Leopard  (2) 2008.08.19
WAV파일 분석  (0) 2006.11.10
간단한 소켓통신  (0) 2006.10.13
간단한 대화식 프로그램  (0) 2006.07.24
시스템 모니터링 툴  (0) 2006.07.17
posted by 물결(Wave)
원문 : http://www.webmasterworld.com/forum91/68.htm

(원문을 그대로 카피했습니다)

I recently pulled together a bunch of information about JavaScript support for personal use, and thought it might be a handy reference for others. To start with, it might be good to talk about names. Mucho confusion here.

JAVASCRIPT
Netscape originally called their creation LiveScript. They had a tight partnership with Sun at the time, who had just generated a lot of marketing buzz around Java. Netscape piggy-backed on the buzz by changing the name to JavaScript. However JavaScript is not Java, not at all. But the naming confusion carries on to this very day!

JSCRIPT
Microsoft created their own version of the scripting language, which they call JScript. They made it "roughly" the same so that basic features would be supported cross-browser.

ECMAScript
ECMA is the European Computer Manfacturers Association. Netscape offered JavaScript to the ECMA for standardization in 1996. Netscape and Microsoft then both agreed to support the standards ECMA developed.

With that bit of complication handled,
here's the timeline I researched.

JavaScript 1.0
Netscape 2.0
Mar 1996

JavaScript 1.1
Netscape 3.0
Aug 1996

JavaScript 1.2
Netscape 4.0
Jun 1997

JavaScript 1.3
Netscape 4.5
Oct 1998

JavaScript 1.4
Netscape Server Only
No Client Side release

Javascript 1.5
Netscape 6.0
Nov 2000

JScript 1.0
IE 3.0 - early versions
Approx. JavaScript 1.0
Aug 1996

JScript 2.0
IE 3.0 - later versions
Approx. JavaScript 1.1
Jan 1997

JScript 3.0
IE 4.0
Approx. JavaScript 1.3
Oct 1997

Jscript 4.0
No Browser Products

JScript 5.0
IE 5.0
partly compliant with ECMAScript v3
Mar 1999

JScript 5.5
IE 5.5
Approx. JavaScript 1.5
Jul 2000

JScript 5.6
IE 6.0
Approx. JavaScript 1.5
Oct 2001

ECMAScript v1
More precisely ECMA-262
Approx. JavaScript 1.3 or JScript 3.0
June 1998

ECMAScript v2
Released for maintenance purposes only

ECMAScript v3
Approx. JavaScript 1.5 or Jscript 5.5
Dec 1999

REFERENCES:

1. [url=http://www.mozilla.org/js/language/es4/]ECMA v4 Proposal[/url]
projected for this year (2002)

2. [url=http://developer.netscape.com/docs/manuals/javascript.html]Netscape's Javascript Info[/url]

3. [url=http://msdn.microsoft.com/library/en-us/script56/html/js56jslrfJScriptLanguageReference.asp]Microsoft's JScript Info[/url]

신고
크리에이티브 커먼즈 라이선스
Creative Commons License
posted by 물결(Wave)
브라우저에 따라 달리 동작하는 자바스크립트 함수 몇몇을 소개합니다.
가장 기본적인 문자열 처리와 이벤트 처리에 해당하는 함수들이기 때문에 숙지하시어 개발시 활용하시기 바랍니다.

문자열 처리




이벤트 처리

신고
크리에이티브 커먼즈 라이선스
Creative Commons License
posted by 물결(Wave)
자바스크립트 코딩을 하던 중 제 머리를 아프게 했던 문제가 있었습니다.
약 30분 가량을 이 문제로 씨름하다가 단 한줄로 문제를 해결했습니다.
자바사크립트로 oop를 구현하는게 일반적인 요즘, 자칫 간과하기 쉬운 객체 초기화의 중요성을 다시 한 번 상기시켜 준 문제였기에 공유합니다.

제가 설계한 객체는 기본적으로 자바스크립트의 배열을 사용하고 배열을 조작할 몇 가지 부가 기능을 첨가한 단순한 객체였습니다.

function TemporaryBasket(){
    this.basket = [];
}

TemporaryBasket.prototype.add = function(){
    var temp = [];

    for(var i=0,max=arguments.length; i
        this.basket.push(arguments[i]);
    }

    return this.size();
}

TemporaryBasket.prototype.remove = function(obj){
    for(var idx in this.basket){
        if(this.basket[idx] == obj){
            this.basket.splice(idx,1);
        }
    }
}

TemporaryBasket.prototype.removeAt = function(idx){
    return this.basket.splice(idx,1);
}

(이하 메서드 생략)





그리고 이 TemporaryBasket를 상속받고 몇몇 메서드들을 오버라이드하는 SelectedItemBasket 이라는 객체가 있습니다.

function SelectedItemBasket(){}
SelectedItemBasket.prototype = new TemporaryBasket;
SelectedItemBasket.prototype.compareSequence = function(a,b){
    return a.sequence - b.sequence;
}
SelectedItemBasket.prototype.add = function(obj){
    var cnt = TemporaryBasket.prototype.add.call(this,obj);
    Consol.print("add> selected itmes: " + this.size());
   
    Consol.print('board type: ' + obj.fldtype);
    this.basket.sort(this.compareSequence);
   
    return cnt;
}
SelectedItemBasket.prototype.remove = function(obj){
    var removedItem = TemporaryBasket.prototype.remove.call(this,obj);
    Consol.print("delete> selected itmes: " + this.size());
    this.basket.sort(this.compareSequence);
   
    return removedItem;
}

(이하 메서드 생략)


정말 단순한 객체죠?
하지만 그 단순함에 속아 커다란 문제점을 놓치고 말았습니다.

어떤 페이지에 SelectedItemBasket객체의 인스턴스를 두 개 이상 생성하였는데 문제가 발생하였습니다.
인스턴스가 한 개 일땐 전혀 일어나지 않던 문제였기에 무척이나 당황스러웠죠;;

문제는, 각 인스턴스가 자신의 속성으로 갖고 있는 Array객체인 basket 을 공유하는 것이었습니다.
분명 독립적으로 생성된 서로 다른 인스턴스지만 이상하게도 basket을 공유해서 한 쪽에서 add() 메서드를 호출하면 다른 쪽 basket에도 항목이 추가되어 결국 두 개의 인스턴스가 동일한 basket을 갖게 되었습니다.


결론부터 말하자면 문제의 원인은 SelectedItemBasket의 생성자 함수 였습니다.

function SelectedItemBasket(){}


prototype을 TemporaryBasket의 인스턴스로 하였기 때문에 당연히 초기화는 필요 없으리라 생각했는데 오산이었습니다.

SelectedItemBasket.prototype = new TemporaryBasket;

위와 같이 SelectedItemBasket 생성자 함수 아래에 prototype을 지정하였지만 이 코드는 페이지 로딩시 단 한 번 실행될 뿐입니다.

SelectedItemBasket 객체를 생성할때마다 호출 되는 것이 아니기 때문에 SelectedItemBasket 객체를 생성할 때마다 처음 생성된 TemporaryBasket 객체를 그대로 쓰게 됩니다. (개인적인 추측입니다;;;)

때문에 SelectedItemBasket의 생성자 함수에서 초기화 하는 작업이 필요합니다.

function SelectedItemBasket(){
    this.constructor();
}

물론 위 코드는 TemporaryBasket와 SelectedItemBasket 의 생성자 함수가 동일 하기 때문에 SelectedItemBasket만의 초기화 코드가 없습니다. 그저 TemporaryBasket의 생성자 함수를 빌려 쓰면 되는 것이지요.


'초기화'의 부재로 인해서 일어난 문제였던 만큼 다른 코드들을 건드리지 않고 쉽게 마무리가 되었습니다만, '초기화'의 중요성을 다시 한번 느끼게 되었습니다^^;; (C언어 책을 다시 보게 만드네요...)

신고
크리에이티브 커먼즈 라이선스
Creative Commons License
posted by 물결(Wave)
TAG 초기화
FireFox 확장 기능 중 웹 개발자들이 가장 많이 사용하는 확장 기능은 아마 FirebugWeb Developer가 아닐까 합니다.
웹 개발자의 필수품, Firebug

Web Developer 역시 없어서는 곤란하죠~

두 확장기능은 웹개발시 없어서는 안될 정말 유용한 툴들이죠.
IE에도 IE Developer 이라는 툴이 있어서 어느정도 유용하게 쓸 수 있습니다만 위의 것들에 비해 좀 부실한 면이 없지 않습니다.
반면 OperaSafari에는 저러한 툴이 없어 아쉬웠는데요, 그런 아쉬움은 이제 추억으로 묻어버려도 좋을 것 같습니다.


Opera Inspector

오페라 9.0 이후 버전 부터는 간단한 조작만으로 브라우저에 Inspector를 설치 할 수 있습니다.
설치를 위해서는 오페라 9.0 이후 버전으로 다음 URL의 페이지를 엽니다.
http://dev.opera.com/tools/

오페라 DOM Inspector 설치 버튼

그럼 위와 같은 버튼 두 개가 보이는데요, 저 버튼들을 드래그 하여 오페라 브라우저의 툴바에 드롭하는 것으로 Inspector의 추가는 끝납니다.

버튼을 드래그 하여 이곳에 드롭하면

설치 진행 여부를 확인하는 창이 뜨고, 예를 클릭하면,


새로운 툴바 버튼이 생성이 됩니다

이제 Opera의 DOM Inspector의 위용을 한 번 볼까요?

이쁘게도 생겼네요~

DOM Tree,CSS inspect, HTTP network 정보까지 Firebug와 비교해도 전혀 손색이 없죠? ^^

이번엔 사파리쪽을 살펴볼까요?


Safari Inspector

Safari 3.1 부터는 브라우저에 Inspector를 내장하고 있습니다.
하지만 메뉴속에 꼭꼭 숨어있어서 있는지조차 모르고 있었습니다;;;

메뉴의 편집>기본설정 또는 Ctrl + ,(콤마)를 누르면 아래와 같은 패널이 뜹니다.
Safari의 설정 패널

고급 탭의 하단을 보시면 "메뉴 막대에서 개발자용 메뉴 보기" 라는 항목이 있습니다.
이걸 체크해서 활성화를 시켜주면 메뉴바가 다음과 같이 바뀝니다.

단, Mac용 Safari에서 Inspector를 활성화 하려면 콘솔에서 아래와 같이 해주시면 됩니다.

defaults write com.apple.Safari \
WebKitDeveloperExtras -bool true


사용자 삽입 이미지

개발자용 메뉴가 새로 생겼습니다~ 캬~
메뉴를 클릭해보면 다양한 세부 항목들이 보입니다.

사용자 삽입 이미지

 Inspector의 활용방법은 간단합니다.
웹페이지의 요소에서 마우스의 우측버튼을 클릭하면 컨텍스트 메뉴 하단에 "구성 요소 점검" 이란 항목이 보입니다. 클릭하면 아래와 같은 감개무량한 Safari의 Inspector이 모습을 드러냅니다...

역시 애플 답구나~@.@

이제 Inspector를 쓰기위해 특정 브라우저를 고집할 이유는 없어진듯 합니다.(물론 지극히 주관적인 의견일테지만요~^^)
Opera,Safari도 많이 사랑해주세요~~^^




신고
크리에이티브 커먼즈 라이선스
Creative Commons License
posted by 물결(Wave)
Javascript OOP

최근 javascript로 OOP를 구현 하는 사례가 증가하고 있습니다.
AJAX와 함께 JSON이라는 효율적인 표기법과, prototype.js 이나 ExtJS같은 걸출한 javascript 프레임웍, 라이브러리 등이 출현하면서 javascript OOP는 점점 더 대중화가 되어가고 있습니다.
extjs sample

ExtJS 샘플

prototype.js

prototype.js


다시 말하면 javascript로 OOP를 구현하는 기술은 더이상 스페셜리스트들만 알고 있는 고급기술이 아니란거죠. 이를 다시 바꿔말하면 이제는 javascript OOP를 모르면 안된다는 말이기도 합니다~^^;;

가끔 웹서핑을 하다 페이지 소스를 보면 여기저기 많은 js 소스들에서 심심치 않게 'new' 연산자(operator)나 '{}' 같은 리터럴(object literal)을  볼 수가 있습니다.

'new'와 '{}' 은 javascript에서 객체를 생성할때 쓰는 연산자와 리터럴 입니다.


객체 생성하기

객체를 한 번 만들어 볼까요?

var car = new Car();

car라는 변수에 Car객체를 생성하여 대입하는 코드입니다.
실행하면 Car를 찾을 수 없다는 오류가 발생합니다.
클래스가 있어야겠죠?
클래스를 만들어보겠습니다.
javascript에서는 'function' 키워드를 써서 클래스 정의를 합니다. 함수 하나 만든다고 생각하시면 됩니다~

function Car(){
   
}

이제 Car객체가 만들어집니다.


Property

그런데 Car객체는 아무것도 가진게 없네요~^^ 껍데기만 있는 빈클래스는 의미가 없죠?
이제 Car에게 책임을 좀 지어줄까요?
먼저 이름을 주어야겠습니다. '애마1호기','달려라번개호' 같은 이름을 붙여준다면 더욱 애착이 가는 객체가 되겠죠?
이름은 객체의 속성(property)으로 볼 수 있습니다. javascript에서 객체의 속성은 '객체.속성이름 = 속성 값' 이렇게 할당 할 수 있습니다.

function Car(){
    this.name = '달려라번개호';
}

var car = new Car();
alert(car.name);

'달려라번개호'가 메세지 박스에 출력되네요~

그런데 저 this는 뭘까요?
이것의 이름은 달려라 번개호다?
네, 맞습니다~^^
여기서 this라는 키워드는 'new' 연산자를 통해 만들어진 Car객체의 인스턴스(instance)를 뜻합니다.

var car1 = new Car();
var car2 = new Car();
var car3 = new Car();

new 연산자가 실행될때마다, 붕어빵 기계에서 붕어빵이 나오듯 Car객체가 하나씩 만들어져서 나오게 됩니다. 이렇게 만들어진 하나하나의 객체를 인스턴스라고 하며 this란 그 인스턴스를 가리키는 것이지요~

this가 붙은 변수, 즉 객체의 property는 객체가 살아있는 동안 객체의 어느 곳에서든 사용 할 수 있습니다. 객체의 전역변수라고 생각하시면 되겠죠?

this 대신에 'var'를 붙여주면 지역 변수로 사용할 수 있습니다.

function Car(){
   
var engineSize = '5000cc';
    this.name = '달려라번개호' + engineSize;
}

var car = new Car();
alert(car.name);
alert(car.engineSize);

'달려라번개호5000cc'라는 이름은 출력이 되는데, engineSize은 'undefined' 라고 나오네요~
engineSize는 객체를 만들때 name 속성을 위해 희생하고는
지역변수의 비참한 최후를 맞이한듯 합니다.
var와 this의 차이랍니다~^^

그런데 Car를 세대(car1,car2,car3) 만들었는데 이름이 모두 똑같습니다.
달려라번개호
달려라번개호
달려라번개호
이제 그만 달리고 싶네요 ㅡ.ㅡ;;

Car 객체를 생성할때 이름을 따로따로 지어주고 싶습니다.
생성자인 function Car() 를 조금 손봐줘야겠군요.

function Car(name){
    this.name = name;
}

이렇게 해주면 Car를 생성할때 원하는 이름을 지어줄 수 있습니다.

var car1 = new Car('번개호');
var car2 = new Car('천둥이');
var car3 = new Car('폭풍3호');

alert(car1.name);
alert(car2.name);
alert(car3.name);

이제 만들어진 Car객체들이 저마다 다른 이름을 가질 수 있게 되었습니다.^^


javascript로 객체 만들기~ 참 쉽죠? ^^
다음엔 Car를 움직여보도록 하겠습니다. 이름만 있는 차 보다는 타고 다닐 수 있는 차가 더 좋겠죠?
javascript object's method를 기대해 주세요~!!


신고
크리에이티브 커먼즈 라이선스
Creative Commons License
posted by 물결(Wave)

티스토리 툴바