purebasic.info

PureBasic forum
Текущее время: Вс июл 22, 2018 11:26 pm

Часовой пояс: UTC + 3 часа




Начать новую тему Ответить на тему  [ Сообщений: 20 ]  На страницу 1, 2  След.
Автор Сообщение
 Заголовок сообщения: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Пн май 15, 2017 11:27 am 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Всем привет!
Есть извесный код
Код:
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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
#LVM_GETHEADER = #LVM_FIRST + 31
 
Structure MY_Str
  dwItemSpec.i
  hdc.i
  rc.RECT
EndStructure
 
Global oldListIconCallback, hHeader, brush
brush=CreateSolidBrush_(#Yellow)
 
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item
  Static Column
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  If uMsg=#WM_NOTIFY
    ;Debug "#WM_NOTIFY"
    *pnmh.NMHDR = lparam
    If *pnmh\code = #NM_CUSTOMDRAW
      *pnmcd.NMCUSTOMDRAW = lparam
      Select *pnmcd\dwDrawStage
        Case #CDDS_PREPAINT
          result = #CDRF_NOTIFYITEMDRAW
        Case #CDDS_ITEMPREPAINT
          text$=GetGadgetItemText(0, -1, *pnmcd\dwItemSpec)
         
          If *pnmcd\uItemState & #CDIS_SELECTED
            DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
            *pnmcd\rc\left+2 : *pnmcd\rc\top+1
          Else
            DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
          EndIf
         
          *pnmcd\rc\bottom-1 : *pnmcd\rc\right-1
          SetBkMode_(*pnmcd\hdc,#TRANSPARENT)
          If *pnmcd\dwItemSpec&1
            FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
            SetTextColor_(*pnmcd\hdc, #Blue)
          Else
            FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
            SetTextColor_(*pnmcd\hdc, #Red)
          EndIf
          If *pnmcd\rc\right>*pnmcd\rc\left
            DrawText_(*pnmcd\hdc, @text$, Len(text$), *pnmcd\rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
          EndIf
          result = #CDRF_SKIPDEFAULT
      EndSelect
    EndIf
  EndIf
  ProcedureReturn result
EndProcedure
 
If OpenWindow(0, 100, 100, 415, 300, "", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
  ListIconGadget(0, 5, 5, 405, 200, "col 0", 50, #PB_ListIcon_FullRowSelect | #PB_ListIcon_AlwaysShowSelection)
  hHeader = SendMessage_(GadgetID(0), #LVM_GETHEADER, 0, 0)
  ;Subclass ListIcon so we can customdraw the header text
  oldListIconCallback = SetWindowLong_(GadgetID(0), #GWL_WNDPROC, @SubclassedListIcon())
 
  ;Add 10 more columns.
  For i = 1 To 10
    AddGadgetColumn(0, i, "col "+Str(i), 50)
  Next
  ;Add some data
  For b=0 To 99; Add 100 rows.
    AddGadgetItem(0,-1,"")
  Next
  For i = 0 To 99
    For j = 0 To 50
      SetGadgetItemText(0,i,Str(i+j),j)
    Next j
  Next i          
 
  Repeat
  Until WaitWindowEvent() = #PB_Event_CloseWindow
  DeleteObject_(brush)
EndIf


Щёлкнеш заголовок он красиво нажимается. Но мне надо тоже по ПКМ.
Но проблема. #WM_NOTIFY приходит по отжатию ПКМ (раскоментируйте строку 17)
Тогда я стал юзать #WM_PARENTNOTIFY. Но структуры пустые.
Тогда я сделал свою MY_Str и пишу в нее что надо. Вобщем вот:
Код:
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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
#LVM_GETHEADER = #LVM_FIRST + 31
 
Structure MY_Str
  dwItemSpec.i
  hdc.i
  rc.RECT
EndStructure
 
Global oldListIconCallback, hHeader, brush, Var.MY_Str
brush=CreateSolidBrush_(#Yellow)
 
 
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item
  Static Column
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  Select uMsg
    Case #WM_NOTIFY                   ;The moment button release
      *pnmh.NMHDR = lparam
      If *pnmh\code = #NM_CUSTOMDRAW
        *pnmcd.NMCUSTOMDRAW = lparam
        Select *pnmcd\dwDrawStage
          Case #CDDS_PREPAINT
            result = #CDRF_NOTIFYITEMDRAW
          Case #CDDS_ITEMPREPAINT
            text$=GetGadgetItemText(0, -1, *pnmcd\dwItemSpec);:Debug *pnmcd\dwItemSpec
           
            If *pnmcd\uItemState & #CDIS_SELECTED
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
              *pnmcd\rc\left+2 : *pnmcd\rc\top+1
            Else
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
              ;DrawFrameControl_(*pnmcd\hdc, Var\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)             ; Так не работает
             
              Var\hdc=*pnmcd\hdc
              Var\rc=*pnmcd\rc
              Var\dwItemSpec=*pnmcd\dwItemSpec
              ;Debug "Button release"
             
            EndIf
           
            *pnmcd\rc\bottom-1 : *pnmcd\rc\right-1
            SetBkMode_(*pnmcd\hdc,#TRANSPARENT)
            If *pnmcd\dwItemSpec&1
              FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
              SetTextColor_(*pnmcd\hdc, #Blue)
            Else
              FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
              SetTextColor_(*pnmcd\hdc, #Red)
            EndIf
            If *pnmcd\rc\right>*pnmcd\rc\left
              DrawText_(*pnmcd\hdc, @text$, Len(text$), *pnmcd\rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
            EndIf
            result = #CDRF_SKIPDEFAULT
        EndSelect
      EndIf
     
    Case #WM_PARENTNOTIFY           ; The pressing moment
     
      If wParam=#WM_RBUTTONDOWN
        With hitinfo.LVHITTESTINFO
          \pt\x = lparam &$FFFF
          \pt\y = lparam>>16
        EndWith
        SendMessage_(hwnd,#LVM_SUBITEMHITTEST, 0, @hitInfo)
        Column=hitinfo\iSubItem
        ;DrawFrameControl_(Var\hdc, Var\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)             ; Так не работает
        DrawFrameControl_(GetDC_(GadgetID(0)), Var\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
        Debug "Column №:"+Column
        Debug "hdc="+Str(Var\hdc)+"  Gadget Context="+Str(GetDC_(GadgetID(0)))
        Debug "dwItemSpec="+Str(Var\dwItemSpec)
        Debug "rc\bottom="+Str(Var\rc\bottom)
        Debug "rc\left="+Str(Var\rc\left)
        Debug "rc\right="+Str(Var\rc\right)
        Debug "rc\top="+Str(Var\rc\top)
        Debug ""
      EndIf
  EndSelect
  ProcedureReturn result
EndProcedure
 
 
If OpenWindow(0, 100, 100, 415, 300, "", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
  ListIconGadget(0, 5, 5, 405, 200, "col 0", 50, #PB_ListIcon_FullRowSelect | #PB_ListIcon_AlwaysShowSelection)
  hHeader = SendMessage_(GadgetID(0), #LVM_GETHEADER, 0, 0)
  ;Subclass ListIcon so we can customdraw the header text
  oldListIconCallback = SetWindowLong_(GadgetID(0), #GWL_WNDPROC, @SubclassedListIcon())
 
  ;Add 10 more columns.
  For i = 1 To 10
    AddGadgetColumn(0, i, "col "+Str(i), 50)
  Next
  ;Add some data
  For b=0 To 99; Add 100 rows.
    AddGadgetItem(0,-1,"")
  Next
  For i = 0 To 99
    For j = 0 To 50
      SetGadgetItemText(0,i,Str(i+j),j)
    Next j
  Next i          
 
  Repeat
  Until WaitWindowEvent() = #PB_Event_CloseWindow
  DeleteObject_(brush)
EndIf


Как то каряво. Не те координаты. Можно дальше рыть но сдаётся мне есть решение красивей.
Мож знает кто?


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Вт май 16, 2017 11:03 am 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Чтоли мысли нет нигде?
Мне поможет тут никто?!
Ant писал(а):
...сдаётся мне есть решение красивей.
Мож знает кто?

Значит моё самое красивое. не спорю :D
Вобщем сделал так:
Код:
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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
#LVM_GETHEADER = #LVM_FIRST + 31
 
Global oldListIconCallback, Gadget, hHeader, brush, *Var, ColorBackDefault=$D8E9EC
brush=CreateSolidBrush_(ColorBackDefault)
 
 
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item
  Static Column,text$
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  Select uMsg
    Case #WM_NOTIFY                   ;Нажатие/Отжатие ЛКМ
      *pnmh.NMHDR = lparam
      If *pnmh\code = #NM_CUSTOMDRAW
        *pnmcd.NMCUSTOMDRAW = lparam
        Select *pnmcd\dwDrawStage
          Case #CDDS_PREPAINT
            result = #CDRF_NOTIFYITEMDRAW
          Case #CDDS_ITEMPREPAINT
            text$=GetGadgetItemText(Gadget, -1, *pnmcd\dwItemSpec)
           
            If *pnmcd\uItemState & #CDIS_SELECTED
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
              *pnmcd\rc\left+2 : *pnmcd\rc\top+1
             
            Else
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
 
              *Var=*pnmcd\hdr\hwndFrom
             
            EndIf
           
            *pnmcd\rc\bottom-1 : *pnmcd\rc\right-1
            SetBkMode_(*pnmcd\hdc,#TRANSPARENT)
            If *pnmcd\dwItemSpec&1
              FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
              SetTextColor_(*pnmcd\hdc, #Blue)
            Else
              FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
              SetTextColor_(*pnmcd\hdc, #Red)
            EndIf
            If *pnmcd\rc\right>*pnmcd\rc\left
              DrawText_(*pnmcd\hdc, @text$, Len(text$), *pnmcd\rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
            EndIf
            result = #CDRF_SKIPDEFAULT
        EndSelect
      EndIf
     
    Case #WM_PARENTNOTIFY           ; Нажатие ПКМ
     
      If wParam=#WM_RBUTTONDOWN
        With hitinfo.LVHITTESTINFO
          \pt\x = lparam &$FFFF
          \pt\y = lparam>>16
        EndWith
        SendMessage_(hwnd,#LVM_SUBITEMHITTEST, 0, @hitInfo)
        Column=hitinfo\iSubItem
        text$=GetGadgetItemText(Gadget,-1,Column)
       
        SendMessage_(*Var,#HDM_FIRST+7,Column,@rc.RECT)
 
        DrawFrameControl_(GetDC_(*Var), rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
        Debug "Column №:"+Column+"   => "+text$
        Debug "rc.RECT\bottom="+Str(rc\bottom)
        Debug "rc.RECT\left="+Str(rc\left)
        Debug "rc.RECT\right="+Str(rc\right)
        Debug "rc.RECT\top="+Str(rc\top)
        Debug ""
       
        ;rc\bottom-1 : rc\right-1
        SetBkMode_(GetDC_(*Var),#TRANSPARENT)
        ;FillRect_(GetDC_(*Var), rc, brush)
       
        If Column & 1
          SetTextColor_(GetDC_(*Var), #Blue)
        Else
          SetTextColor_(GetDC_(*Var), #Red)
        EndIf
       
        If rc\right>rc\left
          DrawText_(GetDC_(*Var), @text$, Len(text$), rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
        EndIf
        result = #CDRF_SKIPDEFAULT
      EndIf
 
    Case #WM_CONTEXTMENU            ; Отжатие ПКМ
     
      SendMessage_(*Var,#HDM_FIRST+7,Column,@rc.RECT)
      DrawFrameControl_(GetDC_(*Var), rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
     
      ;rc\bottom-1 : rc\right-1
      SetBkMode_(GetDC_(*Var),#TRANSPARENT)
      ;FillRect_(GetDC_(*Var), rc, brush)
     
      If Column & 1
        SetTextColor_(GetDC_(*Var), #Blue)
      Else
        SetTextColor_(GetDC_(*Var), #Red)
      EndIf
     
      DrawText_(GetDC_(*Var), @text$, Len(text$), rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
      result = #CDRF_SKIPDEFAULT
     
  EndSelect
  ProcedureReturn result
EndProcedure
 
 
If OpenWindow(0, 100, 100, 415, 300, "", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
  Gadget=ListIconGadget(#PB_Any, 5, 5, 405, 200, "col 0", 50, #PB_ListIcon_FullRowSelect | #PB_ListIcon_AlwaysShowSelection)
  hHeader = SendMessage_(GadgetID(Gadget), #LVM_GETHEADER, 0, 0)
  oldListIconCallback = SetWindowLong_(GadgetID(Gadget), #GWL_WNDPROC, @SubclassedListIcon())
 
  For i = 1 To 10
    AddGadgetColumn(Gadget, i, "col "+Str(i), 50)
  Next
  For b=0 To 99
    AddGadgetItem(Gadget,-1,"")
  Next
  For i = 0 To 99
    For j = 0 To 50
      SetGadgetItemText(Gadget,i,Str(i+j),j)
    Next j
  Next i          
 
  Repeat
  Until WaitWindowEvent() = #PB_Event_CloseWindow
  DeleteObject_(brush)
EndIf


Почему то работает хотя через ж.
Вопрос: зачем она меняет шрифт в заголовке? да еще вырезает прямоугольник в фоне?
И как она понимает контекст пока ни нажата кнопка мыши? Ведь *Var=0 в начале а #WM_NOTIFY приходит по отжатию ПКМ. Тогда и присваивается *Var. А по нажатию?


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Вт май 16, 2017 12:36 pm 
Не в сети
МОДЕРАТОР
Аватар пользователя

Зарегистрирован: Пн апр 09, 2007 4:53 pm
Сообщений: 11208
Благодарил (а): 4 раз.
Поблагодарили: 421 раз.
Ant писал(а):
Вопрос: зачем она меняет шрифт в заголовке?
Потому что
Ant писал(а):
через ж.
В частности это касается множества вызовов GetDC. Нужно внимательно прочитать описание этой функции http://vsokovikov.narod.ru/New_MSDN_API ... _getdc.htm
То что сейчас в коде через время приведет к подобному результату (дело было давно и часть картинок уже исчезло) viewtopic.php?t=662

Думаю имеет смысл рисовать в событии #WM_PAINT заголовка таблицы.

_________________
Компьютер позволяет решать все те проблемы, которые до его изобретения не существовали. :) :)


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Вт май 16, 2017 1:07 pm 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Спасибо, Пётр наверно надо было освобождать контест по ReleaseDC_(). Попробую после я сейчас на работе.
Пётр писал(а):
Думаю имеет смысл рисовать в событии #WM_PAINT заголовка таблицы.

Пример можно? Я не очень понял. #WM_PAINT не приходит:
Код:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item
  Static Column,text$
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  Select uMsg
    Case #WM_NOTIFY                   ;Нажатие/Отжатие ЛКМ
...
Case #WM_PARENTNOTIFY           ; Нажатие ПКМ
...
Case #WM_CONTEXTMENU            ; Отжатие ПКМ
...
Default
      Debug umsg                    ; нет такого #WM_PAINT. Может надо #WM_MOUSEACTIVATE?
EndSelect
  ProcedureReturn result
EndProcedure
 



Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Вт май 16, 2017 1:23 pm 
Не в сети
МОДЕРАТОР
Аватар пользователя

Зарегистрирован: Пн апр 09, 2007 4:53 pm
Сообщений: 11208
Благодарил (а): 4 раз.
Поблагодарили: 421 раз.
Нужно ловить сообщение в CB функции заголовка таблицы.
Код:
1
2
hHeader = SendMessage_(GadgetID(Gadget), #LVM_GETHEADER, 0, 0)
oldListIconCallback = SetWindowLong_(hHeader, #GWL_WNDPROC, @SubclassedListIcon())


_________________
Компьютер позволяет решать все те проблемы, которые до его изобретения не существовали. :) :)


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Вт май 16, 2017 4:10 pm 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Пётр писал(а):
Нужно ловить сообщение в CB функции заголовка таблицы.
Код:
1
2
hHeader = SendMessage_(GadgetID(Gadget), #LVM_GETHEADER, 0, 0)
oldListIconCallback = SetWindowLong_(hHeader, #GWL_WNDPROC, @SubclassedListIcon())


#WM_NOTIFY приходит всегда и с ЛКМ нет проблем.
Но с ПКМ приходит по отжатию. Callback ни видит клика и ни рисует.
А с другими событиями ни получается считать из NMHDR структуры
Вот цитата из Всоковикова:

Структура NMHDR
Содержит в себе информацию об уведомляющем сообщении.
Синтаксис

typedef struct tagNMHDR {
HWND hwndFrom;
UINT idFrom;
UINT code;
} NMHDR;

Члены структуры
hwndFrom..............................Дескриптор окна, которому орган управления посылает сообщение.
idFrom...................................Идентификатор органа управления, отправляющего сообщение.
code.....................................Код уведомления. Этот член структуры может быть указанным для органа управления кодом уведомления, или это может быть один из обычных кодов уведомления


И как я там понял только по #WM_NOTIFY можно читать из NMHDR. Можно проверить что будет:
Код:
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
#LVM_GETHEADER = #LVM_FIRST + 31
 
Global oldListIconCallback, Gadget, hHeader, brush, *Var, ColorBackDefault=$D8E9EC
brush=CreateSolidBrush_(ColorBackDefault)
 
 
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item
  Static Column,text$
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  Select uMsg
 
    Case #WM_NCHITTEST          ; все что есть события ПКМ
;     Case #WM_MOUSEACTIVATE
;     Case #WM_RBUTTONDOWN
     
      *pnmh.NMHDR = lparam
        Debug *pnmh\code
 
      result = #CDRF_SKIPDEFAULT
     
  EndSelect
  ProcedureReturn result
EndProcedure
 
 
If OpenWindow(0, 100, 100, 415, 300, "", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
  Gadget=ListIconGadget(#PB_Any, 5, 5, 405, 200, "col 0", 50, #PB_ListIcon_FullRowSelect | #PB_ListIcon_AlwaysShowSelection)
 
  hHeader = SendMessage_(GadgetID(Gadget), #LVM_GETHEADER, 0, 0)
  oldListIconCallback = SetWindowLong_(hHeader, #GWL_WNDPROC, @SubclassedListIcon())
 
  For i = 1 To 10
    AddGadgetColumn(Gadget, i, "col "+Str(i), 50)
  Next
  For b=0 To 99
    AddGadgetItem(Gadget,-1,"")
  Next
  For i = 0 To 99
    For j = 0 To 50
      SetGadgetItemText(Gadget,i,Str(i+j),j)
    Next j
  Next i          
 
  Repeat
  Until WaitWindowEvent() = #PB_Event_CloseWindow
  DeleteObject_(brush)
EndIf



А что надо DrawFrameControl_()?
Контест да RECT структуру. А как можно добыть контест не по #WM_NOTIFY?

Или я ни понял опять?


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Ср май 17, 2017 11:44 am 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
А всё получилось.
Код:
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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
#LVM_GETHEADER = #LVM_FIRST + 31
 
Global oldListIconCallback, Gadget, hHeader, brush, *Var, ColorBackDefault=$D8E9EC
brush=CreateSolidBrush_(ColorBackDefault)
 
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item
  Static Column,text$,Context
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  Select uMsg
    Case #WM_NOTIFY                   ;Нажатие/Отжатие ЛКМ
      *pnmh.NMHDR = lparam
      If *pnmh\code = #NM_CUSTOMDRAW
        *pnmcd.NMCUSTOMDRAW = lparam
        Select *pnmcd\dwDrawStage
          Case #CDDS_PREPAINT
            result = #CDRF_NOTIFYITEMDRAW
          Case #CDDS_ITEMPREPAINT
            text$=GetGadgetItemText(Gadget, -1, *pnmcd\dwItemSpec)
           
            If *pnmcd\uItemState & #CDIS_SELECTED
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
              *pnmcd\rc\left+2 : *pnmcd\rc\top+2
             
            Else
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
              *Var=*pnmcd\hdr\hwndFrom:Context=GetDC_(*Var)
             
            EndIf
           
            *pnmcd\rc\bottom-1 : *pnmcd\rc\right-1
            SetBkMode_(*pnmcd\hdc,#TRANSPARENT)
            If *pnmcd\dwItemSpec&1
              FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
              SetTextColor_(*pnmcd\hdc, #Blue)
            Else
              FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
              SetTextColor_(*pnmcd\hdc, #Red)
            EndIf
            If *pnmcd\rc\right>*pnmcd\rc\left
              DrawText_(*pnmcd\hdc, @text$, Len(text$), *pnmcd\rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
            EndIf
            result = #CDRF_SKIPDEFAULT
        EndSelect
      EndIf
     
    Case #WM_PARENTNOTIFY           ; Нажатие ПКМ
     
      If wParam=#WM_RBUTTONDOWN
        With hitinfo.LVHITTESTINFO
          \pt\x = lparam &$FFFF
          \pt\y = lparam>>16
        EndWith
        SendMessage_(hwnd,#LVM_SUBITEMHITTEST, 0, @hitInfo)
        Column=hitinfo\iSubItem
        text$=GetGadgetItemText(Gadget,-1,Column)
       
        SendMessage_(*Var,#HDM_FIRST+7,Column,@rc.RECT)
       
        DrawFrameControl_(Context, rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
        Debug "Column №:"+Column+"   => "+text$
        Debug "rc.RECT\bottom="+Str(rc\bottom)
        Debug "rc.RECT\left="+Str(rc\left)
        Debug "rc.RECT\right="+Str(rc\right)
        Debug "rc.RECT\top="+Str(rc\top)
        Debug ""
       
        rc\top+2 : rc\left+2
        SetBkMode_(Context,#TRANSPARENT)
        FillRect_(Context, rc, brush)
       
        If Column & 1
          SetTextColor_(Context, #Blue)
        Else
          SetTextColor_(Context, #Red)
        EndIf
       
        If rc\right>rc\left
          DrawText_(Context, @text$, Len(text$), rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
        EndIf
        result = #CDRF_SKIPDEFAULT
      EndIf
 
    Case #WM_CONTEXTMENU            ; Отжатие ПКМ
     
      SendMessage_(*Var,#HDM_FIRST+7,Column,@rc.RECT)
      DrawFrameControl_(Context, rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
     
      rc\bottom-1 : rc\right-1
      SetBkMode_(Context,#TRANSPARENT)
      FillRect_(Context, rc, brush)
     
      If Column & 1
        SetTextColor_(Context, #Blue)
      Else
        SetTextColor_(Context, #Red)
      EndIf
     
      DrawText_(Context, @text$, Len(text$), rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
      result = #CDRF_SKIPDEFAULT
     
  EndSelect
  ProcedureReturn result
EndProcedure
 
Window=OpenWindow(#PB_Any, 100, 100, 415, 300, "", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
  Gadget=ListIconGadget(#PB_Any, 5, 5, 405, 200, "col 0", 50, #PB_ListIcon_FullRowSelect | #PB_ListIcon_AlwaysShowSelection)
  FontDefault = GetGadgetFont(Gadget)                                                          ; Узнать шрифт по умолчанию (без создания хотя бы формального ListIconGadget невозможно)
  SendMessage_(SendMessage_(GadgetID(Gadget),#LVM_GETHEADER,0,0),#WM_SETFONT,@FontDefault,1)   ; Шрифт заголовка
 
  hHeader = SendMessage_(GadgetID(Gadget), #LVM_GETHEADER, 0, 0)
  oldListIconCallback = SetWindowLong_(GadgetID(Gadget), #GWL_WNDPROC, @SubclassedListIcon())
 
  For i = 1 To 10
    AddGadgetColumn(Gadget, i, "col "+Str(i), 50)
  Next
  For b=0 To 99
    AddGadgetItem(Gadget,-1,"")
  Next
  For i = 0 To 99
    For j = 0 To 50
      SetGadgetItemText(Gadget,i,Str(i+j),j)
    Next j
  Next i          
 
  Repeat
  Until WaitWindowEvent() = #PB_Event_CloseWindow
  DeleteObject_(brush)



Правда это по моему. Кому ни нравится может исправить и обязательно показать как надо.
Мне тоже хочется без извращений. Большое спасибо Петру за совет и важную ссылку.
Освобождать контест пытался. Плохо. Но там
Цитата:
Для DC класса и частный контексты устройства не должны освобождаться.

Надеюсь все правильно.Там же ответ насчёт шрифта
Цитата:
GetDC назначает атрибуты контексту устройства (DC) по умолчанию, каждый раз, когда он извлекается. Например, заданный по умолчанию шрифт System, который является растровым шрифтом.

Код Петра у меня почему то не работает. я уж гадаю на кофе чего ни так
Пётр писал(а):
Нужно ловить сообщение в CB функции заголовка таблицы.

CB это Callback()? Судя по примеру нет. Но я поробывал. Вышло через ж. Теперь ясно почему все юзают хуки а есть нативная пуриковская функция.
Вобщем буду рад если мне покажут правильно. А пока так :|


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Ср май 17, 2017 2:31 pm 
Не в сети
МОДЕРАТОР
Аватар пользователя

Зарегистрирован: Пн апр 09, 2007 4:53 pm
Сообщений: 11208
Благодарил (а): 4 раз.
Поблагодарили: 421 раз.
Ant писал(а):
Освобождать контест пытался. Плохо.
Пробовали перед строкой
Код:
1
*Var=*pnmcd\hdr\hwndFrom:Context=GetDC_(*Var)

добавить
Код:
1
2
3
If Context And *Var
  ReleaseDC_(*Var, Context)
EndIf


Ant писал(а):
Но там
Цитата:
Для DC класса и частный контексты устройства не должны освобождаться.
Судя по тему что память все еще течет, распространяется.
Ant писал(а):
Код Петра у меня почему то не работает. я уж гадаю на кофе чего ни так
Рисовали в обработчике события #WM_PAINT или код процедуры SubclassedListIcon был неизменным?

Если кликать правой кнопкой мышки по таблице, то текст колонок заголовка изменяется.

_________________
Компьютер позволяет решать все те проблемы, которые до его изобретения не существовали. :) :)


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Ср май 17, 2017 3:42 pm 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Пётр писал(а):
Пробовали перед строкой
Код:
1
*Var=*pnmcd\hdr\hwndFrom:Context=GetDC_(*Var)

добавить
Код:
1
2
3
If Context And *Var
  ReleaseDC_(*Var, Context)
EndIf


Нет я без условия и после:
Код:
1
*Var=*pnmcd\hdr\hwndFrom:Context=GetDC_(*Var):ReleaseDC_(*Var, Context)


Вот показали мне и понял всё: самую суть!
Пётр писал(а):
Судя по тему что память все еще течет, распространяется.

Я неопытный. Уже читал про утечку памяти на форуме. Но пишут всколзь (у меня утечка...) А как это узнать есть или нет?
Ей богу не сном ни духом.
Пётр писал(а):
Рисовали в обработчике события #WM_PAINT или код процедуры SubclassedListIcon был неизменным?

Подозреваю это такой термин "обработчик события". Какая нибудь процедура или хук. Значит поэтому я не понял и тупо ловил само событие #WM_PAINT в процедуре SubclassedListIcon()
А оно приходит всего 1 раз ! Можно пример какой или ссылку что значит "рисовать в обработчике"?
Код:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item
  Static Column,text$,Context
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  Select uMsg
    Case #WM_NOTIFY                   ;Нажатие/Отжатие ЛКМ
 
     ...
    Case #WM_PARENTNOTIFY           ; Нажатие ПКМ
     
 
     ...
    Case #WM_CONTEXTMENU            ; Отжатие ПКМ
     
      ...
     
    Case #WM_PAINT
     
  EndSelect
  ProcedureReturn result
EndProcedure
 


Пётр писал(а):
Если кликать правой кнопкой мышки по таблице, то текст колонок заголовка изменяется.

Не приятная новость. Буду разбираться.Спасибо.


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Ср май 17, 2017 4:32 pm 
Не в сети
МОДЕРАТОР
Аватар пользователя

Зарегистрирован: Пн апр 09, 2007 4:53 pm
Сообщений: 11208
Благодарил (а): 4 раз.
Поблагодарили: 421 раз.
Ant писал(а):
Нет я без условия и после
Тогда уничтожается только что созданный контекст и дальше его использовать нельзя. Конечно работать не будет. Это все равно что вообще по получать контекст.

Ant писал(а):
А как это узнать есть или нет?
Просто посмотреть что происходит с памятью процесса в диспетчере задач. Если без причины увеличивается размер используемой памяти процессом, это утечка.

Ant писал(а):
А оно приходит всего 1 раз !
Происходит при необходимости перерисовки. Если проводить мышкой по заголоку таблицы, то будет периодически происходить. Подробнее http://vsokovikov.narod.ru/New_MSDN_API ... _paint.htm
Код:
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
#LVM_GETHEADER = #LVM_FIRST + 31
 
Global oldListIconCallback, Gadget, hHeader, brush, *Var, ColorBackDefault=$D8E9EC
 
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item
  Static Column,text$,Context
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  Select uMsg
    Case #WM_PAINT
      Debug "WM_PAINT"
  EndSelect
  ProcedureReturn result
EndProcedure
 
Window=OpenWindow(#PB_Any, 100, 100, 415, 300, "", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
Gadget=ListIconGadget(#PB_Any, 5, 5, 405, 200, "col 0", 50, #PB_ListIcon_FullRowSelect | #PB_ListIcon_AlwaysShowSelection)
FontDefault = GetGadgetFont(Gadget)                                                          ; Узнать шрифт по умолчанию (без создания хотя бы формального ListIconGadget невозможно)
SendMessage_(SendMessage_(GadgetID(Gadget),#LVM_GETHEADER,0,0),#WM_SETFONT,@FontDefault,1)   ; Шрифт заголовка
 
hHeader = SendMessage_(GadgetID(Gadget), #LVM_GETHEADER, 0, 0)
oldListIconCallback = SetWindowLong_(hHeader, #GWL_WNDPROC, @SubclassedListIcon())
 
For i = 1 To 10
  AddGadgetColumn(Gadget, i, "col "+Str(i), 50)
Next
For b=0 To 99
  AddGadgetItem(Gadget,-1,"")
Next
For i = 0 To 99
  For j = 0 To 50
    SetGadgetItemText(Gadget,i,Str(i+j),j)
  Next j
Next i          
 
Repeat
Until WaitWindowEvent() = #PB_Event_CloseWindow


_________________
Компьютер позволяет решать все те проблемы, которые до его изобретения не существовали. :) :)


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Чт май 18, 2017 7:39 pm 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Пётр писал(а):
Если кликать правой кнопкой мышки по таблице, то текст колонок заголовка изменяется.

Исправил:
Код:
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
...
          Case #CDDS_ITEMPREPAINT
            text$=GetGadgetItemText(Gadget, -1, *pnmcd\dwItemSpec)
           
            If Context And *Var
              ReleaseDC_(*Var, Context)
              *Var=0                   ; устранение глюка (текст заголовка меняется по клику в строке)
            EndIf
            *Var=*pnmcd\hdr\hwndFrom:Context=GetDC_(*Var)
           
            If *pnmcd\uItemState & #CDIS_SELECTED
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
              *pnmcd\rc\left+2 : *pnmcd\rc\top+2
             
            Else
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
 
            EndIf
           
            *pnmcd\rc\bottom-1 : *pnmcd\rc\right-1
            SetBkMode_(*pnmcd\hdc,#TRANSPARENT)
            If *pnmcd\dwItemSpec&1
              FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
              SetTextColor_(*pnmcd\hdc, #Blue)
            Else
              FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
              SetTextColor_(*pnmcd\hdc, #Red)
            EndIf
            If *pnmcd\rc\right>*pnmcd\rc\left
              DrawText_(*pnmcd\hdc, @text$, Len(text$), *pnmcd\rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
            EndIf
            result = #CDRF_SKIPDEFAULT
        EndSelect
...


Утечки памяти вроде нет.
Петру:
Да Пётр путь к счастю лежит через страдания. Надо помучаться. Получаеш контест окна, потом регион отсечения, потом еще 33 удовольствия.
Решишь одно получишь 10 других. Освоить рисовать через #WM_PAINT значит научится половине API :D Освою куда денусь со временем.
Но сейчас чувствую надо учиться потрошить стуктуры с членом hdc
Их всего 7: MCI_ANIM_UPDATE_PARMS, DRAWITEMSTRUCT, CHOOSEFONT, PRINTDLG, NMCUSTOMDRAW, FORMATRANGE, PAINTSTRUCT.
C последней я долго бился ( например через BeginPaint_() но получил только контест гаджета.
Код:
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
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Protected hdi.hd_item, MY.PAINTSTRUCT
  Static Column,text$,Context
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
  Select uMsg
    Case #WM_PAINT
      Debug "WM_PAINT"
     
      HDC=BeginPaint_(hwnd,@MY)
      Debug HDC
      EndPaint_(hWnd, @MY)
     
      With hitinfo.LVHITTESTINFO           ; структура пуста. тогда какую вместо этой?
        \pt\x = lparam &$FFFF
        \pt\y = lparam>>16
      EndWith
      SendMessage_(hwnd,#LVM_SUBITEMHITTEST, 0, @hitInfo)
      Column=hitinfo\iSubItem
      Debug Column
 
    Case #WM_RBUTTONDOWN
 
      SendMessage_(hwnd,#WM_PAINT, 0, @MY)  ; ну а как ещё заставить чувствовать ПКМ?
 
  EndSelect
  ProcedureReturn result
EndProcedure


Вот думаю настоящее извращение столько сил убить в миллиметре от цели. Может есть пара пимеров как люди не по #WM_NOTIFY добирались до контеста заголовка?.


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Чт май 18, 2017 7:51 pm 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Пардон ошибся
Код:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
    Case #WM_CONTEXTMENU            ; Отжатие ПКМ
     
      SendMessage_(*Var,#HDM_FIRST+7,Column,@rc.RECT)
      DrawFrameControl_(Context, rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
     
      rc\bottom-1 : rc\right-1
      SetBkMode_(Context,#TRANSPARENT)
      FillRect_(Context, rc, brush)
     
      If Column & 1
        SetTextColor_(Context, #Blue)
      Else
        SetTextColor_(Context, #Red)
      EndIf
      text$=GetGadgetItemText(Gadget,-1,Column) ; вот настоящая причина
      DrawText_(Context, @text$, Len(text$), rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)


а предыдущие исправление неработает


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Пт май 19, 2017 11:11 am 
Не в сети
МОДЕРАТОР
Аватар пользователя

Зарегистрирован: Пн апр 09, 2007 4:53 pm
Сообщений: 11208
Благодарил (а): 4 раз.
Поблагодарили: 421 раз.
В #WM_PAINT нужно полностью все рисовать, а не только hDC получать.

_________________
Компьютер позволяет решать все те проблемы, которые до его изобретения не существовали. :) :)


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Пт май 19, 2017 12:25 pm 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Пётр писал(а):
В #WM_PAINT нужно полностью все рисовать, а не только hDC получать.

Тогда наверно на канвасе сразу


Вернуться наверх
 Профиль  
 
 Заголовок сообщения: Re: Работа DrawFrameControl_() по ПКМ
СообщениеДобавлено: Пн май 22, 2017 11:41 am 
Не в сети
ассистент
Аватар пользователя

Зарегистрирован: Пн май 15, 2017 11:06 am
Сообщений: 19
Благодарил (а): 3 раз.
Поблагодарили: 1 раз.
Пункты репутации: 0
Ant писал(а):
Пётр писал(а):
В #WM_PAINT нужно полностью все рисовать, а не только hDC получать.

Тогда наверно на канвасе сразу

Код:
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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
#LVM_GETHEADER = #LVM_FIRST + 31
 
Structure SII
  Canvas.l
  Column.l
  ColumnName.s
  ColumnHeadColor.l
  Container.l
  X.l
  WidthColumn.l
EndStructure
 
Structure SI
  Array Column.SII(0)
  ColumnCount.l
  Height.l
EndStructure
 
Global oldListIconCallback, Gadget, hHeader, brush, H.SI, ColorBackDefault=$D8E9EC
brush=CreateSolidBrush_(ColorBackDefault)
 
Procedure SubclassedListIcon(hWnd, uMsg, wParam, lParam)
  Static Column, PosX
  result = CallWindowProc_(oldListIconCallback, hWnd, uMsg, wParam, lParam)
 
  Select uMsg
    Case #WM_NOTIFY                   ;Нажатие/Отжатие ЛКМ
      *pnmh.NMHDR = lparam
      If *pnmh\code = #NM_CUSTOMDRAW
        *pnmcd.NMCUSTOMDRAW = lparam
        Select *pnmcd\dwDrawStage
          Case #CDDS_PREPAINT
            result = #CDRF_NOTIFYITEMDRAW
          Case #CDDS_ITEMPREPAINT
            text$=GetGadgetItemText(Gadget, -1, *pnmcd\dwItemSpec)
            If H\Height<10
              With H\Column(i)
                H\Height=*pnmcd\rc\bottom; исправление высоты заголовка
                For i=0 To H\ColumnCount-1
                  HideGadget(\Container,0):HideGadget(\Canvas,0)
                  ResizeGadget(\Container,#PB_Ignore,#PB_Ignore,#PB_Ignore,H\Height+1)
                  ResizeGadget(\Canvas,#PB_Ignore,#PB_Ignore,#PB_Ignore,H\Height)
                  HideGadget(\Container,1):HideGadget(\Canvas,1)
                Next
              EndWith
            EndIf
            If *pnmcd\uItemState & #CDIS_SELECTED
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH|#DFCS_PUSHED)
              *pnmcd\rc\left+2 : *pnmcd\rc\top+2
            Else
              DrawFrameControl_(*pnmcd\hdc, *pnmcd\rc, #DFC_BUTTON, #DFCS_BUTTONPUSH)
            EndIf
           
            *pnmcd\rc\bottom-1 : *pnmcd\rc\right-1
            SetBkMode_(*pnmcd\hdc,#TRANSPARENT)
            FillRect_(*pnmcd\hdc, *pnmcd\rc, brush)
            SetTextColor_(*pnmcd\hdc, H\Column(*pnmcd\dwItemSpec)\ColumnHeadColor)
           
            If *pnmcd\rc\right>*pnmcd\rc\left
              DrawText_(*pnmcd\hdc, @text$, Len(text$), *pnmcd\rc, #DT_CENTER|#DT_VCENTER|#DT_SINGLELINE|#DT_END_ELLIPSIS)
            EndIf
            result = #CDRF_SKIPDEFAULT
        EndSelect
      EndIf
     
    Case #WM_PARENTNOTIFY           ; Нажатие ПКМ
      If wParam=#WM_RBUTTONDOWN
        With hitinfo.LVHITTESTINFO
          \pt\x = lparam &$FFFF
          \pt\y = lparam>>16
        EndWith
        SendMessage_(hwnd,#LVM_SUBITEMHITTEST, 0, @hitInfo)
        Column=hitinfo\iSubItem
       
        With H\Column(Column)
          HideGadget(\Container,0):HideGadget(\Canvas,0)
          If StartDrawing(CanvasOutput(\Canvas))
            OffsetX1=GadgetX(Gadget)-GadgetX(\Container)
            Box(0,0,\WidthColumn,H\Height,ColorBackDefault)
           
            If OffsetX1>0 And \WidthColumn-OffsetX1>0
              LineXY (OffsetX1, 0, \WidthColumn, 0, #Gray)
              LineXY (OffsetX1, 0, OffsetX1, H\Height, #Gray)
              ClipOutput(OffsetX1+2,0,\WidthColumn,H\Height)
            Else
              LineXY (0, 0, \WidthColumn, 0, #Gray)
              LineXY (1, 0, 1, H\Height, #Gray):LineXY (2, 0, 2, H\Height, #Gray):LineXY (3, 0, 3, H\Height, #Gray)
            EndIf
            OffsetX2=GadgetX(Gadget)+GadgetWidth(Gadget)-20
            If GadgetX(\Container)+\WidthColumn>OffsetX2
              ResizeGadget(\Container,#PB_Ignore,#PB_Ignore,OffsetX2-GadgetX(\Container),#PB_Ignore)
            EndIf
           
            DrawText ((\WidthColumn-TextWidth(\ColumnName))/2+2, (H\Height-TextHeight(\ColumnName))/2+2, \ColumnName, \ColumnHeadColor, ColorBackDefault); смещение текста
          EndIf
          StopDrawing()
        EndWith
      EndIf
     
    Case #WM_CONTEXTMENU            ; Отжатие ПКМ
      HideGadget(H\Column(Column)\Container,1)
      HideGadget(H\Column(Column)\Canvas,1)
     
    Case #WM_HSCROLL                                                                                                                                                                                                    ; Событие горизонтальной прокрутки
     
      PosX=GetScrollPos_(GadgetID(Gadget),#SB_HORZ)
     
    Case #WM_SYSCOMMAND                                              ; Коррекция
     
      With H\Column(i)
        For i=0 To H\ColumnCount-1
          HideGadget(\Container,0):HideGadget(\Canvas,0)
          ResizeGadget(\Container,\X-PosX,#PB_Ignore,#PB_Ignore,#PB_Ignore)
          HideGadget(\Container,1):HideGadget(\Canvas,1)    
        Next
      EndWith
      PosX=0
     
  EndSelect
  ProcedureReturn result
EndProcedure
 
Window=OpenWindow(#PB_Any, 100, 100, 415, 300, "", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
Gadget=ListIconGadget(#PB_Any, 5, 5, 405, 200, "col 0", 50, #PB_ListIcon_FullRowSelect | #PB_ListIcon_AlwaysShowSelection)
H\Height=5                                                                                ; Высота заголовка заведомо мало. Потом исправится
H\ColumnCount=10                                                                          ; Число столбцов
FontDefault = GetGadgetFont(Gadget)                                                       ; Узнать шрифт по умолчанию (без создания хотя бы формального ListIconGadget невозможно)
SendMessage_(SendMessage_(GadgetID(Gadget),#LVM_GETHEADER,0,0),#WM_SETFONT,@FontDefault,1); Шрифт заголовка
 
ReDim H\Column(H\ColumnCount)
 
oldListIconCallback = SetWindowLong_(GadgetID(Gadget), #GWL_WNDPROC, @SubclassedListIcon())
 
X=GadgetX(Gadget)+1:i=0
For i = 0 To H\ColumnCount-1
  If i
    AddGadgetColumn(Gadget, i, "col "+Str(i), 50)
  EndIf
 
  With H\Column(i)
    \X=X
    \Container=ContainerGadget(#PB_Any, \X, GadgetY(Gadget)+1, GetGadgetItemAttribute(Gadget,0,#PB_ListIcon_ColumnWidth,i)+1, H\Height+1)
    \Canvas=CanvasGadget(#PB_Any, 0, 0, GadgetWidth(\Container), H\Height, #PB_Canvas_ClipMouse)
    \Column=i
    \ColumnName=GetGadgetItemText(Gadget,-1,i)
    \WidthColumn=GetGadgetItemAttribute(Gadget,0,#PB_ListIcon_ColumnWidth,i)
   
    If \Column & 1
      \ColumnHeadColor=#Blue
    Else
      \ColumnHeadColor=#Red
    EndIf
   
    X+\WidthColumn
    HideGadget(\Container,1):HideGadget(\Canvas,1)
    CloseGadgetList()
  EndWith
Next
 
For b=0 To 99
  AddGadgetItem(Gadget,-1,"")
Next
For i = 0 To 99
  For j = 0 To 50
    SetGadgetItemText(Gadget,i,Str(i+j),j)
  Next j
Next i          
 
Repeat
Until WaitWindowEvent() = #PB_Event_CloseWindow
DeleteObject_(brush)



Получилось сложнее. Зато можно рисовать что хош на то и канвас.
Но это ни в тему и я закругляюсь иначе забанят за тролинг :D


Вернуться наверх
 Профиль  
 
Показать сообщения за:  Сортировать по:  
Начать новую тему Ответить на тему  [ Сообщений: 20 ]  На страницу 1, 2  След.

Часовой пояс: UTC + 3 часа


Кто сейчас на форуме

Сейчас этот форум просматривают: balex1978, Bing [Bot] и гости: 9


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Перейти:  
Создано на основе phpBB® Forum Software © phpBB Group (блог о phpBB)
Сборка создана CMSart Studio
Русская поддержка phpBB