Как надежно менять цвет текста подсказки в RadioButton ?

Вопросы программирования и использования среды Lazarus.

Модератор: Модераторы

Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alex2013 » 28.03.2024 15:51:40

Вообщем пока сделал как-то так.
Изображение
(Работает, и даже масштабирование (причем исключительно при перезапуске программы ) только пунктирную рамочку выделения непонятно почему сбивает по ширине )
Но сделано это на редкость кодово ( просто "нарисовал" ТLabel поверх RadioButton подобрав шаг смещения "в ручную" )
В принципе в этом не было бы ничего страшного если бы я использовал это фокус на "статической форме", но проблема в том, что форма заполняется динамически.
Так что ни черт ни бог не знает, что там будут за настройки ОС и какие шрифты и как это отразится на контролах созданных динамически . ( Разумеется я использую Font.GetTextHeight и т.п. но как показвает практика этого бывает недостаточно)
В общем может у кого-то хотя-бы какие-то идеи есть? Бо у меня они определенно закончились .... :roll:
Зы
Попытки ловить WM_CtlColor и WM_CtlColorStatic ничего не дали.
Последний раз редактировалось Alex2013 29.03.2024 03:09:44, всего редактировалось 1 раз.
Alex2013
долгожитель
 
Сообщения: 2937
Зарегистрирован: 03.04.2013 11:59:44

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Sharfik » 29.03.2024 00:33:32

Ничего непонятно :)
Аватара пользователя
Sharfik
энтузиаст
 
Сообщения: 763
Зарегистрирован: 20.07.2013 01:04:30

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alex2013 » 29.03.2024 02:32:18

Sharfik писал(а):Ничего непонятно :)

Все просто! Есть RadioButton стандартное MyRadioButton.Font. Color:= clRed; не работает со времен Дэльфи 7 .
(Что в дельфи что в лазарусе ) И как результат буквы "подсказки" всегда выводятся черным цветом что для темного фона фатально.Как-то обойти это дело как случае CheckBox найдя готовое решение не получилось. Нашел временную затычку : "нарисовать" текст поверх текущего . (Просто вставил ТLabel по заданным координатам бо мучать класс ТRadioButton прикрывая перерисовку как бы не кривее и точно будет мнение удобно в отладке . )

Есть чуть более простой путь перекрытие обработчика WM_CtlColorХХХХ , WM_CtlColorStatic ( и тому подобных сообщений ) в форме но тут он не сработал . (WM_CTLCOLORBTN вроде есть но почему-то не вызывается хотя возможно я где-то что-то напутал )
Зы
Вся беда этой штуки в том что это стандартный элемент винды за отрисовку которого отвечает сама система, а LCL просто создает оболочку вокруг стандартного интерфейса WinAPI.

Временный код
Код: Выделить всё
  Lst:=Tlist.Create;
  EI:=Sl.GetEnumerator;

   While EI.MoveNext do
       begin
        CControl:= TRadioButton.Create(SubP);
        CControl.Align:=alBottom;CControl.Font.Color:=clWhite;
        S1:=EI.GetCurrent; FillChar(s1[1],s1.Length,'_');
        TRadioButton(CControl).Caption:=S1+'__';
        TRadioButton(CControl).Alignment:=taLeftJustify;
        SubP.InsertControl(CControl);

      L_RB:= TLabel.Create(SubP);
      L_RB.Caption:=' '+EI.GetCurrent;
      L_RB.Font.Color:=clWhite;
      L_RB.Top:=3+(SubP.ControlCount-1)*(3+P.Font.GetTextHeight('|')); //! Вот эта строчка самая "подозрительная".
      L_RB.Left:=1;
      Lst.add(L_RB);
    end;
    Ei.Free;

    //--------------------
    EL:=Lst.GetEnumerator;
    While EL.MoveNext do
     SubP.InsertControl(Tlabel(EL.GetCurrent));
    El.Free;
    Lst.Free;
///     
Последний раз редактировалось Alex2013 29.03.2024 10:34:28, всего редактировалось 1 раз.
Alex2013
долгожитель
 
Сообщения: 2937
Зарегистрирован: 03.04.2013 11:59:44

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Снег Север » 29.03.2024 07:56:34

