삽질하는플머

'Lazarus/KOL-CE'에 해당되는 글 4건

  1. 달력 컨트롤 2
  2. KOL-CE 2.80.3 릴리즈.
  3. KOL.PAS의 SHCreateMenuBar 호출부 수정
  4. KOL-CE 사용하기 2

달력 컨트롤

Lazarus/KOL-CE
라자루스를 어디에 쓸까 고민하다가... 음력에 대한 공부도 할 겸 "달 구경" 프로그램을 짬짬이 만들고 있다.
날짜 선택을 위해 달력 컨트롤을 올려놓으려고 했더니... 응? 델파이의 TDateTimePicker에 해당하는 TKOLDateTimePicker 는 있는데 TMonthCalendar에 해당하는 컨트롤이 없다. 허걱~~ fpc의 wince 유니트를 열어보니 DateTimePicker와 MonthCal에 사용되는 ICC_DATE_CLASSES 가 주석으로 막혀있네~ (라자루스 0.9.24 의 LCL 윈CE 인터페이스는 현재 베타버전이다.)

그렇다면 KOL의 TKOLDateTimePicker 는 뭘까 싶어 다시 KOL.pas 를 뒤져보니... 여기에 다시 재정의 되어있었다. 그러나 애석하게도 달력 컨트롤에 대한 코드는 찾아볼 수 없었다.

처음에는 간단히 LCL로 DLL을 만들어 쓰려고 했었는데... 위에서 언급했듯이 아직 윈CE 인터페이스가 베타라 arm-wince 로 달력 컨트롤을 컴파일하면 에러가 발생한다. 뭐 여차저차해서 만들기로 했고, 아직 내공부족으로 KOL 컴포넌트화 할 수는 없었지만 그럭저럭 쓸만하기에 방법을 정리 해 본다.

달력 컨트롤에 관련된 상수들은 evc와 함께 설치한 STANDARDSDK 5.0 에 정의되어 있으며 "C:\Program Files\Windows CE Tools\wce500\STANDARDSDK_500\Include\...\commctrl.h" 에서 찾을 수 있다. 이 파일을 번역하려고 슬쩍 훑어보니 다행히 상수 및 구조체가 윈도 32와 99% 동일하다. 그렇다면?? 델파이의 VCL을 가져와 쓰자.


VCL은 오픈소스가 아니므로 여기에 옮길 수 없다. 델파이 5.0을 기준으로 과정만 소개 해 본다.


1. 먼저 라자루스의 File->NewUnit 를 선택, 새로 만들 달력 컨트롤이 담길 유니트를 만들어 준다. 이름은 적당히.

2. uses 섹션에는 Windows, Messages, KOL, CommCtrl 유니트를 적어넣는다.

3. ...\Delphi5\source\rtl\win\commctrl.pas 파일을 열고 다음 내용들을 복사 해 온다.

3-1. 6371번 줄 (MONTHCAL CONTROL) 부터 6664번 줄 (MonthCal_GetUnicodeFormat) 까지 interface 섹션에 복사 해 넣는다.

3-2. 8508번 줄 (MonthCal_GetCurSel 함수) 부터 8623번 줄 까지 implementation 섹션에 복사 해 넣는다.

3-3. MonthCal_SetUnicodeFormat, MonthCal_GetUnicodeFormat 함수는 wince에서는 동작하지 않는다. 이 두 함수의 선언 및 구현부는 {$ifdef win32} 지시자로 감싸둔다.

4. KOL의 TControl 기반의 달력 컨트롤을 생성할 수 있도록 다음과 같이 NewMonthCalendar 함수를 만들어 준다.

function WndProcMonthCalendarNotify( Self_: PControl; var Msg: TMsg; var Rslt: Integer ): Boolean;
begin
  Result := false;
end;

function NewMonthCalendar( AParent: PControl): PControl;
const
  CS_OFF = {$ifdef win32}CS_OWNDC or CS_CLASSDC or {$endif}CS_PARENTDC or CS_GLOBALCLASS or
           CS_VREDRAW or CS_HREDRAW;
