반응형


기본 화면은 변한것이 없다. 단지 매 사용시마다 프로그램을 실행시키는 것이 불편하였다.
그리하여.. 트레이에 추가 하는 부분을 추가. 그리고 트레이에서 화면으로 전환시 목록 리프레쉬.

여기서 발생한 문제점
1.최소화 버튼 클릭시 화면은 숨기고 트레이에 넣었는데 상태표시줄에는 남아있었다.
2.트레이 아이콘 팝업메뉴를 넣었는데 팝업메뉴를 뛰운후 다른 위치를 클릭해도 사라지지 않는다.






1 최소화시 트레이에 넣은후 화면을 숨기기 위해 ShowWindow(hwnd, SW_HIDE)를 사용했는데...
  이렇게 할 경우 화면은 사라지지만 작업표시줄에는 사라지지 않는다 하여... 알아보니..
// 최소화를 먼저 해준후 숨겨야 작업표시줄에도 사라진다. ㅡㅡ;;

2.트레이 아이콘에 이벤트 발생시 팝업을 뛰었는데 그게 한번 뜨면 그 메뉴를 선택하지 않는 이상 안사라진다.
  이럴경우 메뉴를 화면에 보여주는 TrackPopupMenu()를 호출하기 전에 SetForegroundWindow(hwnd)를 호출

반응형
비트논리연산자
정수형 자료( int, short, long)에 대해 비트단위로 논리 연산을 수행한다.
연산되는 값을 먼저 2진수로 바꾸어서 연산한다.
연산자 의미
~ 해당 비트를 반전시킨다.(1 -> 0, 0->1)
& 두 비트 모두 참이면 결과가 참
^ 두 비트가 서로 값이 다르면 참
| 두 비트가 모두 거짓이어야 거짓

< 소스출처 >http://kldp.net/projects/winningchaos/

SentinelDlg.cpp
BOOL CSentinelDlg::OnInitDialog() 진영선택부분에서 다이얼로그 초기화 부분
((CButton *)GetDlgItem(IDC_RADIO1))->SetCheck(BST_CHECKED);  //센티넬  선택
((CButton *)GetDlgItem(IDC_RADIO2))->SetCheck(BST_CHECKED);  //스콜지  선택

void CSentinelDlg::OnOK() 활성화시에 전역변수에 설정값 셋팅 부분
pBtn = (CButton *)GetDlgItem(IDC_RADIO1);
  if (pBtn->GetCheck()) m_uOpt |= 0x1000; // 센티널
  else m_uOpt |= 0x2000; // 스콜지
  m_uOpt |= (((CComboBox *)GetDlgItem(IDC_COMBO1))->GetCurSel()); // 본진 클릭 옵션 (본진단축키값이다.)


Scourge.cpp
static LRESULT CALLBACK MsgHook(UINT nCode, WPARAM wParam, LPARAM lParam)  //메시지 후킹부분
if(pkbhs->vkCode == '특정키이면') {
//센티넬이나 스콜지로 변경되게끔 한다.
m_uOpt |= 0x1000; // 센티널
((CButton *)GetDlgItem(IDC_RADIO1))->SetCheck(BST_CHECKED);  //센티넬  선택

m_uOpt |= 0x2000; // 스콜지
((CButton *)GetDlgItem(IDC_RADIO2))->SetCheck(BST_CHECKED);  //센티넬  선택

}

소스에 대한 전체적인 수정이 필요하다. 전역변수로의 설정하는 등의

반응형

Guda Project의 API 플밍 2번째 GudaMoreTran 입니다.

왜 GudaMoreTran 인가?

Guda Project + 메신저명의 일부 + transparency(투명)



개인적으로 사용하고 있는 메신저에 투명화 기능이 존재 하지 않기에...

API도 공부할겸 한번 만들어 보았다. 아직 수정 보완해야 할 부분이 많지만.

원하는 기능은 정상적으로 작동하기에 일단 프로젝트 완료.. 후에 업데이트 해야겠다.

일단 현재 떠있는 채팅창의 목록이 화면에 보이는 리스트 박스에 뜨게 되어있다.

어플 로딩시 갱신되지만 실시간으로 갱신되지 않기 때문에 투명화 하고 싶은 창을 선택전에

새로고침 버튼을 눌러서 갱신해야 한다. 그리고 투명화 하고자 하는 채팅창을 선택하고

아래 투명도를 조절하여 선택 적용을 하면 선택창만 투명화가 적용된다.

모든 채팅창을 동일한 투명도로 적용하고자 한다면 투명도를 조절하고 전체적용버튼을 클릭.^^

이후에는 업데이트시 기타 잘잘한 기능을 추가 하고자 한다.^^

주 목적은 개인적으로 필요한 기능을 구현하고 API 프로그래밍의 공부를 위해서 시작한것이다.

