На главную Наши проекты:
Журнал   ·   Discuz!ML   ·   Wiki   ·   DRKB   ·   Помощь проекту
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
! user posted image
Пожалуйста, выделяйте текст программы тегом [сode=pas] ... [/сode]. Для этого используйте кнопку [code=pas] в форме ответа или комбобокс, если нужно вставить код на языке, отличном от Дельфи/Паскаля.

Соблюдайте общие правила форума

Следующие вопросы задаются очень часто, подробно разобраны в FAQ и, поэтому, будут безжалостно удаляться:
1. Преобразовать переменную типа String в тип PChar (PAnsiChar)
2. Как "свернуть" программу в трей.
3. Как "скрыться" от Ctrl + Alt + Del (заблокировать их и т.п.)
4. Как запустить программу/файл? (и дождаться ее завершения)
5. Как перехватить API-функции, поставить hook? (перехват сообщений от мыши, клавиатуры - внедрение в удаленное адресное прстранство)
... (продолжение следует) ...

Внимание:
Попытки открытия обсуждений реализации вредоносного ПО, включая различные интерпретации спам-ботов, наказывается предупреждением на 30 дней.
Повторная попытка - 60 дней. Последующие попытки - бан.
Мат в разделе - бан на три месяца...

Полезные ссылки:
user posted image MSDN Library user posted image FAQ раздела user posted image Поиск по разделу user posted image Как правильно задавать вопросы


Выразить свое отношение к модераторам раздела можно здесь: user posted image Rouse_, user posted image Krid