Найти замену в библиотеках компонентах или писать собственный компонент. Ваш Кэп, не благодарите.
Аватара пользователя
Снег Север
долгожитель
 
Сообщения: 2995
Зарегистрирован: 27.11.2007 16:14:47

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alexander » 29.03.2024 08:54:53

Скорее всего это называется не подсказка (hint), а лейбл (наклейка, надпись).

Вся беда этой штуки в том что это стандартный элемент винды за отрисовку которого отвечает сама система, а LCL просто создает оболочку вокруг стандартного интерфейса WinAPI.


Скорее всего здесь заключается неявная ошибка. До какой-то степени это так, но не в целом. Часть функций (каркас) конечно задействуются, но основная масса собственная отрисовка. Для того чтобы понять это, нужно понять методом исключения, что Лазарус скорее "Делфи для Линукс", а здесь тоже есть Паскаль, есть Лазарус, в нём есть RadioButton, есть Label, а WinAPI нет и всё работает. То есть странно именно для Лазаруса искать эту функцию в WinAPI.
Аватара пользователя
Alexander
энтузиаст
 
Сообщения: 695
Зарегистрирован: 18.12.2005 19:10:00
Откуда: оттуда

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alex2013 » 29.03.2024 10:35:06

Снег Север писал(а):Найти замену в библиотеках компонентах или писать собственный компонент. Ваш Кэп, не благодарите.

:D
Зы
Гораздо более удивительно в сети так мало инфы на данную тему . Понятно что RadioButton применятся не так уж часто и обычно на отдельной панельке но все-же не настолько же редко что бы не было хотя-бы обсуждения!
Найти замену наверное можно, но как это было например со скроллбаром, в "левых" компонентах часто заметно не хватает функционала. На писать или "эмулировать" свой компонет имеет смысл если задача в принципе не имеет другого решения и/или проблема возникает достаточно часто .

Добавлено спустя 8 минут 11 секунд:
Alexander писал(а):Скорее всего это называется не подсказка (hint), а лейбл (наклейка, надпись).

Вся беда этой штуки в том что это стандартный элемент винды за отрисовку которого отвечает сама система, а LCL просто создает оболочку вокруг стандартного интерфейса WinAPI.


Скорее всего здесь заключается неявная ошибка. До какой-то степени это так, но не в целом. Часть функций (каркас) конечно задействуются, но основная масса собственная отрисовка. Для того чтобы понять это, нужно понять методом исключения, что Лазарус скорее "Делфи для Линукс", а здесь тоже есть Паскаль, есть Лазарус, в нём есть RadioButton, есть Label, а WinAPI нет и всё работает. То есть странно именно для Лазаруса искать эту функцию в WinAPI.

1 В принципе согласен "подсказка" это hint а тут скорре "описание варианта выбора" но лейба тоже пойдет.
2 Читал что проблемы началась после того как в Дельфи научили использовать манифест. ( в современным программах он включен по умолчанию )
3 WinAPI в лазарусе навалом( функционал WinAPI доступен почти полностью) . Другое дело что юзать его та еще "попаболь" да и проблемы вылезают те же самые . ( типа невозможности свободно менять цвет кнопки )

Добавлено спустя 1 час 3 минуты 32 секунды:
Алиса Яндексовна подсказала...
RadioButton1.Style := RadioButton1.Style + [tfFlat]
Это сделает радиокнопку плоской, без градиента и прочего, но зато позволит менять цвет текста.

Надо проверить.
... Не работает!
Последний раз редактировалось Alex2013 29.03.2024 12:56:00, всего редактировалось 1 раз.
Alex2013
долгожитель
 
Сообщения: 2937
Зарегистрирован: 03.04.2013 11:59:44

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alexander » 29.03.2024 12:03:22

А SetTextColor не срабатывает ?

В старину я делал так:

Код: Выделить всё
DC := GetWindowDC(hwnd); {WDC := }BeginPaint(hwnd, p);

if app.tun.mute or app.tun.NoAct then BkColor := colr_rd else BkColor := colr_db;
  if app.tun.mute or app.tun.NoAct then BColor := hb_rd else BColor := hb_db;

r.Left := 0; r.Right := FWidth; r.Top := 0; r.Bottom := FHeight;