다른 분들에게는 필요 없는 어플이기에 여기에 공개는 하지 않겠다.^^
반응형

GetDesktopWindow
: 데스크탑 윈도우(루트 윈도우)의 핸들을 반환해준다.

HWND GetDesktopWindow(VOID);
ex) 데스크탑 윈도우에 출력하는 소스


EnumWindows
: 차일드 윈도우를 제외한 모든 윈도우를 검색한다. 그러나 시스템이 생성한 최상위 윈도우중에서
  WS_CHILD 스타일을 가지고 있으면 예외적으로 검색에 포함된다.

BOOL EnumWindows(     
    WNDENUMPROC lpEnumFunc,    //찾은 윈도우를 처리해줄 프로시저
    LPARAM lParam              //특정 사용자 정의 데이터를 콜백함수로 넘겨준다. 없을경우 NULL
);

EnumWindowsProc
EnumWindows에서 윈도우를 찾으면 EnumWindowsProc으로 값을 넘겨준다. 여기서 처리
EnumWindowsProc(
    HWND hWnd,                 //검색된 윈도우의 핸들
    LPARAM lParam              //EnumWindows에서 넘겨준 lParam값
);
ex) 윈도우 검색정보를 출력


EnumChildWindows
:특정 부모윈도우의 차일드만 검색
BOOL EnumChildWindows(      

    HWND hWndParent,
    WNDENUMPROC lpEnumFunc,
    LPARAM lParam
);

EnumThreadWindows
:스레드에 속한 윈도우 목록을 조사하는 함수들
BOOL EnumThreadWindows( 
    DWORD dwThreadId,
    WNDENUMPROC lpfn,
    LPARAM lParam
);

반응형
이번 프로젝트 이름은 GudaWinSet

Win32 API를 이용한 프로그램을 처음 작성한 것이다.

딱히 내놓을 만한 것은 아니지만 개인적인 프로젝트로 수정 보완하며 진행할 생각이다.

그리고 자바와는 또다른 매력이 있고 오랫만에 플밍에 오르가즘(?)을 느끼는 것 같기도 하다.

이렇게 말한다고 딱히 거창한 것은 아니다. 내가 사용하고자 진행하는 것이기 때문이다.


일단은 콘솔창 및 윈도우 화면의 설정을 변경할 목적으로 만들생각이다.
업무중 어쩔수 없이 콘솔창을 통해 로그를 보는데 각 콘솔창의 타이틀명을 바꾸기 번거럽고
버퍼라인 설정도 일일히 변경하기 귀찮은 관계로 해당 어플을 만들기로 하였다.
그리고 추가적으로 투명도 설정을 할수 있도록 기능을 추가할 예정이다. ㅎㅎ
메신저중에 네이트온처럼 투명창이 되었으면 하는 바램이 있기에 추가할 생각이다.
허접한 어플이지만 내공이 부족하여 구현하는 도중 찾은 여러가지 자료를 정리하고자 한다.

일단 다이얼로그 창에 한글입력시 깨짐 현상이 발생하였는데 이는 visual studio 설정으로 해결.

Resource View에서 해당 다이얼로그를 클릭하면 프로퍼티 속성에서 Language 항목을 볼수가 있다
여기서 한국어를 선택하면 실행시 한글깨짐 현상을 해결할수 있다.

다음 문제는 해당 윈도우의 핸들을 구하는 과정에서의 삽질 부분이다.

윈도우 간의 상호작용을 위해서는 우선 윈도우의 핸들을 알아야지 윈도우 관련 함수들을 사용할 수 있다.

HWND FindWindow(     

    LPCTSTR lpClassName,      //조사할 윈도우의 클래스 이름
    LPCTSTR lpWindowName      //조사할 윈도우의 캡션
);
조건에 맞는 윈도우를 찾으면 윈도우의 핸들을 리턴해 주고 못찾을경우 NULL을 리턴해준다.
최상위 부모 윈도우의 핸들만 리턴해준다.
 

HWND FindWindowEx(      

    HWND hwndParent,      //hwndParent에 속한 차일드 윈도우를 검색해낸다. NULL이면 데스크탑 윈도우의 차일드를 검색한다.
    HWND hwndChildAfter,  //검색을 시작할 차일드 윈도우를 지정한다. NULL이면 첫번째 차일드부터 검색한다.
    LPCTSTR lpszClass,    //조사할 윈도우의 클래스 이름
    LPCTSTR lpszWindow    //조사할 윈도우의 캡션
); 
부모 윈도우에 속한 차일드 윈도우 핸들을 찾을때 사용한다.

//이번에 사용한 함수이다.
HWND WindowFromPoint(      

    POINT Point
);
화면 좌표로 윈도우를 검색하는 함수로 인수로 화면 좌표를 POINT형으로 넣어주면 된다.
조건에 맞는 윈도우를 찾으면 윈도우의 핸들을 리턴해 주고 못찾을경우 NULL을 리턴해준다.
SPY++ 에서 사용하는 함수 인듯하다..  

