Наши проекты:
Журнал · Discuz!ML · Wiki · DRKB · Помощь проекту |
||
ПРАВИЛА | FAQ | Помощь | Поиск | Участники | Календарь | Избранное | RSS |
[18.117.186.92] |
|
Сообщ.
#1
,
|
|
|
Добрый день!
Возникла необходимость скрывать пункты PopupMenu в момент, когда оно раскрыто. Но это приводит к сильному мерцанию, избавиться от которого не удается. Как можно избавиться от мерцания PopupMenu? procedure TForm1.PopupMenu1Popup(Sender: TObject); begin Timer1.Enabled := True; end; procedure TForm1.Timer1Timer(Sender: TObject); var i: Integer; begin Timer1.Enabled := False; for i := PopupMenu1.Items.Count-1 downto 0 do if i mod 2 = 0 then PopupMenu1.Items[i].Visible := False; end; DFM Скрытый текст object Form1: TForm1 Left = 0 Top = 0 Caption = 'Form1' ClientHeight = 109 ClientWidth = 258 Color = clBtnFace Font.Charset = DEFAULT_CHARSET Font.Color = clWindowText Font.Height = -11 Font.Name = 'Tahoma' Font.Style = [] OldCreateOrder = False PopupMenu = PopupMenu1 PixelsPerInch = 96 TextHeight = 13 object Timer1: TTimer Enabled = False Interval = 500 OnTimer = Timer1Timer Left = 64 Top = 24 end object PopupMenu1: TPopupMenu OnPopup = PopupMenu1Popup Left = 16 Top = 24 object N11: TMenuItem Caption = '1' end object N21: TMenuItem Caption = '2' end object N31: TMenuItem Caption = '3' end object N41: TMenuItem Caption = '4' end object N51: TMenuItem Caption = '5' end object N61: TMenuItem Caption = '6' end object N71: TMenuItem Caption = '7' end object N81: TMenuItem Caption = '8' end object N91: TMenuItem Caption = '9' end object N01: TMenuItem Caption = '0' end object N12: TMenuItem Caption = '1' end object N22: TMenuItem Caption = '2' end object N32: TMenuItem Caption = '3' end object N42: TMenuItem Caption = '4' end object N52: TMenuItem Caption = '5' end object N62: TMenuItem Caption = '6' end object N72: TMenuItem Caption = '7' end object N82: TMenuItem Caption = '8' end object N92: TMenuItem Caption = '9' end object N02: TMenuItem Caption = '0' end object N13: TMenuItem Caption = '1' end object N23: TMenuItem Caption = '2' end object N33: TMenuItem Caption = '3' end object N43: TMenuItem Caption = '4' end object N53: TMenuItem Caption = '5' end object N63: TMenuItem Caption = '6' end object N73: TMenuItem Caption = '7' end object N83: TMenuItem Caption = '8' end object N93: TMenuItem Caption = '9' end object N03: TMenuItem Caption = '0' end object N14: TMenuItem Caption = '1' end object N24: TMenuItem Caption = '2' end object N34: TMenuItem Caption = '3' end object N44: TMenuItem Caption = '4' end object N54: TMenuItem Caption = '5' end object N64: TMenuItem Caption = '6' end object N74: TMenuItem Caption = '7' end object N84: TMenuItem Caption = '8' end object N94: TMenuItem Caption = '9' end object N04: TMenuItem Caption = '0' end object N15: TMenuItem Caption = '1' end object N25: TMenuItem Caption = '2' end object N35: TMenuItem Caption = '3' end object N45: TMenuItem Caption = '4' end object N55: TMenuItem Caption = '5' end object N65: TMenuItem Caption = '6' end object N75: TMenuItem Caption = '7' end object N85: TMenuItem Caption = '8' end object N95: TMenuItem Caption = '9' end object N05: TMenuItem Caption = '0' end object N16: TMenuItem Caption = '1' end object N26: TMenuItem Caption = '2' end object N36: TMenuItem Caption = '3' end object N46: TMenuItem Caption = '4' end object N56: TMenuItem Caption = '5' end object N66: TMenuItem Caption = '6' end object N76: TMenuItem Caption = '7' end object N86: TMenuItem Caption = '8' end object N96: TMenuItem Caption = '9' end object N06: TMenuItem Caption = '0' end end end PAS Скрытый текст unit Unit1; interface uses Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics, Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.Menus, Vcl.ExtCtrls; type TForm1 = class(TForm) Timer1: TTimer; PopupMenu1: TPopupMenu; N11: TMenuItem; N21: TMenuItem; N31: TMenuItem; N41: TMenuItem; N51: TMenuItem; N61: TMenuItem; N71: TMenuItem; N81: TMenuItem; N91: TMenuItem; N01: TMenuItem; N12: TMenuItem; N22: TMenuItem; N32: TMenuItem; N42: TMenuItem; N52: TMenuItem; N62: TMenuItem; N72: TMenuItem; N82: TMenuItem; N92: TMenuItem; N02: TMenuItem; N13: TMenuItem; N23: TMenuItem; N33: TMenuItem; N43: TMenuItem; N53: TMenuItem; N63: TMenuItem; N73: TMenuItem; N83: TMenuItem; N93: TMenuItem; N03: TMenuItem; N14: TMenuItem; N24: TMenuItem; N34: TMenuItem; N44: TMenuItem; N54: TMenuItem; N64: TMenuItem; N74: TMenuItem; N84: TMenuItem; N94: TMenuItem; N04: TMenuItem; N15: TMenuItem; N25: TMenuItem; N35: TMenuItem; N45: TMenuItem; N55: TMenuItem; N65: TMenuItem; N75: TMenuItem; N85: TMenuItem; N95: TMenuItem; N05: TMenuItem; N16: TMenuItem; N26: TMenuItem; N36: TMenuItem; N46: TMenuItem; N56: TMenuItem; N66: TMenuItem; N76: TMenuItem; N86: TMenuItem; N96: TMenuItem; N06: TMenuItem; procedure PopupMenu1Popup(Sender: TObject); procedure Timer1Timer(Sender: TObject); private { Private declarations } public { Public declarations } end; var Form1: TForm1; implementation {$R *.dfm} procedure TForm1.PopupMenu1Popup(Sender: TObject); begin Timer1.Enabled := True; end; procedure TForm1.Timer1Timer(Sender: TObject); var i: Integer; begin Timer1.Enabled := False; for i := PopupMenu1.Items.Count-1 downto 0 do if i mod 2 = 0 then PopupMenu1.Items[i].Visible := False; end; end. |
Сообщ.
#2
,
|
|
|
Я не заметил мерцания
Добавлено Как вариант, попробуйте procedure TForm1.Timer1Timer(Sender: TObject); var i: Integer; begin Timer1.Enabled := False; LockWindowUpdate(PopupMenu1.Handle); for i := PopupMenu1.Items.Count-1 downto 0 do if i mod 2 = 0 then PopupMenu1.Items[i].Visible := False; LockWindowUpdate(0); end; |
Сообщ.
#3
,
|
|
|
Это я уже делал, не помогает.
|
Сообщ.
#4
,
|
|
|
Свойство DoubleBuffered стоит?
|
Сообщ.
#5
,
|
|
|
У меню его в принципе нет, а выставлять его для формы нет никакого смысла.
Вся проблема в методе TMenuItem.MenuChanged, внутри которого есть строка if Assigned(FOnChange) then FOnChange(Self, Source, Rebuild); она вызывает метод MenuItem.SubItemChanged, который на каждый чих пересоздает меню. ... RebuildHandle; ... Захотим, например, скрыть 20 пунктов в цикле, меню будет 20 раз пересоздано, отсюда и дикое мерцание... |
Сообщ.
#6
,
|
|
|
Ну во первых LockWindowUpdate(PopupMenu1.Handle);
PopupMenu1.Handle - это не хэндл окна меню, это хэндл самого меню. Чтобы получить хэндл окна надо хотя бы GetForegroundWindow сказать. Во сторых согласно майкросовтовских гуидлайнам у меню не должно быть 1. скролов (из-за большого количества пунктов меню) 2. двойного уровня сабменю 3. динамического изменения элементов в момент отображения Все это делает крайне не удобным работу с меню и если в GUI есть хотя бы один из этих пунктов, надо что-то менять. |
Сообщ.
#7
,
|
|
|
В этом и прелесть задачи - если нельзя, но очень хочется, то можно
На самом деле прогресс наметился, на тестовом приложении с таймером я добился нужного результата. В боевую прикладу перенести не получается, буду дальше копать... |