FillRect(DC, r, BColor);

SelectObject(DC, hf_clock);

if app.orgtodaycount > 0 then
    SetTextColor(DC, colr_white) else
    SetTextColor(DC, colr_yl);
SetBkColor(dc, BkColor);
SetTextAlign(dc, TA_CENTER);

      EndPaint(hwnd, p);
Аватара пользователя
Alexander
энтузиаст
 
Сообщения: 695
Зарегистрирован: 18.12.2005 19:10:00
Откуда: оттуда

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alex2013 » 29.03.2024 15:29:15

Оказывается "Алиса права"(тм) правда пришлось творчески "допилить её совет напильником" .
Изображение
Единственный недостаток чуть меньшая точка отмечающая выделение. :idea:
Но это уже дело десятое.
Добавлено спустя 7 минут 37 секунд:
Подключаю модуль.
Uses UxTheme,...
Заполнение...

Код: Выделить всё
...
Var
СControl:TWinControl;
SubP:TPanel;
Sl:TSrtringList;
EI : TStringsEnumerator; 
...
   EI:=sl.GetEnumerator;
   While EI.MoveNext do
       begin
        CControl:= TRadioButton.Create(SubP);
        C11:=CControl;// Запоминаю какой нибудь TRadioButton
        CControl.Align:=alBottom;
        CControl.Font.Color:=clLime;//clWhite;
        TRadioButton(CControl).Caption:=ei.Current;
        TRadioButton(CControl).Alignment:=taLeftJustify;
        SubP.InsertControl(CControl);
    end;
    Ei.Free;
...

А потом делаю вот такой фокус ...
Код: Выделить всё
// FormActivate нужен чтобы были "живые" Handle 
//UxTheme.SetWindowTheme работает только с активными контролами .   
procedure TForm1.FormActivate(Sender: TObject);
begin
With TPanel(c11.Owner).GetEnumeratorControls do
begin
while MoveNext do
   if Current.ClassType=TRadioButton then
   UxTheme.SetWindowTheme(TWinControl(Current).Handle,nil,'');
free;
end;
end;


Разумеется это просто упрощенный тест который работает только при одном наборе RadioButton
И вообще без многих проверок но как пример вполне годится
( Суть в том что SetWindowTheme кроме прочего насильно включает "плоский" режим)

Добавлено спустя 34 минуты 29 секунд:
Alexander писал(а):А SetTextColor не срабатывает ?

В старину я делал так:

Код: Выделить всё
DC := GetWindowDC(hwnd); {WDC := }BeginPaint(hwnd, p);

if app.tun.mute or app.tun.NoAct then BkColor := colr_rd else BkColor := colr_db;
  if app.tun.mute or app.tun.NoAct then BColor := hb_rd else BColor := hb_db;

r.Left := 0; r.Right := FWidth; r.Top := 0; r.Bottom := FHeight;

FillRect(DC, r, BColor);

SelectObject(DC, hf_clock);

if app.orgtodaycount > 0 then
    SetTextColor(DC, colr_white) else
    SetTextColor(DC, colr_yl);
SetBkColor(dc, BkColor);
SetTextAlign(dc, TA_CENTER);

      EndPaint(hwnd, p);


Это разумеется тоже вариант, но он "на несколько этажей ниже" и я до него просто не добрался ...
(ИМХО Почти всегда если есть возможность лучше не лезть в перерисовку через WinAPI, а то внезапно вылезают кучи проблем с кодировкой,видимостью, центровкой и еще черт знает чем ... )
Alex2013
долгожитель
 
Сообщения: 2937
Зарегистрирован: 03.04.2013 11:59:44

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alexander » 29.03.2024 18:05:37

Ну да, так и есть. Тогда может быть написать багрепорт разработчикам Лазаруса да и всё ?
Аватара пользователя
Alexander
энтузиаст
 
Сообщения: 695
Зарегистрирован: 18.12.2005 19:10:00
Откуда: оттуда

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alex2013 » 29.03.2024 20:07:10

Непередаваемое ощущение сломанного тессеракта... :wink: :idea:
(Зато без лишних списков которые того гляди запутаются при повтором чтении )
Изображение

