Как сделать затемнение (как при выключении винды)

Тема в разделе "WASM.WIN32", создана пользователем darkcoder, 13 июн 2007.

  1. darkcoder

    darkcoder New Member

    Публикаций:
    0
    Регистрация:
    7 фев 2007
    Сообщения:
    58
    т.е. чтобы моя прога была в нормальном цвете, а все остальное плавно становилось черно-белым, как при пуск->завершение работы
     
  2. crypto

    crypto Active Member

    Публикаций:
    0
    Регистрация:
    13 дек 2005
    Сообщения:
    2.533
  3. darkcoder

    darkcoder New Member

    Публикаций:
    0
    Регистрация:
    7 фев 2007
    Сообщения:
    58
    ась?Ж)
     
  4. kush

    kush New Member

    Публикаций:
    0
    Регистрация:
    24 май 2007
    Сообщения:
    46
    Можно попробовать ч/з DC Desktop-a
     
  5. rain

    rain New Member

    Публикаций:
    0
    Регистрация:
    22 апр 2006
    Сообщения:
    976
    на сайте есть пример scramble.zip, который извращает текущую картинку на мониторе, а как затемнить думаю сам догадаешься
     
  6. Avoidik

    Avoidik New Member

    Публикаций:
    0
    Регистрация:
    29 дек 2004
    Сообщения:
    288
    Адрес:
    Russia
    на code-project.com есть пример
     
  7. tinok

    tinok New Member

    Публикаций:
    0
    Регистрация:
    2 июн 2007
    Сообщения:
    26
    Можно, наверное, создать окно без границ с WS_EX_TOPMOST, развернув на весь экран.
    Ну, а, дальше, сделать постепенное приравнивание байтов цвета RGB к среднему арифметическому.
     
  8. Mental_Mirror

    Mental_Mirror New Member

    Публикаций:
    0
    Регистрация:
    7 май 2007
    Сообщения:
    431
  9. Mental_Mirror

    Mental_Mirror New Member

    Публикаций:
    0
    Регистрация:
    7 май 2007
    Сообщения:
    431
    tinok
    Не, так не получиться, будут тормоза и мигание. В XP какой-то хитрый механизм введенный вместе с темами. Кто-нибудь об этом слышал?
     
  10. Mental_Mirror

    Mental_Mirror New Member

    Публикаций:
    0
    Регистрация:
    7 май 2007
    Сообщения:
    431
  11. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    Зачем окно без границ? Сделать тогда уж CreateDC("DISPLAY",0,0,0) и там орудовать с цветами
     
  12. Mental_Mirror

    Mental_Mirror New Member

    Публикаций:
    0
    Регистрация:
    7 май 2007
    Сообщения:
    431
    На язык кода не кричите. На других языках будет аналогично! Статья отличная с CodeProject. Но сделать можно лучше чем в статье, т.к. там вначале эффект мигания. Итак. Основная идея - создаем другой десктоп, там окно и рисуем по таймеру постепенно засерЯем. Десктоп создается функцией CreateDesktop. Далее вызываем SetThreadDesktop тем самым ассоциируем вызывающий поток с новый десктопом. Теперь все окна созданные данным потоком будут создаваться и выводиться на новом десктопе. Переключение делается функцией SwitchDesktop. Важно тут заметить зачем вообще окно создается на новом десктопе. Можно создать окно неперекрывающееся, вырисовывать его и брать экран и рисовать на его hdc. Это действительно работает, если бы не другие окна которые постоянно лезут наверх и фокус с нашего окна постоянно уходит. Тривиально это решить не удается. Т.о. мы используем другой десктоп и как результат - других окон кроме наших там нет вообще, и еще отключатся разные ненужные в данном случае клавиши - Alt+Tab, Win и другие, потому что их обрабатывают хуки експлорера, а у каждого десктопа свой набор хуков. Далее у нового класса окна делаем стиль CS_SAVEBITS, чтобы лишний раз не перерисовываться, а background устанавливаем в NULL. Таймер создаем в оконной прицедуре. На самом окне рисуем функциями GDI+, засерение предыдущей картинки в памяти также с помощью функций GDI+. Функция LockBits даем возможность менять пиксели картинки, возвращая область памяти с пикселями. Функция UnlockBits копирует измененные пиксели обратно в объект типа Bitmap. Рисуем с помощью ImageDraw как обычно в GDI+. Скрин экрана все знают как получить. Для преобразования обычного TBITMAP, в TGPBITMAP (GDI+) делаем так
    Код (Text):
    1. GpBitmap := TGpBitmap.Create(Bitmap.Handle,Bitmap.Palette);
    Далее функция одного шага засерения. В GpBitmap - старая картинка.
    Код (Text):
    1. procedure DimBitmap;
    2. var
    3.   BitmapData:TBitmapData;
    4.   Rect:TGpRect;
    5.   ScanData:PBYTE;
    6.   nOffset:integer;
    7.   red,green,blue:integer;
    8.   i,j,width,height:integer;
    9. begin
    10.   Rect.X := 0;
    11.   Rect.Y := 0;
    12.   Rect.Width := Screen.Width;
    13.   Rect.Height := Screen.Height;
    14.   GpBitmap.LockBits(Rect,3,PixelFormat24bppRgb,BitmapData);
    15.   ScanData := BitmapData.Scan0;
    16.   nOffset := BitmapData.Stride - GpBitmap.GetWidth()*3;
    17.   width := GpBitmap.GetWidth;
    18.   height := GpBitmap.GetHeight;
    19.   for i:=0 to height-1 do
    20.   begin
    21.     for j:=0 to width-1 do
    22.     begin
    23.       blue := ScanData^;
    24.      green := pbyte((dword(ScanData)+1))^;
    25.       red := pbyte((dword(ScanData)+2))^;
    26.       case ColorStep of
    27.         1:
    28.         begin
    29.           ScanData^  := byte(round((0.001 * red + 0.286 * green + 0.713 * blue)));
    30.           pbyte((dword(ScanData)+1))^  := byte(round((0.001 * red + 0.986 * green + 0.013 * blue)));
    31.           pbyte((dword(ScanData)+2))^  := byte(round((0.899 * red + 0.087 * green + 0.013 * blue)));
    32.         end;
    33.         2:
    34.         begin
    35.           ScanData^  := byte(round((0.099 * red + 0.387 * green + 0.514 * blue)));
    36.           pbyte((dword(ScanData)+1))^  := byte(round((0.099 * red + 0.887 * green + 0.014 * blue)));
    37.           pbyte((dword(ScanData)+2))^  := byte(round((0.699 * red + 0.287 * green + 0.013 * blue)));
    38.         end;
    39.         3:
    40.         begin
    41.           ScanData^  := byte(round((0.199 * red + 0.487 * green + 0.314 * blue)));
    42.           pbyte((dword(ScanData)+1))^  := byte(round((0.199 * red + 0.787 * green + 0.014 * blue)));
    43.           pbyte((dword(ScanData)+2))^  := byte(round((0.499 * red + 0.487 * green + 0.014 * blue)));
    44.         end;
    45.         4:
    46.         begin
    47.           ScanData^  := byte(round((0.299 * red + 0.587 * green + 0.114 * blue)));
    48.           pbyte((dword(ScanData)+1))^  := ScanData^;
    49.           pbyte((dword(ScanData)+2))^  := ScanData^;
    50.           end;
    51.         end;
    52.         ScanData := pbyte(dword(ScanData) + 3);
    53.       end;
    54.       ScanData := pbyte(dword(ScanData) + nOffset);
    55.     end;
    56.   end;
    57.   GpBitmap.UnlockBits(BitmapData);
    58. end;
    Само рисование тривиально.
    Код (Text):
    1. graphics := TGPGraphics.Create(DC);
    2. graphics.DrawImage(GpBitmap,0,0);
    3. graphics.Free;
     
  13. Mental_Mirror

    Mental_Mirror New Member

    Публикаций:
    0
    Регистрация:
    7 май 2007
    Сообщения:
    431
    Great
    Нет, окно нужно. Потому как мы над серым фоном собираемся выводить другое окно, а полностью экран мы можем перерисовать имея полноэкранное окно.
     
  14. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    Я могу перерисовывать экран не имея окон
     
  15. Mental_Mirror

    Mental_Mirror New Member

    Публикаций:
    0
    Регистрация:
    7 май 2007
    Сообщения:
    431
    Great
    Вах, отлично. Как узнаешь, что экран похерился окном выше экрана? Или будем перерисоввывать по таймеру? Если есть окно, то есть и WM_PAINT.
     
  16. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    А ну это уже смотря как тебе надо сделать затемнение такое. Если надолго - то конечно нужно окно. А если просто нарисовать и забыть, то можно и просто так