2016/11/04

Free Delphi/C++ Builder 10.1 Berlin Starter Edition

Embacadero 사에서 그동안 유로로 배포해오던 Delphi/C++ Builder 10.1 Berlin Starter Edition을 무료로 공개하였다. 특별 제공이라 하는데 기한이 있는지는 모르겠다.

다운로드 경로
Delphi: https://www.embarcadero.com/products/delphi/starter/promotional-download
C++ Builder: https://www.embarcadero.com/products/cbuilder/starter/promotional-download

경로는 다르나 동일 파일인 것 같다. 아직 설치는 하지 않았지만 인터넷이 연결된 상태에서 설치가 가능할 파일로 설치시 패키지를 설정하는 것 같다.

다운로드를 위해서는 Embarcadero Developer Network (EDN)에 가입이 되어 있어야 한다. 가입이 되어 있지 않을 경우 간단한 가입 절차를 거쳐 다운로드 할 수 있으며 가입된 메일 계정으로 설치에 필요한 키가 전달이 된다.

Embacadero 사가 Starter 버전을 무료로 배포하는 이유는 아무래도 경쟁사 제품을 의식해서인듯 하다. 개발툴의 저변 확대를 노리고 있을테지만 그리 큰 효과를 볼 수는 없을 것 같다.
경쟁제품이라 할 수 있는 MS사의 Visual Studio는 아주 오래전부터 Express 버전을 제공해 왔고 얼마전부터는 거의 모든 기능을 포함하고 있는 Community 버전을 개인에 한하여 무료로 제공하고 있었다.
Embacadero 사의 Starter 버전은 얼마되지 않았으며 그 동안 유료(Delphi - $320.2, C++ Builder - $238.7)로 배포되고 있었다. 게다가 이번에 무료로 공개하는 Embacadero 사의 Starter 버전의 기능 제한이 매우 많아 보인다. MS의 Visual Studio Community 버전의 경우 일반 개발에 필요한 대부분의 기능을 사용할 수 있지만 Embacadero 사의 Starter 버전은 대부분의 기능을 사용하지 못 한다. 할 수 있는 것이라고는 윈도우에서 32비트 Application 개발에만 사용할 수있다.

아래 제품 비교표를 보면 쉽게 알 수 있다.
Visual Studio: https://www.visualstudio.com/vs/compare/
Delphi: https://www.embarcadero.com/products/delphi/product-editions
C++ Builder: https://www.embarcadero.com/products/cbuilder/product-editions

Community 버전을 생각하고 다운을 받았는데 확인해보니 그렇지 않아 설치를 망설이고 있다.
아마 하지 않을 것 같다.

2016/11/03

Using CEF(Chromium Embedded Framework) with MFC Part2

