Author Topic: Programming Windows: a major example  (Read 3352 times)

0 Members and 1 Guest are viewing this topic.

Arnold

  • Guest
Programming Windows: a major example
« on: April 06, 2016, 08:04:27 AM »
Hi Charles,

this is the code of a Keyboard MIDI player of "Programming Windows" chapter 22. The original code can be found at the Homepage of Charles Petzold:
ftp://ftp.charlespetzold.com/ProgWin5/Chap22/KBMidi/

The code is still useable and can be run on modern computers. For me it provides proof that it is possible to create many applications in OxygenBasic with minimal workarounds. I was able to produce executables with RTL32.inc and RTL64.inc.

The app offers two options: Horizontal Scroll changes the velocity. Pressing a key and moving Vertical Scrollbar will change the Pitch Bend. I have no suitable compiler for the C code, but I think running the o2bas file will give the same results as kbmidi.exe in the folder Release.

Although I think this program runs fine I wonder if there is perhaps a trick to shorten e.g. the for next loop in about line 440 - 465. I cannot use the variable iIns for
fam[iFam].inst[iIns].szInst.
Could I apply a pointer to iIns instead or an offset added to fam[iFam]?

Roland

Code: OxygenBasic
  1. ''          for iIns = 0 to 7          
  2.        szBuffer= 1 "." tab fam[iFam].inst[0].szInst                
  3.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[0].iVoice, MF_UNCHECKED, MF_CHECKED),
  4.                     fam[iFam].inst[0].iVoice + IDM_VOICE, szBuffer)
  5.         szBuffer= 2 "." tab fam[iFam].inst[1].szInst
  6.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[1].iVoice, MF_UNCHECKED, MF_CHECKED),
  7.                     fam[iFam].inst[1].iVoice + IDM_VOICE, szBuffer)
  8.         szBuffer= 3 "." tab fam[iFam].inst[2].szInst
  9.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[2].iVoice, MF_UNCHECKED, MF_CHECKED),
  10.                     fam[iFam].inst[2].iVoice + IDM_VOICE, szBuffer)
  11.         szBuffer= 4 "." tab fam[iFam].inst[3].szInst
  12.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[3].iVoice, MF_UNCHECKED, MF_CHECKED),
  13.                     fam[iFam].inst[3].iVoice + IDM_VOICE, szBuffer)
  14.         szBuffer= 5 "." tab fam[iFam].inst[4].szInst
  15.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[4].iVoice, MF_UNCHECKED, MF_CHECKED),
  16.                     fam[iFam].inst[4].iVoice + IDM_VOICE, szBuffer)
  17.         szBuffer= 6 "." tab fam[iFam].inst[5].szInst
  18.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[5].iVoice, MF_UNCHECKED, MF_CHECKED),
  19.                     fam[iFam].inst[5].iVoice + IDM_VOICE, szBuffer)
  20.         szBuffer= 7 "." tab fam[iFam].inst[6].szInst
  21.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[6].iVoice, MF_UNCHECKED, MF_CHECKED),
  22.                     fam[iFam].inst[6].iVoice + IDM_VOICE, szBuffer)
  23.         szBuffer= 8 "." tab fam[iFam].inst[7].szInst
  24.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[7].iVoice, MF_UNCHECKED, MF_CHECKED),
  25.                     fam[iFam].inst[7].iVoice + IDM_VOICE, szBuffer)
  26. ''          next
  27.  

.

jack

  • Guest
Re: Programming Windows: a major example
« Reply #1 on: April 07, 2016, 03:39:54 AM »
hi Arnold
nice example :)

Charles Pegge

  • Guest
Re: Programming Windows: a major example
« Reply #2 on: April 08, 2016, 01:08:17 AM »
Hi Roland,

Excellent example!

We must include it in the package.

O2 did not cope very well with the double indexing. I suggest the following. (the pointer resolution is a little more efficient anyway):

family * famt = &fam[ifam]

