Page 1 sur 1

Pb CallBack -> Accès memoire invalide

Publié : mer. 27/juin/2012 22:27
par wood51
Bonsoir,

J'ai un soucis d'accès mémoire invalide avec des fonction callback . Je fais un callback principal sur la fenêtre pour intercepter le changement du texte du StringGadget puis je voudrais récupérer la touche "taper" (Tab,Entrée,haut,bas) . D'après je que j'ai compris (c'est à dire pas grand chose :mrgreen:)Il faut que je refasse un callback sur le StringGadget et la çà bug !!!! :twisted:

Pour la petite histoire je voulais un StringGadget qui ce complète tous seul . Pourquoi passer par les Callback , Pour que tous soit autonome un peu comme un nouveau Gadget Bref pourquoi faire simple quand on peut faire compliqué :D

Voilà mon code spécial méga Bug ....

Code : Tout sélectionner

;- Enumerations
;{
Enumeration
  #WinMain
  #String
EndEnumeration
;}

;- Structure
;{
Structure Lst
  Text.s
  Affiche.i
EndStructure

Structure ACStringInfo
  ID_Edit.i
  ID_List.i
  ListHeight.i 
EndStructure

  

;}

;- Variables
;{
Global NewList Liste.Lst()
Global ACS.ACStringInfo
Global Flag_EnCours = 0
Global oldEditProc.l
;}

;- Procedure
;{
Procedure LoWord(value)
  ProcedureReturn value & $FFFF
EndProcedure

Procedure HiWord(value)
  ProcedureReturn value >> 16 & $FFFF
EndProcedure 

Procedure AddToList(String.s)
  If ACS\ID_List
    Result=AddElement(Liste())
    If Result
      Liste()\Text = String
      Liste()\Affiche = 1
      SortStructuredList(Liste(), #PB_Sort_Ascending, OffsetOf(Lst\Text), #PB_Sort_String)
    EndIf
  EndIf
EndProcedure

Procedure UpdateListView()
  ClearGadgetItems(ACS\ID_List)
  ResetList(Liste())
  
  While NextElement(Liste())
    If Liste()\Affiche = 1
      AddGadgetItem(ACS\ID_List,-1,Liste()\Text)
    EndIf
  Wend
  
EndProcedure

Procedure SearchInList()
  Flag_EnCours = 1
  ;Texte tapé et sa longueur
  TextTyped.s = GetGadgetText(ACS\ID_Edit)
  LenTextTyped = Len(TextTyped)
  
  ;Maj Liste chainée
  ResetList(Liste())
  While NextElement(Liste())
    If UCase(Left(TextTyped,LenTextTyped)) = UCase(Left(Liste()\Text,LenTextTyped))
      Liste()\Affiche = 1
    Else
      Liste()\Affiche = 0
    EndIf
  Wend
  
  ;Maj du ListView
  ClearGadgetItems(ACS\ID_List)
  
  
  ResetList(Liste())
  
  While NextElement(Liste())
    If Liste()\Affiche = 1
      AddGadgetItem(ACS\ID_List,-1,Liste()\Text)
    EndIf
  Wend
  
  LenTextSave = GetGadgetData(ACS\ID_Edit)
  If LenTextTyped <= LenTextSave
    SetGadgetData(#String, LenTextTyped)
  Else
    ;Selection dans le ListView
    ItemCount = CountGadgetItems(ACS\ID_List)
    
    For Item = 0 To ItemCount - 1
      ItemText.s = GetGadgetItemText(ACS\ID_List,Item)
      If  UCase(TextTyped) = UCase(Left(ItemText,LenTextTyped)) 
        SetGadgetState(ACS\ID_List,Item)
        Selection_Start = LenTextTyped
        Selection_End = Len(ItemText)
        
        
        SetGadgetText(#String,ItemText)
        SendMessage_(GadgetID(ACS\ID_Edit), #EM_SETSEL, Selection_Start, Selection_End)
   
        SetGadgetData(ACS\ID_Edit, LenTextTyped)
        Break
      EndIf
    Next
  EndIf
  Flag_EnCours = 0
EndProcedure

Procedure StringProc(hWnd,uMsg,wParam,lParam)
  result = #PB_ProcessPureBasicEvents
  Select uMsg
    Case #WM_CHAR
      Debug wParam
  EndSelect
  
  ProcedureReturn result
EndProcedure


Procedure AC_StringGadgetProc(hWnd,uMsg,wParam,lParam)
 result = #PB_ProcessPureBasicEvents
  Select uMsg
    Case #WM_COMMAND
      If (wParam >> 16 = #EN_CHANGE) And (lParam =GadgetID(ACS\ID_Edit)) 
        Debug "#EN_CHANGE"
        If Flag_EnCours = 0
          SearchInList()
        EndIf 
      EndIf   
  EndSelect
  
  ProcedureReturn result
EndProcedure



Procedure AC_StringGadget(Gadget,x,y,w,h,lh,text.s="")
  ACS\ID_Edit=Gadget
  If StringGadget(Gadget,x,y,w,h,text)
    
    ACS\ID_List=ListViewGadget(#PB_Any,x,y+GadgetHeight(Gadget),w,lh)
    If ACS\ID_List
      SetWindowCallback(@AC_StringGadgetProc())
      ;si je décommente la ligne suivante , CA BUG !!!!
      oldEditProc=SetWindowLong_(GadgetID(ACS\ID_Edit),GWL_WNDPROC,@StringProc)
    EndIf

  EndIf
EndProcedure

Procedure Open_WinMain()
  If OpenWindow(#WinMain,0,0,300,150,"StringGadgetEx",#PB_Window_ScreenCentered|#PB_Window_SystemMenu)
    AC_StringGadget(#String,50,10,200,20,100)
    
  EndIf
EndProcedure
;}

;- Main
;{

Open_WinMain()

    AddToList("AS250M150V3")
    AddToList("AS250L250V2")
    AddToList("AS250/100V2")
    AddToList("AS250M130-16V4")
    AddToList("AS250M160")
    AddToList("AB100V2")
    AddToList("AC100")
    AddToList("AS280L240-28V6")
    AddToList("AS280L240-28V5")
    AddToList("AS280L240-28V8")
    AddToList("AB100V3")
    AddToList("AS180L170")

    UpdateListView()

SetActiveGadget(ACS\ID_Edit)
SetGadgetState(ACS\ID_List,0)

;}

;- Event Loop
;{
Repeat
  Event = WaitWindowEvent()
  
  Select Event
     Case #PB_Event_CloseWindow
      EventWindow = EventWindow()
      If EventWindow = #WinMain
        CloseWindow(#WinMain)
        Break
      EndIf
  EndSelect
ForEver
;}

Re: Pb CallBack -> Accès memoire invalide

Publié : jeu. 28/juin/2012 8:26
par Mesa
Si je commente la ligne 157 comme ça

Code : Tout sélectionner

 ;oldEditProc=SetWindowLong_(GadgetID(ACS\ID_Edit),GWL_WNDPROC,@StringProc)
alors tout fonctionne bien avec XP32b et PB 4.61.

Mesa.

Re: Pb CallBack -> Accès memoire invalide

Publié : jeu. 28/juin/2012 11:26
par nico
@StringProc()

Re: Pb CallBack -> Accès memoire invalide

Publié : jeu. 28/juin/2012 12:37
par Mindphazer
Personnellement, je n'ai aucun plantage (avec ou sans la fameuse ligne commentée)

Re: Pb CallBack -> Accès memoire invalide

Publié : jeu. 28/juin/2012 14:43
par Kwai chang caine
+1 avec VISTA et v4.51

Re: Pb CallBack -> Accès memoire invalide

Publié : jeu. 28/juin/2012 17:11
par wood51
Salut
avec Vista et PB4.61 toujours le problème d'accès mémoire invalide .

Nico : J'ai corrigé mais toujours le même résultat

J'y comprend plus rien :cry:

Re: Pb CallBack -> Accès memoire invalide

Publié : jeu. 28/juin/2012 17:41
par nico

Code : Tout sélectionner

;- Enumerations
;{
Enumeration
  #WinMain
  #String
EndEnumeration
;}

;- Structure
;{
Structure Lst
  Text.s
  Affiche.i
EndStructure

Structure ACStringInfo
  ID_Edit.i
  ID_List.i
  ListHeight.i 
EndStructure

  

;}

;- Variables
;{
Global NewList Liste.Lst()
Global ACS.ACStringInfo
Global Flag_EnCours = 0
Global oldEditProc.l
;}

;- Procedure
;{
Procedure LoWord(value)
  ProcedureReturn value & $FFFF
EndProcedure

Procedure HiWord(value)
  ProcedureReturn value >> 16 & $FFFF
EndProcedure 

Procedure AddToList(String.s)
  If ACS\ID_List
    Result=AddElement(Liste())
    If Result
      Liste()\Text = String
      Liste()\Affiche = 1
      SortStructuredList(Liste(), #PB_Sort_Ascending, OffsetOf(Lst\Text), #PB_Sort_String)
    EndIf
  EndIf
EndProcedure

Procedure UpdateListView()
  ClearGadgetItems(ACS\ID_List)
  ResetList(Liste())
  
  While NextElement(Liste())
    If Liste()\Affiche = 1
      AddGadgetItem(ACS\ID_List,-1,Liste()\Text)
    EndIf
  Wend
  
EndProcedure

Procedure SearchInList()
  Flag_EnCours = 1
  ;Texte tapé et sa longueur
  TextTyped.s = GetGadgetText(ACS\ID_Edit)
  LenTextTyped = Len(TextTyped)
  
  ;Maj Liste chainée
  ResetList(Liste())
  While NextElement(Liste())
    If UCase(Left(TextTyped,LenTextTyped)) = UCase(Left(Liste()\Text,LenTextTyped))
      Liste()\Affiche = 1
    Else
      Liste()\Affiche = 0
    EndIf
  Wend
  
  ;Maj du ListView
  ClearGadgetItems(ACS\ID_List)
  
  
  ResetList(Liste())
  
  While NextElement(Liste())
    If Liste()\Affiche = 1
      AddGadgetItem(ACS\ID_List,-1,Liste()\Text)
    EndIf
  Wend
  
  LenTextSave = GetGadgetData(ACS\ID_Edit)
  If LenTextTyped <= LenTextSave
    SetGadgetData(#String, LenTextTyped)
  Else
    ;Selection dans le ListView
    ItemCount = CountGadgetItems(ACS\ID_List)
    
    For Item = 0 To ItemCount - 1
      ItemText.s = GetGadgetItemText(ACS\ID_List,Item)
      If  UCase(TextTyped) = UCase(Left(ItemText,LenTextTyped)) 
        SetGadgetState(ACS\ID_List,Item)
        Selection_Start = LenTextTyped
        Selection_End = Len(ItemText)
        
        
        SetGadgetText(#String,ItemText)
        SendMessage_(GadgetID(ACS\ID_Edit), #EM_SETSEL, Selection_Start, Selection_End)
   
        SetGadgetData(ACS\ID_Edit, LenTextTyped)
        Break
      EndIf
    Next
  EndIf
  Flag_EnCours = 0
EndProcedure


Procedure StringProc(Hwnd.i, uMsg.i, wParam.i, lParam.i)
   Protected OriginProc.i

  OriginProc.i = GetProp_(Hwnd, "OriginProc")

  Select uMsg
    Case #WM_CHAR
      Debug wParam

      
      Case #WM_NCDESTROY
         SetWindowLong_(Hwnd, #GWL_WNDPROC, OriginProc)
         RemoveProp_(Hwnd, "OriginProc")
   EndSelect
  
   ProcedureReturn CallWindowProc_(OriginProc, Hwnd, uMsg, wParam, lParam)
EndProcedure

Procedure AC_StringGadgetProc(hWnd,uMsg,wParam,lParam)
result = #PB_ProcessPureBasicEvents
  Select uMsg
    Case #WM_COMMAND
      If (wParam >> 16 = #EN_CHANGE) And (lParam =GadgetID(ACS\ID_Edit)) 
        Debug "#EN_CHANGE"
        If Flag_EnCours = 0
          SearchInList()
        EndIf 
      EndIf   
  EndSelect
  
  ProcedureReturn result
EndProcedure



Procedure AC_StringGadget(Gadget,x,y,w,h,lh,text.s="")
  ACS\ID_Edit=Gadget
  If StringGadget(Gadget,x,y,w,h,text)
    
    ACS\ID_List=ListViewGadget(#PB_Any,x,y+GadgetHeight(Gadget),w,lh)
    If ACS\ID_List
      oldEditProc=SetWindowLong_(GadgetID(ACS\ID_Edit),#GWL_WNDPROC,@StringProc())
      SetProp_(GadgetID(ACS\ID_Edit), "OriginProc", oldEditProc)
      Debug oldEditProc
    EndIf

  EndIf
EndProcedure

Procedure Open_WinMain()
  If OpenWindow(#WinMain,0,0,300,150,"StringGadgetEx",#PB_Window_ScreenCentered|#PB_Window_SystemMenu)
    AC_StringGadget(#String,50,10,200,20,100)
    
  EndIf
EndProcedure
;}

;- Main
;{

Open_WinMain()

    AddToList("AS250M150V3")
    AddToList("AS250L250V2")
    AddToList("AS250/100V2")
    AddToList("AS250M130-16V4")
    AddToList("AS250M160")
    AddToList("AB100V2")
    AddToList("AC100")
    AddToList("AS280L240-28V6")
    AddToList("AS280L240-28V5")
    AddToList("AS280L240-28V8")
    AddToList("AB100V3")
    AddToList("AS180L170")

    UpdateListView()

SetActiveGadget(ACS\ID_Edit)
SetGadgetState(ACS\ID_List,0)

;}

;- Event Loop
;{
Repeat
  Event = WaitWindowEvent()
  
  Select Event
     Case #PB_Event_CloseWindow
      EventWindow = EventWindow()
      If EventWindow = #WinMain
        CloseWindow(#WinMain)
        Break
      EndIf
  EndSelect
ForEver
;}

Re: Pb CallBack -> Accès memoire invalide

Publié : jeu. 28/juin/2012 18:16
par wood51
MERCI NICO !!!!!! :D
Je vais regarder un petit peu plus la magie que tu as utilisé histoire de bien comprendre pour les prochaines fois.Merci aussi as tous ceux qui on essayer le code :D

Re: Pb CallBack -> Accès memoire invalide

Publié : ven. 29/juin/2012 7:24
par Mesa
Pour info, le nouveau code ne plante pas chez moi mais ne fonctionne plus, à moins de modifier la fonction ci-dessous comme cela :

Code : Tout sélectionner

Procedure AC_StringGadget(Gadget,x,y,w,h,lh,text.s="")
  ACS\ID_Edit=Gadget
  If StringGadget(Gadget,x,y,w,h,text)
   
    ACS\ID_List=ListViewGadget(#PB_Any,x,y+GadgetHeight(Gadget),w,lh)
    If ACS\ID_List
      oldEditProc=SetWindowLong_(GadgetID(ACS\ID_Edit),#GWL_WNDPROC,@StringProc())
      SetProp_(GadgetID(ACS\ID_Edit), "OriginProc", oldEditProc)
      Debug oldEditProc
      SetWindowCallback(@AC_StringGadgetProc()) ; il faut ajouter ça
    EndIf

  EndIf
EndProcedure
Mesa.

Pb CallBack -> Accès memoire invalide

Publié : ven. 29/juin/2012 11:42
par wood51
Bonjour , je m'en était aperçu mais j'ai oublier d'éditer . Merci Mesa
Je essayer de rajouter un callback pour la Listview pour gérer le double click ...
Si j'arrive à faire mon petit gadget ou faut-il que je poste le code ?

Re: Pb CallBack -> Accès memoire invalide

Publié : ven. 29/juin/2012 13:03
par Mesa
Dans la rubrique Windows, je pense, ou truc et astuces au pire.

Mesa.

Re: Pb CallBack -> Accès memoire invalide

Publié : ven. 29/juin/2012 14:50
par Backup
Mesa a écrit :Dans la rubrique Windows, je pense, ou truc et astuces au pire.

Mesa.

.. au mieux :)

Pb CallBack -> Accès memoire invalide

Publié : lun. 02/juil./2012 11:37
par wood51
Salut ,
J'ai poster le code dans truc et astuce
http://www.purebasic.fr/french/viewtopi ... 23#p143981

Merci de votre aide