Announcement

Collapse
No announcement yet.

Treeview Problem

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • Treeview Problem

    Hi all,

    I hope I don't feel like an idiot after this question.

    I am trying to learn how to use tree view control. I have code which creates the window nicely. After that I try to insert just the root item using following two procedures, but I only manage to produce GPF.

    Can somebody just by looking at this code give any hints where the problem might be? I don't like posting the original code because it is quite extensive.

    Variables not declared in these produres are globals.

    TIA
    Lasse Rantanen
    [email protected]

    Code:
    SUB TV_InitTreeView (hInst AS LONG, hWndTree AS LONG)
    
        LOCAL szText    AS ASCIIZ*%MAX_CATEGORY
    
        CALL LoadString(hInst, %IDS_NETWORK, szText, %MAX_CATEGORY)
    
        hTPrev = %TVI_ROOT
        iImage = idxNetwork
        hTParent = %NULL
        iSelect = idxNetwork
    
        hTRoot = TV_AddOneItem(BYVAL VARPTR(szText),BYVAL  hwndTree, -1)
    
        hTParent = hTRoot
        hTPrev = %TVI_FIRST
        iImage = idxNic
        iSelect = idxSelect
    
    END SUB
    
    FUNCTION TV_AddOneItem( lpszText AS ASCIIZ PTR , hwndTree AS LONG, index AS INTEGER) AS LONG
    
        LOCAL hItem AS LONG
        LOCAL tvI 	AS TV_ITEM_UNION
        LOCAL tvIns AS TV_INSERTSTRUCT
    
        tvI.item.mask = %TVIF_TEXT OR %TVIF_IMAGE OR %TVIF_SELECTEDIMAGE OR %TVIF_PARAM
        tvI.item.pszText = lpszText
        tvI.item.cchTextMax = LEN(@lpszText)
        tvI.item.iImage = iImage
        tvI.item.iSelectedImage = iSelect
        tvI.item.lParam = index
    
        tvIns.item = tvI
        tvIns.hInsertAfter = hTPrev
        tvIns.hParent = hTParent
        hItem = SendMessage(hwndTree, %TVM_INSERTITEM, 0, VARPTR(tvIns)) '<-- GPF here
    
        FUNCTION = hItem
    
    END FUNCTION

  • #2
    Lasse --

    I don't see anything that is obviously wrong. What does the TV_ITEM_UNION structure look like? Unless you're doing something unusual it would be much easier for you to get rid of it and do this...

    Code:
    FUNCTION TV_AddOneItem( lpszText AS ASCIIZ PTR , hwndTree AS LONG, index AS INTEGER) AS LONG
        LOCAL tvIns AS TV_INSERTSTRUCT
        tvIns.item.mask = %TVIF_TEXT OR %TVIF_IMAGE OR %TVIF_SELECTEDIMAGE OR %TVIF_PARAM
        tvIns.item.pszText = lpszText
        tvIns.item.cchTextMax = LEN(@lpszText)
        tvIns.item.iImage = iImage
        tvIns.item.iSelectedImage = iSelect
        tvIns.item.lParam = index
        tvIns.hInsertAfter = hTPrev
        tvIns.hParent = hTParent
        FUNCTION = SendMessage(hwndTree, %TVM_INSERTITEM, 0, VARPTR(tvIns))
    END FUNCTION
    Other than that, I'd suggest starting with an easier addition. Forget the images and lParam stuff until you can get it to add a simple text item to the tree. Less to troubleshoot. And this would be more "traditional" and (IMO) easier to troubleshoot...

    Code:
    FUNCTION TV_AddOneItem( lpszText AS [b]ASCIIZ[/b] , hwndTree AS LONG, index AS INTEGER) AS LONG
        '(etc)
        tvIns.item.pszText = VARPTR(lpszText)
        tvIns.item.cchTextMax = LEN(lpszText)
    For that matter, the .ccTextMax element is ignored when you are setting a tree item. Simplify, simplify...

    -- Eric


    ------------------
    Perfect Sync: Perfect Sync Development Tools
    Email: mailto:[email protected][email protected]</A>

    "Not my circus, not my monkeys."

    Comment


    • #3
      Thank you response Eric. Tried to do what you suggested, but I still can't make it work.

      Here are the declarations from my COMMCTRL.INC (dated Dec. 10, 1999 )

      UNION TV_ITEM_UNION
      itemex AS TVITEMEX
      item AS TV_ITEM
      END UNION

      TYPE TV_INSERTSTRUCT
      hParent AS DWORD
      hInsertAfter AS DWORD
      item AS TV_ITEM_UNION
      END TYPE

      FUNCTION TreeView_InsertItem (BYVAL hWnd AS LONG, lpis AS TV_INSERTSTRUCT) AS DWORD
      FUNCTION = SendMessage(hWnd, %TVM_INSERTITEM, 0, VARPTR(lpis))
      END FUNCTION

      If I change the declaration of TV_INSERTSTRUCT to what API docs say (member item has type TV_ITEM) the result is still the same.

      I stripped away all the irrelevant code from the program I'm working on and attached resulting code hoping somebody has time to look at it and possibly find out why it does not work. The really embarrassing thing is that the C code I'm using as an example, works OK. It must be something rather simple I'm missing here.

      TIA
      Lasse Rantanen
      [email protected]


      Code:
      ' Eliminate unnecessary macros
      %NOANIMATE = 1
      %NODRAGLIST = 1
      %NOHEADER = 1
      '%NOIMAGELIST = 1
      '%NOLISTVIEW = 1
      %NOTABCONTROL = 1
      %NOTRACKBAR = 1
      '%NOTREEVIEW = 1
      %NOUPDOWN = 1
      
      $DIM ALL
      $COMPILE EXE
      $OPTION VERSION4
      
      $INCLUDE "WIN32API.INC"
      $INCLUDE "COMMCTRL.INC"
      
      '==========================================================
      '//* Constants
      %ID_TREEVIEW        = 1003
      %MAX_CATEGORY       = 32
      
      '//* structures
      TYPE tagLISTINFO
          hInst           AS LONG
          hWndMain        AS LONG
          hWndTreeView    AS LONG
      END TYPE
      
      '//* Globals
      GLOBAL g_ListInfo   AS tagLISTINFO
      GLOBAL hTRoot AS DWORD
      GLOBAL hTPrev AS DWORD
      GLOBAL hTParent AS DWORD
      
      '//* Function prototypes
      DECLARE FUNCTION InitInstance(BYVAL hInstance AS LONG, BYVAL iCmdShow AS LONG) AS INTEGER
      DECLARE FUNCTION InitApplication(BYVAL hInstance AS LONG) AS INTEGER
      DECLARE FUNCTION CreateControls(BYVAL hWndParent AS LONG) AS INTEGER
      DECLARE FUNCTION TV_CreateTreeView ( hWndParent AS LONG, hInst AS LONG) AS LONG
      DECLARE FUNCTION TV_AddOneItem( lpszText AS ASCIIZ PTR , hwndTree AS LONG, index AS INTEGER) AS DWORD
      
      '==========================================================
      FUNCTION WINMAIN (BYVAL hInstance     AS LONG, _
                        BYVAL hPrevInstance AS LONG, _
                        lpCmdLine           AS ASCIIZ PTR, _
                        BYVAL iCmdShow      AS LONG) AS LONG
      
          LOCAL Msg   AS tagMSG
      
          InitApplication hInstance
          InitInstance hInstance, iCmdShow
          WHILE (GetMessage(Msg, %NULL, 0, 0) > 0)
              TranslateMessage Msg
              DispatchMessage Msg
          WEND
          FUNCTION = Msg.wParam
      END FUNCTION
      
      '==========================================================
      FUNCTION InitApplication(BYVAL hInstance AS LONG) AS INTEGER
      
          LOCAL wcNetwork     AS WndClassEx
          LOCAL szMenuName    AS ASCIIZ * 80
          LOCAL szClassName   AS ASCIIZ * 80
      
          szMenuName  = "NetworkMenu"
          szClassName = "NetworkWClass"
      
          wcNetwork.cbSize           = SIZEOF(wcNetwork)
          wcNetwork.style            = %CS_HREDRAW OR %CS_VREDRAW
          wcNetwork.lpfnWndProc      = CODEPTR( WndProc )
          wcNetwork.cbClsExtra       = 0
          wcNetwork.cbWndExtra       = 0
          wcNetwork.hInstance        = hInstance
          wcNetwork.hIcon            = LoadIcon(hInstance, BYVAL %NULL)
          wcNetwork.hCursor          = LoadCursor(%NULL, BYVAL %IDC_ARROW)
          wcNetwork.hbrBackground    = GetStockObject(%LTGRAY_BRUSH )
          wcNetwork.lpszMenuName     = VARPTR( szMenuName )
          wcNetwork.lpszClassName    = VARPTR( szClassName )
          wcNetwork.hIconSm          = LoadIcon( hInstance, BYVAL %NULL)
      
          FUNCTION = RegisterClassEx(wcNetwork)
      
      END FUNCTION
      
      '==========================================================
      FUNCTION InitInstance(BYVAL hInstance AS LONG, BYVAL iCmdShow AS LONG) AS INTEGER
      
          LOCAL hWnd AS LONG
      
          g_ListInfo.hInst = hInstance
          g_ListInfo.hWndMain = CreateWindow( "NetworkWClass", _
                                              "Treeview Test", _
                                              %WS_OVERLAPPEDWINDOW, _
                                              GetSystemMetrics ( %SM_CXSCREEN )/4, _
                                              GetSystemMetrics ( %SM_CYSCREEN )/4, _
                                              GetSystemMetrics ( %SM_CXSCREEN )/2, _
                                              GetSystemMetrics ( %SM_CYSCREEN )/2, _
                                              %NULL, _
                                              %NULL, _
                                              hInstance, _
                                              BYVAL %NULL)
          ShowWindow g_ListInfo.hWndMain, iCmdShow
          UpdateWindow g_ListInfo.hWndMain
          FUNCTION=%TRUE
      END FUNCTION
      
      '==========================================================
      FUNCTION WndProc (BYVAL hWnd AS LONG, BYVAL wMsg AS LONG, _
                        BYVAL wParam AS LONG, BYVAL lParam AS LONG) AS LONG
          SELECT CASE wMsg
              CASE %WM_CREATE
                  CreateControls hWnd
                  FUNCTION = %NULL
                  EXIT FUNCTION
              CASE %WM_DESTROY
                  PostQuitMessage 0
                  FUNCTION = %NULL
                  EXIT FUNCTION
          END SELECT
          FUNCTION = DefWindowProc(hWnd, wMsg, wParam, lParam)
      END FUNCTION
      
      '==========================================================
      FUNCTION CreateControls(BYVAL hWndParent AS LONG) AS INTEGER
      
          InitCommonControls
          g_ListInfo.hWndTreeview = TV_CreateTreeview(hWndParent, g_ListInfo.hInst)
          IF g_ListInfo.hWndTreeview = 0 THEN
              FUNCTION = %FALSE
              EXIT FUNCTION
          END IF
          FUNCTION = %TRUE
      END FUNCTION
      
      '==========================================================
      FUNCTION TV_CreateTreeView ( hWndParent AS LONG, hInst AS LONG) AS LONG
      
          LOCAL hwndTree      AS LONG
          LOCAL rcl           AS RECT
          LOCAL iLeft         AS INTEGER
          LOCAL iTop          AS INTEGER
          LOCAL iWidth        AS INTEGER
          LOCAL iHeight       AS INTEGER
      
          GetClientRect hWndParent, BYVAL VARPTR(rcl)
          iLeft = 0
          iTop = 0
          iWidth = (rcl.nRight - rcl.nLeft)/4
          iHeight = rcl.nBottom - rcl.nTop
          hwndTree = CreateWindowEx(  %WS_EX_CLIENTEDGE, _
                                      $WC_TREEVIEW , _
                                      "",_
                                      %WS_VISIBLE OR %WS_CHILD OR %WS_BORDER OR %TVS_HASLINES OR _
                                      %TVS_HASBUTTONS OR %TVS_LINESATROOT , _
                                      iLeft, iTop, iWidth, iHeight, _
                                      hWndParent, _
                                      %ID_TREEVIEW, _
                                      hInst, _
                                      BYVAL %NULL )
          CALL TV_InitTreeView(hInst, hwndTree)
          FUNCTION = hWndTree
      END FUNCTION
      
      '==========================================================
      SUB TV_InitTreeView (hInst AS LONG, hWndTree AS LONG)
      
          LOCAL szText    AS ASCIIZ*%MAX_CATEGORY
      
          szText = "Root Item"
          hTPrev = %TVI_ROOT
          hTParent = %NULL
          hTRoot = TV_AddOneItem(BYVAL VARPTR(szText),BYVAL  hwndTree, -1)
          hTParent = hTRoot
          hTPrev = %TVI_FIRST
      END SUB
      
      '==========================================================
      FUNCTION TV_AddOneItem( lpszText AS ASCIIZ PTR , hwndTree AS LONG, index AS INTEGER) AS DWORD
      
          LOCAL hItem AS DWORD
          LOCAL tvI AS TV_ITEM_UNION
          LOCAL tvIns AS TV_INSERTSTRUCT
      
          tvIns.item.mask = %TVIF_TEXT OR %TVIF_IMAGE OR %TVIF_SELECTEDIMAGE OR %TVIF_PARAM
          tvIns.item.pszText = lpszText
          tvIns.item = tvI
          tvIns.hInsertAfter = hTPrev
          tvIns.hParent = hTParent
          ' Following statement GPF's
          hItem = SendMessage(hwndTree, %TVM_INSERTITEM, 0, VARPTR(tvIns))
          FUNCTION = hItem
      END FUNCTION

      Comment


      • #4
        Oh boy, I knew it was something simple.

        The problem was function declaration

        FUNCTION TV_AddOneItem( lpszText AS ASCIIZ PTR , hwndTree AS LONG, index AS INTEGER) AS DWORD

        After changing it to

        FUNCTION TV_AddOneItem( lpszText AS ASCIIZ PTR , BYVAL hwndTree AS LONG, index AS INTEGER) AS DWORD

        everything works.

        I don't know why these little stupid things keep haunting me.

        Lasse Rantanen
        [email protected]

        Comment


        • #5
          Lasse --

          > I don't know why these little stupid things keep haunting me.

          Don't feel bad, that's a hard one to find, once you've typed it wrong. I've done it many times myself.

          Maybe we should add something like this...

          Code:
          #PARAMETERS BYVAL
          ...to the PB/DLL wish list, to specify the default numeric-parameter-passing method. BYVAL is the most efficient method, so it would be nice to have a way to specify it globally.

          -- Eric


          ------------------
          Perfect Sync: Perfect Sync Development Tools
          Email: mailto:[email protected][email protected]</A>



          [This message has been edited by Eric Pearson (edited February 18, 2000).]
          "Not my circus, not my monkeys."

          Comment

          Working...
          X