Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Основная";
Текущий архив: 2006.12.31;
Скачать: [xml.tar.bz2];

Вниз

"Всплывающее окно"   Найти похожие ветки 

 
RASkov   (2006-11-12 22:34) [0]

Как сделать окно всплывающим? Измучился я с этим окном. В этой области знаний не хватает. Разбирал примеры от Алексея Румянцева с ComboBox"ами. Запутался в корень. Вообщем нужно сделать свою попап форму. Все мои эксперементы были над TCustomControl. Вот примерно так делал:

 TMyPopup = class(TCustomControl)
 private
   FChek: TCheckBox;
   FPopupVisible: Boolean;
   procedure CMCancelMode(var Message: TCMCancelMode); message CM_CANCELMODE;
   procedure WMKillFocus(var Message: TMessage); message WM_KILLFOCUS;
 protected
   procedure CreateParams(var Params: TCreateParams); override;
   procedure CloseUp(Accept: Boolean); dynamic;
 public
   constructor Create(AOwner: TComponent); override;
   procedure Show(const P: TPoint);
   property PopupVisible: Boolean read FPopupVisible;
 end;
.............

constructor TMyPopup.Create(AOwner: TComponent);
begin
 inherited Create(AOwner);
 Width := 84;
 Height := 100;
 FCheck := TCheckBox.Create(Self);  //Чисто ради эксперимента.
 FCheck.Parent := Self;
 FCheck.Width := 80;
 FCheck.Left := 2; FCheck.Top := 2;
 FCheck.Show;
 FPopupVisible := False;
end;

procedure TMyPopup.CreateParams(var Params: TCreateParams);
begin
 inherited;
 with Params do begin
  Style := Style or WS_BORDER;
  ExStyle := WS_EX_TOOLWINDOW or WS_EX_TOPMOST;
  AddBiDiModeExStyle(ExStyle);
  WindowClass.Style := CS_SAVEBITS;
 end;
end;

procedure TMyPopup.CloseUp(Accept: Boolean);
begin
 if GetCapture <> 0 then SendMessage(GetCapture, WM_CANCELMODE, 0, 0);
 if Accept then begin
  SetWindowPos(Handle, 0, 0, 0, 0, 0, SWP_NOZORDER or
     SWP_NOMOVE or SWP_NOSIZE or SWP_NOACTIVATE or SWP_HIDEWINDOW);
  //Visible:=False;
  FPopupVisible:=False;
 end;
end;

procedure TMyPopup.CMCancelMode(var Message: TCMCancelMode);
begin
 if (Message.Sender <> Self) then CloseUp(True);
end;

procedure TMyPopup.WMKillFocus(var Message: TMessage);
begin
 inherited;
 CloseUp(True);
end;

procedure TMyPopup.Show(const P: TPoint);
begin
 if not PopupVisible then begin
  SetWindowPos(Handle, 0, P.X, P.Y, 0, 0,  SWP_NOSIZE or SWP_NOACTIVATE or SWP_SHOWWINDOW);
  FPopupVisible := True;
  Invalidate;
  Windows.SetFocus(Handle);
 end;
end;


И конечно же это не работает:(
Как сделать:
1 - Что бы область показа не ограничивалась клиентской областью формы?
  (Т.е. если щелкнуть в нижней области формы то мое окно показывается и обрезается краем формы, у формы появляются "скролы")
2 - Как правильно его прятать? Должно прятаться при потере фокуса...
Вообщем должно вести себя (показываться/прятаться) почти как попап меню, за исключением того, что при щелчке мышью внутри моего окна, можно было управлять закрытием онного (PopupMenu закрывается всегда).

Пример вызова был таким:
procedure TForm1.FormContextPopup(Sender: TObject; MousePos: TPoint; var Handled: Boolean);
begin
 MyP.Show(MousePos); //или MyP.Show(ClientToScreen(MousePos));
end;
где MyP: TMyPopup

Приведенный код для наглядности, и может в корне не верен(я уже запутался что и как). А вообщем идея из примеров Румянцева. Никогда ранее не занимался подобным:) Спасибо.


 
Ketmar ©   (2006-11-12 22:49) [1]

а зачем ты ему parent"ом свою форму назначаешь? вот и "скрывается". desktop ему в parent"ы. дальше, думаю, сам поймёшь.


 
RASkov   (2006-11-13 01:16) [2]

Это тоже из тех же примеров Румянцева:

procedure TMyPopup.CreateWnd;
begin
 inherited;
 Windows.SetParent(Handle, 0);
 //CallWindowProc(DefWndProc, Handle, wm_SetFocus, 0, 0);
end;