Это как-бы исправленный код для возможности пропатчить несколько динамически созданных списков RadioButton .
(Разумеется все привязано к конкретной программе но сама по себе идея вполне масштабируется )
Код: Выделить всё
E:=ScrollBox1.GetEnumeratorControls;// Левел 1  ( обычный ScrollBox)
while E.MoveNext do
  begin
  C1:=TPanel(E.Current);  If TPanel(C1).ControlCount>1 then // Левел 2  Панель параметра
begin
C1:=TPanel(TPanel(C1).Controls[1]);//Левел 3  панель внутри панели   
//(возможно что это слабое место (нумерация контролов не очень надежная штука ), но пока вроде работает )
   
If (TPanel(C1).ControlCount>0) And (TPanel(C1.Controls[0]).ClassType=TRadioButton) then

With TPanel(c1).GetEnumeratorControls do // Левел 4  собственно список RadioButton
//(наконец врубился  фишку с GetEnumerator оказывается их можно вообще без переменной использовать )
begin
while MoveNext do UxTheme.SetWindowTheme(TWinControl(Current).Handle,nil,'');
free;
end;
end
end;
E.Free;

(Интересно можно ли это "чудовище" немного оптимизировать ? )

Добавлено спустя 9 минут 4 секунды:
Alexander писал(а):Ну да, так и есть. Тогда может быть написать багрепорт разработчикам Лазаруса да и всё ?

Не думаю что это вина Лазаруса и Дельфи ... Это товарищи мелкомягкие мудрят.
( При включении "плоского режима" все работает как часы так что LCL все делает верно )
Зы
Интересно можно ли принудительно отключить манифест? Сдается мне что в этом случае многое станет работать как надо !
Зы Зы
Замечен но продолен странный глюк (перестала показываться рамка выбора RadioButton )
Ну поскольку я и так хотел поравить фокус при старте то это ерунда легко задвинулась .
Но что это было не понял. :idea:
Впрочем это винда где периодически возможно почти ВСЕ !
Последний раз редактировалось Alex2013 01.04.2024 09:53:17, всего редактировалось 4 раз(а).
Alex2013
долгожитель
 
Сообщения: 2937
Зарегистрирован: 03.04.2013 11:59:44

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Sharfik » 29.03.2024 22:26:03

Alex2013 писал(а):Гораздо более удивительно в сети так мало инфы на данную тему

Потому что нормальные люди цвета не меняют. Я вот стал тестировать программу в режиме повышенной контрасности и понял что у меня все работает, а RXDBGrix (к примеру) в строке фильтр срать хотел на системные настройки, и что у человека могут быть проблемы с глазами - тупо белое поле.
Аватара пользователя
Sharfik
энтузиаст
 
Сообщения: 763
Зарегистрирован: 20.07.2013 01:04:30

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alex2013 » 29.03.2024 22:57:44

Sharfik писал(а):
Alex2013 писал(а):Гораздо более удивительно в сети так мало инфы на данную тему

Потому что нормальные люди цвета не меняют. Я вот стал тестировать программу в режиме повышенной контрасности и понял что у меня все работает, а RXDBGrix (к примеру) в строке фильтр срать хотел на системные настройки, и что у человека могут быть проблемы с глазами - тупо белое поле.

Только почему то большая часть современных программ имеет четко выраженные цветовой стили.
(Часть этого идет от моды водимой ОС но значительная часть обращается с цветами довольно резко )
Кроме того я пишу не про отсутствие обсуждение настроек цветов вообще (этого сколько угодно ) а конкретно о RadioButton.
Зы
( И вообще в 90-х были "демократы" сейчас тенденция "дерьмократии" с посылом "ЕШЬ ЧТО ДАЮТ ЦУКА!" Я такой: :shock: "Зачем есть-же выбор!", а мне в ответ... "Все едят и ты потребляй..." ...и нафига "совок" спрашивается с такими романсами развалили? Там хоть обоснование пытались давать... типа "пейте дети молоко будете здоровы"! А тут ... "Массовая контркультура" Оксюморон... Тьфу! Одним словом! )