*주의사항
위 함수를 이용해 얻은 CWnd * 형식의 값은 임시적으로 생성된 객체의 주소값이기 때문에
전역 변수 또는 멤버 변수에 저장한 후, 계속 사용하면 문제가 발생할수 있다.
해당 작업을 하는 그 순간에만 사용하고 더 이상 사용하면 안된다. 주의 할것!

위와 같은 함수를 이용해 윈도우의 핸들을 구했지만 내가 구하고 싶은것은 최상위 부모 윈도우의 핸들
이와 관련하여 HWND GetParent(HWND hWnd) 을 사용했지만 컨트롤의 경우 다른 컨트롤에 포함된 상태이면
상위 윈도우를 리턴하므로 원하는 결과가 나오지 않았다 그래서 사용한 함수가
GetAncestor(hWndChild,GA_ROOTOWNER); 두번째 인자인 플래그에 따라 GA_PARENT, GA_ROOT, GA_ROOTOWNER

GA_PARENT GetParent()와 비슷한 작업.
GA_ROOT, GA_ROOTOWNER  호출하는 컨트롤을 포함하는 최상위 윈도우 핸들

부모 윈도우의 차일드 윈도우를 조사하는 함수

BOOL EnumChildWindows(
    HWND hWndParent,                         // 부모 윈도우 핸들
    WNDENUMPROC IpEnumFunc,        // Call Back 함수의 포인터
    LPARAM IParam);  

하위 윈도우의 캡션값을 가져오기 위해서는  WM_GETTEXT 를 사용하면 된단다.. ^^;; 자료만 수집

코딩보다 자료정리하는데 더 많은 시간이 걸리는 것 같다. 그래도 정리를 해야 다음에 또 써먹기에.. ㅋ

반응형

어플을 실행할때 중복 실행이 되지 않게 하기 위해 방지 하는 방법에 대해서 알아보자.
그 방법에는 FindWindow()를 이용하거나 EnumWindows()를 이용하는등의 방법이 있지만
Mutex를 이용하여 간단하게 처리 하는 방법에 대해 알아보도록 하자.



함수원형
HANDLE CreateMutex(LPSECURITY_ATTRIBUTES lpMutexAttributes, BOOL blnitialOwner, LPCTSTR lpName);

Argument
- lpMutexAttributes : Mutex의 보안속성을 지정, 주로 상속관계를 지정하기 위해 사용, 일반적으로 NULL
- blnitialOwner : 생성시 사용권한을 갖을것인지 여부,
- lpName : Mutex의 이름, Mutex 이름을 아는 다른 프로세스와의 동기화 가능, 유니크한 이름 지정.

CreateMutex는 생성한 Mutex의 핸들을 리턴하고
같은 이름의 Mutex가 생성되어 있을 경우 해당 뮤텍스 핸들을 리턴
GetLastError()로는 ERROR_ALREADY_EXIST값을 얻을수 있고
Mutex에 접근할 수 있는 권한이 없는 경우 (ERROR_ACCESS_DENIED)NULL 을 리턴한다.

이를 통해 위 소스를 이용하여 중복실행 방지를 할수 있는 것이다.
중요한것은 CreateMutex()를 통해 Mutex의 핸들을 리턴 받은 루틴 후에
GetLastError()를 확인했을때 ERROR_ALREADY_EXIST 값과 같다면 이미 실행되어 있다는 것이고
그렇다면 종료 루틴으로 흘러가게 되고 어플은 종료 되는 것이다.
참고로 게임이나 다중 실행 방지 처리가 되어 있는데 이런방식을 사용했다면 리버싱관점에서
이 부분을 뛰어 넘기면 멀티로더를 제작할수도 있을듯 하다.

반응형

* 커뮤니티 (한국)
http://osxdev.org/      
http://iphoneos.co.kr/       


* 블로그 (한국)
Lingo *  http://nabiri.tistory.com/
http://wangsy.com/blog/
Jenix  http://jinhyung.org/  코코아 프로그래밍
http://i-dreaming.com/  예제로


