Rambler's Top100
"Knowledge itself is power"
F.Bacon
Поиск | Карта сайта | Помощь | О проекте | ТТХ  
 Круглый стол
  
Правила КС
>> Настройки

Фильтр вопросов
>> Новые вопросы
отслеживать по
>> Новые ответы

Избранное

Страница вопросов
Поиск по КС


Специальные проекты:
>> К л ю к в а
>> Г о л о в о л о м к и

Вопрос №

Задать вопрос
Off-topic вопросы

Помощь

 
 К н и г и
 
Книжная полка
 
 
Библиотека
 
  
  
 


Поиск
 
Поиск по КС
Поиск в статьях
Яndex© + Google©
Поиск книг

 
  
Тематический каталог
Все манускрипты

 
  
Карта VCL
ОШИБКИ
Сообщения системы

 
Форумы
 
Круглый стол
Новые вопросы

 
  
Базарная площадь
Городская площадь

 
   
С Л С

 
Летопись
 
Королевские Хроники
Рыцарский Зал
Глас народа!

 
  
ТТХ
Конкурсы
Королевская клюква

 
Разделы
 
Hello, World!
Лицей

Квинтана

 
  
Сокровищница
Подземелье Магов
Подводные камни
Свитки

 
  
Школа ОБЕРОНА

 
  
Арсенальная башня
Фолианты
Полигон

 
  
Книга Песка
Дальние земли

 
  
АРХИВЫ

 
 

Сейчас на сайте присутствуют:
 
  
 
Во Флориде и в Королевстве сейчас  21:14[Войти] | [Зарегистрироваться]
Ответ на вопрос № 83587

03-09-2018 04:19
Добрый день! Помогите решить проблему! По клику на каком-либо элементе необходимо отобразить подсказку в стиле Ballon Hint. Подсказка должна отображаться пару секунд. При перемещении мыши или любом другом пользовательском вводе, подсказка должна сразу исчезнуть.
Нашел в интернете нижеследующий код, который модифицировал в части активации подсказки. Однако проблема в том, что при повторном наведении курсора на элемент, активировавший подсказку, она появляется опять! Как от этого избавиться???

Код "помощника"

unit ComponentBaloonHintU;

interface
uses
    Controls, CommCtrl, Graphics;

{$SCOPEDENUMS ON}

type
    TIconKind = (None = TTI_NONE, Info = TTI_INFO, Warning = TTI_WARNING, Error = TTI_ERROR, Info_Large = TTI_INFO_LARGE, Warning_Large = TTI_WARNING_LARGE, Eror_Large = TTI_ERROR_LARGE);
    TComponentBaloonhint = class helper for TWinControl
    public
    procedure ShowBalloonTip(Icon: TIconKind; const Title, Text: string);
    end;

implementation
uses
    Windows;

{ TComponentBaloonhint }

procedure TComponentBaloonhint.ShowBalloonTip(Icon: TIconKind; const Title, Text: string);
var
    hWndTip: THandle;
    ToolInfo: TToolInfo;
    BodyText: pWideChar;
begin
    hWndTip := CreateWindow(TOOLTIPS_CLASS, nil, WS_POPUP or TTS_NOPREFIX or TTS_BALLOON or TTS_ALWAYSTIP, 0, 0, 0, 0, Handle, 0, HInstance, nil);

    if hWndTip = 0 then
    exit;

    GetMem(BodyText, 2 * 256);

    try
    ToolInfo.cbSize := SizeOf(TToolInfo);
    ToolInfo.uFlags := TTF_CENTERTIP or TTF_TRANSPARENT or TTF_SUBCLASS;
    ToolInfo.hWnd := Handle;
    ToolInfo.lpszText := StringToWideChar(Text, BodyText, 2 * 256);
    SetWindowPos(hWndTip, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOACTIVATE or SWP_NOMOVE or SWP_NOSIZE);
    ToolInfo.Rect := GetClientRect;

    SendMessage(hWndTip, TTM_ADDTOOL, 1, integer(@ToolInfo));
    SendMessage(hWndTip, TTM_SETTITLE, integer(Icon), integer(PChar(Title)));
    SendMessage(hWndTip,TTM_SETDELAYTIME,TTDT_AUTOPOP, 2000);
    SendMessage(hWndTip,TTM_SETDELAYTIME,TTDT_INITIAL, 100);
    SendMessage(hWndTip,TTM_SETDELAYTIME,TTDT_RESHOW, 100);
    SendMessage(hWndTip, TTM_ACTIVATE, integer(true), integer(@ToolInfo));
    finally
    FreeMem(BodyText);
    end;
