CEF - мощнейший продвинутый открытый кросплатформенный фреимворк, созданный в качестве пользовательской обвертки над открытым браузером Chromium, который позволяет встраивать браузер в свои приложения. Сам фреимворк написан на С++ однако наиболее популярны биндинги под разные популярные языки. В основном самые развивающиеся на сегодня это биндинги для C#, среди них CefSharp, Chromium FX, CefGlue. Также есть биндинг под Python2 от поляка Czarek Tomczak, но он уже год как заброшен, хотя в текущих планах автора есть его обновление до новой версии Chromium и поддержка Python3.4-3.5.

Не зависимо от языка все биндинги используют DLL-ку libcef.dll (и еще несколько файлов включая всякие ресурсы). Несмотря на то что фреимворк дает возможность на уровне биндингов настраивать много полезнейших настроек, и переопределить пользователю кучу обработчиков, иногда все же возникает необходимость подпилить небольшую часть брауза под свои нужды. Собственно в статье пойдет речь о самом главном - как собрать этот CEF. Собирать на этот раз мы будем в Windows.

Сборка фреимворка весьма привередлива так как включает в себя и сборку самого Chromium, следственно нужно выдержать и требования к нему. Но я постараюсь сэкономить вам время и более кратко рассказать все шаги и требования.  При сборке вам обязательно понадобится 64-битная система, начиная с 7ки, обязательно установить английский язык системы (локаль). Перед установкой также рекомендуется выключить анти-вирус и индексирование виндовс. Еще убедитесь что на рабочем диске не менее 40 ГБ свободного места (Собранный вариант конечно будет небольшим, но сам процесс сборки требует огромногом места на диске и создает кучу как мелких так и больших файлов). Не выполнив этих простых требований можно впустую потратить несколько часов. В принципе все можно делать на виртуалке, но в данном случае, пожалуй, будет предпочтительней ОС на железе так как процесс сборки и без того очень долгий, на старых компьютерах может занять день - два. Далее вам нужно:

1) Установить Visual Studio 2013, подойдет бесплатный выпуск Community, но обязательно не ниже Update 4. Также нужно установить Win8.1 SDK.  Вообще требования к среде зависят от версии CEF которую вы будете собирать, см таблицу в разделе "Release Branches" тут. Кстати на этой странице находится весь гайд по сборке, который я пересказываю в этой статье. Я буду собирать 2454 версию (версия CEF - это ветка в его репозитарии), основанную на 45ом хроме и выпущенную в июле 2015 потому что поддержка 47ой разными биндингами еще остается "сырой" а 49ая и вовсе многими не поддерживается:

2) Теперь создадим файл pre_env.bat в каталоге сборки, который настроит среду в рабочей консоле (cmd).

set DEPOT_TOOLS_WIN_TOOLCHAIN=0
set GYP_GENERATORS=ninja,msvs-ninja
set GYP_MSVS_VERSION=2013

Саму сборку или пересборку всегда нужно начинать с запуска этого файла.

3) Скачайте файл automate-git.py в каталог сборки. Для запуска этого скрипта вам понадобится python, так что установите его если у вас его еще нет. Я использую Python 3.4.3 64-бит.

4) Выполните pre_env.bat, и затем начните сборку следующей коммандой:

automate-git.py --download-dir=download --branch=2454 --force-build

Если python не в PATH, можете просто перед коммандой добавить c:\Python34\python.exe  (с пробелом).

Эта комманда запускает загрузку и сборку последней ревизии в ветке 2454. Посмотреть какие есть ревизии можно, например в репозитории собранных сборок на https://cefbuilds.com/. Обычно требования к ревизии выдвигает биндинг, например я собираюсь использовать биндинг на C# ChromiumFX версии 3.2454.2, в описании которого сказано что эта его версия нуждается в ревизии 1344 - CEF 3.2454.1344 (эту инфу можно найти в файле CefVersion.txt репозитория ChromiumFX). Идем на https://cefbuilds.com/#branch_2454 и видим что ревизия последняя (остальные видны нажав More revisions), значит все ок.