이전 글(http://neodreamer-dev.blogspot.kr/2016/11/UsingCEFwithMFCPart1.html)에 기록한대로 만든 libcef_dll_warpper.dll 을 테스트하여 보았다.
테스트에 사용된 코드는 인터넷에서 CEF 사용 방법을 찾아 돌아다니다 얻은 여러 코드를 조합하여 작성한 코드인데 출처가 기억이 나지 않는다.
단순히 CEF를 올리고 구글 페이지로 접속을 하는 코드이다.
프로젝트는 다이얼로그 기반으로 기본 컨트롤을 모두 삭제하고 브라우저를 생성하기 위해 Static  컨트롤 하나만 올린 상태이다.


//////////////////////////////////////////////////////////////////////////
// CEF
//#define CEF_USING_SANDBOX
#include "include/cef_app.h"
#include "include/cef_client.h"

//* CEF_3.2840.1511
 #ifdef _WIN64
  #ifdef _DEBUG
    #pragma comment(lib, "../CEF_3.2840.1511/bin_x64/Debug/libcef.lib")
    #ifdef CEF_USING_SANDBOX
      // MT Only
      #pragma comment(lib, "../CEF_3.2840.1511/lib_x64/Sandbox/Debug/libcef_dll_wrapper.lib")
    #else
      #ifdef _DLL
        // MD
        #pragma comment(lib, "../CEF_3.2840.1511/lib_x64/Debug/libcef_dll_wrapper_mdd.lib")
      #else
        // MT
        #pragma comment(lib, "../CEF_3.2840.1511/lib_x64/Debug/libcef_dll_wrapper_mtd.lib")
      #endif
    #endif
  #else // Release
    #pragma comment(lib, "../CEF_3.2840.1511/bin_x64/Release/libcef.lib")
    #ifdef CEF_USING_SANDBOX
      // MT Only
      #pragma comment(lib, "../CEF_3.2840.1511/lib_x64/Sandbox/Release/libcef_dll_wrapper.lib")
    #else
      #ifdef _DLL
        // MD
        #pragma comment(lib, "../CEF_3.2840.1511/lib_x64/Release/libcef_dll_wrapper_md.lib")
      #else
        // MT
        #pragma comment(lib, "../CEF_3.2840.1511/lib_x64/Release/libcef_dll_wrapper_mt.lib")
      #endif
    #endif
  #endif
#else
  #ifdef _DEBUG
    #pragma comment(lib, "../CEF_3.2840.1511/bin_x86/Debug/libcef.lib")
    #ifdef CEF_USING_SANDBOX
      // MT Only
      #pragma comment(lib, "../CEF_3.2840.1511/lib_x86/Sandbox/Debug/libcef_dll_wrapper.lib")
    #else
      #ifdef _DLL
        // MD
        #pragma comment(lib, "../CEF_3.2840.1511/lib_x86/Debug/libcef_dll_wrapper_mdd.lib")
      #else
        // MT
        #pragma comment(lib, "../CEF_3.2840.1511/lib_x86/Debug/libcef_dll_wrapper_mtd.lib")
      #endif
    #endif
  #else // Release
    #pragma comment(lib, "../CEF_3.2840.1511/bin_x86/Release/libcef.lib")
    #ifdef CEF_USING_SANDBOX
      // MT Only
      #pragma comment(lib, "../CEF_3.2840.1511/lib_x86/Sandbox/Release/libcef_dll_wrapper.lib")
    #else
      #ifdef _DLL
        // MD
        #pragma comment(lib, "../CEF_3.2840.1511/lib_x86/Release/libcef_dll_wrapper_md.lib")
      #else
        // MT
        #pragma comment(lib, "../CEF_3.2840.1511/lib_x86/Release/libcef_dll_wrapper_mt.lib")
      #endif
    #endif
  #endif
#endif
//*/
//////////////////////////////////////////////////////////////////////////

BOOL CTestCEFinMFCDlg::DestroyWindow()
{
  CefShutdown();

  return CDialogEx::DestroyWindow();
}

BOOL CTestCEFinMFCDlg::OnInitDialog()
{
  :
  CRect rcBrowser;
  GetDlgItem(IDC_STATIC_BROWSER)->GetClientRect(&rcBrowser);

  //Create the necessary objects needed to initialize CEF 
  CefMainArgs cefMainArgs(theApp.m_hInstance);

  CefSettings cefSettings;
  CefBrowserSettings cefBrowserSettings;
  CefRefPtr<CefApp> cefApplication;
  CefWindowInfo cefWindowinfo;

  cefSettings.multi_threaded_message_loop = true; //needed for MFC projects (unless we want to implement custom message-loop)
  cefWindowinfo.SetAsChild(GetDlgItem(IDC_STATIC_BROWSER)->GetSafeHwnd(), rcBrowser);

  //   CefRefPtr<CefClient> client(new ClientHandler());
  //   m_Handler = (ClientHandler*)client.get();

  //Initialize CEF 
  bool bSucceeded = CefInitialize(cefMainArgs, cefSettings, cefApplication, nullptr);
  CefRefPtr<CefRequestContext> request_context;

  CefRefPtr<CefClient> client;
  if (bSucceeded)
  {
    CefBrowserHost::CreateBrowser(cefWindowinfo, client, L"http://www.google.com/", cefBrowserSettings, request_context);
  }  
  :
}


Using CEF(Chromium Embedded Framework) with MFC Part1

Using CEF(Chromium Embedded Framework) with MFC Part1

MFC를 이용하여 Application을 만들 때 Windows 기본 브라우저 말고 크롬을 올리기 위해 방법을 찾아 보았다.
Chromium Embedded Framework(이하 CEF) 라는 프로젝트를 찾았고 현재 버전 3까지 나와 있다. CEF를 MFC 프로젝트에 사용을 하려면 libcef_dll_wrapper.dll을 만들어야 한다.
이때, 컴파일러 옵션중 Runtime Library 설정에 따라 사용할 수 있는 libcef_dll_wrapper.dll을 만들어야 한다. 라이브러리를 만들 때 Sandbox 사용 설정 여부에따라 만들어진 라이브러리의 사용에 제한이 있는 것 같았다. 우선 Sandbox 설정을 제외하고 빌드 해 보았다.
빌드를 하는 방법은 어렵지 않으나 나중에 참고하기 위해 정리를 하였다.

libcef_dll_wrapper.dll를 만들기 위해서는 CEF Automated Builds 사이트(http://opensource.spotify.com/cefbuilds/index.html)에서 소스를 다운 받는다. 그리고 빌드 환경을 구성할 CMake 를 준비한다.
글을 작성하는 현재 버전은 CEF 3.2840.1512.g3f66e81(Chromium 54.0.2840.59) 이고, 빌드에 사용된 버전은 CEF 3.2840.1511.gb345083(Chromium 54.0.2840.59) 이다.
사용하고자 하는 버전과 일치하는 Standard Distribution 을 다운 받아 압축을 해제한다.
CMake를 실행하여 소스 경로에 압축을 해제한 경로를 설정하고 Build the binaries 경로에 프로젝트를 생성한 경로를 설정한고 Configure를 신행한다.
많은 설정 중 마지막에 있는 USE_OFFICIAL_BUILD_SANDBOX, USE_SANDBOX 설정을 해제한다.
해제하지 않을 경우 만들어 지는 프로젝트는 Runtime Library 옵션이 /MT 로 고정이 된다. 다른 옵션을 만들어 테스트해 보았지만 기존의 만들어진 cef_sandbox 라이브러리가 /MT 옵션으로 고정되어 있어서인지 다른 설정으로 바꾸면 프로젝트를 빌드 할 때 링크 에러가 발생하여고 빌드가 되지 않았다.
Sandbox를 사용하지 않는 경우에는 여러 Runtime Library에 대한 사용에 문제가 없었다. Sandbox 이용에 대해서는 나중에 좀 더 확인을 해 봐야겠다.
설정을 마치고 Configure 를 실행 한 후 Generate를 실행하여 프로젝트를 생성한다.

그리고 Build the binaries 경로에있는 cef.sln 을 Visual Studio로 열어 libdef_dll_wrapper 프로젝트의 속성 페이지를 열어 추가하고자 하는 프로젝트와 동일한 Runtime Library 옵션을 선택하고 빌드한다.
본인의 경우 /MD /MDd /MT /MTd 옵션을 각각 설정하고 출력 파일 이름을 달리하여 추후 사용할 때 골라서 사용할 수 있도록 빌드하였다. 그래서 만들어진 파일이 아래 파일들이다.
libcef_dll_wrapper_mtd.pdb
libcef_dll_wrapper_mdd.lib
libcef_dll_wrapper_mtd.lib
libcef_dll_wrapper_mdd.pdb
libcef_dll_wrapper_mt.lib
libcef_dll_wrapper_md.lib

이 파일들을 이용하여 MFC 프로젝트에 CEF를 사용하면 된다.