end;

end.



В своей программе использую так:

const
  SI_TITLE = 'Заголовок подсказки';
  SI_TEXT  = 'Текст подсказки' + #13 + 'Текст подсказки' + #13 + 'Текст подсказки';
procedure TForm1.Label1Click(Sender: TObject);
begin
  TWinControl(Sender).ShowBalloonTip(TIconKind.Error, 'Baloon Title', 'Baloon text' + #13 + 'Baloon text' + #13 + 'Baloon text');
end;

[+] Добавить в избранные вопросы

Отслеживать ответы на этот вопрос по RSS

Ответы:


Уважаемые авторы вопросов! Большая просьба сообщить о результатах решения проблемы на этой странице.
Иначе, следящие за обсуждением, возможно имеющие аналогичные проблемы, не получают ясного представления об их решении. А авторы ответов не получают обратной связи. Что можно расценивать, как проявление неуважения к отвечающим от автора вопроса.

04-09-2018 04:26 | Комментарий к предыдущим ответам
А есть ли необходимость использовать именно окно TOOLTIPS_CLASS?
Для подобной задачи можно показывать когда надо своё окно. А то лишние сложности, чтобы создать окно, а потом подавлять его главную функциональность. Имхо, конечно.

Если я не ошибаюсь, то в хелпере можно объявлять поля, которые, естественно, доступны только в методах хелпера.
Но, кажется, класс может иметь лишь один хелпер. (?). А вдруг где-то уже используется хелпер, или будет добавлен?
Поправьте меня, если я не прав.

03-09-2018 13:23
И еще надо проверить TTM_TRACKACTIVATE - по-моему именно оно включает-отключает подсказку. Так что можно так:
SendMessage(hWndTip, TTM_ACTIVATE, integer(false), integer(@ToolInfo));

03-09-2018 13:16
Я пишу в билдере, но попробую сделать набросок
procedure TWinControl.WMNotify(var Message: TWMNotify);
var
    ToolInfo: TToolInfo;
begin
  if Message.NMHdr.code = TTN_POP then begin
    ToolInfo.cbSize := SizeOf(TToolInfo);
    ToolInfo.uFlags := TTF_IDISHWND;
    ToolInfo.hWnd := Handle;
    ToolInfo.uId := hWndTip;
    SendMessage(hWndTip, TTM_DELTOOL, 0, integer(@ToolInfo));
  end
  else inherited;
end;
От этого можно попробовать оттолкнуться. Вместо хэндла подсказки можно использовать целочисленный идентификатор, который также следует задать в TTM_ADDTOOL, и тогда нужно убрать флаг TTF_IDISHWND

03-09-2018 09:39 | Сообщение от автора вопроса
Сам такое не пробовал, предлагаю в качестве эксперимента
А можно пример кода?

03-09-2018 09:13
На хелпере не настаиваю. Нужно наиболее рациональное и полноценное решение. Ваше предложение попробую реализовать, о результатах сообщу позже.

03-09-2018 09:13
Да, надо где-то хранить хэндл самой подсказки. К сожалению, не знаю, можно ли в хэлпере добавить поле в класс

03-09-2018 09:10
>>>Как это реализовать?
Так-то надо обрабатывать WM_NOTIFY, но у Вас хелпер, а не полноценный класс. Попробуйте завести метод-обработчик события:
procedure WMNotify(var Message: TMessage); message WM_NOTIFY;
не забывайте внутри вызвать inherited метод. Внутри в lParam ждем заголовок с информацией и кодом события (TTN_POP), которое, если верить msdn, оповещает о сокрытии подсказки. А потом уж снова вызываем SendMessage(hWndTip, TTM_ADDTOOL, 1, integer(@ToolInfo)), только в хэндл пишем nil.
Сам такое не пробовал, предлагаю в качестве эксперимента

03-09-2018 09:02 | Сообщение от автора вопроса
Как это реализовать? Создать компонент, который будет реализовать процедуру вызова хинта и создать в нем обработчик данного события? Он будет получать это событие?

03-09-2018 08:54
Попробуйте отлавливать сообщение TTN_POP (внутри WM_NOTIFY) и отцеплять окно подсказки через TTM_ADDTOOL, указывая там нулевой хэндл

03-09-2018 06:43 | Сообщение от автора вопроса
1. По задаче, ситуация такая: Есть форма с рядом надписей типа StaticText с возможностью фокусирования. Из них (на выбор) мне нужно копировать текст в буфер обмена. Я сделал конечно всплывающее меню, с пунктом копирования, но когда часто приходится пользоваться, через меню неудобно. Я решил сделать через клик. Но нужна визуальная реакция контрола, что команда выполнена или ответ о недоступности операции. Через диалоговое окно слишком неудобно (закрывать его - отдельно мышкой по экрану рыскать). Т.е. нужно сделать визуальное оповещение, не требующее специальной реакции пользователя. Хинты в этом плане идеально подходят.
2. TBallonHint не подходит, поскольку топорно отображает иконки и многострочный текст, а также не исчезает при перемещении мышки, только по таймеру (или по клику, вызывающему его отображение на другой надписи).

03-09-2018 06:06 | Вопрос к автору: запрос дополнительной информации
А почему бы не использовать TBalloonHint? Его можно показать когда надо и где надо. Или код подсмотреть. Там, вроде, все просто и можно в Helper использовать.
А по вопросу предполагаю, что TOOLTIP-окно привязывается к контролу и ведет себя стандартным образом.
Т.е. активируется при наведении. И тут вопрос: действительно ли необходимо показывать хинт именно в Click? Не могу представить такой задачи.

Добавьте свое cообщение

Вашe имя:  [Войти]
Ваш адрес (e-mail):На Королевстве все адреса защищаются от спам-роботов
контрольный вопрос:
Раз дощечка, два дощечка будет лесенка. Раз словечко, два словечко, будет ЧТО?
в качестве ответа на вопрос или загадку следует давать только одно слово в именительном падеже и именно в такой форме, как оно используется в оригинале.
Надоело отвечать на странные вопросы? Зарегистрируйтесь на сайте.
Тип сообщения:
Текст:
Жирный шрифт  Наклонный шрифт  Подчеркнутый шрифт  Выравнивание по центру  Список  Заголовок  Разделительная линия  Код  Маленький шрифт  Крупный шрифт  Цитирование блока текста  Строчное цитирование
  • вопрос Круглого стола № XXX

  • вопрос № YYY в тесте № XXX Рыцарской Квинтаны

  • сообщение № YYY в теме № XXX Базарной площади
  • обсуждение темы № YYY Базарной площади
  •  
     Правила оформления сообщений на Королевстве

    Страница избранных вопросов Круглого стола.
      
    Время на сайте: GMT минус 5 часов

    Если вы заметили орфографическую ошибку на этой странице, просто выделите ошибку мышью и нажмите Ctrl+Enter.
    Функция может не работать в некоторых версиях броузеров.

    Web hosting for this web site provided by DotNetPark (ASP.NET, SharePoint, MS SQL hosting)  
    Software for IIS, Hyper-V, MS SQL. Tools for Windows server administrators. Server migration utilities  

     
    © При использовании любых материалов «Королевства Delphi» необходимо указывать источник информации. Перепечатка авторских статей возможна только при согласии всех авторов и администрации сайта.
    Все используемые на сайте торговые марки являются собственностью их производителей.

    Яндекс цитирования