Текущий архив: 2007.09.02;
Скачать: CL | DM;
Вниз
Наиболее быстро изменить размер Bitmap-а (уменьшить). Найти похожие ветки
← →
DVM © (2006-11-21 10:11) [0]Как наиболее быстро изменить размер Bitmap-а? Скорость стандартного StretchBlt не совсем устраивает. Можно ли обогнать StretchBlt и если да, то как?
Может кто занимался подобным. Можно ли привлечь для масштабирования SSE, MMX и прочие наборы инструкций? Если кто знает, расскажите как.
← →
clickmaker © (2006-11-21 10:17) [1]DirectDraw?
← →
KilkennyCat © (2006-11-21 10:21) [2]TBitmap.Width := ...
TBitmap.Height := ...
← →
DVM © (2006-11-21 10:23) [3]
> KilkennyCat © (21.11.06 10:21) [2]
Это отсечение, а не масштабирование.
← →
DVM © (2006-11-21 10:23) [4]
> clickmaker © (21.11.06 10:17) [1]
DirectDraw, сам по себе как мне кажется скорости не прибавит. Мне нужно просто масштабирование, без вывода на экран. Я с DD знаком мало, там есть функции масштабирования более быстрые, чем StretchBlt? Идеальным бы вариантом оказалось использование аппаратной поддержки со стороны видеоадаптера (он наврняка умеет, такая мощь простаивает). Но как этим воспользоваться?
← →
WondeRu © (2006-11-21 10:26) [5]http://rsdn.ru/forum/Message.aspx?mid=2201982 тут обсуждается
← →
KilkennyCat © (2006-11-21 10:29) [6]> Это отсечение, а не масштабирование.
неправда. это
> наиболее быстро изменить размер Bitmap-а?
а если менять картинку, то зависит от алгоритма.
> Идеальным бы вариантом оказалось использование аппаратной
> поддержки со стороны видеоадаптера (он наврняка умеет, такая
> мощь простаивает). Но как этим воспользоваться?
DirectDraw... но не все видеокарты реализуют аппаратный StretchBlt.
← →
DVM © (2006-11-21 10:37) [7]
> неправда. это
Я не смотрел реализацию TBitmap.Width := ... и TBitmap.Height := ... в VCL, но что-то мне подсказывает, что за ними скрывается то же StretchBlt :)
Это вряд ли быстрее.
← →
DVM © (2006-11-21 10:39) [8]
> KilkennyCat © (21.11.06 10:21) [2]
Неправ я. Оказалось чуть-чуть быстрее. Но настолько незначительнее, что овчинка выделки не стоит.
← →
DVM © (2006-11-21 10:44) [9]
> KilkennyCat © (21.11.06 10:21) [2]
Только все же TBitmap.Width := ... и TBitmap.Height := не масштабируют - они обрезают лишнее. :)
← →
Barloggg (2006-11-21 10:51) [10]из под винды аппаратно ускоренный есть bltfast на прямом WinApi, но масштабирования он не держит.
к тому же там вагон параметров в типе TBltFx с поганой документацией.
так что да, директдрав. можно через ДельфиХ, можно через заголовочные файлы.
Но если это единичная операция, то загрузка битмапа в поверхность, потом масштабирование, потом выгрузка обратно займет столько времени, что ни о каком ускорении и речи идти не может...
← →
clickmaker © (2006-11-21 10:51) [11]
> Только все же TBitmap.Width := ... и TBitmap.Height := не
> масштабируют - они обрезают лишнее
если через TImage и включено Strecth, то масштабируют
← →
DVM © (2006-11-21 10:57) [12]
> clickmaker © (21.11.06 10:51) [11]
Не, ни о каком TImage речь не идет. Медленно и тяжеловесно.
> Barloggg (21.11.06 10:51) [10]
> Но если это единичная операция, то загрузка битмапа в поверхность,
> потом масштабирование, потом выгрузка обратно займет столько
> времени, что ни о каком ускорении и речи идти не может
У меня в огромном количестве образуются картинки (получаются по сети). Они не того размера, какой нужен. Размер надо преобразовывать и возможно их отображать потом. Это я так понимаю подпадает под определение "единичные операции"?
← →
atruhin © (2006-11-21 11:46) [13]Посмотри GraphicEx, там несколько способов масшабирования, может будет быстрее.
← →
Думкин © (2006-11-21 12:12) [14]
> DVM © (21.11.06 10:44) [9]
Но размер они меняют, что и требовалось в сабже.
← →
DVM © (2006-11-21 13:00) [15]
> Но размер они меняют, что и требовалось в сабже.
Буквоедство это. В том же сабже указано StretchBlt. Речь о масштабировании. Русский язык богат и неоднозначен.
← →
Sapersky (2006-11-21 13:39) [16]StretchBlt требуется с фильтрацией или без?
Если с фильтрацией, FastLIB"овский Bilinear быстрее, хотя и даёт несколько худшее качество (видимо, сам алгоритм проще). Если без (FastResize) - скорость примерно та же, что и у StretchBlt.
Насчёт единичных операций - да, от DDraw в такой ситуации будет мало пользы. Разве что хранить в том размере, который пришёл, и делать stretch непосредственно при выводе.
← →
DVM © (2006-11-21 14:12) [17]
> StretchBlt требуется с фильтрацией или без?
Не фильтрация необязательна.
Т.е.
SetStretchBltMode(Canvas.Handle, COLORONCOLOR); Для StretchBlt
Вобщем я пришел к выводу, что не обогнать StretchBlt.
Попробовал и DrawDibDraw() и INTEL Image Processing Library - все медленнее, чем StretchBlt с COLORONCOLOR;
Результат для 100 повторов на некоторой картинке:
StretchBlt - 281 тиков
DrawDibDraw - 625 тиков (хотя это скорее подготовительные операции)
INTEL Image Processing Library - 844 (тоже подготовка дольше, чем обработка)
← →
DVM © (2006-11-21 14:15) [18]Для StretchBlt + HALFTONE - 1547 тиков.
← →
Sapersky (2006-11-21 14:47) [19]Сейчас потестировал - FastResize оказалась быстрее... (когда тестировал в прошлый раз - комп был другой, возможно в этом дело).
http://sourceforge.net/project/showfiles.php?group_id=173551
← →
DVM © (2006-11-21 15:53) [20]
> Sapersky (21.11.06 14:47) [19]
Для FastResize результат - 79 тиков. Однако.
← →
Pavia © (2006-11-22 00:30) [21]Быстрее всего будет если на ассемблере написать. Немогу точно сказать будетли прирост от MXX и SSE нужно пробовать.
Насчет DDraw не все видео карты поддерживают маштабированный вывод для спрайтов, но можно задействовать 3D рэндринг. Правда скорее всего если боддерживался то виндоус его бы использовал. И можно было бы маштабировать через BitBlt(не помню точно).
Так вот для аппоратного ускорения нужно делать 3D рэндринг использовать Direct3D. Но аппоратный вывод он долгий из за всяких простоев.
Незнаю как в DirectX но в OpenGL есть функция GlFlush для того чтобы была возможность немедленно скинуть результат обработки из видео памяти. Кто то сказал что передача в видео память операция медленная. Это зависет от компьютера если брать AGP8 то 66МГц что в 6 раз медленнее памяти. А если EPCI-16 то 1056МГц что наровне с памятью компьютера.
← →
Eraser © (2006-11-22 01:54) [22]> [21] Pavia © (22.11.06 00:30)
Стандартная Bit/StretchBlt тоже уже аппаратно-ускоренная на сколько это возможно, получить более быстрый результат проблематично.
← →
DVM © (2006-11-22 10:17) [23]
> Eraser © (22.11.06 01:54) [22]
Обогнать в плане вывода на экран - да вряд ли возможно. Тут BitBlt вне конкуренции. А вот изменение размера у StretchBlt сделано не самым быстрым способом. У FastDIB FastResize в 3 раза быстрее. На нем и остановился. Вообще FastDIB удобнее в использовании, чем стандартный TBitmap из VCL. В нем есть все то, чего мне не хватало в TBitmap.
← →
Sapersky (2006-11-22 13:46) [24]Стандартная Bit/StretchBlt тоже уже аппаратно-ускоренная на сколько это возможно
Аппаратно-ускоренной реализации StretchBlt я ещё не встречал. См. ссылку на rsdn из [5] - там человек пишет, что теоретически её можно ускорить, но практически, по моему опыту, производители драйверов почему-то этого не делают. Для подтверждения опыта я выкладывал пример - хотя скорость он иногда меряет криво, преимущество DirectDraw в stretch по нему видно невооружённым глазом.
Вообще FastDIB удобнее в использовании, чем стандартный TBitmap из VCL
Угу, я уже почти забыл, что такое TBitmap :)
Хотя есть у FastLIB и свои недостатки, слабая устойчивость к ошибкам, например (шаг влево, шаг вправо - AV).
← →
Eraser © (2006-11-23 19:57) [25]> [24] Sapersky (22.11.06 13:46)
> Аппаратно-ускоренной реализации StretchBlt я ещё не встречал
ошибаешься, удали фирменный драйвер видеокарты и поставь стандартный, увидишь, что значит Blt- фции без аппаратного ускорения )
← →
Eraser © (2006-11-23 20:00) [26]к слову у меня StretchBlt + HALFTONE работает намного быстрее и меньше жрет проц, чем остальные режимы StretchBlt.
почему? сам не знаю.
← →
DVM © (2006-11-24 10:43) [27]
> к слову у меня StretchBlt + HALFTONE работает намного быстрее
> и меньше жрет проц, чем остальные режимы StretchBlt.
> почему? сам не знаю.
Не может быть быстрее оно. Если это поддержка со стороны драйвера, то пересылка в видеопамять и обратно займет больше времени, чем масштабирование.
← →
Sapersky (2006-11-24 14:57) [28]ошибаешься, удали фирменный драйвер видеокарты и поставь стандартный, увидишь, что значит Blt- фции без аппаратного ускорения
В смысле, они ещё больше будут тормозить, чем с фирменными драйверами? Ну это само собой, но я не о том. Я о том, что какие фирменные драйвера ни ставь, StretchBlt всё равно будет работать по крайней мере отчасти софтверно. Т.е. медленнее surface.Blt.
Хотя вот это:
к слову у меня StretchBlt + HALFTONE работает намного быстрее и меньше жрет проц, чем остальные режимы StretchBlt.
может указывать на то, что чудеса иногда случаются :) Дело в том, что во всех аппаратных реализациях DirectDraw-stretch, которые я видел, HALFTONE прошит намертво и никак не отключается (хотя это не совсем то, что софтверный HALFTONE, качество несколько хуже). Т.е. если HALFTONE быстрее, StretchBlt в этом случае, возможно, работает аппаратно.
Если интересно, можешь проверить это предположение (тест-exe, 160 кб):
http://slil.ru/23461557
Не может быть быстрее оно. Если это поддержка со стороны драйвера, то пересылка в видеопамять и обратно займет больше времени, чем масштабирование.
Может, имелся в виду вывод на экран, т.е. "обратно" не надо. А DDB-битмап, как говорили на rsdn (и это, в общем, подтверждается опытами), может жить в видеопамяти.
← →
DVM © (2006-11-27 10:28) [29]
> Sapersky (24.11.06 14:57) [28]
> Если интересно, можешь проверить это предположение (тест-
> exe, 160 кб):
> http://slil.ru/23461557
А можно исходник данного теста?
← →
Sapersky (2006-11-27 14:26) [30]http://slil.ru/23476254
← →
DVM © (2006-11-27 15:41) [31]
> Sapersky (27.11.06 14:26) [30]
Спасибо
← →
DVM © (2006-11-27 16:42) [32]DDraw почти в 3 раза медленне FastDIB из за долгой загрузки Bitmap-a.
Если без загрузки то раз в 5 быстрее.
← →
Дмитрий Белькевич © (2006-11-28 04:08) [33]>Посмотри GraphicEx, там несколько способов масшабирования, может будет быстрее.
У них очень хорошие алгоритмы, кстати. Рекомендую. У себя из них переписанный на асм делал для больших изображений.
Самый быстрый способ:
строится матрица координат, два массива линий получающегося изображения в координатах исходного. Т.е. откуда брать точки из исходного массива.
Дальше идут вложенные циклы по оси х, и у, для каждой линии х и у выбираются согласно предварительно рассчитанным координатам точки из исходного битмапа-сырья.
Скорость очень высокая, mmx/sse здесь не поможет, т.к. считать особо нечего, только пересылки.
Качество, конечно, от скорости страдает, но в моём случае, работая с большими картинками не критично, у меня изображения достаточно монотонные (или как это сказать)? Отбрасывание 3/4 точек почти не заметно.
Есть у них же похожие алгоритмы, но со сглаживанием.
← →
Дмитрий Белькевич © (2006-11-28 04:22) [34]Посмотрел rsdn:
>В варианте видео->видео DirectDraw, по моим тестам, быстрее GDI в десятки-сотни раз
Здесь тоже, мягко говоря, не всё так просто. Для того, что бы изображение отстретчить, его нужно в видеопамять перегнать, а это процесс. Это хорошо, когда изображение одно, а когда их отстретченных на экране штук 20, и все изначально метров по 40-50, последовательно - agp не выдерживает, параллельно - видеопамяти не напасёшься. Я у себя недавно именно из-за этого второй 2d движок писал. Для мелких изображений всё ок, а вот когда по agp начинаешь гонять гигабайты, тут она и помирает. А хочеться полёта... ;)
Вот и приходится предварительно в обычной памяти масштабировать, а потом уже в видео перикидывать и отображать как есть. Так что, обычный процессор, без gdi и дайректа, может работать не хуже последного. Качество, правда, страдает, видюхи хардварно сглаживают хорошо и быстро, что есть, то есть...
← →
Pent (2006-11-28 15:24) [35]Где-то у вас ошибка в тесте.. На моем компьютере StretchBlt быстрее, чем FastResize, чуть ли не на порядок. Даже с интерполяцией. Это при условии, что отрисовка происходит сразу на экран, а если на другой Bitmap, то скорости должны быть примерно одинаковыми.
← →
Pent (2006-11-28 15:26) [36]А использование DirectX не для игр мало когда оправдано, не в последнюю очередь из-за вопросов совместимости имхо.
← →
DVM © (2006-11-28 15:28) [37]
> Pent (28.11.06 15:24) [35]
> Где-то у вас ошибка в тесте.. На моем компьютере StretchBlt
> быстрее, чем FastResize, чуть ли не на порядок. Даже с интерполяцией.
> Это при условии, что отрисовка происходит сразу на экран,
> а если на другой Bitmap, то скорости должны быть примерно
> одинаковыми.
Не верю. :) Что за видеокарта? Какие драйвера, какая ОС?
В каком тесте?
FastResize не выводит на экран - она с битмапа на битмап масштабирует.
После результирующий битмап надо BitBlt куда надо.
← →
Sapersky (2006-11-28 19:50) [38]Сейчас обнаружил, что скорость StretchBlt с COLORONCOLOR имеет не вполне очевидную зависимость от глубины цвета, 32 bpp в 7-8 раз быстрее чем 24 bpp. А я раньше тестировал 24...
При выводе на экран в таком варианте StretchBlt немного быстрее FastResize, при масштабировании в другой битмап - наоборот.
Чтоб одновременно всё-всё сравнить, прикрутил FastLIB к своему тесту:
http://slil.ru/23483988
(исходник)
← →
DVM © (2006-11-29 13:03) [39]
> Sapersky (28.11.06 19:50) [38]
Прикрути еще DrawDIBDraw из vfw:
procedure DDDraw( Canvas: TCanvas; dTop, dLeft, dHeight, dWidth: Integer;
Bitmap: TBitmap);
var
lpBits : Pointer;
pBmpInfo: PBitmapInfo;
nColors : Cardinal;
hdd : HDRAWDIB;
BitmapStream: TMemoryStream;
procedure SetSize;
var
RatioH,
RatioW : Extended;
begin
with pBmpInfo^.bmiHeader do begin
if ( biWidth > dWidth ) or ( biHeight > dHeight ) then
begin
RatioH := dHeight / biHeight;
RatioW := dWidth / biWidth;
if RatioH > RatioW then RatioH := RatioW;
dHeight := Trunc( biHeight * RatioH );
dWidth := Trunc( biWidth * RatioH );
Exit;
end;
dHeight := biHeight;
dWidth := biWidth;
end;
end;
begin
if Bitmap = nil then exit;
BitmapStream := TMemoryStream.Create;
Bitmap.SaveToStream(BitmapStream);
pBmpInfo := PBitmapInfo( PChar( BitmapStream.Memory )
+ SizeOf(TBitmapFileHeader) );
with pBmpInfo^, bmiHeader do begin
if biClrUsed = 1 then
nColors := biClrUsed
else
nColors := ( 1 shl biBitCount );
if biBitCount > 8 then
begin
lpBits := PChar( @bmiColors ) + Ord( biClrUsed )
+ Ord( biCompression = BI_BITFIELDS ) * 3;
end
else lpBits := PChar( @bmiColors ) + nColors;
hdd := DrawDibOpen;
try
DrawDibRealize( hdd, Canvas.Handle, True );
SetSize;
DrawDibDraw( hdd,
Canvas.Handle,
dLeft, dTop,
dWidth, dHeight,
PBitmapInfoHeader( @bmiHeader ),
lpBits,
0, 0,
biWidth, biHeight,
DDF_HALFTONE );
finally
DrawDibClose( hdd );
end;
end;
BitmapStream.Free;
end;
Еще INTEL Image Processing Library тоже. Будет полезная весчь.
← →
DVM © (2006-11-29 13:13) [40]
> Сейчас обнаружил, что скорость StretchBlt с COLORONCOLOR
> имеет не вполне очевидную зависимость от глубины цвета
Ничего себе. А я и не знал.
> Чтоб одновременно всё-всё сравнить, прикрутил FastLIB к
> своему тесту:
Проверил у себя. Результаты такие:
ToScreen:
Stretchblt + 24bpp = 27004
FastLib + 24bpp = 10381
Stretchblt + 32bpp = 6219
FastLib + 24bpp = 8258
Страницы: 1 2 вся ветка
Текущий архив: 2007.09.02;
Скачать: CL | DM;
Память: 0.57 MB
Время: 0.036 c