* 아이폰 어플 제작소 (한국)
http://xevious7.com/  FreshWater Aquarium
http://vanillabreeze.com/  Maneki Neko, Crack LCD, Ruler Deluxe, Hypnotized!, iSurprise
http://orclab.com/  iPuzzle, Touch up
http://blog.naver.com/whatisid/  Big Day
http://orchardparty.com/  The GoStop
http://krazyeom.wordpress.com/  Crocodile Dentist
http://imagebakery.tv/iphone/  The Thumb
http://aiart.tistory.com/  Janggi - Korean Chess
http://leopardmac.tistory.com/  Kimchi Recipe
http://cre8ive.tistory.com/  Bounced
http://clearday.tistory.com/  Hard Game, Sakura Clock
http://daummobile.tistory.com/  Daum tvPot
http://sociag.com/  Valentine Flowers
http://onlinegamer.co.kr/  iConductor
http://kkapps.wordpress.com/  GoStop
http://nemustech.com/  iHappyDays
http://alonesworld.blogspot.com/  Love Gauge
http://arouse.cafe24.com/tc/  Brave Prince
http://i-bocom.com/  MyCents
http://zigzix.com/  Zemote
http://iphone.com2us.com/
http://appstore.dreamwiz.com/
http://neohelp.sayclub.com/sayclub/  (IE 전용)
http://iphone_eng.daolsoft.com/
http://www.cbs.co.kr/event/08/radioIpod/
http://truemobile.com/


* 서적
꿈, 희망=아이폰 개발=맥 개발? 코코아부록.pdf http://blog.insightbook.co.kr/107
예제로 시작하는 아이폰 개발 http://acornpub.co.kr/book/iphone-appdev


World
* 아이폰 어플 제작소
http://illusionlabs.com/  Sway, Touchgrind, Labyrinth, iPint


* 개발자 블로그
Jeff Lamarche http://iphonedevelopment.blogspot.com/
Matt Gallagher http://cocoawithlove.com/
Bill Dudney http://bill.dudney.net/roller/ob

 


그래픽 기반의 어플들을 개발하기 쉽게 되어 있습니다.
OpenGL 기반으로 한 와퍼라고 해야할까요.

오픈프레임웍스, openFrameworks for iPhone
http://www.openframeworks.cc/forum/index.php

API 문서
http://www.openframeworks.cc/documentation

 

이폰 게임류의 어플 개발에 최고 라이브러리.
더이상 말이 필요 없습니다.

http://cocos2d.org/

OpenGL 기반
스프라이트 처리, 몇가지 효과들(불, 파티클 등등), 애니메이션 등
이런 것들이 제공되고 있습니다.

[출처] 아이팟 개발 참고 사이트 (모든 가능성의 무한세계) |작성자 시아미즈

아이팟 터치 3세대 32G를 사려고 준비중인 시점에서 구매와 함께 개발에 착수 예정이므로 ㅎㅎ
그냥 예정일 뿐이다 관련 서적과 사이트를 수집하고 있다. 과연 아팟 터치3세대 구매 할것인가...
그리고 어플 개발에 들어갈것인가.. 여건과 시간은 언제나 주어지지 않는다.
다만 나의 의지가 필요 할 뿐이지만.. 마음만 먹어본다.. ㅋ

반응형

출처: http://cbiscuit.info/114

Java API for CVS
전 우주적으로 가장 활발하게 사용하는 버전컨트롤 도구는 아마도 CVS일지도 모른다아니면 MS SourceSafe 정도보다 강력한 상용 형상관리 도구들이 있지만 발주처 빵빵하고 대규모 프로젝트 아니면 만져볼 기회 조차 없는 것이 현실이다또한, 이런 형상관리 도구는 대부분 Open API를 제공한다지금 몸 담고 있는 프로젝트에서도 CVS 써버를 4대로 구성하여 아주 빵빵하게(?) 돌리고 있는데, 이 마저도 느리고 모자라다고 난리다. 가끔 출몰하는 좀비 cvs.exe때문인데, 그 원인은 아직 밝혀내지 못 하고 있다혹시 아시는 분은 바로 댓글 달아주시면 감사하겠다.

아무튼 이야기가 시작하자마자 바로 옆으로 샛는데, 본론은 Java API를 이용한 CVS 핸들링이다.   CVS와 연계하여 시스템적으로 무엇인가 처리해야 할 일이 있으면 아주 유용하게 쓸 수 있어 소개한다


jar 파일 다운 받는 곳
: 여기
ㅁ 관련 싸이트는 : 여기

사용법은 대충 이렇다.

public class CVSUtil {
  
    private static Log log = LogFactory.getLog(CVSUtil.class);
   
    public static void main(String[] args) {
        String destDir = "
체크아웃 받을 디렉토리";
        //
) D:\\cvs_repository\\test  <- \\ 두개 주의 하삼
!
        String location = "CVSROOT";
        //
) :pserver:anoncvs@localhost:/cvs
        String module = "CVS Module";
        //
) /MyModule
       
        CVSUtil.checkout( destDir, location, module);
    }
   
    public static void checkout(String destDir, String location, String module) {
        CVSRoot cvsroot = CVSRoot.parse(location);
        GlobalOptions globalOptions = new GlobalOptions();
        globalOptions.setCVSRoot(cvsroot.toString());
       
        PServerConnection con = new PServerConnection(cvsroot);
       
        Client client = new Client(con, new StandardAdminHandler());
        client.setLocalPath(destDir);
       
        CheckoutCommand checkout = new CheckoutCommand(true, module);
        try {
            client.executeCommand(checkout, globalOptions);
        } catch (Exception e) {
            log.error("", e);
        }
    }
}


