Реалізація AI-колоризації чорно-білих фотографій у мобільному додатку
Ми не раз стикалися з ситуацією: користувач завантажує стару чорно-білу фотографію, сподіваючись отримати природні кольори. Але колоризація — задача з одним правильним входом і нескінченною множиною «правильних» виходів. Небо може бути блакитним або сірим. Пальто — чорним або синім. AI-модель робить статистично ймовірний вибір, а не відновлює реальність. Цей нюанс ми пояснюємо користувачеві прямо в інтерфейсі, але технічна реалізація залишається найцікавішою частиною. Наш досвід — 5 років у мобільній розробці та 12+ проектів з інтеграцією AI — дозволяє гарантувати якісний результат. Мобільна колоризація на iOS та Android потребує ретельного вибору моделі.
Яка модель підходить для мобільної колоризації?
Класика — DeOldify (fastai + U-Net з self-attention). Добре узагальнюється, дає насичені кольори. Мінус: іноді «забруднює» колір у небажані плями на обличчях або одязі при складному фоні. DDColor (2023) — transformer-based архітектура, працює значно краще на портретах та архітектурі. Точніше передає колір шкіри та неба. BigColor і ChromaGAN — для специфічних задач (історичні знімки з сильною деградацією). DeOldify працює на 30% швидше на iPhone, ніж DDColor, але DDColor точніший в 2 рази на портретах.
| Модель | Архітектура | Розмір (базовий) | Особливості |
|---|---|---|---|
| DeOldify | U-Net + self-attention | 250 МБ (FP32), 60-70 МБ (INT8) | Насичені кольори, ризик плям на обличчях |
| DDColor | Transformer | 110 МБ | Точна передача шкіри, неба |
| BigColor | GAN + ResNet | 150 МБ | Хороший для деградованих знімків |
| ChromaGAN | GAN | 130 МБ | Стійкий до шумів |
На мобільний іде один із них — сконвертований у Core ML або TFLite. Після квантизації INT8 DeOldify важить 60–70 МБ — прийнятно для мобільного додатку.
Як інтегрувати модель на iOS та Android?
Процес інтеграції складається з кількох кроків:
- Вибір моделі та конвертація в цільовий формат (Core ML / TFLite / ONNX).
- Налаштування preprocessing: перетворення grayscale в RGB, нормування.
- Запуск інференсу з оптимізацією під пристрій (Neural Engine, GPU, NNAPI).
- Постобробка: тайловий інференс для великих зображень та colour normalization.
Конвертація DeOldify у Core ML
Приклад коду конвертації
import coremltools as ct
import torch
from deoldify.visualize import get_image_colorizer
colorizer = get_image_colorizer(artistic=True)
model = colorizer.learn.model.eval()
# Експорт через torch.jit.trace
example = torch.zeros(1, 3, 256, 256)
traced = torch.jit.trace(model, example)
mlmodel = ct.convert(
traced,
inputs=[ct.TensorType(name="input", shape=(1, 3, 256, 256))],
compute_precision=ct.precision.FLOAT16,
minimum_deployment_target=ct.target.iOS16
)
mlmodel.save("DeOldify_artistic.mlpackage")
Важливий момент: DeOldify приймає RGB-вхід (навіть для grayscale — він сам конвертує в Lab та працює з AB-каналами). Перед подачею grayscale-зображення його потрібно розширити в 3-канальний RGB реплікацією: gray → [gray, gray, gray]. У CoreML це робиться в preprocessing, не в самій моделі.
iOS: запуск інференсу
let config = MLModelConfiguration()
config.computeUnits = .cpuAndNeuralEngine // ANE для FLOAT16
let model = try DeOldify_artistic(configuration: config)
// Підготовка: grayscale CVPixelBuffer → RGB
func prepareInput(from grayImage: UIImage) -> CVPixelBuffer? {
// Створюємо RGB піксельний буфер з grayscale, реплікуючи канал
var pixelBuffer: CVPixelBuffer?
CVPixelBufferCreate(nil, width, height,
kCVPixelFormatType_32BGRA, nil, &pixelBuffer)
// ... копіюємо сірий канал у всі три
return pixelBuffer
}
let input = DeOldify_artisticInput(input: pixelBuffer)
let output = try model.prediction(input: input)
let colorizedImage = UIImage(cvPixelBuffer: output.output)
На iPhone 13 зображення 512×512 обробляється за 0.8–1.2 секунди. Для Full HD (1920×1080) — тайловий інференс з патчами 512×512 та блендингом на стиках. Тайловий підхід створює проблему кольорової неузгодженості між патчами: модель може пофарбувати один фрагмент неба в блакитний, а сусідній — у сірий. Рішення — global color histogram matching: нормалізуємо гістограму кожного тайла до глобальної гістограми.
Android: TFLite з ONNX Runtime як альтернатива
// ONNX Runtime дає гнучкість: одна модель для iOS та Android
val env = OrtEnvironment.getEnvironment()
val session = env.createSession(
"deoldify_optimized.onnx",
OrtSession.SessionOptions().apply {
addNnapi() // або addCuda() якщо є GPU
}
)
val inputTensor = OnnxTensor.createTensor(env, inputArray, longArrayOf(1, 3, 512, 512))
val results = session.run(mapOf("input" to inputTensor))
val outputArray = (results[0].value as Array<*>)
ONNX Runtime Mobile — хороший вибір коли одна модель потрібна на обох платформах: не потрібно двічі конвертувати. NNAPI-делегат працює на пристроях з Android 8.1+. TFLite з NNAPI прискорює інференс в 3–4 рази порівняно з CPU.
UX: що важливо врахувати
Колоризація — повільна операція (1–5 секунд). Показуємо анімований прогрес. Хороший патерн — «before/after» слайдер: користувач зсуває роздільник і бачить оригінал та результат одночасно. Це і UX, і наочна демонстрація роботи моделі.
Збереження результату — у .heic або .jpg з максимальною якістю. Результат колоризації погано переносить повторне JPEG-стиснення: артефакти на кольорових переходах стають помітними. Тайловий інференс збільшує час обробки в 2 рази, але дає змогу обробляти Full HD.
Що входить в роботу
- Вибір та конвертація моделі під цільову платформу (Core ML / TFLite / ONNX)
- Оптимізація під конкретні пристрої (Neural Engine, GPU, NNAPI)
- Реалізація тайлового інференсу з кольоровою нормалізацією
- Розробка UI з before/after порівнянням та прогресом
- Інтеграція збереження в галерею та шерингу
- Документація по моделі, preprocessing, та інструкція для App Store Review (згідно з App Store Review Guidelines розділ 5.1 для обробки фотографій)
- Тестування на історичних фотографіях різної якості
Економія на ліцензіях: ви не платите за open-source моделі. Економія може сягати $10,000–$30,000 на рік на ліцензіях комерційних рішень. Вартість розробки від $5,000 до $15,000 залежно від платформ і складності. Вартість розробки порівнянна з зарплатою одного розробника за місяць. Отримайте консультацію — ми оцінимо ваш проект та запропонуємо оптимальний стек за два дні. Замовте розробку прямо зараз.
Орієнтири за термінами
| Етап | Термін (одна платформа) | Термін (обидві платформи) |
|---|---|---|
| Вибір та конвертація моделі | 1 тиждень | 1.5 тижня |
| Реалізація інференсу та UI | 1-2 тижні | 2-3 тижні |
| Тайловий інференс + кольор. нормалізація | 0.5-1 тиждень | 1-2 тижні |
| Тестування та оптимізація | 0.5-1 тиждень | 1-1.5 тижня |
| Разом | 2–4 тижні | 5–8 тижнів |
Отримайте консультацію — ми оцінимо ваш проект та запропонуємо оптимальний стек за два дні.







