Не обязательно отдельным, если использовать vertex color, то можно обойтись тем же шейдером, расположив uv так, чтобы весь квад оказался заполненным.
Декларативное описание разметки – не слишком уникальная фишка, есть разные движки, которые имеют такую возможность. Там по крайней мере можно многое подсмотреть.
PS изначально-то у вас что было, не с Flash мигрируете случайно?
В вашем решении буфер индексов никак не связан с дублированием геометрии, у вас сами вершинные данные отличаются флагом (Или флаг и геометрия у вас в разных буферах?). Я имел в виду порядок треугольников: сначала надо писать все треугольники подложки, потом треугольники заливки. Это и должно определить порядок перекрытия.
Interleaving к батчингу отношения не имеет, я говорил об записи всех текстов в один буфер, с уже примененными трансформами. Тогда вообще весь текст будет рисоваться в 1–2 дроукола. Если расположение текстов не активно меняется друг относительно друга, то это может быть эффективно.
Буфер должно быть можно шарить.
А в чем проблема фона? Просто квад, как я понял. Надо только правильно размеры определить. Вообще, вам может готовые движки посмотреть? АПИ уникальный, или изначально с чего-то известного брался, а потом потребовал переноса на GPU?
А и действительно, фрагментный шейдер же должен заполнять в том порядке, в котором треугольники в индексбуфере переданы. У вас геометрия как дублируется, каждая буква по два раза? А если сначала заполнить все индексы окантовки, а потом все индексы заливки?
Идея двух дроколов – сначала отрисовать всю окантовку, потом все заполнение.
Что по перформансу лучше – будет зависеть. В том числе, от юзкейсов. Если текст сам часто меняется, то удвоенная геометрия будет создавать небольшой оверхэд на генерацию, если текст меняется очень редко, то его можно сбатчить в один буфер, даже из разных нод. В этом случае 2 дроукола будут вообще на весь текст.
А зачем геометрию-то два раза пихать? Шейдер, на который я приводил ссылку выше, рисует ровно то же, без дублирования геометрии, и без флага.
Количество drawcall-ов на производительность, конечно, влияет, как и многие другие факторы. Причем, на разном железе, определяющие факторы (ботлнек) могут быть разными. Слепо стремиться к уменьшению количества дроуколов не всегда хорошая идея. Если у вас весь текст на экране рисуется за раз, а не как куча отдельных label, которые сортируются независимо, то экономия в 1 дроукол на всю отрисовку – это не то, на чем стоит фокусироваться.
Если вам нужно решить проблему наслоения в общем виде, то вполне возможно, что стоит рисовать в 2 drawcall, как у автора статьи.
Не решал такой задачи. Сомневаюсь, что есть универсальное хорошее решение. В ситуациях с конкретными обстоятельствами можно подойти творчески. Например, если буквы всегда темнее, и во время их отрисовки они не блендятся с фоном (отрисовка идет спереди или используется отдельный выходной буфер) – можно попробовать GL_MIN из Blend_Equations. Если поизучать ссылку, могут еще какие-то идеи в голову прийти. Главное, не слишком увлекаться. Во-первых, определить, точно ли это является критичным. Если да, то в конечном итоге решение с двумя проходами может оказаться оптимальным – оно достаточно простое, а один лишний drawcall – не то, над чем стоит заморачиваться.
Конечно, можно. Я же говорю, суть SDF-шейдера сводится к тому, чтобы посчитать цвет в зависимости от расстояния до границы символа. Это идеальное же апи, чтобы рисовать окантовку! Если расстояние до границы меньше 0 – рисуем заливку, если больше 0, но меньше толщины обводки – рисуем обводку.
Это будет что-то вроде передать два веса, рассчитать две opacity, а потом
Добавлю: природа MDSF как раз такова, чтобы отображаться одинаково на любых масштабах, размер шрифта в атласе просто регулирует уровень сохраняемой детализации. Поэтому иногда технологию сравнивают с векторными форматами.
От размеров квада на экране зависит следующее. Поскольку в текстуре закодировано не растровое изображение глифа, а расстояние до кривой, его описывающей, то шейдер должен позаботиться о всех аспектах растеризации, в том числе о сглаживании.
Самый простой вариант сглаживания, доступный в шейдере – рисовать пиксели, близкие к границам символа полупрозрачными. Нюанс в том, что шейдер работает в нормализованном пространстве символа. То есть, если мы подбираем параметры, определяющие «достаточно близко к границе», чтобы они примерно равнялись 1 пикселю для квада в 16 экранных пикселей, то на кваде в 64 пикселя это будет выглядеть уже не как сглаживание, а как размытие в 4 пикселя. Видимо, именно это в понимаете под «качеством».
Если весь текст в drawcall одного кегля, то вместе с матрицей можно рассчитывать и параметр сглаживания, передавая его так же в константу. Я делал прототип для произвольных экранных размеров квада так: в вершины писал дополнительно атрибут размеров квада в пикселях, а в шейдере считал параметр сглаживания по логистической кривой.
По тем же принципам определения пикселей вблизи границы, можно рисовать и окантовку – часто пример MSDF-шейдера ее содержит. У вас была какая-то хитрая задумка, которая потребовала рисовать окантовку в отдельный проход?
Спасибо за развернутый пример. Действительно, почти аналог, хоть и с некоторым оверхедом.
Если по-честному, то js-таргет у haxe немного в более привилегированном положении, так как его Sdt (в т.ч. стандартный массив) схож с js-ными по апи, так как исторически был альтернативой as3, который тоже является ECMAScript. Для других таргетов код массива тоже будет включен в сгенерированный.
Родной scala/java массив, который мог бы быть транслирован в js массив, использовать нельзя. Потому что в jvm массивы размеры динамически менять не умеют, а выделить новый массив и поменять ссылку мы не можем, потому что ссылка константная.
Но прелесть haxe как мультитранспилера выражается в том, что мы можем написать
а код в абстрактах для подгонки апи будет инлайниться.
+=следовало бы заменить на + который бы возвращал новый объект Signal
Ненене. Haxe изначально очень практичный и прикладной инструмент, а массовый прикладной код сейчас все-таки пишется императивный-ООП-стайл, и я заходил именно с этой стороны. То есть, ожидается, что я могу отдать куда-то ссылку на сигнал, потом в него что-то напихать, а кто-то по ссылке до напиханного достучится.
Хотя в то же время на haxe можно написать и OCaml-стайл портянку паттернматчина по AST, представленного в виде ADT. Собственно, macro апи для метапрограммирования тоже является отличительной фишкой haxe.
Не имел дел на практике с обоими языками, так что могу быть не точным. Все же разница есть, и может быть существенной ввиду двух факторов:
1. haxe – мультипарадигменный язык с уклоном в ООП, большая часть прикладного кода пишется в императивном ООП-стиле
2. haxe – мультитаргетный транспилятор, одна из широко используемых возможностей – шаринг кодовой базы между целевыми платформами. Написание прикладного кода так, чтобы он работал на всех (нужных) платформах одинаково и эффективно – задача специфическая, решать ее не всегда требуется. Но если все же – то аналогов я не знаю.
Сейчас попробую пояснить. Действительно, один из способов применения абстрактов в haxe – zero-overhead описание алгебры предметной области. То есть, можно описать, что метры*метры = метры квадратные, складывать их между собой можно, а друг с другом – нельзя.
Scala – пожалуй, единственный язык из известных мне, который имеет похожую абстракцию и позволяет писать в императивном стиле. И то – вопрос еще, что получится при транспиляции в js. Как минимум, раньше она тащила с собой жирнющий рантайм в несколько мегабайт.
А при транспиляции хаскеля в js newtype превращается просто в underlying type?
Как бы то ни было, абстракты в хакси могут быть над любым типом, а не только примитивным, у них явно описывается конструктор с произвольным телом. Кроме этого, можно явно управлять способом транспиляции для каждого метода или перегруженного оператора: если в объявлении не указан инлайн, то сгенерируется хэлпер со статическим методом.
У Haxe есть экстерны для описания типов целевой платформы, абстракты – это отличный способ изолировать особенности «нативных» сущностей с разных платформ, добавить к ним некоторое поведение, не внося новых сущностей в целевой код.
То есть в некотором смысле абстракты еще могут быть и альтернативой миксинам/трейтам.
Хороший пример – реализация сигналов. Абстракт над массивом, этакий аналог (почти) invokation list в пару строк и без внесения лишних сущностей в язык.
пилили на HaXe игрухи, которые потом переваривали в JS ES5, было круто, но дебаг и оптимизация производительности периодически были крайне непростыми. В зависимости от происходящего твой класс на HaXe в 20 срок могло переварить в 50 — 300 строк кода на джаваскрипте-пятёрке
И обратное тоже возможно: благодаря dce из 100 строк получить 20.
и когда после языка высокого уровня нужно было лазить в прототипно-ориентированной каше,
Как раз для js там очень прозрачные трансформации, структурно код очень близкий, просто блок может назначаться через свойство prototype. Основное отличие, которое бросалось в глаза – это for трансформирующийся в while с вынесением объявления счетчика, мне кажется это могло быть основной причиной раздувания.
ES6 на классах сейчас тоже поддерживается через флаг компиляции.
разбираясь, что где течёт или много жрёт — иногда морочились днями-неделями, пока полировали игру перед релизом.
Если искать протечки в своем коде, а не в движке, то обилие таргетов может помочь. Искать безудержно аллоцирующие места можно на любой платформе, выбирая по наличию удобных инструментов. Flash в этом весьма хорош, кстати. Быстрая компиляция, быстрый запуск, отличный дебаггер. HxScout есть, работает и для swf, и для c++.
Ещё нравилась сильная система кастования, возможность делать дженерики
Дженериками сегодня никого не удивишь, ADT это уже интереснее, а аналогов абстрактам в популярных языках я и не назову.
и отдельно запомнилось, что у языка 2 null — для скриптовых языков и для статически-типизируемых и динамически-типизируемых языков.
Я бы сказал немного по-другому: haxe старается не вносить оверхэд на ровном месте, поэтому null на haxe превращается в null на целевом языке, а вот его поведение уже определяется природой целевой платформы.
Жаль, что язык представлен в разработках очень нишево
Вот с этим соглашусь, пиарить его особо не кому, кто знает – тихо использует. Кто не знает – думает, «если он такой хороший, что ж я про него не знал до сих пор» и проходит мимо. Поэтому сложнее набирать команду – это риск для бизнеса, замкнутый круг.
К плюсам транспиляции из статически-типизированных языков можно добавить гораздо большие возможности compile-time оптимизаций, в том числе dead code elimination.
Среди примеров можно было бы упомянуть Reason и Kotlin.
Отдельного внимания заслуживает haxe, который тоже обладает полноценной системы типов, хорошим апи для метапрограммирования, но транспилируется не только в js, а еще и в C++, C#, Java, JVM, Python, Lua, PHP, SWF.
Звучит очень интересно. А мобильные клиенты тоже на haxe, openfl-stage3d-away?
А на ризоне у вас для клиента какие-то вещи, типа админок и лобби?
Команда большая? Как сотрудников находите на такой необычный стек?
Добавлю, что компиляторы не только прототипируют. Например, компилятор haxe написан на OCaml.
Причем, haxe частично был вдохновлен: имеет встроенную поддержку метапрограммирования, которая обрабатывает синтаксическое дерево, представленное в виде ADT. Так что его обработка посредством паттерн-матчинга выглядит очень в духе OCaml. nastvood, возможно, слышал об этом языке – в геймдеве он популярнее, чем в других нишах. Кстати, было бы очень интересно узнать чуть больше о вашей компании, я кроме списка игр ничего не смог найти. На чем у вас клиент, например?
Из интересных проектов на OCaml (на Reason, если быть точнее) могу еще отметить Oni2 – гибрид VSCode и Vim с упором на скорость и удобство.
Комментарий был о возможном способе доставки открытого форка массовому потребителю.
Лично я глубоко убежден, что сегодняшняя ненужность флэша – следствие того, насколько долго и настойчиво адоби его закапывали.
Если бы для flash стабильно выходили обновления, а мэинтейнеры не говорили на протяжении долгих лет, что планируют его закрыть, то вряд ли бы он так сдал в популярности. И даже Джобс не был бы ему помехой – на мобилы можно публиковать через Air.
Если учесть отличный тулинг и богатый мультимедийный апи, то вполне возможно, что и многие разработчики продолжили бы держаться этой платформы.
Что до разработчиков браузеров: если технология востребована среди пользователей, то ее поддержка – конкурентное преимущество. И если не пришлось бы расплачиваться безопасностью, то почему не тащить?
Гипотетически, если бы отдали в какой-нибудь солидный Apache Foundation, как произошло с Flex SDK, и нашлись бы мэинтейнеры, готовые иметь дело с уязвимостями – то с течением времени разработчики браузеров могли бы постепенно переползти на открытую версию. Таким образом, обновление пользователям прилетело бы с браузером.
Возможно, частично причина кроется в лицензиях – внутри флэшплеера есть всякие технологии, лицензированные снаружи (кодеки, например), и открывать связанный с ними код – нарываться на иски; а подготовить чистую версию исходников адоби не потянули.
Это не самая удачная ссылка для данного примера, стандартная библиотека языка не реализует flash api, и позволяет использовать его лишь при компиляции в те же самые swf.
Однако, есть и кроссплатформенные реализации практически всего api под haxe: openfl и nme. То есть, сконвертировать as3-проект в haxe и, с последующей доработкой напильником, собрать под мобилы, десктоп и веб – такой шанс есть.
Ну здесь проблема не столько языка, сколько именно русскоязычной вики-статьи, которая концептуально не актуализировалась, наверно, с ее появления. 15 лет назад Haxe появился в качестве альтернативы AS3. Flash-платформа тогда была на пике: плеер в каждом утюге; игры, ютуб, энтерпрайз. Но сам язык уже тогда обладал гораздо более развитой системой типов и кучей других фишек, часть из которых позже стала мэинстримом, и кое-что сверху.
Что до флэша – сейчас это одна из десятки целевых платформ, далеко не самая популярная. Думаю, что трансляция в JS или что-то нативное сейчас используются гораздо чаще.
Рекомендую ознакомиться с англоязычной статьей на вики, она выглядит более актуальной.
Либо он загнется и не надо будет его поддерживать, либо он станет стандартом в геймдеве и надо срочно впиливать его поддержку.
Я бы оценил его шансы не загнуться в обозримом будущем достаточно высоко: инструмент изначально разрабатывался «для себя», и активно используется рядом весьма успешных инди-студий (MotionTwin, Shiro, Proletariat)
А куда предполагается впиливать его поддержку? Он сам кого хочешь поддержит: есть кейсы успешной интеграции с UnrealEngine, Unity, SDL, Node.js, массы браузерных библиотек типа pixi.js и т.д.; поддержка во многих IDE.
Самое забавное, что его используют компании с миллионными оборотами в $, и похоже не особо донатят в фонд т.к. как вы говорите там два землекопа и стажер.
Тут все на удивление прозрачно: на их сайте есть «тарифные планы спонсорства» и список компаний спонсоров (в том числе, уже упомянутых в треде).
К тому же, несмотря на небольшую команду, работа над компилятором ведется весьма активно (гитхаб, все видно). Далеко не факт, что есть потребность раздувании команды. Ну и вообще, «писать компилятор на OCaml» – довольно нишевая позиция, на которую вряд ли есть куча соискателей.
Декларативное описание разметки – не слишком уникальная фишка, есть разные движки, которые имеют такую возможность. Там по крайней мере можно многое подсмотреть.
PS изначально-то у вас что было, не с Flash мигрируете случайно?
Interleaving к батчингу отношения не имеет, я говорил об записи всех текстов в один буфер, с уже примененными трансформами. Тогда вообще весь текст будет рисоваться в 1–2 дроукола. Если расположение текстов не активно меняется друг относительно друга, то это может быть эффективно.
Буфер должно быть можно шарить.
Идея двух дроколов – сначала отрисовать всю окантовку, потом все заполнение.
Что по перформансу лучше – будет зависеть. В том числе, от юзкейсов. Если текст сам часто меняется, то удвоенная геометрия будет создавать небольшой оверхэд на генерацию, если текст меняется очень редко, то его можно сбатчить в один буфер, даже из разных нод. В этом случае 2 дроукола будут вообще на весь текст.
Количество drawcall-ов на производительность, конечно, влияет, как и многие другие факторы. Причем, на разном железе, определяющие факторы (ботлнек) могут быть разными. Слепо стремиться к уменьшению количества дроуколов не всегда хорошая идея. Если у вас весь текст на экране рисуется за раз, а не как куча отдельных label, которые сортируются независимо, то экономия в 1 дроукол на всю отрисовку – это не то, на чем стоит фокусироваться.
Если вам нужно решить проблему наслоения в общем виде, то вполне возможно, что стоит рисовать в 2 drawcall, как у автора статьи.
Это будет что-то вроде передать два веса, рассчитать две opacity, а потом
этот кусок шейдера взял отсюда.
От размеров квада на экране зависит следующее. Поскольку в текстуре закодировано не растровое изображение глифа, а расстояние до кривой, его описывающей, то шейдер должен позаботиться о всех аспектах растеризации, в том числе о сглаживании.
Самый простой вариант сглаживания, доступный в шейдере – рисовать пиксели, близкие к границам символа полупрозрачными. Нюанс в том, что шейдер работает в нормализованном пространстве символа. То есть, если мы подбираем параметры, определяющие «достаточно близко к границе», чтобы они примерно равнялись 1 пикселю для квада в 16 экранных пикселей, то на кваде в 64 пикселя это будет выглядеть уже не как сглаживание, а как размытие в 4 пикселя. Видимо, именно это в понимаете под «качеством».
Если весь текст в drawcall одного кегля, то вместе с матрицей можно рассчитывать и параметр сглаживания, передавая его так же в константу. Я делал прототип для произвольных экранных размеров квада так: в вершины писал дополнительно атрибут размеров квада в пикселях, а в шейдере считал параметр сглаживания по логистической кривой.
По тем же принципам определения пикселей вблизи границы, можно рисовать и окантовку – часто пример MSDF-шейдера ее содержит. У вас была какая-то хитрая задумка, которая потребовала рисовать окантовку в отдельный проход?
Если по-честному, то js-таргет у haxe немного в более привилегированном положении, так как его Sdt (в т.ч. стандартный массив) схож с js-ными по апи, так как исторически был альтернативой as3, который тоже является ECMAScript. Для других таргетов код массива тоже будет включен в сгенерированный.
Но прелесть haxe как мультитранспилера выражается в том, что мы можем написать
а код в абстрактах для подгонки апи будет инлайниться.
Ненене. Haxe изначально очень практичный и прикладной инструмент, а массовый прикладной код сейчас все-таки пишется императивный-ООП-стайл, и я заходил именно с этой стороны. То есть, ожидается, что я могу отдать куда-то ссылку на сигнал, потом в него что-то напихать, а кто-то по ссылке до напиханного достучится.
Хотя в то же время на haxe можно написать и OCaml-стайл портянку паттернматчина по AST, представленного в виде ADT. Собственно, macro апи для метапрограммирования тоже является отличительной фишкой haxe.
1. haxe – мультипарадигменный язык с уклоном в ООП, большая часть прикладного кода пишется в императивном ООП-стиле
2. haxe – мультитаргетный транспилятор, одна из широко используемых возможностей – шаринг кодовой базы между целевыми платформами. Написание прикладного кода так, чтобы он работал на всех (нужных) платформах одинаково и эффективно – задача специфическая, решать ее не всегда требуется. Но если все же – то аналогов я не знаю.
Сейчас попробую пояснить. Действительно, один из способов применения абстрактов в haxe – zero-overhead описание алгебры предметной области. То есть, можно описать, что метры*метры = метры квадратные, складывать их между собой можно, а друг с другом – нельзя.
Scala – пожалуй, единственный язык из известных мне, который имеет похожую абстракцию и позволяет писать в императивном стиле. И то – вопрос еще, что получится при транспиляции в js. Как минимум, раньше она тащила с собой жирнющий рантайм в несколько мегабайт.
А при транспиляции хаскеля в js newtype превращается просто в underlying type?
Как бы то ни было, абстракты в хакси могут быть над любым типом, а не только примитивным, у них явно описывается конструктор с произвольным телом. Кроме этого, можно явно управлять способом транспиляции для каждого метода или перегруженного оператора: если в объявлении не указан инлайн, то сгенерируется хэлпер со статическим методом.
У Haxe есть экстерны для описания типов целевой платформы, абстракты – это отличный способ изолировать особенности «нативных» сущностей с разных платформ, добавить к ним некоторое поведение, не внося новых сущностей в целевой код.
То есть в некотором смысле абстракты еще могут быть и альтернативой миксинам/трейтам.
Хороший пример – реализация сигналов. Абстракт над массивом, этакий аналог (почти) invokation list в пару строк и без внесения лишних сущностей в язык.
И обратное тоже возможно: благодаря dce из 100 строк получить 20.
Как раз для js там очень прозрачные трансформации, структурно код очень близкий, просто блок может назначаться через свойство prototype. Основное отличие, которое бросалось в глаза – это for трансформирующийся в while с вынесением объявления счетчика, мне кажется это могло быть основной причиной раздувания.
ES6 на классах сейчас тоже поддерживается через флаг компиляции.
Если искать протечки в своем коде, а не в движке, то обилие таргетов может помочь. Искать безудержно аллоцирующие места можно на любой платформе, выбирая по наличию удобных инструментов. Flash в этом весьма хорош, кстати. Быстрая компиляция, быстрый запуск, отличный дебаггер. HxScout есть, работает и для swf, и для c++.
Дженериками сегодня никого не удивишь, ADT это уже интереснее, а аналогов абстрактам в популярных языках я и не назову.
Я бы сказал немного по-другому: haxe старается не вносить оверхэд на ровном месте, поэтому null на haxe превращается в null на целевом языке, а вот его поведение уже определяется природой целевой платформы.
Вот с этим соглашусь, пиарить его особо не кому, кто знает – тихо использует. Кто не знает – думает, «если он такой хороший, что ж я про него не знал до сих пор» и проходит мимо. Поэтому сложнее набирать команду – это риск для бизнеса, замкнутый круг.
Среди примеров можно было бы упомянуть Reason и Kotlin.
Отдельного внимания заслуживает haxe, который тоже обладает полноценной системы типов, хорошим апи для метапрограммирования, но транспилируется не только в js, а еще и в C++, C#, Java, JVM, Python, Lua, PHP, SWF.
А на ризоне у вас для клиента какие-то вещи, типа админок и лобби?
Команда большая? Как сотрудников находите на такой необычный стек?
Причем, haxe частично был вдохновлен: имеет встроенную поддержку метапрограммирования, которая обрабатывает синтаксическое дерево, представленное в виде ADT. Так что его обработка посредством паттерн-матчинга выглядит очень в духе OCaml.
nastvood, возможно, слышал об этом языке – в геймдеве он популярнее, чем в других нишах. Кстати, было бы очень интересно узнать чуть больше о вашей компании, я кроме списка игр ничего не смог найти. На чем у вас клиент, например?
Из интересных проектов на OCaml (на Reason, если быть точнее) могу еще отметить Oni2 – гибрид VSCode и Vim с упором на скорость и удобство.
Лично я глубоко убежден, что сегодняшняя ненужность флэша – следствие того, насколько долго и настойчиво адоби его закапывали.
Если бы для flash стабильно выходили обновления, а мэинтейнеры не говорили на протяжении долгих лет, что планируют его закрыть, то вряд ли бы он так сдал в популярности. И даже Джобс не был бы ему помехой – на мобилы можно публиковать через Air.
Если учесть отличный тулинг и богатый мультимедийный апи, то вполне возможно, что и многие разработчики продолжили бы держаться этой платформы.
Что до разработчиков браузеров: если технология востребована среди пользователей, то ее поддержка – конкурентное преимущество. И если не пришлось бы расплачиваться безопасностью, то почему не тащить?
Возможно, частично причина кроется в лицензиях – внутри флэшплеера есть всякие технологии, лицензированные снаружи (кодеки, например), и открывать связанный с ними код – нарываться на иски; а подготовить чистую версию исходников адоби не потянули.
Однако, есть и кроссплатформенные реализации практически всего api под haxe:
openfl и nme. То есть, сконвертировать as3-проект в haxe и, с последующей доработкой напильником, собрать под мобилы, десктоп и веб – такой шанс есть.
Что до флэша – сейчас это одна из десятки целевых платформ, далеко не самая популярная. Думаю, что трансляция в JS или что-то нативное сейчас используются гораздо чаще.
Рекомендую ознакомиться с англоязычной статьей на вики, она выглядит более актуальной.
А куда предполагается впиливать его поддержку? Он сам кого хочешь поддержит: есть кейсы успешной интеграции с UnrealEngine, Unity, SDL, Node.js, массы браузерных библиотек типа pixi.js и т.д.; поддержка во многих IDE.
Тут все на удивление прозрачно: на их сайте есть «тарифные планы спонсорства» и список компаний спонсоров (в том числе, уже упомянутых в треде).
К тому же, несмотря на небольшую команду, работа над компилятором ведется весьма активно (гитхаб, все видно). Далеко не факт, что есть потребность раздувании команды. Ну и вообще, «писать компилятор на OCaml» – довольно нишевая позиция, на которую вряд ли есть куча соискателей.