다양한 cvs커맨드를 날릴수 있는 api 사용예제이다. .... 몇일을 인터넷을 뒤져서 겨우 찾은....^^

java cvs functions
Checkout from CVS


public void checkoutFromCVS(String userName, String password, String hostName, String repository) throws ExecutionException{
     PServerConnection c = null;
     try {
      logger.info("entering checkOutImages");
     
      String encryptedPassword = StandardScrambler.getInstance().scramble(password);
     
      CVSRoot root = CVSRoot.parse(":pserver:"+userName+"@"+hostName+":"+SC_PORT+repository);
      c = (PServerConnection)ConnectionFactory.getConnection(root);
      
       c.setEncodedPassword(encryptedPassword);     
      
       logger.info("open connection....");
       c.open();     
       logger.info("after open connection");
      
       Client client = new Client(c, new StandardAdminHandler()); 
       GlobalOptions options = new GlobalOptions();
       options.setCVSRoot(":pserver:"+userName+"@"+hostName+":"+SC_PORT+repository);
      
       client.ensureConnection();
      
       CheckoutCommand checkout = new CheckoutCommand(true,SC_MODULE);
       checkout.setPruneDirectories(true);
       File f = new File(SC_CVS_HOME);
       if(!f.exists())
        f.mkdirs();
      
       client.setLocalPath(SC_CVS_HOME);
       client.getEventManager().addCVSListener(new LogCVSListener());
      
       boolean success = client.executeCommand(checkout,options);
       logger.info("cmd checkout execute success:"+success);
       //client.executeCommand(uc, options);
  } catch (CommandAbortedException e) {
   logger.error("command aborted ex:"+e.getMessage());
   throw new ExecutionException(e.getMessage());
  } catch (AuthenticationException e) {
   logger.error("authenticate ex:"+e.getMessage());
   throw new ExecutionException(e.getMessage());
  }catch (CommandException e) {
   logger.error("command ex:"+e.getCause());
   throw new ExecutionException(e.getMessage());
  }   finally {
   if(null != c) {
    try {
     c.close();
    } catch (IOException e) {
     logger.error(e.getMessage());
    }
   }
  }
    }
 



Add to CVS


public void addToCVS(List filesToAdd, File fileToAdd, String userName, String password, String hostName, String repository)throws ExecutionException{
     logger.info("entering addToCVS");
     PServerConnection c = null;
     try {
      String[] children;
       // It is also possible to filter the list of returned files.
       // This example does not return any files that end with `.txt'.
       FilenameFilter filter = new FilenameFilter() {
           public boolean accept(File dir, String name) {
            if(dir.getName().equals("CVS")){
                return false;
               }

               return true;
           }
       };
      children = fileToAdd.list(filter);    
       File f = null;
     
          for (int i=0; i < children.length; i++) {
          
           f = new File(fileToAdd.getAbsoluteFile()+"/"+children[i]);
          
           try {
      logger.info("file:"+f.getCanonicalFile());
      logger.info("is file:"+f.isFile()+" is dir:"+f.isDirectory());
      if(f.isDirectory() ) {
        if(!f.getName().equals("CVS")){
        logger.info("recursive...");      
        filesToAdd.add(f);
        addToCVS(filesToAdd, f, userName, password, hostName, repository);     
        }
      }else {
       filesToAdd.add(f);
      }
           }catch(IOException e) {
            throw new ExecutionException(e.getMessage());
           }
          }
     
          if(filesToAdd.size() == 0) {
           logger.info("nothing to add....");
           return;
          }
         
      String encryptedPassword = StandardScrambler.getInstance().scramble(password);
     
      CVSRoot root = CVSRoot.parse(":pserver:"+userName+"@"+hostName+":"+SC_PORT+repository);
      c = (PServerConnection)ConnectionFactory.getConnection(root);
      
       c.setEncodedPassword(encryptedPassword);     
      
       logger.info("open connection....");
       c.open();     
       logger.info("after open connection");
      
       Client client = new Client(c, new StandardAdminHandler());       
            
       GlobalOptions options = new GlobalOptions();
       options.setCVSRoot(":pserver:"+userName+"@"+hostName+":"+SC_PORT+repository);          
      
      
       AddCommand add = new AddCommand();           
       add.setMessage("adding images for site portal...");
       add.setKeywordSubst(KeywordSubstitutionOptions.BINARY);
       logger.info("file path:"+fileToAdd.getPath());
       logger.info("file parent:"+fileToAdd.getParent());
       client.setLocalPath(SC_DIR_TO_SAVE);
       client.ensureConnection();
      
       add.setFiles((File[])filesToAdd.toArray(new File[filesToAdd.size()]));
       client.getEventManager().addCVSListener(new LogCVSListener());
      
       logger.info("executing command...");     
       boolean success = client.executeCommand(add,options);
       logger.info("cmd add execute success:"+success);
                                   
  } catch (CommandAbortedException e) {
   logger.error("command aborted ex:"+e.getMessage());
   throw new ExecutionException(e.getMessage());
  } catch (AuthenticationException e) {
   logger.error("authenticate ex:"+e.getMessage());
   throw new ExecutionException(e.getMessage());
  }catch (CommandException e) {
   logger.error("command ex:"+e.getMessage());
   throw new ExecutionException(e.getMessage());
 
  }finally {
 
   if(null != c) {
    try {
     c.close();
    } catch (IOException e) {
     logger.error(e.getMessage());
    }
   }
  }
     logger.info("leaving addToCVS");
    }
   



