Сортировка палитры RGB565
- Войдите на сайт для отправки комментариев
Ср, 08/08/2018 - 09:26
Может кто подсказать пример, как можно отсортировать набор цветов RGB565, находящиеся в случайном порядке что бы он соответсвовал спектру? Я находил и пробовал применить способы преобразования в HSL (HSV) и сортировку по hue и более менее что-то приближенное получалось, но все равно с третью цветов разбросанных как попало. Проблема в том, что все примеры рассчитаны на преобразование RGB888, и мне достаточно сложно на текущий момент понять, как можно примеры адаптировать под RGB565.
typedef struct RgbColor{ unsigned char r; unsigned char g; unsigned char b; } RgbColor; typedef struct HsvColor{ unsigned char h; unsigned char s; unsigned char v; } HsvColor; RgbColor HsvToRgb(HsvColor hsv){ RgbColor rgb; unsigned char region, p, q, t; unsigned int h, s, v, remainder; if(hsv.s == 0){ rgb.r = hsv.v; rgb.g = hsv.v; rgb.b = hsv.v; return rgb; } // converting to 16 bit to prevent overflow h = hsv.h; s = hsv.s; v = hsv.v; region = h / 43; remainder = (h - (region * 43)) * 6; p = (v * (255 - s)) >> 8; q = (v * (255 - ((s * remainder) >> 8))) >> 8; t = (v * (255 - ((s * (255 - remainder)) >> 8))) >> 8; switch(region){ case 0: rgb.r = v; rgb.g = t; rgb.b = p; break; case 1: rgb.r = q; rgb.g = v; rgb.b = p; break; case 2: rgb.r = p; rgb.g = v; rgb.b = t; break; case 3: rgb.r = p; rgb.g = q; rgb.b = v; break; case 4: rgb.r = t; rgb.g = p; rgb.b = v; break; default: rgb.r = v; rgb.g = p; rgb.b = q; break; } return rgb; } HsvColor RgbToHsv(RgbColor rgb){ HsvColor hsv; unsigned char rgbMin, rgbMax; rgbMin = rgb.r < rgb.g ? (rgb.r < rgb.b ? rgb.r : rgb.b) : (rgb.g < rgb.b ? rgb.g : rgb.b); rgbMax = rgb.r > rgb.g ? (rgb.r > rgb.b ? rgb.r : rgb.b) : (rgb.g > rgb.b ? rgb.g : rgb.b); hsv.v = rgbMax; if(hsv.v == 0){ hsv.h = 0; hsv.s = 0; return hsv; } hsv.s = 255 * ((long)(rgbMax - rgbMin)) / hsv.v; if(hsv.s == 0){ hsv.h = 0; return hsv; } if(rgbMax == rgb.r) hsv.h = 0 + 43 * (rgb.g - rgb.b) / (rgbMax - rgbMin); else if (rgbMax == rgb.g) hsv.h = 85 + 43 * (rgb.b - rgb.r) / (rgbMax - rgbMin); else hsv.h = 171 + 43 * (rgb.r - rgb.g) / (rgbMax - rgbMin); return hsv; }
void sort(uint16_t a[], int size, uint16_t a2[]){ for(int i=0; i<(size-1); i++){ for(int o=0; o<(size-(i+1)); o++){ if(a[o] > a[o+1]){ int t = a[o]; a[o] = a[o+1]; a[o+1] = t; int t2 = a2[o]; a2[o] = a2[o+1]; a2[o+1] = t2; } } } }
void colorsSort(){ //randomSeed(analogRead(0)); int len = 112; //16, 112 uint16_t arr[len] = {0}; uint16_t arr2[len] = {0}; byte bb[] = {5,6,5}; byte x = 0; byte y = 0; RgbColor rgb; for(byte a=0; a<2; a++){ if(a) sort(arr2,len,arr); for(int b=0; b<len; b++){ if(!a){ arr[b] = random(0,65536); for(byte c=0, e=0; c<3; c++){ byte z = 0; for(byte d=0; d<bb[c]; d++, e++){ bitWrite(z,d,bitRead(arr[b],e)); } switch(c){ case 0 : rgb.r = z; break; //z << 3; break; //(z << 3) | (z >> 2); break; //z; break; case 1 : rgb.g = z; break; //z << 2; break; //(z << 2) | (z >> 4); break; //z; break; case 2 : rgb.b = z; break; //z << 3; break; //(z << 3) | (z >> 2); break; //z; break; } } HsvColor hsv = RgbToHsv(rgb); arr2[b] = hsv.h; } tft.fillRect(x,y,6,6,arr[b]); x += 8; if(x >= 122){ x = 0; y += 8; } } x = 0; y += 8; } }
Это пример того что получается. До и после, типа.
https://pp.userapi.com/c846323/v846323252/bc1b7/K__ltXMXpLM.jpg
красиво.
что значит "чтобы соответствовал спектру"?
тут написано, что формат 15-16 битный а у вас 3 байта?
https://en.wikipedia.org/wiki/RGB565
текст программы не компилируется.
https://upload.wikimedia.org/wikipedia/commons/thumb/5/5d/HSV-RGB-compar... Что бы сортировались в таком или приближенном порядке. Что бы не были оттенки одного цвета разбросаны по всей палитре.
Да 16 битный, 5 - 6 - 5 бит на цвет, который я в силу своих познаний привел к байту каждый для передачи в конвертер.
Сейчас все соберу в один файл, ибо по кусочкам надрал что бы показать.
Что красиво?
https://www.dropbox.com/s/olgq9ity6sj0xk3/Test.7z?dl=0
Красивая фотография дисплея с нанкой на борде.
На нижней части изображения видна сортировка сверху вниз от синего до синего.
На этой палитре отсутствуют белый, серый, чёрный.
В ваших данных есть похожие цвета.
На нижней части изображения видна сортировка сверху вниз от синего до синего.
На этой палитре отсутствуют белый, серый, чёрный.
В ваших данных есть похожие цвета.
И как со всем этим справиться?)
Nefelisk, глядя на приведенное Вами фото, можно предположить, что сортировка осуществляется правильно. Только "спектр" представлен в виде круга, а "разорван" этот круг не совсем в нужном месте: между синим и фиолетовым вместо того, чтобы между фиолетовым и красным.
И еще: если хотите конкретного совета, четко сформулируйте проблему. Повторяю, по фото проблемы не видно.
Подниму старую тему,
балуюсь со спрайтами на STM32, дисплей 320*240 ili9341, отображение в формате RGB565, конвертацию во время вывода из обычного RGB888 легко можно сделать и быстродействия хватит, но хранить во flash в 24 битном формате картинки - расточительство.
Никто не встречал online сайт преобразования файлов или программу конвертации из RGB888/BMP в RGB565?
Никто не встречал online сайт преобразования файлов или программу конвертации из RGB888/BMP в RGB565?
вот http://www.rinkydinkelectronics.com/t_imageconverter565.php
Никто не встречал online сайт преобразования файлов или программу конвертации из RGB888/BMP в RGB565?
вот http://www.rinkydinkelectronics.com/t_imageconverter565.php
Спасибо, отлично работает, цвета правда съезжают, но надо над исходником поработать, это мелочи.
Мля.... Ребята, ну это же элементарная хрень :(
Есть еще немного более продвинутый алгоритм, который копирует старшие биты цвета в обнуленные компрессией младшие, тогда диапазон расширяется вверх до максимальных 255. Но особого смысла в этом не вижу. Можно еще использовать табличное преобразование которое растянет диапазон 8...248 в 1...255, а оно ннада ?
Прочитал в пол глаза, ответил не в тему... Ну пусть остается.
// пиксель RGB 16 бит
Есть еще немного более продвинутый алгоритм, который копирует старшие биты цвета в обнуленные компрессией младшие, тогда диапазон расширяется вверх до максимальных 255. Но особого смысла в этом не вижу. Можно еще использовать табличное преобразование которое растянет диапазон 8...248 в 1...255, а оно ннада ?
На крошечном экране точность цветов нафиг не надо.
А на светодиодной ленте яркость сильно зависит от значений.
Никто не встречал online сайт преобразования файлов или программу конвертации из RGB888/BMP в RGB565?
вот http://www.rinkydinkelectronics.com/t_imageconverter565.php
Спасибо, отлично работает, цвета правда съезжают, но надо над исходником поработать, это мелочи.
Дополнение:
цвета в моем случае съезжали из за другой последовательности битов в 16 битном слове, что бы не изобретать велосипед, вышел из положения следующим способом:
1. преобразую по выше указанной ссылке jpg файл в raw
2. перевожу набор байтов в СИ массив ссылкой:
Bin2C — преобразование бинарных файлов в массив C/C++ (krivyy.com)