• Welcome to Jose's Read Only Forum 2023.
 

Zstring in O2 - need some clarifications

Started by Chris Chancellor, December 10, 2018, 06:39:27 PM

Previous topic - Next topic

0 Members and 1 Guest are viewing this topic.

Chris Chancellor

Hello Charles

when i was doing the combobox control program, i notice that O2 uses zstring   (which i think is a legacy from  C style coding)

the question is that why we cannot use wstring or string but we must stick to zstring ?

i have tried string and it didn't work out for the combobox but it works for the Listbox control.

Charles Pegge

#1
Hi Chris,

Could you try initialising the array of strings in global space first, and see whether this works in ComboBox


   int i
   dim string ArrayCB(20) : for i=1 to 20 : ArrayCB(i)="" : next


Fixed.

Chris Chancellor

Hello Charles

i tried using your method but gotten a parameters mismatch error during compilation
please see the attachment


' Od_Combbox.o2bas
' Owner drawn Combobox

$ filename "Od_Combbox.exe"
use rtl64
#lookahead

' %review

uses O2Common
uses dialogs






' identifiers
%  IDC_Combobox = 101

'  The program logo icon  is obtained from the resource file
'  the 400 must corespondence to the 400 in the rc file
   %  IDI_LOGO     400


sys  hDlg   , hCombobox





'  Will need this Array dimensioning macro
'  otherwise results would be garbage
'  Dim_zstring  ArrayCB , 20, 30
string ArrayCB(20)

'=======================
FUNCTION  O2Main
 
Dialog( 150, 70, 160,  75, "Ownerdrawn ComboBox ",  WS_CAPTION OR   WS_SYSMENU )
   
 
  ' Add in the combo box
    sys CBBStyle =   WS_CHILD or WS_VSCROLL  or  WS_TABSTOP OR  CBS_DROPDOWNLIST  OR  _
                          CBS_HASSTRINGS  or CBS_OWNERDRAWFIXED
   COMBOBOX( "" ,IDC_Combobox, 10, 10, 60, 50, CBBStyle, WS_EX_CLIENTEDGE  or WS_EX_ACCEPTFILES , 0 )


   sys  ebStyle = WS_CHILDWINDOW or WS_VISIBLE    or  BS_DEFPUSHBUTTON   or WS_DLGFRAME
     CONTROL "Exit", IDCANCEL,"Button", ebStyle , 85, 35, 30, 14


    hDlg = CreateModalDialog( 0, @DlgProc, 0 )

END FUNCTION



'============================
'   Main callback function
    Function DlgProc( hDlg, uint uMsg, sys wParam, lParam ) as sys callback

     zstring  SelString , wAnswer 
     Long jj , CBIndex     
   

    hCombobox = GetDlgItem(hDlg,  IDC_Combobox)



SELECT CASE  uMsg

CASE   WM_INITDIALOG
       '     display the program icon
            sys  hInstance = GetModuleHandle(NULL)
             sys hIcon = LoadIcon(hInstance, IDI_Logo)
            'Set Icon to Main Window
             SendMessage(hDlg, WM_SETICON, ICON_BIG, hIcon)

  '        Setup the combobox elements
       '    BuildArrayCB
            '  Initialise the ArrayCB
              sys i
              for i=1 to 20 : ArrayCB(i) ="" : next i
                BuildArrayCBst

           For jj = 1 to  20
                '   SendMessage(hCombobox, CB_ADDSTRING, 0, ArrayCB[jj] )
                   SendMessage(hCombobox, CB_ADDSTRING, 0, ArrayCB(jj) )
           Next jj
           '  set cursor to the first element of the combobox
            SendMessage(hCombobox,  CB_SETCURSEL, 0, 0)
       

     CASE WM_ERASEBKGND   
'            added to display background color for the main window
            '  for a Light Yellow background
               MainWindBGColor = 6
               hBGDC = wParam
  '          Pass the DC of the region to be repaint
             DrawGradient hBGDC           
             FUNCTION = 1
             EXIT FUNCTION


CASE  WM_COMMAND
          SELECT CASE LOword(wParam)
            CASE   IDCANCEL
                       EndDialog( hDlg, null )

       CASE  IDC_Combobox
         IF HIWORD(WPARAM) = CBN_SELENDOK THEN
            ' user selected something
              CBindex = SendMessage(hComboBox, CB_GETCURSEL, 0, 0)
              SendMessage(hComboBox, CB_GETLBTEXT, CBindex, @SelString)
             wAnswer = TRIM(SelString)
             Mbox   " Selected : " + wAnswer , 0
         END IF
     END SELECT               


   CASE  WM_DRAWITEM
      '    for owner drawn combo box
           IF  LOword(wParam) =  IDC_Combobox THEN
                    OwnerDrwCombo hCombobox, WPARAM, LPARAM
             END IF

END SELECT

END FUNCTION