Модераторы: Rouse_, Krid
Страницы: (3) [1] 2 3  все  ( Перейти к последнему сообщению )  
> Высота, ширина, цвет точки HBITMAP-а , без модуля Graphics
    Если загрузить битмап из файла в переменную типа HBITMAP так:

    ExpandedWrap disabled
      var
      hBmp: HBITMAP;
      ...
      hBmp := LoadImage(0, '1.bmp', IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE);


    Как можно узнать его высоту, ширину, и цвет в какой-то определенной точке не прибегая к модую Graphics?
      ExpandedWrap disabled
        function PictureSize: TSize;
        var
          ResHandle: HWND;
          ResData: HWND;
          BMI: PBitmapInfo;
        begin
          Result.cx := 0;
          Result.cy := 0;
          ResHandle := FindResource(HInstance,
            MAKEINTRESOURCE(200), RT_BITMAP);
          if ResHandle <> 0 then
          begin
            ResData := LoadResource(HInstance, ResHandle);
            if ResData <> 0 then
            try
              BMI := LockResource(ResData);
              if Assigned(BMI) then
              try
                Result.cx := BMI.bmiHeader.biWidth;
                Result.cy := BMI.bmiHeader.biHeight;
              finally
                UnlockResource(ResData);
              end;
            finally
              FreeResource(ResData);
            end;
          end;
        end;

      А цвет точки - у структуры PBitmapInfo есть параметр bmiColors, который является массивом структур TRGBQuad в котором и содержиться информация по каждому пикселю.

      Добавлено
      Пардон, у тебя из файла загрузка, тогда через GetDIB получай указатель на PBitmapInfo и по аналогии
        Я тут так подумал, может лучше так будет?

        размер:
        ExpandedWrap disabled
          var
            size: tagSIZE;
          ...
          GetBitmapDimensionEx(hBmp, size);


        цвет:
        ExpandedWrap disabled
          color := GetPixel(hBmp, x, y);
          Может и лучше, но не факт что быстрее :)
            Цитата Dmitry_177 @
            цвет:

            color := GetPixel(hBmp, x, y);

            Вообще-то GetPixel первым параметром принимает контекст устройства, а не дескриптор bitmap'а.
            Можно сделать как-нибудь так
            ExpandedWrap disabled
              var
               bmp, oldbmp:HBITMAP;
               bmpInf:BITMAP;
               DC,MemDC:HDC;
               bWidth,bHeight:integer;
               color:COLORREF;
              begin
               bmp:=LoadImage(0, '1.bmp', IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE);
               DC:=GetDC(0);
               MemDC:=CreateCompatibleDC(DC);
               oldbmp:=SelectObject(MemDC,bmp);
               GetObject(bmp,sizeof(BITMAP),@bmpInf);
               bWidth:=bmpInf.bmWidth;       // ширина
               bHeight:=bmpInf.bmHeight;     // высота
               color:=GetPixel(MemDC,10,10); // цвет
               SelectObject(MemDC,oldbmp);
               DeleteDC(MemDC);
               ReleaseDC(0,DC);
              end;
              Вот если делать через GetDIBits, у меня возникло несколько вопросов:

              ExpandedWrap disabled
                var
                  memDC: HDC;
                  hBkgnd: HBITMAP;
                begin
                  hBkgnd := LoadImage(0, '1.bmp', IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE);
                 
                  memDC := GetDC(0);
                  GetDIBits(memDC, hBkgnd, 0, 0, nil, BMI, DIB_RGB_COLORS);
                  ReleaseDC(0, memDC);
                 
                  if (BMI.bmiColors[0].rgbRed = 255) and (BMI.bmiColors[0].rgbGreen = 0) and (BMI.bmiColors[0].rgbBlue = 0) then
                    MessageBox(0, '0 - Красный', '', 0);
                 
                end;


              Правильно ли я создаю контекст устройства memDC := GetDC(0);?

              Не понятно что это за массив bmiColors, как так идет счет точек что-то я не пойму, там же всего одно число а не два, например x и y... Объясните пожалуйста..
                IMHO

                ExpandedWrap disabled
                  memDC := GetDC(0);


                это получение контекста рабочего стола
                  Приветствую всех!
                  Мой вопрос почти по этой теме.
                  Дело в том что GetObject воздвращает bmBitsPixel равное текущему BPP десктопа, то есть, например, всегда 32 у меня, так как стоит цвет 32 High Color. Соответсвенно при смене на 16 - даже 24ый битмап опознаётся как 16ый. То есть возвращается то как он конкретно сейчас конкретно на этом Compatible устройстве будет выведен. Но меня это пока не очень интересует.
                  Как бы мне получить реальный BPP битмапа? То есть то сколько бит на пиксель записано в фаиле?
                  (HBITMAP загружается - всё нормально, GetDIBits - работает нормально, то есть возвращает 3 * W * H в случае с 24 битным битмапом.)
                  Неужели надо размер массива полученных точек делить на площадь его? :lool:
                    Цитата Rouse_ @
                    А цвет точки - у структуры PBitmapInfo есть параметр bmiColors, который является массивом структур TRGBQuad в котором и содержиться информация по каждому пикселю

                    Разве? Совсем нет. И кстати, для полноцветных битмапов данные в файле могут храниться структурах как RGBQUAD так и в RGBTRIPLE (определяется по BITMAPINFOHEADER.biBitCount).
                    Цитата Dmitry_177 @
                    Не понятно что это за массив bmiColors

                    Массив bmiColors содержится только в неполноцветных файлах, и это не цвета точек, это палитра. Сам массив изображения как правило начинается за массивом bmiColors. Но если рисунок полноцветный, то этот массив в файле отсутствует.
                    ЗЫ: никогда не вычисляй размер bmiColors через BITMAPINFOHEADER.biBitCount, т.к. если рисунок к примеру 256-ти цветный, то не факт что и записей в палитре будет 256. Как правило меньше.

                    Добавлено
                    Цитата WDaft @
                    Как бы мне получить реальный BPP битмапа? То есть то сколько бит на пиксель записано в фаиле?

                    Очень просто. Считывай заголовок с помощью BlockRead(sizeof(BITMAPINFOHEADER) + sizeof(BITMAPFILEHEADER)). Затем, если BITMAPINFOHEADER.biBitCount равен 16,24 или 32 то файл не содержит палитры, и размер рассчитывается как (W * H * (biBitCount / 8)).
                    Если biBitCount равен 1,2,4 или 8 то нужно расчитать размер палитры. Ее размер можешь вычислить как (sizeof(RGBQUAD) * biClrUsed). Сразу за ней и начинается изображение.
                    А теперь тонкости(мягкотелые без них не могут ;) Заголовок файла бывает двух видов:
                    BITMAPINFOHEADER и BITMAPCOREHEADER. Если попался CORE, то палитра хранится в формате RGBTRIPLE и ее размер расчитывается по bcBitCount. Это во первых. Во вторых старайся использовать как можно меньше полей заголовка, поскольку встречаются отклонения от стандарта, сам вычисляй. В третьих, палитровые рисунки могут быть сжаты по RLE. В четвертых, заголовки можешь определить по bcSize. В пятых - поле bfSize частенько некорректное, а BITMAPINFOHEADER начинается сразу за BITMAPFILEHEADER. Остальное мелочи ;)
                      AndNot, 10x! =)
                      Я предвидел ответ в виде этого метода. И всё же - нет ли WinAPIшного метода для определения битности по HBITMAPу?
                      Или только так? :huh:
                        Вот и фиг то что не припомню :( А загрузку подобным образом не только я делал, т.ч. может не зря?

                        Добавлено
                        А разве сложно через заголовок посмотреть BPP?
                          Не так сложно, но разве Микрософтовцы при загрузке Битмапа ИХНЕЙ же функцией не знают какой там BPP записан? Какого они кроют от нас эту инфу теперь?
                          И ведь всё равно при GetDIBits получается массив именно столько байт на пиксель, сколько в файле - то есть всё правильно.
                            Цитата WDaft @
                            Битмапа ИХНЕЙ же функцией не знают какой там BPP записан?

                            Зачем им это?
                            Цитата WDaft @
                            Какого они кроют от нас эту инфу теперь?

                            Я переправлю дидюшке биллу ;)
                            Цитата WDaft @
                            И ведь всё равно при GetDIBits получается массив именно столько байт на пиксель, сколько в файле - то есть всё правильно.

                            И это естественно, поэтому и есть функции преобразования к нужному тебе формату, при этом не обязательно знать уже загруженный, вот и получилась такая хрень. Хотя черт ее знает, может и есть какая апи.
                              Цитата AndNot @
                              Разве? Совсем нет.

                              Да? Странно, а вот спецификация данного формата говорит что да:

                              Цитата
                              Each bitmap file contains a bitmap-file header, a bitmap-information header,
                              a color table, and an array of bytes that defines the bitmap bits. The file
                              has the following form:

                              BITMAPFILEHEADER bmfh;
                              BITMAPINFOHEADER bmih;
                              RGBQUAD aColors[];
                              BYTE aBitmapBits[];

                              The bitmap-file header contains information about the type, size, and layout
                              of a device-independent bitmap file. The header is defined as a
                              BITMAPFILEHEADER structure.

                              The bitmap-information header, defined as a BITMAPINFOHEADER structure,
                              specifies the dimensions, compression type, and color format for the bitmap.

                              The color table, defined as an array of RGBQUAD structures, contains as many
                              elements as there are colors in the bitmap. The color table is not present
                              for bitmaps with 24 color bits because each pixel is represented by 24-bit
                              red-green-blue (RGB) values in the actual bitmap data area. The colors in the
                              table should appear in order of importance. This helps a display driver
                              render a bitmap on a device that cannot display as many colors as there are
                              in the bitmap. If the DIB is in Windows version 3.0 or later format, the
                              driver can use the biClrImportant member of the BITMAPINFOHEADER structure to
                              determine which colors are important.
                                Цитата Rouse_ @
                                Странно, а вот спецификация данного формата говорит что да

                                Ну и где здесь сказано что:
                                Цитата Rouse_ @
                                А цвет точки - у структуры PBitmapInfo есть параметр bmiColors, который является массивом структур TRGBQuad в котором и содержиться информация по каждому пикселю

                                bmiColors это именно массив палитры (в вышеприведенном файле это - RGBQUAD aColors[]), который у полноцветных отсутствует(в таком случае этого поля просто нет). Цвета точек расположены в массиве "BYTE aBitmapBits[]", сразу за палитрой(если есть), о чем я и толковал. И даже в большинстве непалитровых битмапов каждая точка хранится в структуре RGBTRIPLE, т.к. 32-х разрядные появились опосля(также как и 16-ти битные).
                                Несколько лет назад писал загрузчик бмп,кур и иконок под дос. Посмотри кусочек:
                                ExpandedWrap disabled
                                          sub     esp,size BitmapInfoHeader
                                          mov     edx,esp
                                          mov     ecx,size BitmapCoreHeader
                                          mov     esi,edx         ; esi   - входной буффеp
                                          mov     ah,3Fh
                                          int     21h             ; считали заголовок
                                      __core:                     ; пpедполагаем что заголовок BitmapCoreHeader
                                          movzx   ecx,[esi+BitmapCoreHeader.biBitCount]
                                          cmp     [esi+BitmapCoreHeader.biSize],size BitmapCoreHeader
                                          je      __read_palette
                                      __win:                      ; заголовок BitmapInfoHeader
                                          mov     ecx,size BitmapInfoHeader - size BitmapCoreHeader
                                          mov     ah,3Fh
                                          int     21h             ; считываем остаток заголовка
                                          movzx   ecx,[esi+BitmapInfoHeader.biBitCount]
                                   
                                          ; считываем и конвеpтиpуем палитpу (если нам это надо ;-)
                                      __read_palette:
                                          cmp     cl,18h
                                          je      __select_outpnt ; -> pисунок полноцветный,уходим!
                                          push    ecx             ; сохpаняем BPP
                                          ; получаем количество цветов
                                          mov     ebx,1
                                          shl     ebx,cl          ; ebx - количество цветов
                                          ; выделяем память под палитpу
                                          lea     ecx,[ebx*4]
                                          call    Alloc PASCAL,ecx
                                          xchg    edx,eax
                                          cmp     [esi+BitmapCoreHeader.biSize],size BitmapCoreHeader
                                          jne     __win_pal       ; -> виндозный pисунок
                                          sub     ecx,ebx         ; ecx - pазмеp палитpы в байтах
                                          mov     ah,3Fh
                                          int     21h             ; считываем палитpу
                                          ; пpеобpазуем в RGBQuad
                                          xchg    ecx,ebx         ; ecx - количество цветов
                                                                  ; ebx - pазмеp палитpы в байтах
                                          push    esi
                                          lea     edi,[edx+ecx*4-4]
                                          lea     esi,[edx+ebx-3]
                                          std
                                          xor     eax,eax
                                      __conv_pal:
                                          movsw
                                          lodsb
                                          stosw
                                          loop    __conv_pal
                                          cld
                                          pop     esi
                                          jmp     short __end_pal
                                   
                                      __win_pal:
                                          cmp     [esi+BitmapInfoHeader.biClrUsed],0
                                          je      __read_pal
                                          ; использована не вся палитpа
                                          mov     ebx,[esi+BitmapInfoHeader.biClrUsed]
                                      __read_pal:
                                          shl     ebx,2           ; ebx - pазмеp палитpы в байтах
                                          xchg    ecx,ebx         ; ecx - pазмеp палитpы
                                          mov     ah,3Fh
                                          int     21h             ; считываем палитpу
                                          xchg    edx,edi
                                   
                                          ; палитpа обpаботана
                                      __end_pal:
                                          pop     ecx

                                Если есть желание разбираться, то увидишь, про что я все это время толковал ;)
                                Код кстати рабочий. Проверен на сотнях бмпшек всех разновидностей.
                                0 пользователей читают эту тему (0 гостей и 0 скрытых пользователей)
                                0 пользователей:
                                Страницы: (3) [1] 2 3  все


                                Рейтинг@Mail.ru
                                [ Script execution time: 0,0459 ]   [ 16 queries used ]   [ Generated: 23.04.24, 20:35 GMT ]