Commit to CVS


    public void commitToCVS(File fileToCommit, String userName, String password, String hostName, String repository) throws ExecutionException{
     PServerConnection c = null;
     try {
      logger.info("entering commitToCVS");
     
      String encryptedPassword = StandardScrambler.getInstance().scramble(password);
     
      CVSRoot root = CVSRoot.parse(":pserver:"+userName+"@"+hostName+":"+SC_PORT+repository);
      c = (PServerConnection)ConnectionFactory.getConnection(root);
      
       c.setEncodedPassword(encryptedPassword);     
      
       logger.info("open connection....");
       c.open();     
       logger.info("after open connection");
      
       Client client = new Client(c, new StandardAdminHandler()); 
       GlobalOptions options = new GlobalOptions();
       options.setCVSRoot(":pserver:"+userName+"@"+hostName+":"+SC_PORT+repository);
      
      
       client.ensureConnection();
                              
       client.getEventManager().addCVSListener(new BasicListener());
      
       //File file = new File(SC_CVS_HOME+"\\"+SC_MODULE+"\\resize_needed\\"+SC_TESTER);
       File afile[] = new File[] { fileToCommit };
      
       CommitCommand commit = new CommitCommand();      
             commit.setMessage("auto commit adding to cvs...");
             commit.setFiles(afile);
            
            
             commit.setForceCommit(true);
            
       client.getEventManager().addCVSListener(new LogCVSListener());
       client.setLocalPath(SC_DIR_TO_SAVE);
      
       logger.info("executing command...");
       boolean success = client.executeCommand(commit,options);
       logger.info("cmd commit execute success:"+success);

       //client.executeCommand(uc, options);
   }catch (CommandAbortedException e) {
    logger.error("command aborted ex:"+e.getMessage());
    throw new ExecutionException(e.getMessage());
   }catch (AuthenticationException e) {
    logger.error("authenticate ex:"+e.getMessage());
    throw new ExecutionException(e.getMessage());
   }catch (CommandException e) {
    logger.error("command ex:"+e.getCause());
    throw new ExecutionException(e.getMessage());
   }   finally {
    if(null != c) {
     try {
      c.close();
     } catch (IOException e) {
      logger.error(e.getMessage());
     }
    }
   }
   logger.info("leaving commitToCVS");
    }



InnerClass LogCVSListener


static public class LogCVSListener implements CVSListener {
              protected CVSCommandResult result = new CVSCommandResult();
              protected Logger logger  = Logger.getLogger(LogCVSListener.class.getName());
              public LogCVSListener() {
              }
             
              /***
               * @return Returns the result.
               */
              public CVSCommandResult getResult() {
                  return this.result;
              }
             
              /*
               * (non-Javadoc)
               *
               * @see org.netbeans.lib.cvsclient.event.CVSListener#messageSent(org.netbeans.lib.cvsclient.event.MessageEvent)
               */
              public void messageSent(MessageEvent e) {
                  if (e.isError()) {
                      logger.error(e.getMessage());
                      // permet de stocker les traces
                      result.getTrace().append(e.getMessage() + "\n");
                  } else {
                      logger.info(e.getMessage());
                  }
              }
     
              /*
               * (non-Javadoc)
               *
               * @see org.netbeans.lib.cvsclient.event.CVSListener#messageSent(org.netbeans.lib.cvsclient.event.BinaryMessageEvent)
               */
              public void messageSent(BinaryMessageEvent e) {
                  logger.info(e.getMessage());
              }
     
              /*
               * (non-Javadoc)
               *
               * @see org.netbeans.lib.cvsclient.event.CVSListener#fileAdded(org.netbeans.lib.cvsclient.event.FileAddedEvent)
               */
              public void fileAdded(FileAddedEvent e) {
                  logger.debug("File has been added.");
                  result.getFileAdded().add(e.getFilePath());
              }
     