Только хуже стало...
Как нужно правильно сделать? Я так понимаю тут всё к одному связано - ошибся в одном месте и все полетело.
Методом перебора параметров в SetWindowsPos таких как HWND_XXX и стилей в CreateParam.... вообщем сижу в луже.
Вот делаю как у Румянцева (у него хорошо получилось с комбобоксами - выпадающий список можно сделать на основе любого винконтрола) и вот сообственно мой попап - это и есть его выпадающий список, но запутался и не пойму в чем:(

На данный момент (с SetParent) чекбокс, который создается на моем "окне", становится недоступнум и вообще окно недоступно. Т.е. появляется один раз и висит ни на что не реагируя:( Так же нехорошая фича присутствует - если первый(единственный) раз мое окно отобразить в нижнем правом углу формы и потом попробывать изменить размеры формы, что бы как бы мое окно осталось справа от формы, то у формы прокрутка появляется, как будто мое окно на форме.

SetWindowPos(Handle, HWND_TOP, P.X, P.Y, 0, 0,  SWP_NOACTIVATE or SWP_NOSIZE or SWP_SHOWWINDOW);
SetWindowPos(Handle, HWND_NOTOPMOST, 0, 0, 0, 0, SWP_NOACTIVATE or SWP_NOSIZE or SWP_HIDEWINDOW);
Нужно ли совместно делать Visible:=True/False;?


 
Ketmar ©   (2006-11-13 01:26) [3]

CreateParentedControl() не пробовал? ну очень мне лениво VCL вспоминать. %-) и зачем тебе SetWindowPos() сдался? и вообще -- возьми да напиши на API. %-)


 
RASkov   (2006-11-13 01:45) [4]

Вообщем тут без литры не разберешься, вот еще заметил, что у меня
 MnP:=TMyPopup.Create(Self);
//  MnP.Parent:=Self; <-!!!

Вообщем один раз ^ написал и внимания не обращал, но если закомментировать, то вообще ничего не работает:( Ладно, буду до последнего ковырять исходники с комбиками, может и получится выдернуть тот самый злопалучный список и превратить его в отдельный(независимый) класс, может и в компонент.
Хотя... если у кого есть какие мысли по этому поводу, пишите, может быстрее разберусь с этим "плавучим окном в стиле попап меню". Спасибо.


 
RASkov   (2006-11-13 01:49) [5]

> [3] Ketmar ©   (13.11.06 01:26)
> и зачем тебе SetWindowPos()

Ну там в этих примерах... вообщем не мне сдался, я чесно пытался стырить:)

> CreateParentedControl() не пробовал?

Нет. Спасибо, попробую и этот вариант.

> напиши на API. %-)

Вот только так и останется наверное. Буду вспоминать того чего незнаю:)


 
Наиль ©   (2006-11-13 16:25) [6]

Если размер EXE не принципиален, то можно делать на чистом VCL.
1. Создаёшь PopupForm=class(TForm)
2. PopupForm.BorderStyle=bsNone
3. Всплытие:
3.1 Задать положение PopupForm (SetBounds)
3.2 PopupForm.Show
4. Скрытие
4.1 PopupForm.OnDeactivate=begin; hide; end;
4.2 или просто Hide

Не проверял, но даже если здесь имеются ошибки, то общий смысл верен.
В противном случае, тебе поможет только чистый API.


 
RASkov   (2006-11-14 01:12) [7]

> [6] Наиль ©   (13.11.06 16:25)

Спасибо, но так будет теряться фокус у основной формы. Мне бы хотелось как можно более сымитировать попап меню. Т.е. сделать окно таким как делается оно у выподающих списков например. Оно не отбирает фокус и может выходить за рамки формы. Должно прятаться когда теряет фокус или при определенных условиях в самом окне.

> В противном случае, тебе поможет только чистый API.

Не хотелось бы, т.е. пока незнаю... Возможно нужно поколдовать с CreateParam(Wnd) правильно.
Сейчас пока некогда этим заниматься но на неделе поробую что нибудь решить. Отпишусь если (не)получится.



Страницы: 1 вся ветка

Форум: "Основная";
Текущий архив: 2006.12.31;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.47 MB
Время: 0.039 c
3-1160653217
Gun Expert
2006-10-12 15:40
2006.12.31
ADO-компоненты в Delphi2006. Совместимость с D6


15-1165399919
boriskb
2006-12-06 13:11
2006.12.31
Годовщина победы под Москвой


9-1140722396
Fenix
2006-02-23 22:19
2006.12.31
Поблемы с DCE. (нет компонента)


2-1165914539
WhiteBarin
2006-12-12 12:08
2006.12.31
Как узнать имя текущего пользователя и его логин


1-1158053382
Calibr
2006-09-12 13:29
2006.12.31
Вставка в чужое окно.





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский