Форум: "WinAPI";
Текущий архив: 2007.11.18;
Скачать: [xml.tar.bz2];
Внизперевод 8 битного битмапа в 24 битный Найти похожие ветки
← →
Альберт © (2007-05-02 21:17) [0]Здравствуйте!
Проблема заключается, может быть, в неправильном обращении к 8 битному рисунку.
SRCDATA - запись с данными о 24 битном
MAPDATA - ... о 8 битном
SRCINC - размер строки в 24битном
...BASE - ссылки на bits
цвета некорректно выводятся.
SRCINC := SRC_DATA.BIH^.bmiHeader.biWidth * 3;
for yy := 0 to MAP_DATA.BIH^.bmiHeader.biHeight - 1 do
begin
for xx := 0 to MAP_DATA.BIH^.bmiHeader.biWidth - 1 do
begin
DWORD(SRCBASE^) := DWORD(MAP_DATA.BIH^.bmiColors[BYTE(MAPBASE^)]) ;
DWORD(MAPBASE) :=DWORD(MAPBASE) + 1;
DWORD(SRCBASE) :=DWORD(SRCBASE) + 3;
if xx>=SRC_DATA.BIH^.bmiHeader.biWidth then
begin
DWORD(SRCBASE):=DWORD(bits24)+DWORD(yy*SRCINC);
break;
end;
end;
Буду рад помощи
← →
Rouse_ © (2007-05-02 23:06) [1]Эээ, а BitBlt на 24-битный канвас религия не позволяет?
← →
Альберт © (2007-05-02 23:32) [2]да я это прекрасно понимаю и сделал бы, проблема в том, что не фига не удается нормально работать с 8 битным.
у меня цель вообще совместить в 32 битное 8битное и 24битное изображение. 24 битное я-то нарисую на 32 битном, но вот в поле, назовем alpha, надо вставить нормально 8 битное. а оно вот как-то неправильно читается... шит...
← →
Альберт © (2007-05-02 23:33) [3]как правильно получить значение пикселя холста 8битного?
← →
Альберт © (2007-05-02 23:46) [4]вот даже специально создал бмпшку на 8бит в режиме grayscale.. проверяю значение пикселей, не то выводится. должно быть R=G=B, и не выходит такого..
← →
tesseract © (2007-05-03 10:11) [5]
> у меня цель вообще совместить в 32 битное 8битное и 24битное
> изображение.
гм расширить shr/shl 8 бит до 32 и OR-м блоки памяти?
← →
Vovan # 2 (2007-05-05 01:04) [6]>вот даже специально создал бмпшку на 8бит в режиме grayscale.. проверяю значение пикселей, не то выводится. должно быть R=G=B, и не выходит такого..
Палитру устанавливал?
← →
GrayFace © (2007-05-05 10:43) [7]Ну
1) Ты не учитываешь выравнивание - ширина ScanLine делается кратной 4.
2) DWORD(SRCBASE^) := DWORD(MAP_DATA.BIH^.bmiColors[BYTE(MAPBASE^)]) - затирает байт соседнего цвета, хотя почти ни на что не влияет, но нет гарантии, что не залезешь куда не надо при модификации последнего пикселя.
> Палитру устанавливал?
Для alpha-канала палитра вообще будут не нужна, достаточно BYTE(MAPBASE^) вместо DWORD(MAP_DATA.BIH^.bmiColors[BYTE(MAPBASE^)].
← →
Альберт © (2007-05-10 22:54) [8]может быть я что-то недопонимаю,палитра - это есть таблица цветов.. да вообще в любом случае полностью копирую BIH. проблема даже не 32 битном изображении, а в неправильном считывании 8мибитного. 24х битном тоже не нужна она.. да может проблема не в последнем пикселе?
я вообще разбираюсь с битмапами 200 на 200. поэтому кратность 4м очевидна
← →
Альберт © (2007-05-10 22:54) [9]может быть я что-то недопонимаю,палитра - это есть таблица цветов.. да вообще в любом случае полностью копирую BIH. проблема даже не 32 битном изображении, а в неправильном считывании 8мибитного. 24х битном тоже не нужна она.. да может проблема не в последнем пикселе?
я вообще разбираюсь с битмапами 200 на 200. поэтому кратность 4м очевидна
← →
Sapersky (2007-05-11 13:10) [10]DWORD(SRCBASE^) := DWORD(MAP_DATA.BIH^.bmiColors[BYTE(MAPBASE^)]) ;
Если здесь берётся цвет из палитры, то это, как уже говорилось в [7], не нужно. Нужно брать байт прямо из битмапа (считаем, что он grayscale).
Вообще, не сочтите за наезд, но код из [0] страшно даже читать, а уж писать таким образом...
Сравните с FastLIB:
procedure SetAlphaChannel(Bmp,Alpha:TFastDIB);
var
pb: PByte;
pc: PFColorA;
x,y: Integer;
begin
pb:=Pointer(Alpha.Bits);
pc:=Pointer(Bmp.Bits);
for y:=0 to Alpha.AbsHeight-1 do
begin
for x:=0 to Alpha.Width-1 do
begin
pc^.a:=pb^;
Inc(pc);
Inc(pb);
end;
pc:=Ptr(Integer(pc)+Bmp.Gap);
Inc(pb,Alpha.Gap);
end;
end;
На самом деле можно ещё проще, вообще без адресной арифметики.
http://sourceforge.net/project/showfiles.php?group_id=173551
← →
Альберт © (2007-05-12 00:47) [11]> Sapersky, спасибо за совет и ссылку. приму к сведению красивый код. ну извините за страх ниже, не успел переправить, сразу отвечать тут стал.
DWORD(SRCBASE^) := DWORD(MAP_DATA.BIH^.bmiColors[BYTE(MAPBASE^)])
исправил на
tagRGBQUAD(DSTBASE^).rgbReserved:=$FF - MAP_DATA.BIH^.bmiColors[BYTE(MAPBASE^)].rgbBlue;
и аналогично 2 другие строки.
и ничего не изменилось.
может дело в DIB_RGB_COLORS и DIB_PAL_COLORS?
хотя перестановка констант не решает проблемы.
по документации при работе с 8мибитным надо обращаться к его палитре.. обращение к bits тоже не решило проблемы.
← →
Альберт_ (2007-05-12 19:46) [12]есть гипотеза о том, что виндовая структура палитры отличается от ее представления в файле
← →
Sapersky (2007-05-13 12:22) [13]у меня цель вообще совместить в 32 битное 8битное и 24битное изображение. 24 битное я-то нарисую на 32 битном, но вот в поле, назовем alpha, надо вставить нормально 8 битное. а оно вот как-то неправильно читается...
Кстати, вопрос - ГДЕ в приведённом коде 32-битная картинка?
cпасибо за совет и ссылку. приму к сведению красивый код.
Ссылка дана ещё и к тому, что чем изобретать велосипед с нуля (долго и мучительно), можно воспользоваться существующей библиотекой.
Ещё есть SpriteUtils2, например.
по документации при работе с 8мибитным надо обращаться к его палитре..
Смотря чего вы хотите добиться. Если правильного вывода на экран произвольных палитровых картинок - то да, но если 8-битная картинка у вас играет роль альфа-канала, само собой подразумевается, что она grayscale, т.е. значения r,g,b палитры = своему индексу (байту картинки).
есть гипотеза о том, что виндовая структура палитры отличается от ее представления в файле
По-разному может быть, зависит от формата заголовка битмапа. Их 2 типа, в "новом" (обычно используемом) формате - не отличается.
См. TFastDIB.LoadFromFile (LoadHeader).
Страницы: 1 вся ветка
Форум: "WinAPI";
Текущий архив: 2007.11.18;
Скачать: [xml.tar.bz2];
Память: 0.48 MB
Время: 0.072 c