Но что если нужна непоследняя ревизия ветки. Например когдато я использовал CefSharp которому нужна была CEF 3.2272.2035. Перейдя на https://cefbuilds.com/#branch_2272 и раскрыв "More revisions" мы действительно можем убедится что такая ревизия есть. Но вот указывать ее в automate-git.py мы не можем. Зато мы можем указывать хеш коммита на который нужно перейти перед сборкой. Хеш коммита для новых веток уже виден прям на cefbuilds.com через точку после номера ревизиии, например ревизия 1342 ветки 2454 находится в коммите с хешем g4e94f47: 2015-10-20 CEF 3.2454.1342.g4e94f47

Для более старых веток (наприер 2272)  хеша нет поскольку тогда еще использовался SVN портирования репозитория на GIT это соответствие ревизий приходится искать самому тут https://bitbucket.org/chromiumembedded/cef/commits/branch/2272 и выполнив Ctrl+F нати 2035 и получить f51610d. automate-git в случае с кастомной ревизией нужно вызвать так:

automate-git.py --download-dir=download --branch=2272 --force-build --checkout=f51610d

5) Как я писал выше сама сборка может длиться очень долго так что будьте терпеливыми. Первую половину (примерно) времени вы будете видеть:

[прошло времени] Still working on:
[прошло времени] src

У меня на 4-х ядерном Core i7 с гиперпоточностью и рабочим каталогом на SSD этот этап закончился лишь спустя три часа. Дальше еще столько же времени заняли следующие этапы.

После сборки вы должны получить точно такой же пакет файлов который можете скачать с cefbuilds.com. Они будут лежать в download\chromium\src\cef\binary_distrib\.

Само изменение в коде зависит от ваших задач. Мне нужно было убарть изменение курсора мышки при запуске очередного процесса браузера. Дело в том что создание любого процесса в Windows изменяет на небольшое время курсор, а что бы этого не происходило необходимо в функцию CreateProcess передать флаг STARTF_FORCEOFFFEEDBACK. При помощи grep  мне удалось найти два CreateProcess и я внес следующие изменения:

/cygdrive/e/cefbuild/download/chromium/src $ git diff base/process/launch_win.cc
warning: LF will be replaced by CRLF in base/process/launch_win.cc.
The file will have its original line endings in your working directory.
diff --git a/base/process/launch_win.cc b/base/process/launch_win.cc
index fa59f1a..26322e1 100644
--- a/base/process/launch_win.cc
+++ b/base/process/launch_win.cc
@@ -154,6 +154,7 @@ Process LaunchProcess(const string16& cmdline,
   if (options.empty_desktop_name)
     startup_info->lpDesktop = const_cast(L"");
   startup_info->dwFlags = STARTF_USESHOWWINDOW;
+  startup_info->dwFlags |= STARTF_FORCEOFFFEEDBACK;
   startup_info->wShowWindow = options.start_hidden ? SW_HIDE : SW_SHOW;

   if (options.stdin_handle || options.stdout_handle || options.stderr_handle) {
@@ -311,7 +312,8 @@ bool GetAppOutput(const StringPiece16& cl, std::string* output) {
   start_info.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
   start_info.hStdError = GetStdHandle(STD_ERROR_HANDLE);
   start_info.dwFlags |= STARTF_USESTDHANDLES;
-
+  start_info.dwFlags |= STARTF_FORCEOFFFEEDBACK;
+
   // Create the child process.
   PROCESS_INFORMATION temp_process_info = {};
   if (!CreateProcess(NULL,
(END)

После внесения необходимых изменений в исходный код вы должны заново запустить automate-git.py с теми же ключами из той же дириктории и он сам поймет какие объектные файли нужно пересобрать и что перелинковать при этом заняв значительно меньшее время.

На этом все, удачной сборки!