powered by simpleCommunicator - 2.0.53     © 2025 Programmizd 02
Форумы / Visual Basic [игнор отключен] [закрыт для гостей] / Кнопка с popup меню - пара вопросов
2 сообщений из 2, страница 1 из 1
Кнопка с popup меню - пара вопросов
    #38580763
Дмитрий77
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Есть обычная кнопка. Ей вызывается меню (сделанное на VB6) -растет от нижнего левого края кнопки.
Проще привести недоработанный код
Код: vbnet
1.
2.
3.
4.
5.
Private Sub Command1_MouseDown(Button As Integer, Shift As Integer, X As Single, Y As Single)
  Static b_menu As Boolean
  If b_menu = False Then PopupMenu menu_test, , Command1.Left, Command1.Top + Command1.Height
  b_menu = Not b_menu
End Sub



Надо по щелчку на кнопке:
1) чтоб если меню не выведено, то оно появлялось, если выведено - исчезало.
2) чтоб сама кнопка "визуально" не нажималась.

Нечто подобное делает кнопка Параметры в любом классическом HTMLhelp.

По п.1 могу сказать, что моя b_menu хороша только если стукать исключительно по кнопке.
Если выбрать пункт меню, либо щелкнуть не по кнопке, то оно закроется а b_menu не сработает. WM_ENTERMENULOOP не уверен что что-то даст, потому что сначала "предыдущее" меню выйдет, а потом кнопка щелкнется

По п.2 могу сказать, что _MouseDown вместо _Click практически устраняет визуальный эффект нажатия только если меню "появляется". При "исчезании" нажимается по полной.

Кнопка нужна ОБЫЧНАЯ. Чтоб была такая же как соседние.
...
Рейтинг: 0 / 0
Кнопка с popup меню - пара вопросов
    #38581694
Дмитрий77
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Дмитрий771) чтоб если меню не выведено, то оно появлялось, если выведено - исчезало.
Чтоб не было визуального эффекта нажатия (вызывает его либо мышь, либо сенсорный экран), надо отменить WM_LBUTTONDOWN. При этом туда же надо писать код, который обычно пишется в Command_Click или Mouse_Down(Up), т.к. отмена WM_LBUTTONDOWN отменяет все стандартные события.
Дмитрий772) чтоб сама кнопка "визуально" не нажималась.
Надо разрешать выводить меню по новой не по WM_EXITMENULOOP, а по тику таймера, кот. запускается из WM_EXITMENULOOP. Все другие способы типа отслеживания координат мыши на момент WM_EXITMENULOOP не дают 100% гарантию. Пример: при выведенном меню нажали Enter/Esc а мышь была над кнопкой. Интервала таймера 1мс достаточно (и оптимально) для случая мыши. Но недостаточно для сенсора. Опытным путем установил, что 300мс вроде как оптимально (юзер вряд ли сделает 2 осмысленных щелчка мыши за меньший интервал, и сенсор вроде как тоже реагирует правильно если конечно не пытаться протереть экран пальцем).

Но честно говоря глядючи на 11-дюймовый экран нетбука, и пытаясь попасть лапой в крошечные кнопки (которые на даже стареньком 19-дюймовом Sony кажутся неприлично огромными), начинаешь задумываться о приложениях Windows Store, причем в приоритете относительно освоения и переписывания существующего VB6 кода под классический (уже наверно) .Net (WinForms, да хоть бы и WPF), который по сути то ничего нового то и не даст.

Собственно по теме, код и тестовый проект, если кому интересно поиграться.

Код: vbnet
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
Private Sub Command1_Click()
  'вызывается только нажатием кнопки
  '(для мыши и сенсорного экрана не вызывается, т.к. WM_LBUTTONDOWN мы отменили)
  'Debug.Print "Command1_Click"
  b_show_ButtonMenu = True
  Form1.PopupMenu Form1.menu_test, , Form1.Command1.Left, Form1.Command1.Top + Form1.Command1.Height
End Sub

Private Sub TimerUnShowButtonMenu_Timer()
  TimerUnShowButtonMenu.Enabled = False
  b_show_ButtonMenu = False
End Sub
'---
Public b_show_ButtonMenu As Boolean 'true если popup menu активно
Private Const WM_EXITMENULOOP = &H212
Private Const WM_LBUTTONDOWN = &H201

Public Function NewFormMeWindowProc( _
 ByVal hwnd As Long, ByVal Msg As Long, ByVal wParam As Long, ByVal lParam As Long) As Long
  Select Case Msg
    Case WM_EXITMENULOOP 'menu
      'Debug.Print "WM_EXITMENULOOP"
      'таймер не позволяет выполнить код WM_LBUTTONDOWN
      'повторного вызова меню при щелчке мышью по кнопке (при уже выведенном меню)
      'тоже самое для пальца(сенсорный экран)
      'для мыши достаточно 1мс
      'а вот с учетом пальца (опытным путем) нужно где-то 300мс, чтоб не глючило(ХЗ),
      'но это если сильно пальцем по экрану не елозить
      'если делать задержку больше,то нарушает поведение при щелчке мышью(опытным путем)
      If b_show_ButtonMenu Then Form1.TimerUnShowButtonMenu.Enabled = True
    Case Else
  End Select

  NewFormMeWindowProc = _
   CallWindowProc(OldFormMeWindowProc, hwnd, Msg, wParam, lParam)
 End Function

Public Function NewButtonWindowProc( _
 ByVal hwnd As Long, ByVal Msg As Long, ByVal wParam As Long, ByVal lParam As Long) As Long
  'сабклассим конкретную кнопку Command1
  Select Case Msg
    Case WM_LBUTTONDOWN 'вызывается только при щелчке мышью
      'Debug.Print "WM_LBUTTONDOWN(Button)"
      Form1.Command1.SetFocus
      If b_show_ButtonMenu = False Then
        b_show_ButtonMenu = True
        Form1.PopupMenu Form1.menu_test, , Form1.Command1.Left, Form1.Command1.Top + Form1.Command1.Height
      Else
        b_show_ButtonMenu = False
      End If
      Exit Function 'отмена визуального нажатия кнопки и вызова Command_Click
    Case Else
  End Select

  NewButtonWindowProc = _
   CallWindowProc(OldButtonWindowProc, hwnd, Msg, wParam, lParam)
End Function
...
Рейтинг: 0 / 0
2 сообщений из 2, страница 1 из 1
Форумы / Visual Basic [игнор отключен] [закрыт для гостей] / Кнопка с popup меню - пара вопросов
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]