Code: OxygenBasic
  1.      for iFam = 0 to 15
  2.         hMenuSubPopup = CreateMenu ()
  3.         family * famt = &fam[ifam]
  4.         for iIns = 0 to 7
  5.           szBuffer= str(iIns+1) "." tab famt.inst[iIns].szInst
  6.        
  7.           AppendMenu (hMenuSubPopup, MF_STRING | iif(famt.inst[iIns].iVoice, MF_UNCHECKED, MF_CHECKED),
  8.                     famt.inst[iIns].iVoice + IDM_VOICE, szBuffer)
  9.         next
  10.         szBuffer=chr(iFam+65) "."  tab fam[iFam].szFam
  11.         AppendMenu (hMenuPopup, MF_STRING | MF_POPUP,  hMenuSubPopup, szBuffer)
  12.      next
  13.  
  14.  
  15.  
  16.  
  17.         /*          
  18.         szBuffer= 1 "." tab fam[iFam].inst[0].szInst                
  19.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[0].iVoice, MF_UNCHECKED, MF_CHECKED),
  20.                     fam[iFam].inst[0].iVoice + IDM_VOICE, szBuffer)
  21.         szBuffer= 2 "." tab fam[iFam].inst[1].szInst
  22.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[1].iVoice, MF_UNCHECKED, MF_CHECKED),
  23.                     fam[iFam].inst[1].iVoice + IDM_VOICE, szBuffer)
  24.         szBuffer= 3 "." tab fam[iFam].inst[2].szInst
  25.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[2].iVoice, MF_UNCHECKED, MF_CHECKED),
  26.                     fam[iFam].inst[2].iVoice + IDM_VOICE, szBuffer)
  27.         szBuffer= 4 "." tab fam[iFam].inst[3].szInst
  28.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[3].iVoice, MF_UNCHECKED, MF_CHECKED),
  29.                     fam[iFam].inst[3].iVoice + IDM_VOICE, szBuffer)
  30.         szBuffer= 5 "." tab fam[iFam].inst[4].szInst
  31.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[4].iVoice, MF_UNCHECKED, MF_CHECKED),
  32.                     fam[iFam].inst[4].iVoice + IDM_VOICE, szBuffer)
  33.         szBuffer= 6 "." tab fam[iFam].inst[5].szInst
  34.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[5].iVoice, MF_UNCHECKED, MF_CHECKED),
  35.                     fam[iFam].inst[5].iVoice + IDM_VOICE, szBuffer)
  36.         szBuffer= 7 "." tab fam[iFam].inst[6].szInst
  37.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[6].iVoice, MF_UNCHECKED, MF_CHECKED),
  38.                     fam[iFam].inst[6].iVoice + IDM_VOICE, szBuffer)
  39.         szBuffer= 8 "." tab fam[iFam].inst[7].szInst
  40.         AppendMenu (hMenuSubPopup, MF_STRING | iif(fam[iFam].inst[7].iVoice, MF_UNCHECKED, MF_CHECKED),
  41.                     fam[iFam].inst[7].iVoice + IDM_VOICE, szBuffer)
  42.       */
  43.  
« Last Edit: April 08, 2016, 01:19:00 AM by Charles Pegge »

Arnold

  • Guest
Re: Programming Windows: a major example
« Reply #3 on: April 08, 2016, 08:24:39 AM »
Charles,

this is really splendid. I knew there must be a way but I could not find it - shame on me. This approach will be helpful in many other situations too. I only wish I had the skill of you or Mike and the other members of the list.

I modified the corresponding lines in sub CreateTheMenu and function WndProc/WM_PAINT. This reduced the size of the .o2bas file and also the size of the executable.

Roland


.

Charles Pegge

  • Guest
Re: Programming Windows: a major example
« Reply #4 on: April 09, 2016, 12:55:17 AM »

Roland,

I fixed the double indexing problem:

Oxygen DLL Update (200k)  8 April 2016
http://www.oxygenbasic.org/o2zips/Oxygen.zip

Peter

  • Guest
Re: Programming Windows: a major example
« Reply #5 on: April 09, 2016, 03:23:19 AM »
Thank you very much, Charles

A test:
Code: [Select]
include "gdip.inc"
window 640,480,1
hdc = GetBufferDC()

%UnitPixel = 2
%UnitPoint = 3   

Type RectF
   single x
   single y
   single w
   single h
End Type

Extern Lib "gdiplus.dll"
! GdipCreateFontFamilyFromName
! GdipDeleteFontFamily
! GdipCreateSolidFill
! GdipDrawString
! GdipCreateFont
! GdipDeleteFont
! GdipDeleteBrush
End Extern

wstring font

Sub SetFontEx(wstring fontname)
    font = fontname
end sub   

Sub DrawString(single x, y, height, wstring txt)
    RECTF fRect = {x, y, ScrW, ScrH}
    sys pFont, pFontFamily, pBrush
    GdipCreateFontFamilyFromName font, NULL, &pFontFamily
    GdipCreateFont pFontFamily, height, FontStyleRegular, UnitPoint, &pFont
    GdipCreateSolidFill 0xFFFFFFFF, &pBrush
    GdipDrawString hdc, txt, Len(txt), pFont, fRect, NULL, pBrush
    GdipDeleteFont  pFont
    GdipDeleteBrush pBrush
    GdipDeleteFontFamily pFontFamily
End Sub

SetFontEx "david"
DrawString 100,100,24,"Hi Charles,"
SetFontEx "georgia"
DrawString 100,124,24,"great, it works!"
SetFontEx "gisha"
DrawString 100,158,24,"Now, I am looking for another bugs."
SetFontEx "arial"
DrawString 100,186,22,"Anyway, many thanks for your effort."
setfontEx "wingdings"
DrawString 100,260,34,"JJJJJJJJJJJ"

for i=0 to 640 step 40
    DrawString i,0x0,24,"q"
    DrawString i,430,24,"m"
next

waitkey
winEnd

 

.
« Last Edit: April 12, 2016, 06:18:29 AM by Peter »