begin
  DoInitCommonControls( ICC_DATE_CLASSES );
  Result := _NewCommonControl( AParent, MONTHCAL_CLASS,
         WS_CHILD or WS_VISIBLE or WS_TABSTOP,
         TRUE,  nil );
  Result.SetSize( 191, 154 );
  Result.AttachProc( WndProcMonthCalendarNotify );
{$ifdef wince}
  Result.Perform(CCM_SETVERSION, COMCTL32_VERSION, 0);
{$endif wince}
end;



작업은 이것으로 끝. 달력을 생성해 폼 위에 올리는 코드는 다음과 같다.

TCalendarForm = ....
...
private
  fCalendar: PControl;
...

procedure TCalendarForm.KOLForm1FormCreate(Sender: PObj);
begin
  fCalendar := NewMonthCalendar(Form);
end;



달력에 날짜를 지정하거나 읽어올 때는 델파이에서 복사해 온 MonthCal_SetCurSel, MonthCal_GetCurSel 를 쓰면 편하다. 한가지, KOL의 SystemTime2DateTime은 델파이와 달리 1899년12월30일이 아닌 0년 0월 0일을 기준으로 한다. 아직 분석도 다 안끝났고 무엇보다 귀찮으니 그냥 SysUtils에 정의된 SystemTimeToDateTime() 을 쓰자.


function TCalendarForm.GetDateTime: TDateTime;
var
  pst: TSystemTime;
begin
  MonthCal_GetCurSel(fCalendar.Handle, pst);
  Result := SysUtils.SystemTimeToDateTime(pst);
end;

procedure TCalendarForm.SetDateTime(const AValue: TDateTime);
var
  pst: TSystemTime;
begin
  SysUtils.DateTimeToSystemTime(AValue, pst);
  MonthCal_SetCurSel(fCalendar.Handle, pst);
end;




폰트 크기를 50으로 주고 480*800 에뮬레이터에서 돌려본 화면은 짜잔~~ 멋지지 않은가!!







3월 23일 릴리즈 된 0.9.26.2 버전의 윈CE/LCL 인터페이스에 캘린더가 추가되었다고 한다.
그러나 이 팁은 KOL에서는 아직까지 유효하다~~ ^^

KOL-CE 2.80.3 릴리즈.

Lazarus/KOL-CE
간만에 소스포지에 가 봤더니 KOL-CE 2.80.3 버전이 나왔다. 2009년 1월 23일이면 연휴 바로 직전이군..
http://sourceforge.net/projects/kol-ce/

수정된 사항을 간단히 짚어보면,

* Enabled TTrayIcon for wince.
* Fixed compilation with FPC 2.2.3 and FPC 2.3.1. Patch by Carolos Foscolos.
* MCK: Fixed updating of source code in trunk version of Lazarus.
* MCK: Fixed code generation for new KOL application template, when form's unit name is renamed.
* MCK: Add InitCommonControls() call to fix themed control drawing if only standard controls are used.
* MCK: Fixed error "Restoring toolbar buttons bitmap from then previous version of the KOL&MCK format."  version of the KOL&MCK format."

이라는군. 아무튼 기쁜 소식이다~~!!!

이전 2.80.2 버전을 설치했던 경로는 /lazarus/userlib/kol-ce-2.80.2. 새 버전은 /lazarus/userlib/kol-ce-2.80.3 에 설치. (이거 누가 그랬을까~~ 누가 그랬을까!! 아마추어 같이~~ ㅠㅠ) 따라서 이전에 작업했던 프로젝트 파일 (*.lpi) 내의 경로들을 모두 수정 해 주어야 한다. 귀찮네... 다음번에 라자루스를 설치할 때는 그냥 lazarus/userlib/kol-ce 를 사용해야 겠다.

참고로 이 버전의 KOL-CE의 SIP메뉴 관련 수정 위치는 KOL.pas 의 33,847 라인이다.
매번 귀찮으니... 짧은 영어로라도 패치를 만들어 보내야 할 듯... ㅠㅠ;;

