Конференция "WinAPI" » перерисовка надписи [D7]
 
  • Dmitriy (20.08.10 10:15) [0]
    Здравствуйте!
    Задался вопросом разместить на форме Label средствами WinAPI. Но в WinAPI я еще новичек и поэтому прошу у вас совета. Как лучше поступить, какими методами воспользоваться? Мне нужно, чтобу можно было задать цвет, фон, прозрачность, и была возможность перерисовки.
    После поисков в сети наше в принципе то,что мне нужно - функции задания цвета текста, прозрачности фона, шрифта:

    SetBkMode(DC, TRANSPARENT);
    SetTextColor(DC, RGB(255, 0, 0));
    CreateSolidBrush(DC);
    SelectObject(DC, Font);


    Но вот проблема с перерисовкой не могу понять как перерисовать, чтобы надпись не наслаивалась на предыдущую.
    Нашел, что можно использовать BeginPaint. Перерисовка получается только без использования прозрачности, т.е. SetBkMode(DC, TRANSPARENT);
    Как применить прозрачность при перерисовке?
  • DVM © (20.08.10 12:10) [1]

    > Задался вопросом разместить на форме Label средствами WinAPI

    В WinAPI нет Label. Чтобы сделать где либо надпись на окне, ее там надо нарисовать в обработчике WM_PAINT.


    > Мне нужно, чтобу можно было задать цвет, фон, прозрачность,
    >  и была возможность перерисовки.

    Все в твоих силах, в обработчике WM_PAINT все отрисуешь как хочешь.


    > Перерисовка получается только без использования прозрачности,
    >  т.е. SetBkMode(DC, TRANSPARENT);

    DC ты где берешь? И как?
  • Dmitriy (20.08.10 12:43) [2]

    > Все в твоих силах, в обработчике WM_PAINT все отрисуешь
    > как хочешь.

    Может быть, но пока не получается :(


    > DC ты где берешь? И как?


    DC := BeginPaint(hwnd, PaintStruct);
  • DVM © (20.08.10 12:48) [3]

    > Dmitriy   (20.08.10 12:43) [2]

    Приведи сюда весь обработчик WM_PAINT
  • Dmitriy (20.08.10 13:00) [4]
    PaintStruct.hdc := DC;
    PaintStruct.rcPaint.TopLeft.X := 40;
    PaintStruct.rcPaint.TopLeft.Y := 40;
    PaintStruct.rcPaint.BottomRight.X := 250;
    PaintStruct.rcPaint.BottomRight.Y := 80;
    PaintStruct.fErase := true;

    DC := BeginPaint(hwnd, PaintStruct);
    SetBkMode(DC, TRANSPARENT);
    SetTextColor(DC, RGB(255, 0, 0));
    SelectObject(DC, Font);
    CreateSolidBrush(DC);
    DrawText(DC, PChar(Text), Length(Text), Rect, DT_LEFT);
    EndPaint(hwnd, PaintStruct);
  • DVM © (20.08.10 13:35) [5]

    > PaintStruct.hdc := DC;
    > PaintStruct.rcPaint.TopLeft.X := 40;
    > PaintStruct.rcPaint.TopLeft.Y := 40;
    > PaintStruct.rcPaint.BottomRight.X := 250;
    > PaintStruct.rcPaint.BottomRight.Y := 80;
    > PaintStruct.fErase := true;

    убери
  • DVM © (20.08.10 13:37) [6]

    > SelectObject(DC, Font);
    > CreateSolidBrush(DC);

    убери, тут все равно утечка ресурсов GDI
  • Dmitriy (20.08.10 14:16) [7]
    Убрать? А как тогда сделать, чтобы был нужный шрифт?
  • DVM © (20.08.10 14:39) [8]

    ....

       WM_PAINT:
         begin
           Result := OnPaint(Wnd, Msg, wParam, lParam);
         end;

    ....

    function OnPaint(Wnd: HWND; Msg: Integer; wParam: WPARAM; lParam: LPARAM): LRESULT;
    var
     rc: TRect;
     Font, OldFont: HFONT;
     S: string;
     DC: HDC;
     PaintStruct: TPaintStruct;
    begin
     Font := CreateFont(12, 0, 0, 0, FW_BOLD, 0, 0, 0, DEFAULT_CHARSET,
               OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH,
               'MS Sans Serif');
     S := 'bla-bla-bla';
     GetClientRect(Wnd, rc);

     DC := BeginPaint(Wnd, PaintStruct);
     OldFont := SelectObject(DC, Font);

     SetBkMode(DC, TRANSPARENT);
     SetTextColor(DC, RGB(255, 0, 0));

     DrawText(DC, PChar(S), Length(S), rc, 0);

     SelectObject(DC, OldFont);
     DeleteObject(Font);

     EndPaint(Wnd, PaintStruct);
     Result := 1;
    end;




    Само собой необязательно каждый раз создавать и уничтожать Font, достаточно это сделать 1 раз при старте программы.
  • DVM © (20.08.10 14:41) [9]
    Главное подчищай за собой ресурсы, иначе выделение и не освобождение ресурса в WM_PAINT очень быстро приведет к их исчерпанию.
  • Dmitriy (20.08.10 15:58) [10]
    Не получается :(
    Если фон прозрачный, то надписи накладываются друг на друга, а если если убрать SetBkMode(DC, TRANSPARENT), то все нормально перерисовывается, но с серым фоном...
  • DVM © (20.08.10 16:26) [11]
    у меня ничего не накладывается, серых прямоугольников (я правильно понял, они тебя смущают) у меня нет.

    DrawText(DC, PChar(S), Length(S), rc, 0);

    rc.Left := rc.Left + 20;
    rc.Top := rc.Top + 5;

    DrawText(DC, PChar(S), Length(S), rc, 0);

    выводит 2 надписи, одна поверх другой.
  • DVM © (20.08.10 16:28) [12]

    > то надписи накладываются друг на друга

    покажи скриншот, мне непонятно, что у тебя не так.
 
Конференция "WinAPI" » перерисовка надписи [D7]
Есть новые Нет новых   [134431   +11][b:0][p:0.001]