Ладно извини,"Остапа немного понесло!"
Зы Зы
Режим повышенной контрастности и все прочие должно по идее включается специальной настройки "стандартные цвета" отключающей все "свистелки мигалки" под корень . А ценителям авторских и нестандартных настроек нужны темы и полная настройка цветов.
Конкретно в этом случае я пытаюсь скопировать определенный стиль который был у другой программы некоторую я в меру сил равняюсь и если бы подобный интерфейс получался-бы стандартными средствами я бы был бы этому только рад . Но увы в лазарусе нет нормальной темной-темы (и много чего еще) так а что приходится в очередной раз изобретать велосипед.

Например меня тут недавно как-то случайно хвалили за настраиваемую геометрию панелек с имитаций "однооконного интерфейса " так честно говоря мне стыдно было потому, что на эту ерунду ушли почти что "простыни кода" описывающего реакцию каждой финтифлюшки и их взаимодействие, да по идее это все автоматом должно было работать! Но чего нет того нет.. :idea:
(Впрочем почти наверняка кто нибудь более умелый добился бы лучшего результата более правильным путем ... так что увы "маемо те що маемо"! :idea: )
Alex2013
долгожитель
 
Сообщения: 2937
Зарегистрирован: 03.04.2013 11:59:44

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alexander » 30.03.2024 08:07:58

Интересно можно ли принудительно отключить манифест?


Это не оно ?

https://forum.lazarus.freepascal.org/in ... ic=26894.0
Аватара пользователя
Alexander
энтузиаст
 
Сообщения: 695
Зарегистрирован: 18.12.2005 19:10:00
Откуда: оттуда

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Alex2013 » 30.03.2024 10:59:26

Alexander писал(а):
Интересно можно ли принудительно отключить манифест?


Это не оно ?

https://forum.lazarus.freepascal.org/in ... ic=26894.0


"Оно" но с отладчиком действительно беда...

В собранный "без манифеста" код из под лазаруса вообще не запускается (даже без отладки).
А так действительно помогает.
Но походу если темы манифеста действительно работают то стоит копать именно их. :idea:
------------------------------------------------------------
Какая то левая тема
https://gist.github.com/cpicanco/525bd3 ... 58d6fe3531
получить цвет фона из темы. ()
viewtopic.php?f=13&t=12515&p=104881&hilit=UxTheme#p104881

Как покрасить ProgressBar (Со скролл бар вроде не работает но это неточно )
Код: Выделить всё
const
  PBM_SETBARCOLOR = WM_USER + 9;   

  UxTheme.SetWindowTheme(ProgressBar.Handle, nil, '');
  ProgressBar.Brush.Color:= clRed;
  SendMessage(ProgressBar.Handle, PBM_SETBARCOLOR, 0, clRed);

Подозрительный патчер... как я понял патчит uxtheme.dll
https://mhoefs.eu/software_uxtheme.php?lang=en

Зы
Skins for Lazarus
https://github.com/Onur2x/onurcomp
Alex2013
долгожитель
 
Сообщения: 2937
Зарегистрирован: 03.04.2013 11:59:44

Re: Как надежно менять цвет текста подсказки в RadioButton ?

Сообщение Sharfik » 30.03.2024 15:41:15

Alex2013 писал(а):Режим повышенной контрастности и все прочие должно по идее включается специальной настройки "стандартные цвета" отключающей все "свистелки мигалки" под корень . А ценителям авторских и нестандартных настроек нужны темы и полная настройка цветов.

Если программа для узкого круга - что угодно, если программа на широкий круг - надо учитывать потребности людей с проблемами зрения. Вот я к чему. И для нас самый дешевый по времени вариант - стандартные темы ОС.
Ставил тут Linux с KDE и шкуркой как будто Vista. Наиболее похожий просто вариант на Windows для пожилого человека. Так при масштабировании 125% эта шняга в заголовке начала глючить :((

По проблеме - только сторонние компоненты изучать. Можно в Typhon покопать что там есть, и если кто в лазарус перекинуть компоненты.
Аватара пользователя
Sharfik
энтузиаст
 
Сообщения: 763
Зарегистрирован: 20.07.2013 01:04:30

След.

Вернуться в Lazarus

Кто сейчас на конференции

Сейчас этот форум просматривают: Google [Bot] и гости: 2

Рейтинг@Mail.ru
cron