Russian Qt Forum

Qt => Пользовательский интерфейс (GUI) => Тема начата: vertus от Июня 28, 2012, 14:56



Название: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: vertus от Июня 28, 2012, 14:56
При переключении между окнами в ОС Windows меняется фон заголовка окна - у активного окна он становиться светлее чем у не активного.

Можно ли сделать чтобы фон заголовка не менялся?

WA_ShowWithoutActivating - не то, т.к. надо чтобы окно активировалось, но фон заголовка не менялся.

Спасибо за внимание!


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: Пантер от Июня 28, 2012, 15:01
Заголовки отрисовывает ОС, так что Кьют тут не при чем.
Скорее всего никак. :)


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: vertus от Июня 28, 2012, 15:06
Тогда другой вопрос. Если делать окно с флагом FramelessWindowHint, возможно ли нарисовать самому бордер и загаловок окна такой же, как и у окна Windows?


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: Bepec от Июня 28, 2012, 15:11
М... Помоему можно с winApi.

Ставишь хук на WM_NCACTIVATE и меняешь его, насколько я помню.

Так же где то всплывал вариант какого то флага в windows, но этого я никогда не делал.

PS самый простой способ посылать сообщение активности на то окно, но там какой то недостаток был, аля сбитие фокуса чтоли.

update: Если отрисовываешь сам - то рисуй что душе угодно. Да, можно.


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: vertus от Июня 28, 2012, 15:14
М... Помоему можно с winApi.

Ставишь хук на WM_NCACTIVATE и меняешь его, насколько я помню.


QCoreApplication::winEventFilter использовать т.е.?


update: Если отрисовываешь сам - то рисуй что душе угодно. Да, можно.


Проблема в том, что пользователь может менять стили окон, поэтому нужно не просто рисовать самому, а именно так, как установлено в системе.


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: Bepec от Июня 28, 2012, 15:17
Хм. Хм хм хм. Даже незнаю. winEventFilter позволяет реагировать на сообщения винды. А тут нужно изменение сообщения.

Ну попробуй - узнаешь. Я делал хуком.

Получить текущий стиль виндовс - опять таки winApi. Правда счас сложнее - тут уже градиент используется, но вроде бы можно.


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: vertus от Июня 28, 2012, 15:32
Да, в winEventFilter ничего не меняется.

Код:
bool CDXApplication::winEventFilter( MSG *message, long *result )
{
  if (message->message == WM_NCACTIVATE)
  {
    message->wParam = FALSE;
  }

  return false;
}
А как поставить хук? Это имеется ввиду хуки через dll?


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: Bepec от Июня 28, 2012, 15:36
Для хука на свою программу нужды в dll нету. (dll это для глобального хука)

А для обычного хватит и простой функции. Примеров завались. (типа на, почитай http://www.rsdn.ru/article/baseserv/winhooks.xml#EYAAC)





Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: vertus от Июня 28, 2012, 15:38
Ага, понял, спасибо!
Буду пробывать этот вариант.


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: Bepec от Июня 28, 2012, 15:42
Поищите в гугле на тему "цвет неактивного заголовка хук".
Там из примеров и можете дёрнуть.


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: Alex Custov от Июня 28, 2012, 16:31
Тогда другой вопрос. Если делать окно с флагом FramelessWindowHint, возможно ли нарисовать самому бордер и загаловок окна такой же, как и у окна Windows?

См. DrawCaption


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: vertus от Июля 02, 2012, 12:09
Проблему частично решил.

Для того, чтобы заголовок был активным независимо от активации окна можно применить следующий код:

Код:
HHOOK Hook;

LRESULT CALLBACK GetMsgProc(int code, WPARAM wParam, LPARAM lParam)
{
  PCWPRETSTRUCT pStruct = (PCWPRETSTRUCT)lParam;
  if (code == HC_ACTION)
  {
    if (pStruct->message == WM_NCACTIVATE)
    {
      pStruct->wParam = TRUE;
      DefWindowProc(pStruct->hwnd, pStruct->message, pStruct->wParam, pStruct->lParam);
    }
  }
  return CallNextHookEx(Hook, code, wParam, lParam);
}

int main(int argc, char *argv[])
{
  Hook = SetWindowsHookEx(WH_CALLWNDPROCRET, GetMsgProc, 0, GetCurrentThreadId() );
  //здесь код main
  UnhookWindowsHookEx(Hook);
}


Однако, проблема заключается в том, что когда активируется окно другого процесса, нужно возвращать неактивное состояние заголовка окна текущего процесса.


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: Bepec от Июля 02, 2012, 12:17
Не совсем ясно сформулировано.

У тебя была задача - чтоб он не становился неактивным. Ты это сделал - молодца.

Теперь у тебя появилась другая проблема - эм...

Судя по всему, если переключение окон внутри твоей программы - надо постоянно активно отрисовывать, а если активен другой процесс(не твой), тогда надо неактивным делать?


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: vertus от Июля 02, 2012, 12:31
Судя по всему, если переключение окон внутри твоей программы - надо постоянно активно отрисовывать, а если активен другой процесс(не твой), тогда надо неактивным делать?

Да, так и есть, проблема в этом.


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: Bepec от Июля 02, 2012, 12:36
Есть вроде 2 способа на мой взгляд:
1) можно по таймеру смотреть, какое окно активно и по его hwnd получать id процесса, который его запустил. Сравнивать со своим процессом и там уже решать - светить или не светить заголовок.
2) (глуповатый метод => ) вынести обработку(хук) в невидимое окно winApi'шное и ему слать команды когда фокус уходит с твоих окон.


Ну в принципе пока всё у меня.


Название: Re: OS Windows. Изменение фона заголовка окна при активации и деактивации.
Отправлено: vertus от Июля 02, 2012, 15:15
Все оказалось просто элементарно.

Я добавил сигнал дочерним окнам который эмитится когда они активируются.
В слоте обрабатывающем эти сигналы вызываю win32 функцию:
Код:
DefWindowProc(effectiveWinId(), WM_NCACTIVATE, TRUE, 0);
effectiveWinId() - hwnd окна у которого должен оставаться заголовок актвиным.
WM_NCACTIVATE - это и есть идентификатор для сообщения отрисовки заголовка.
TRUE - ставлю, чтобы заголовок отображался активным.
0 - этот параметр так и не разобрался как правильно выставить, но вроде с нулем все работает.

Соответственно никаких хуков теперь не нужно.