KOL.PAS의 SHCreateMenuBar 호출부 수정

Lazarus/KOL-CE

윈도 CE는 종류도 참 많다. 델마당에 올렸던 글에 신성기님이 달아두신 답변을 옮겨본다.

신성기 (barmi)
Windows Mobile(WM)에 비해 Windows CE (WinCE)는 포괄적인 개념입니다. WM5는 WinCE5.0기반으로 구동되는 서브셋입니다. 즉, WinCE는 MS Platform builder로 만들어지는 Embedded OS의 총칭이고, Wimdows Mobile은 이전의 Palm sized PC -> Pocket PC의 차세대 명칭으로 WinCE 기반으로 쉘,기능의 guide line을 만들어 둔 것입니다.
WinCE와 WM의 버전을 비교해 보면 다음과 같습니다.
WinCE 2.1 - Palm Sized PC (Hand Held PC)
WinCE 3.0 - PocketPC 2000/2002/2003/2003SE
WinCE 4.2
WinCE 5.0 - Windows Mobile 5
WinCE 5.2 - Windows Mobile 6
WinCE 6.0 - Windows Mobile 7
실제 Pocket PC는 모두 WinCE 3.0기반으로 만들어 진 것이라, OS의 기본 성능은 동일하고 포함되는 shell이나 dll에 따라 버전이 구분됩니다.
참고하세요.


문제는, KOL로 빌드한 실행파일의 경우 친구놈의 아이나비 플러스에서 에러가 나는 현상이 발생한다는 것. KOL은 폼을 생성하면서 SIP부분을 구현하기 위해 SHCreateMenuBar 를 호출하는데, 아이나비 플러스의 aygshell.dll 에는 이 함수가 없기 때문이다. 또 다른 글에 휘오른님이 달아두신 댓글에서 보이듯 동일한 현상이 포켓피시 2003에서도 발생한다고 하는데,

휘오른 (leekg999)
저번에 라자루스로 wince용으로 만든 다음, 파일크기를 보니 기본이 1M 더군요. 그러려니 하고, 좀 지난 pda(h4150,ppc2003)에 올려서 실행했더니,겨우겨우 로딩한뒤에, 다운먹더군요.KOL-CE 는  실행순간 넉다운..;; 제가 라자루스를 컴퓨터 3대에 깔아서 해봤는데, 윈도우 환경을 너무 타는 것 같습니다. 어떤때는 컴파일 되고, 어떤때는 IDE에서 오류나고,크로스 컴파일을 지원한다는게 매력적인 환경이지만, 초보에겐 삽질이 힘들더라구요 ㅠ_ㅠ
(혹시 WM5 이상 기종에서 성능은 어느정도 나오는지 아시는 분 계시나요?)  


포켓PC 2003에 SIP 영역이 없다는 것을 고려하면 같은 이유라고 짐작된다. (시간 날 때, 책상위에서 잠자고 있는 poz에 밥을 먹인 뒤 테스트 해 봐야 겠다.)

아무튼 이 문제를 해결하려면 KOL.PAS의 TControl.CreateWindow 함수를 손 봐 주어야 한다. 버전 2.80.1 에서는 33,837 번 라인, 버전 2.80.2 에서는 33,845 번 라인을 아래와 같이 수정하자.

2009.1.28 추가.
2009년 1월 23일에 릴리즈 된 2.80.3 버전에서는 33,847 에 해당 코드가 있다. 이거 매번 귀찮으니... 패치를 만들어 보내야 할 듯...


 // if CePlatform <> cpSmartphone then begin
 // -->> 위 코드를 다음과 같이 수정한다. 
 if CePlatform = cpPocketPC then begin


CePlatform 이 단순히 cpPocketPC인 것으로 봐서... 아무래도 2003에서는 또 다른 삽질이 필요할 듯...
이 문서는 삽질이 끝난 뒤 다시 업데이트 하도록 하자.