'===================================
' Owner drawn procedure for the combo box
FUNCTION   OwnerDrwCombo(sys BYVAL hWnd ,  sys BYVAL wParam , sys BYVAL lParam ) AS LONG
         Zstring  zTxt
          RECT  rct
         DRAWITEMSTRUCT lpdis at lParam

  IF   lpdis.itemID = &HFFFFFFFF& THEN
      'When it is an empty list -- just exit
      EXIT FUNCTION
  END IF

  SELECT CASE  lpdis.itemAction
     CASE  ODA_DRAWENTIRE,  ODA_SELECT
   
        'CLEAR BACKGROUND
        IF ( lpdis.itemState AND  ODS_SELECTED) = 0 OR _     
              ( lpdis.itemState AND  ODS_COMBOBOXEDIT) THEN 
              'When not selected
              'text background
              SetBkColor  lpdis.hDC,   O2c_AZURE
              'text color
              SetTextColor  lpdis.hDC, GetSysColor( COLOR_WINDOWTEXT)
             'clear background
              FillRect  lpdis.hDC,  lpdis.rcItem,GetSysColorBrush( COLOR_WINDOW)
        ELSE
          '  When the item is selected
              ' set the text background
               SetBkColor  lpdis.hDC,   O2c_Light_Yellow         
              'set the text color
               SetTextColor  lpdis.hDC,  O2c_MAGENTA
         END IF

        'Get the item text
        SendMessage hWnd,  CB_GETLBTEXT,  lpdis.itemID, VARPTR(zTxt)
        DrawText  lpdis.hDC, zTxt, LEN(zTxt),  lpdis.rcItem, _
                  DT_SINGLELINE OR  DT_LEFT OR  DT_VCENTER

   
   '   Focus rectangle and bullet must be drawn after the text
'    otherwise these will overlap by the text
      IF ( lpdis.itemState AND  ODS_SELECTED) THEN
        '        when selected , set cordinates of bullet
               ' Draw the bullet pointer at the right end
              '  Note that you need to adjust these parameters to suit the
             '  size of  each combobox and do some tests to fine tune
               rct.Left   =  +106
               rct.Right =   lpdis.rcItem.Right + 25
               rct.top    =   lpdis.rcItem.top +6
               rct.bottom =   lpdis.rcItem.bottom - 6
                'Draw a round focus rectangle -- make it look like a bullet
                RoundRect(  lpdis.hDC, rct.Left, rct.top, rct.Right, rct.bottom, 48, 48)
                'draw a focus rectangle around all
               CALL DrawFocusRect( lpdis.hDC,  lpdis.rcItem)
        END IF
        FUNCTION =  TRUE

  END SELECT

END FUNCTION   





'====================================
Sub BuildArrayCB
        ' Setup the Combobox elements
       '   using ArrayCB
            ArrayCB[1] = "One"
            ArrayCB[2] = "Two"
            ArrayCB[3] = "Three"
            ArrayCB[4] = "Four"
           ArrayCB[5] = "Five"
            ArrayCB[6] = "Six"
            ArrayCB[7] = "Seven"
            ArrayCB[8] = "Eight"
            ArrayCB[9] = "Nine"
            ArrayCB[10] = "Ten"

            ArrayCB[11] = "Eleven"
            ArrayCB[12] = "Twelve"
            ArrayCB[13] = "Thirteen"
            ArrayCB[14] = "Fourteen"
            ArrayCB[15] = "Fifteen"
            ArrayCB[16] = "Sixteen"
            ArrayCB[17] = "Seventeen"
            ArrayCB[18] = "Eighteen"
             ArrayCB[19] = "Nineteen"
              ArrayCB[20] = "Twenty"
End Sub


Sub BuildArrayCBst
        ' Setup the Combobox elements
       '   using ArrayCB
            ArrayCB(1) = "One"
            ArrayCB(2) = "Two"
            ArrayCB(3) = "Three"
            ArrayCB(4) = "Four"
           ArrayCB(5) = "Five"
            ArrayCB(6) = "Six"
            ArrayCB(7) = "Seven"
            ArrayCB(8) = "Eight"
            ArrayCB(9) = "Nine"
            ArrayCB(10) = "Ten"

            ArrayCB(11) = "Eleven"
            ArrayCB(12) = "Twelve"
            ArrayCB(13) = "Thirteen"
            ArrayCB(14) = "Fourteen"
            ArrayCB(15) = "Fifteen"
            ArrayCB(16) = "Sixteen"
            ArrayCB(17) = "Seventeen"
            ArrayCB(18) = "Eighteen"
             ArrayCB(19) = "Nineteen"
              ArrayCB(20) = "Twenty"
End Sub


'----------------------------------
'  Program starts
init_common_controls()
O2Main








Chris Chancellor

Hello Charles

in what situation do we use zstring ? 

what is the difference between zstring and the normal string ?

Charles Pegge

#4
Sorry. You will need the square brackets because I used a C-style declaration.


int i
   string ArrayCB[ 20 ] : for i=1 to 20 : ArrayCB( i )="" : next


zstring is the same as char. Still useful for making char buffers for windows stuff.

Chris Chancellor

Thanxx Charles,

Now it works

i'm  confused by the square and round brackets as use in O2 arrays.

in PB, we only use the round brackets for arrays.

Can you please elaborate when and where to use the square brackets  for arrays with an example ?

Thanxx

Charles Pegge

#6
You can use either square or round brackets for arrays. The only time it matters is when dimensioning an array c-style.

When the compiler sees:

int a(...)

it assumes it is a function declaration rather than an array.

Chris Chancellor

#7
Thanxx a lot Charles

Do you mean that when we do dimensioning or type assignment ,
we must use square brackets
for example


String  ArrayCB[300]
  Int  myAry[450]



  whilst  normal  working conditions for array
  we use round brackets  for example


For i = 1 to 45
       myAry(i) = i + 233
   Next i


are these principles correct ?




Charles Pegge

Yes, Chris.

If you prefer to dimension with round brackets, use dim


dim String  ArrayCB(300)
dim Int  myAry(450)