              /* (non-Javadoc)
               * @see org.netbeans.lib.cvsclient.event.CVSListener#fileToRemove(org.netbeans.lib.cvsclient.event.FileToRemoveEvent)
               */
              public void fileToRemove(FileToRemoveEvent e) {
                  logger.debug("File to remove: " + e.getFilePath());
                  //result.getFileToRemove().add(e.getFilePath());
                 
              }
     
              /*
               * (non-Javadoc)
               *
               * @see org.netbeans.lib.cvsclient.event.CVSListener#fileRemoved(org.netbeans.lib.cvsclient.event.FileRemovedEvent)
               */
              public void fileRemoved(FileRemovedEvent e) {
                  logger.debug("File is removed: " + e.getFilePath());
              }
     
              /*
               * (non-Javadoc)
               *
               * @see org.netbeans.lib.cvsclient.event.CVSListener#fileUpdated(org.netbeans.lib.cvsclient.event.FileUpdatedEvent)
               */
              public void fileUpdated(FileUpdatedEvent e) {
                  logger.debug("File has been updated");
                  result.getFileUpdated().add(e.getFilePath());
              }
     
              /*
               * (non-Javadoc)
               *
               * @see org.netbeans.lib.cvsclient.event.CVSListener#fileInfoGenerated(org.netbeans.lib.cvsclient.event.FileInfoEvent)
               */
              public void fileInfoGenerated(FileInfoEvent fileInfoEvent) {
                  logger.debug("File status information has been received");
                  // Avec le diffInfo, possibilité de gestion plus fine des différences.
                  // DiffInformation diffInfo =
                  // ((SimpleDiffBuilder)fileInfoEvent.getSource()).createDiffInformation();
                  result.getFileInfo().add(fileInfoEvent.getInfoContainer());
              }
     
              /*
               * (non-Javadoc)
               *
               * @see org.netbeans.lib.cvsclient.event.CVSListener#commandTerminated(org.netbeans.lib.cvsclient.event.TerminationEvent)
               */
              public void commandTerminated(TerminationEvent e) {
                  if (e.isError()) {
                      logger.error("Server responses has error");
                      result.setError(true);
                  } else {
                      logger.debug("Server responses has OK");
                  }
              }
     
              /*
               * (non-Javadoc)
               *
               * @see org.netbeans.lib.cvsclient.event.CVSListener#moduleExpanded(org.netbeans.lib.cvsclient.event.ModuleExpansionEvent)
               */
              public void moduleExpanded(ModuleExpansionEvent e) {
                  // ne fait rien
              }
     
          }


반응형

g4j - GMail API for Java

GMailer API for Java (g4j) is set of API that allows Java programmer to communicate to GMail. With G4J programmers can made Java based application that based on huge storage of GMail.

An Email application, GMailer for Java is also built to demonstrate the usage of the API. It is planned to include minimalist email capabilities such as browse, search, read, send mail and download attachment.

This software is distributed in GNU General Public Lincense (GPL).

Download

The g4j package includes the library, the Email application and javadocs. The g4j-deps package is required if you want to compile g4j. Current version of API is 0.3.12 and Email application is 0.3.4.

For latest source code you can Browse CVS Repository or get the CVS by:

cvs -d:pserver:anonymous@cvs.sourceforge.net:/cvsroot/g4j login

cvs -z3 -d:pserver:anonymous@cvs.sourceforge.net:/cvsroot/g4j co src

Check the project statistics, woo we've made 10000+ lines of code in a month!

Release Notes 0.3.12

G4J finally support the new contact list interface! (read only)

Matthias fix bug in GMailer that scroll the message to bottom. He have also added open browser function, the links in messages now clickable!

You would need Java Runtime Environment (JRE) to run this software, download it in http://java.sun.com/

To use the software, run g4j.bat on Windows or g4j.sh on Unix. To Use the library include the g4j-lib.jar in your programs.

If you encounter error message: "sun.security.validator.ValidatorException: No trusted certificate found" while connecting gmail, please read the solution.

This program is developed mainly in Windows XP & 2000, it have not been tested on other platforms. If you encounter any problem please post a message in project support page.

G4J

Set of API that allows Java programmer to communicate to GMail. API is avaliable online.

  • Version 0.3.11 - (15-Oct-2004)
    Fixed: Support the new gmail contact interface, GMContact structure changed, new function GMConnector.getContact() replace old requestContact()
  • Version 0.3.10 - (7-Oct-2004)
    Added: GMConnector.fetchOriginalMail(String id) added, download original mail source from gmail
    Added: Preliminary support of send mail.
    Bugfix: "Drafts" mail now being prased correctly
  • Version 0.3.9 (5-Oct-2004)
    Update: GMail new mailbox "Drafts" supported
  • Version 0.3.4 (27-Sep-2004)
    Features: With multi-threaded http client, single connector can send multiple request at the same time
    Features: Parse the java script redirection in request()
  • Version 0.3.3 (22-Sep-2004)
    Bug Fix: Correctly parse escaped characters such as ' " < > \n and \r;
    Features: Implement missing "message body" packets in entries in conversation
  • Version 0.3 (18-Sep-2004)
    API to download conversation and open attachment as InputStream
  • Version 0.2
    API to retrive threads from mailbox/label and search message
  • Version 0.1
    API to connect to GMail

