На главную Наши проекты:
Журнал   ·   Discuz!ML   ·   Wiki   ·   DRKB   ·   Помощь проекту
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
! Правила раздела Visual C++ / MFC / WTL (далее Раздела)
1) На Раздел распространяются все Правила Форума.
2) Перед тем, как создать новый топик, убедитесь, что Вы читали Правила создания тем в Разделе.
3) Вопросы, не связанные с программированием (настройки MS Visual Studio, книги, библиотеки и т.д.),
обсуждаются в разделе C/C++: Прочее
4) Вопросы разработки .NET (Windows Form, C++/CLI и т.п.) приложений на Visual C++/C# обсуждаются в разделе .NET.
5) Нарушение Правил может повлечь наказание со стороны модераторов.

Полезные ссылки:
user posted image FAQ Раздела user posted image Обновления для FAQ Раздела user posted image Поиск по Разделу user posted image MSDN Library Online
Модераторы: ElcnU
Страницы: (2) 1 [2]  все  ( Перейти к последнему сообщению )  
> Мерцание с BitBlt
    Цитата Олег М @
    Ты работаешь в многозадачной системе. И в любом случае, когда вывод изображения не является атомарным, ты получишь мерцание.

    Нет, это не так.
    И вижу сейчас на экране прямое опровержение твоего предположения.
      Мерцание обычно из-за того, что кадр перерисовывается 2 и более раз. От непересекающихся BitBlt мерцаний быть не должно. Скорее всего проблема в том, что перерисовывается сперва фон окна.

      Добавлено
      Sawella, ты поверх чего свою рамку рисуешь?

      Добавлено
      Цитата Олег М @
      И в любом случае, когда вывод изображения не является атомарным, ты получишь мерцание.

      :wacko:

      Добавлено
      И лучше вынести все лишние из цикла рисования:
      ExpandedWrap disabled
        #include <windows.h>
        using namespace std;
         
        void DrawSquare(HDC aHdc, HDC hcDevice)
        {
            for (int x = 1920 / 2.5; x < 1920 - (1920 / 2.5); x++) for (int y = 1080 / 3.5; y < (1080 / 3.5) + 2; y++) //вверх
            {
                BitBlt(aHdc, x, y, 2, 2, hcDevice, 0, 0, SRCCOPY);
            }
            for (int xx = 1920 / 2.5; xx < 1920 - (1920 / 2.5); xx++) for (int yy = 1080 - (1080 / 2.1); yy < (1080 - (1080 / 2.1)) + 2; yy++) //низ
            {
                BitBlt(aHdc, xx, yy, 2, 2, hcDevice, 0, 0, SRCCOPY);
            }
            for (int xx = 1920 / 2.5; xx < (1920 / 2.5) + 2; xx++) for (int yy = 1080 / 3.5; yy < 1080 - (1080 / 2.1); yy++) //левая сторона
            {
                BitBlt(aHdc, xx, yy, 2, 2, hcDevice, 0, 0, SRCCOPY);
            }
            for (int xx = 1920 - (1920 / 2.5); xx < (1920 - (1920 / 2.5)) + 2; xx++) for (int yy = 1080 / 3.5; yy < 1080 - (1080 / 2.1); yy++) //правая сторона
            {
                BitBlt(aHdc, xx, yy, 2, 2, hcDevice, 0, 0, SRCCOPY);
            }
        }
         
        int main()
        {
            HWND aHwnd = GetDesktopWindow();
            HDC aHdc = GetDC(aHwnd);
            HDC hcDevice = CreateCompatibleDC(aHdc);
            HBITMAP hcBitmapDevice = CreateCompatibleBitmap(aHdc, 2, 2);
            HGDIOBJ bufBm = (HBITMAP)SelectObject(hcDevice, hcBitmapDevice);
            while (true)
            {
                DrawSquare(aHdc, hcDevice);
            }
            ReleaseDC(aHwnd, aHdc);
         
            DeleteDC(aHdc);
            DeleteDC(hcDevice);
         
            DeleteObject(hcBitmapDevice);
            DeleteObject(bufBm);
            return 0;
        }

      В целом подход рисовать прямо на DesktopWindow довольно бредовый и мерцания тут практически неизбежны, если другие программы будут тоже что-то активно рисовать.
      Сообщение отредактировано: shm -
        Цитата shm @
        Sawella, ты поверх чего свою рамку рисуешь?

        Поверх рабочего стола и над всеми приложениями.

        Цитата shm @
        И лучше вынести все лишние из цикла рисования:

        Это да, но мерцания не исчезли. Если делать отдельно всё, как у Вас или как мне дали пример выше , мерцаний меньше это да, но я в итоге вставляю в свой while, а там идут разные проверки и в итоге пока код доходит до рисования, всё это мерцает.

        Цитата Олег М @
        Сценарий использования BitBlt примерно следующий:
        - Создаёшь контекст, связанный с bitmap (у тебя это сделано, не знаю насколько правильно)
        - Рисуешь в этом контексте то, что тебе нужно. В твоём случае что-то типа LineTo(hcDevice, ......
        - Копируешь содержимое контекста в контекст окна при помощи BitBlt (Один раз!)

        Я вот так пробую, но пока нечего.

        ExpandedWrap disabled
          HDC memDC, hdc;
           
          hdc = GetDC(GetDesktopWindow());
          memDC = CreateCompatibleDC(hdc);
           
          for (int xx = 1920 / 2.5; xx < 1920 - (1920 / 2.5); xx++) for (int yy = 1080 / 3.5; yy < (1080 / 3.5) + 2; yy++) //верх
               SetPixel(memDC, xx, yy, RGB(255, 0, 255));
          for (int xx = 1920 / 2.5; xx < 1920 - (1920 / 2.5); xx++) for (int yy = 1080 - (1080 / 2.1); yy < (1080 - (1080 / 2.1)) + 2; yy++) //низ
               SetPixel(memDC, xx, yy, RGB(255, 0, 255));
          for (int xx = 1920 / 2.5; xx < (1920 / 2.5) + 2; xx++) for (int yy = 1080 / 3.5; yy < 1080 - (1080 / 2.1); yy++) //левая сторона
               SetPixel(memDC, xx, yy, RGB(255, 0, 255));
          for (int xx = 1920 - (1920 / 2.5); xx < (1920 - (1920 / 2.5)) + 2; xx++) for (int yy = 1080 / 3.5; yy < 1080 - (1080 / 2.1); yy++) //правая сторона
               SetPixel(memDC, xx, yy, RGB(255, 0, 255));
           
          BitBlt(hdc, 2, 2, 222, 222, memDC, 0, 0, SRCCOPY);
        Сообщение отредактировано: Sawella -
          [quote=Sawella,1486483700,3705982]Я вот так пробую, но пока нечего.[/quot
          А bitmap привязываешь?
          ExpandedWrap disabled
                HBITMAP hcBitmapDevice = CreateCompatibleBitmap(aHdc, 2, 2);
                HGDIOBJ bufBm = (HBITMAP)SelectObject(hcDevice, hcBitmapDevice);
            Цитата Sawella @
            Поверх рабочего стола и над всеми приложениями.

            Спасибо, кэп. Попробуй просто над голым рабочим столом. Тоже мерцает?
              Цитата Олег М @
              А bitmap привязываешь?


              Вот сейчас на чистом проекте пробовал, нечего.
              ExpandedWrap disabled
                #include <windows.h>
                using namespace std;
                 
                void DrawLine(HDC hdc, HDC memDC)
                {
                    HBITMAP hcBitmapDevice = CreateCompatibleBitmap(hdc, 2, 2);
                    HGDIOBJ bufBm = (HBITMAP)SelectObject(memDC, hcBitmapDevice);
                 
                    for (int xx = 1920 / 2.5; xx < 1920 - (1920 / 2.5); xx++) for (int yy = 1080 / 3.5; yy < (1080 / 3.5) + 2; yy++) //верх
                        SetPixel(memDC, xx, yy, RGB(255, 0, 255));
                    for (int xx = 1920 / 2.5; xx < 1920 - (1920 / 2.5); xx++) for (int yy = 1080 - (1080 / 2.1); yy < (1080 - (1080 / 2.1)) + 2; yy++) //низ
                        SetPixel(memDC, xx, yy, RGB(255, 0, 255));
                    for (int xx = 1920 / 2.5; xx < (1920 / 2.5) + 2; xx++) for (int yy = 1080 / 3.5; yy < 1080 - (1080 / 2.1); yy++) //левая сторона
                        SetPixel(memDC, xx, yy, RGB(255, 0, 255));
                    for (int xx = 1920 - (1920 / 2.5); xx < (1920 - (1920 / 2.5)) + 2; xx++) for (int yy = 1080 / 3.5; yy < 1080 - (1080 / 2.1); yy++) //правая сторона
                        SetPixel(memDC, xx, yy, RGB(255, 0, 255));
                 
                    BitBlt(hdc, 2, 2, 222, 222, memDC, 0, 0, SRCCOPY);
                 
                    //DeleteDC(hdc);
                    //DeleteDC(memDC);
                 
                    DeleteObject(hcBitmapDevice);
                    DeleteObject(bufBm);
                }
                 
                int main()
                {
                    HDC memDC, hdc;
                 
                    hdc = GetDC(GetDesktopWindow());
                    memDC = CreateCompatibleDC(hdc);
                    
                    while (true)
                    {
                        DrawLine(hdc, memDC);
                    }
                 
                    system("pause");
                    return 0;
                }


              Добавлено
              Цитата shm @
              Спасибо, кэп. Попробуй просто над голым рабочим столом. Тоже мерцает?

              Понятно что если я нарисую просто на раб.столе и не каких действий , то мерцать не будет. А когда идут действия, например скролить в браузере , то мерцает.
                Цитата Sawella @
                Вот сейчас на чистом проекте пробовал, нечего.

                В данном случае у тебя мерцает из-за того, что ты пытаешься рисовать в чужом окне. Которое перерисовывается между твоими вызовами. Здесь ты так ничего не сделаешь.
                Тут либо надо перехватывать сообщение WM_PAINT, либо что-то типа того

                Добавлено
                BitBlt, иначе двойная буферизация, используется когда тебе нужно сделать какой-то сложный рисунок, потом одномоментно вывести его на экран, в своём окне.
                  Цитата Sawella @
                  А когда идут действия, например скролить в браузере , то мерцает.

                  Оно и должно. Ибо ты делаешь неправильно. Рисуй свое окно поверх всех и тогда мерцать не будет.

                  Добавлено
                  [C++] Окно произвольной формы по альфа-каналу из PNG-маски
                    Цитата Sawella @
                    Понятно что если я нарисую просто на раб.столе и не каких действий , то мерцать не будет. А когда идут действия, например скролить в браузере , то мерцает.

                    Могу огорчить тебя ещё сильнее.
                    На WIN7 у меня это работает.
                    В WINXP - нет, и разбираться почему-то не хочется.
                    Точно помню, что похожие мероприятия в WIN98 работали.
                    В виртуальных машинах тоже не работает.
                    Если подключиться к компу с WIN7 (где программа гарантировано работает) "радмином",
                    опять плохо - избражение, выводимое программой, не видно.
                    ---
                    Всё эти исследования абсолютно бессмысленны.
                    Вероятно, есть большая зависимость от аппаратных средств (видео-карта) и драйверов.
                    Вариант с браузером я исследовал - всё работает отлично.
                    Даже повех воспроизводимого он-лайн мультфильма с youtube.
                    Но это именно на моём компьютере, на любом другом может ничего не получиться.
                    Сообщение отредактировано: ЫукпШ -
                      1) BitBlt действительно одна из первых операций, которые стали ускорять аппаратным путём на видеокарте (2D). Поэтому результат сильно зависит от железа, драйверов, разрешения экрана и т.п.
                      2) Если хочется рисовать поверх всего-всего, то я бы пошёл по пути полноэкранного layered window, у которого фон прозрачный (но надо проверять на Win7 со включенным режимом Aero - могут быть конфликты по отрисовке, народ жаловался)
                      0 пользователей читают эту тему (0 гостей и 0 скрытых пользователей)
                      0 пользователей:


                      Рейтинг@Mail.ru
                      [ Script execution time: 0,0448 ]   [ 17 queries used ]   [ Generated: 26.04.24, 08:30 GMT ]