-->> PocketPC 2003 에뮬레이터에서 굴려본 결과는, 위의 경우와 관계없이 제대로 동작한다. 
CePlatform 값 자체도 cpPocketPC로 인식되므로 사실 저 코드와 별 차이가 없어보인다...

쩝... 결국 POZ를 충전해야 한다는 건가...


델마당의 휘오른님의 댓글에 의하면, 저 코드를 적용했을 때 h4150, PPC2003 에서 정상동작 한다고 한다. 따라서 POZ 밥먹이기는 귀차니즘에 의해 잠정중단~~ ^^;

KOL-CE 사용하기

Lazarus/KOL-CE
z라자루스를 깔고 초기 상태 그대로 예제를 만들어 빌드하면... 실행파일의 용량은 약 11메가. 말 그대로 덜덜덜...
윈도 CE용 개발도구로 라자루스를 선택한 사람들에게 그 크기는 재앙에 가깝다.
디버깅의 라인정보 빼고 스마트링크를 켜 주면 1메가로 줄어들지만... 그래도 무겁기는 매 한가지.

그러다 만난 KOL-CE는 말 그대로 복음과도 같은 존재. 윈도용 실행파일은 41kb에서 시작한다. 오오~~!!!
http://wiki.freepascal.org/KOL-CE

델파이에서 KOL-CE를 쓰면 무려 11kb 로 줄어든다는데... 후덜덜덜...

아무튼 이 멋진 도우미의 사용법에 대해 간단히 알아보자.

설치하기.

1. 다운로드 받아서 압축을 푼다. (C:\lazarus\userlib\kol-ce-2.80.2 에 풀었음)
2. Components -> Open package file (.lpk) 메뉴를 선택하고, MCK 폴더를 찾아가 "MirrorKOLPackage.lpk" 를 열어준다.



3. 패키지 윈도가 표시되면 Install 버튼을 눌러준다.
4. MCK와 IDE가 다시 컴파일되고 나서 라자루스가 재시작 될 것이다.

인생 최대의 삽질의 추억!!

몇 개의 컴포넌트가 보이지 않는 현상이 생기길래 라자루스 IDE 재빌드부터 생각나는 일은 모두 시도 해 봄.
심지어는 컴포넌트 팔래트까지 종류별로 바꿔보았다.

MIRROR.pas 의 RegisterComponents는 RegisterComponents( 'KOL Mirror', [...
mckCtrls.pas 에는 RegisterComponents( 'KOL Ctrls', [ ...
mckObjs.pas 에는 RegisterComponents( 'KOL Objs', [ ... 와 같이 변경.

저렇게 했는데도 안보이길래... 우연히 화면을 늘려봤더니 얌전히 숨어있는 것이 아닌가..
라자루스는 화면의 가로폭이 작으면 컴포넌트들을 2열로 배열하는 걸 몰랐었다.



도대체 이 문제 때문에 라자루스를 몇 번이나 재설치 했었는지... 쩝쩝...





사용하기.
새 버전의 KOL에서는 예전처럼 폼을 저장하고 다시 불러오는 닭짓이 필요 없다. 라자루스의 File -> New 메뉴에서 "KOL Application" 을 골라주면 그걸로 끝!!






프로젝트와 폼에 적당한 이름을 지어주고 저장하자.

저장부터 해야 한다!! KOL 프로젝트는 저장될 때 프레임워크의 코다가 추가되는 방식이니 저장하지 않고 빌드하면서 안된다고 삽질하지 말 것!!!

또한 이 때 경로명에 한글이 들어가 있다면 KOL이 인식하지 못하니 유의할 것!!

빌드 해 보면 41kb 짜리 실행파일을 얻을 수 있다.




윈 CE 빌드.
Project -> Compiler options 메뉴를 선택한 뒤, Code 페이지의 설정을 다음과 같이 바꿔준다.
KOL은 LCL을 사용하지 않기 때문에 LCL Widget type 은 그대로 두어도 된다.



빌드 해 보면 53kb 짜리 실행파일이 생긴다. 윈 CE 에뮬레이터로 옮기고 돌려보면 잘 동작하는 것을 확인할 수 있다.