GMailer for Java

Minimalist Email client that retive email from Gmail.

Features:

  • Check and monitor mailboxes
  • Read mail
  • Search mail
  • Minimized to SysTray in Windows and Linux KDE3
  • Message saved to local disk and can be read later offline
  • Version 0.3.4
    (16-Oct-2004)
    Added: Open gmail home page (like original gmail notifier)
    Added: Open links in message
    Bugfix: Scroll to buttom when open a message
  • Version 0.3.3
    (15-Oct-2004)
    Added: Search messages
    Bugfix: Show offline message list correctly
    Bugfix: Click the sys tray icon before the program completely loaded, the program would popup and behave strangly
    Enhance: new toolbar buttons for better looks, across different platform/LAF
  • Version 0.3.2
    (7-Oct-2004)
    Added: Debug console
    Bugfix: Fix the problem that when exit without login, the software might not exiting properly.
    Bugfix: "Drafts" mail now being displayed correctly
  • Version 0.3.1
    (5-Oct-2004)
    Update: GMail new mailbox "Drafts" supported
  • Version 0.3 (3-Oct-2004)
    - BUGFIX: Reformat the message pane so that user can use mouse wheel to scroll message content.
    - ENHANCEMENT: improved performance to apply a LAF
  • Version 0.3-pre3 (1-Oct-2004)
    - FEATURES: Look and Feel chooser avaliable in option, features JGoodies Look and feel and theme
    - ENHANCEMENT: Show or hide message content using a better method, preformance improved
    - BUGFIX: Correctly disable menu items/toolbar buttons
  • Version 0.3-pre2 (27-Sep-2004)
    If a message is already downloaded, now GMailer read message from local disk instead of download again
    With multi-threaded g4j api and rewritten usage of threads, the general performance is improved
    Correct the tooltips of the systray icon
  • Version 0.3-pre1 (26-Sep-2004)
    Save data to local drive, the programs now can work offline to read downloaded message.
    Rewrite UI, now looks more comfortable. Add serveral icons, partly from Eclipse and others are draw by me.
  • Version 0.21 (22-Sep-2004)
    Open message body (partly)
  • Version 0.2 (18-Sep-2004)
    Added support of minimized to SysTray in Windows and KDE3; Support of auto connect and check message and various UI fix (18-Sep-2004)
  • Version 0.1
    This version connect to GMail and listing mailboxes. Searching, Viewing email and download attachment would be included in future release.

Acknowledgement

This project is inspried and motivated by GMailer for PHP and Gmail Agent API , their great works make me want to have an Java Implementation of their kind. Their open sources also made the understanding of GMail's protocol much easier, Thank You!

This project is not possible without following open source softwares:

  • Apache Jakarta Commons HTTPClient to access web page
  • Apache Jakrata Commons Codec to decode email
  • SysTray for Java to make the System Tray tricks
  • SIXBS (Simple XML Bean Serialization) from tagtraum industries, for saving document in XML
  • JGoodies for better UI looks
  • Concurrent Utilities from Doug Lea
  • BeanShell for embbed scripting engine
  • Eclipse for their nice icons
  • Google for their GMail, of course

Support and Contribution

If you have any problem, opinion, or software that built on g4j, please tell me via email or Sourceforge Forum!

Thanks Teodor and Samanth to join this project! They would help me to make GMailer more usable and I can focus more on the G4J API.

If you can join us, send me an email. You can also browse the todo list and give us suggestions!

Related Projects

  • Rishabh made gavamail , a POP3 inetrface for gmail in Java

About Me

I am a tiny programmer in a big enterprise in Hong Kong.

Read my blog in www.siuying.net ( Chinese Content )

[출처] g4j - GMail API for Java|작성자 후니


반응형





우선 OS에 자바가 설치 되어 있어야 한다. 무엇인지 모르거나 설치되어 있지 않다면.. Java 다운
설치되어 있다면  JRE 6 update 10 이상으로 업데이트 해서 사용하길 바란다.
투명도 적용이나 룩앤필 적용에 문제가 없기 위해서 이다.. 이전 버전은 제대로 동작하지 않을수 있다.

수정사항
- 룩앤필을 좀더 다양하게 변경할수 있도록 했다.
- 투명도를 조절할수 있게 하였다.
- 설정파일을 XML 로 변경.

+ Recent posts