Recent posts

#1
OxygenBasic Examples / Re: Slider Box changes triangl...
Last post by Charles Pegge - December 04, 2023, 11:57:19 PM
Hi Frank,

The logistics are too complex when you can already drag the nodes to change the shape of the triangle. Perhaps at a later stage we can do this with a bounding box and resizer.

I have added a grid and made the information panel mobile. All the components of the scene are arranged in micro-layers so they do not conflict.

'-------- experiment to combine triangle data with slider overlapped
  '-------- oxygenbasic, by frank brübach, 27-11-2023
  '
  '17:29 04/12/2023 CP
  #compact
 '%filename "t.exe"
 'uses RTL64
  % Title "Triangle Data:  Move points with mouse and arrow keys etc"

 '% WindowStyle WS_OVERLAPPEDWINDOW
 '% Animated
 '% ScaleUp
  % PlaceCentral
  % AnchorCentral

  '% shaders

  uses consoleG
 'uses glo2/geoplanar
  'uses ControlPanels


  uses controls
  ===================
  class ControlPanelA
  ===================
  float  x,y,z
  int    id
  float  xx,yy,zz
  float  dx,dy,dz
  float  sc
  int    lock
  int    t1,t2
  int    f1,f2
  string lbl
  ===================
  sliders      c[4]
  lightbuttons l[4]
  ===================

  method act(optional int n)
  indexbase 1
  if id=0
    f1=0 'cube
    f2=0 'pent
    ==========================================================================
    'ctrl   x    y   z     sc    shm shb tex id  lk  lbl
    --------------------------------------------------------------------------
    c[1]=>-.40,-.00, .00,  0.10, f1, 00, t1, 10, 1, "slider"
    c[2]=>-.30,-.00, .00 , 0.10, f2, 00, t1, 20, 1, "slider"
    c[3]=>-.20,-.00, .00 , 0.10, f2, 00, t1, 30, 1, "slider"
    c[4]=>-.10,-.00, .00 , 0.10, f2, 00, t1, 40, 1, "slider"
    -------------------------------------------------------------------------
    l[1]=>-.40, .15, .00,  0.02, f1, 00, t1, 50, 1, "light button"
    l[2]=>-.30, .15, .00 , 0.02, f2, 00, t1, 60, 1, "light button"
    l[3]=>-.20, .15, .00 , 0.02, f2, 00, t1, 70, 1, "light button"
    l[4]=>-.10, .15, .00 , 0.02, f2, 00, t1, 80, 1, "light button"
    ==========================================================================
    id=1+n
    int i
    for i=1 to 4
      c[i].id+=n
      l[i].id+=n
    next
  end if
  '
  glpushmatrix
  gltranslatef  x,y,z
  '
  gltranslatef -.25,.0,-.0005
  if sc then glscalef sc,sc,1.0
  if pick
    PickLabel id
  else
    QuadShadow .20,.20,.005,.5
    glcolor3f     .60,.50,.60 'fix alpha bug
    glcolor4f     .60,.50,.60,0.50 'box
  endif
  QuadTex       .20,.20,.0.01
  gltranslatef  .25,.0,-.0
  '
  'DISPLAY LABELS
  if lbl
    glpushmatrix
    gltranslatef -.43,-.13,.0005
    glcolor4f .9,.9,.4,.9
    float j=0.015
    'DISPLAY EACH SLIDER VALUE
    for i=1 to 4
      glpushmatrix
      gltranslatef j,0,0
      glscalef  .035,.035,.035
      if pick
        gltranslatef -.1,-.18,.0
        picklabel id+i
        PutBoxArea 2,1
        gltranslatef .1,.18,.0
      else
        if picked=id+i 'edit
          ------------
          'DATA EDITING
          color 0.9,0.9,0.9
          'box-around
          gltranslatef -.1,-.18,.0
          glBegin GL_LINE_STRIP
          glVertex2f 0,0
          glVertex2f 2,0
          glVertex2f 2,1
          glVertex2f 0,1
          glVertex2f 0,0
          glEnd
          gltranslatef .1,.18,.0
          '
          static string ss
          ss= str(50+c[i].vy*50,0) '0..100
          input ss
          c[i].vy=(val(ss)-50) *0.02
          '
          static int cpick,cy,cx
          if cpick<>picked
            cp=le+1 'place cursor at end of string
            cy=y
            cx=x
            cpick=picked
          endif
          '
          select lastkey
          case VK_UP
            c[i].vy+=0.01
          case VK_DOWN
            c[i].vy-=0.01
          case VK_PRIOR 'PGUP
            c[i].vy+=0.01
          case VK_NEXT 'PGDN
            c[i].vy-=0.01
          case 9 'tab
            if GetAsyncKeyState(VK_SHIFT)=0
              picked++
              if picked>id+4
                picked=id+4
              end if
            else 'left
              picked--
              if picked<id+1
                picked=id+1
              endif
            endif
          end select
          lastkey=0
          lastchar=0
        else 'display
          gprint str(50+c[i].vy*50,0) '0..100
          'gprint str((c[i].vy)*100 , 0) -100..100
        endif
      endif
      glpopmatrix
      j+=0.1
    next
    'DISPLAY MAIN PANEL LABEL
    gltranslatef 0,-.05,0
    glscalef  .04,.04,.04
    glcolor4f .9,.9,.0,.9
    gprint lbl
    glpopmatrix
  endif
  '
  '
  if bleft
    if picked=id
      if not lock
        drag(dx,dy,1.0/sc)
        x=xx+dx : y=yy+dy
      end if
    end if
  else
    xx=x : yy=y : zz=z 'ANCHOR
  end if
  '
  'render
  '
  int i,oi1,oi2
  for i=1 to 4
    c[i].act(1,i,oi1)
    l[i].act(1,i,oi2)
  next
  glpopmatrix
  '
  'show data
  '
  'glDisable GL_TEXTURE_2D
  glDisable GL_LIGHTING
  '
  glPushMatrix
  glLoadIdentity
  if pick
    PickLabel 0
  endif
  gltranslatef -.5,.35,-1.0
  float w,h
  glscalef     .05,.05,.01
  GetWordArea  "Control:",w,h
  if pick
    PutBoxArea   w,h
  else
    /*
    glColor3f    .99,.99,.00
    gprint       "Control: "
    glColor3f    .99,.99,.99
    gprint    str(picked)
    if oi1+oi2
      gprint "   "
      if oi1 then gprint str((1.0+c[oi1].vy)*50 , 0)
      if oi2 then gprint str (l[oi2].lit)
    end if
    */
  end if
  glPopMatrix
  end method
  '
  method destructor()
  ===================
  'del this.label
  'sliders      c[4]
  'lightbuttons l[4]
  int i
  for i=1 to 4
    c[i].destructor
  next
  for i=1 to 4
    l[i].destructor
  next
  end method
  '
  end class

  '#recordof ControlPanelA



  'Keys: Esc, arrow-keys, n,m, F4

  indexbase 1
  sys       texn[16]
  sys       GdiplusToken
  float     ang1
  sys       cube,pent



  BeginScript

  procedure main() 'triangle-data example
  ================

  static single ra,ri,angi1=.5
  static sys    initscene
  static float rr=.5,gg=.5,bb=.5,aa=.8 'object color
  '
  '
'--------------------------------------------------- //
  'WaitForEvent '0 off 1 on (default on)
  static quad t1,t2

  if opening 'FIRST CALL ONLY
    timemark t1
    'picked=100
    'mbox "helo"
  end if
  '
  if closing 'FINAL CALL BEFORE SHUTDOWN
    'mbox "Bye!"
    exit sub
  end if
  '
  cls
  '
  'LAYERS
  =======
  'background    'z=-inf
  'grid          'z=-2.002
  'object        'z=-2
  'info panel    'z=-1.01
  'tool panels   'z=-1 +.001 each layer
  'tool controls '+ .0001 each layer


  'IDENTITIES
  ===========
  '.id
  'control panels
  '100..199
  'controls
  '111 slider1
  '121 slider2
  '131 slider3
  '141 slider4
  '151 light button1
  '161 light button2
  '171 light button3
  '181 light button4
  '200..299 unused
  '300..399 unused
  'data area---------
  'md       400
  'colored area------
  'mpol     900..999
  'polygon nodes-----
  'mu[1]   2100..2199
  'mu[2]   2200..2299
  'mu[3]   2300..2399



  'BACKGROUND GRID
  ================
  if not pick
    pushstate
    color .2,.4,.6,1.0
    thickness 1
    move -50,-30, -2.002
    grid 1,100,60
    popstate
  endif



  subroutine ShowPolygon
  ======================
  '
  pushstate 'polygon
  pushstate 'mpol
  static moveableobject mpol
  mpol.id=900
  mpol.mode=1
  mpol.act
  float zp=-0.001
  '
  'move 0,0,-1
  shading
  UserMovement mu,2100,3 'symbol identity, count
  if opening
    mu[1].x= 0
    mu[1].y= 5
    mu[2].x=-5
    mu[2].y=-5
    mu[3].x= 5
    mu[3].y=-5
  endif
  scale 1
  picklabel 0
  int i
  for i=1 to 3
    pushstate
    mu[i].act
    color 1,.9,0,1
    scale 0.4
    go sphere
    popstate
  next
  '
  picklabel 0
  '
  float xa,xb,xc,ya,yb,yc
  xa=mu[1].x : ya=mu[1].y
  xb=mu[2].x : yb=mu[2].y
  xc=mu[3].x : yc=mu[3].y
  '
  'MOUSE DRAG ADJUSTMENT
  select picked
    'mu.id ...
    case 2100 : xa+=mu[1].d.x : ya+=mu[1].d.y
    case 2200 : xb+=mu[2].d.x : yb+=mu[2].d.y
    case 2300 : xc+=mu[3].d.x : yc+=mu[3].d.y
  end select
  flat
  thickness 2
  '
  color 1,1,0,1
  '
  pushstate
  move xa-.5,ya-1
  gprint "A"
  popstate
  '
  pushstate
  move xb+1,yb+1
  gprint "B"
  popstate
  '
  pushstate
  move xc-1,yc+1
  gprint "C"
  popstate
  '
  color rr,gg,bb,aa 'linked to slider panel 1
  picklabel mpol.id
  float zp=-0.001
  glBegin GL_TRIANGLES
  glVertex3f xa,ya,zp
  glVertex3f xb,yb,zp
  glVertex3f xc,yc,zp
  glEnd
  picklabel 0
  '
  color 0,.9,.9
  glBegin GL_LINES
  glVertex2f xa,ya
  glVertex2f xb,yb
  glVertex2f xb,yb
  glVertex2f xc,yc
  glVertex2f xc,yc
  glVertex2f xa,ya
  glEnd

  popstate 'mpol

  move 5

    move -20,12
    static sys tally
    timemark t2
    scale 1.0
    '
    int dp=3
    '
    '
    pushstate 'md
    move 0,0,0.99
    color .5,.5,.7,.7
    static moveableobject md
    md.id=400
    md.mode=1
    md.act
    float zp=-0.001
    glBegin GL_QUADS
      glVertex3f -.1,-17,zp
      glVertex3f 11,-17,zp
      glVertex3f 11,2,zp
      glVertex3f -.10,2,zp
    glEnd
    if pick
      goto nDataPanel
    endif
    '
    macro pr1(a) 'PRINTING LIST
    -----------------------------
      pushstate : color .5,1,1 : print a : popstate
      printl ""
    end macro
    '
    macro pr2(a,b) 'PRINTING LIST
    -----------------------------
      pushstate : color .5,1,1 : print a : popstate
      pushstate : color 1,1,.5 : move 4 : print str(b,dp) : popstate
      printl ""
    end macro
    '
    macro pr3(a,b,c) 'PRINTING LIST
    ------------------------------
      pushstate : color .5,1,1 : print a : popstate
      pushstate : color 1,1,.5 : move 4 : print str(b,dp) : popstate
      pushstate : color 1,1,.5 : move 8 : print str(c,dp) : popstate
      printl ""
    end macro
    '
    '
    'DISPLAY INFO
    -------------
    picklabel 0

    pushstate
    scale 2
    color 1,1,1
    print "Triangle Data"
    popstate
    pr1 ""
    pr1 ""
   'pr2 "Action Code:   ", act
   'pr2 "indexbase      ", indexbase
   'pr2 "Keyboard Code: ", keyd
    pr2 "Picked ID:     ", picked
    '
    pr3 "Point A: ", str(xa,3), ya
    pr3 "Point B: ", str(xb,3), yb
    pr3 "Point C: ", str(xc,3), yc
    '
    float ab,ac,bc,ar,ht,hb
    '
    ab=hypot(xa-xb, ya-yb)
    ac=hypot(xa-xc, ya-yc)
    bc=hypot(xb-xc, yb-yc)
    '
    hb=0.5* ( ab*ab - ac*ac + bc*bc ) / bc
    ht=sqr(ab*ab-hb*hb)
    ar=0.5*bc*ht

    'ANGLES
    float na,nb,nc
    nb=deg(asin(ht/ab))
    nc=deg(asin(ht/ac))
    na=180-nb-nc

    pr1 ""
    pr2 "Angle A:",na
    pr2 "Angle B:",nb
    pr2 "Angle C:",nc
   
    pr1 ""
    pr2 "Line AB:",ab
    pr2 "Line AC:",ac
    pr2 "Line BC:",bc
    pr2 "Left base:",hb
    pr2 "Height:",ht
    pr2 "Area:", ar
    pr1 ""
    '
    nDataPanel:
    ===========
    popstate 'md
    picklabel 0
    '
    'end polygon display
    '--------------------
    '
    popstate 'polygon
  end subroutine

  'PANEL DISPLAY
  ==============

  static single ra,ri,angi1=.5
  static sys    initscene
 
  '------------------------------
 'glClearColor 0.5, 0.5, 0.7, 0
 'glClearColor 0.1, 0.2, 0.1, 0
  '
  glColor4f .99,.99,.99,.99
  'glEnable GL_TEXTURE_2D
  '
  'RENDERED LOWEST FIRST (FOR TRANSPARENCY BLENDING)
  '
  %                    ordn=1
  static ControlPanelA cb[ordn]
  static int           ord[16]
  static int           idb[16]
  '
  if closing
    int i
    for i=1 to ordn
      cb[i].destructor
    next
    exit sub
  endif
 
  '
  'INITIAL PLACEMENT ETC
  '
  if initscene=0
    ord={1,2,3}
    idb={100,200,300} 'panel identities
    cb[1].x=.8 : cb[1].y=.6 : cb[1].lbl="Color"
    int i
    'set scale
    for i=1 to ordn : cb[i].sc=2.5 : next
    initscene=1
  end if
  '
  'ORDER OF BUILD (SUPPORTING TRANSPARENCY)
  '
  if picked and bleft
    int a=1+trunc(picked/100)
    PlaceTop(a,ord,ordn)
  end if
  '
  'RENDER SCENE
  '
  move 0,0,-2
  gosub ShowPolygon
  move 0,0,2
  '
  glpushmatrix
  static float layr=.001
  static float f = -1 - layr*ordn
  glscalef 15,15,1
  gltranslatef .0, .0, f
  int i,j
  for i=1 to ordn
    j=ord[i]
    cb[j].act idb[j] 'set identity
    gltranslatef .0, .0, layr 'next micro-layer in front
  next
  '
  'LINK TO SLIDERS
  'COLOR
  rr=0.5+cb[1].c[1].vy*.5
  gg=0.5+cb[1].c[2].vy*.5
  bb=0.5+cb[1].c[3].vy*.5
  aa=0.5+cb[1].c[4].vy*.5
  glpopmatrix
  '
  '
 
'  ang1+=angi1
'  if ang1>=360 then ang1-=360
 
  end procedure 'main
  EndScript

#2
OxygenBasic / Re: GetKey
Last post by Nicola - December 04, 2023, 11:46:36 PM
I needed it to complete this small input example.


'La routine serve per tracciare delle "_" al posto
'delle lettere da inserire

'y e x corrispondono alle coordinate
'max è il valore della lunghezza massima della parola
'-----------------------------------------------------

use console

function infos(string tst="", int y, x, max) as string
  local string yy
  local int l, k

  do
    setpos x,y
    'print tst + ": " + yy + string(max-len(yy), "_")
    print tst + yy + string(max-len(yy), "_")
    k=getkey  'aspetta pressione tasto
    select k
      case 9, 13   'tab, enter
        if len(yy)> 0 then
          setpos x,y
          print tst + yy + string(max-len(yy), " ")
          return yy
        endif
      
       case 27    'tasto ESC permette di uscire senza scrivere niente
         return ""

       case 8  'del, cancella i caratteri inseriti
         if len(yy)> 0 then
           yy=left(yy,len(yy)-1)
         endif

       case 32 to 127
         if len(yy)< max then
           yy=yy + chr(k)
         endif

     end select
   loop
end function

'--------------
'--- MAIN -----
string esempio=infos("Nome: ",3,5,10)
string esempio2=infos("Cognome: ",3,25,10)
printl
printl esempio " len= " len(esempio)
printl esempio2 " len= " len(esempio2)

wait
#3
OxygenBasic / Re: GetKey
Last post by Nicola - December 04, 2023, 11:38:26 PM
function GetKey(int c=0) as int
  ===============================
  int d,t
  do
    t=inkey(c)
    if t
      d=KeyRecord.wAsciiCode
      if c
        if d=c
          return c
        endif
      else 'c=0
        return d
      endif
    endif
    sleep 10
  loop
  end function

Getkey in console.inc
Now it works well.
Thank you
#4
OxygenBasic Examples / Re: Slider Box changes triangl...
Last post by Frank Brübach - December 04, 2023, 08:47:22 PM
First of all thank you Charles :) Looks good!

It's Not quite clear for me to Setup a Second sliderbox with Size Manipulation of the triangle..

Look at my Code example more to the end If I need the Link to Slider Go through a separately Slider function Like cb(I).act idb(j) can modified by cb(I).act mu(j).x ?

Code example:


'
'-------- experiment to combine triangle data with slider overlapped
'-------- oxygenbasic, by frank brübach, 27-11-2023, 04-12-23
  '
  #compact
 '%filename "t.exe"
 'uses RTL64
  % Title "Triangle Data:  Move points with mouse and arrow keys etc"

 '% WindowStyle WS_OVERLAPPEDWINDOW
 '% Animated
 '% ScaleUp
  % PlaceCentral
  % AnchorCentral

  '% shaders

  uses consoleG
 'uses glo2/geoplanar
  'uses ControlPanels


  uses controls
  ===================
  class ControlPanelA
  ===================
  float  x,y,z
  int    id
  float  xx,yy,zz
  float  dx,dy,dz
  float  sc
  int    lock
  int    t1,t2
  int    f1,f2
  string lbl
  float  sizer 'for sizing the triangle by sliders
  ===================
  sliders      c[4]
  lightbuttons l[4]
  ===================

  method act(optional int n)
  indexbase 1
  if id=0
    f1=0 'cube
    f2=0 'pent
    ==========================================================================
    'ctrl  x    y  z    sc    shm shb tex id  lk  lbl
    --------------------------------------------------------------------------
    c[1]=>-.40,-.00, .00,  0.10, f1, 00, t1, 10, 1, "slider"
    c[2]=>-.30,-.00, .00 , 0.10, f2, 00, t1, 20, 1, "slider"
    c[3]=>-.20,-.00, .00 , 0.10, f2, 00, t1, 30, 1, "slider"
    c[4]=>-.10,-.00, .00 , 0.10, f2, 00, t1, 40, 1, "slider"
    -------------------------------------------------------------------------
    l[1]=>-.40, .15, .00,  0.02, f1, 00, t1, 50, 1, "light button"
    l[2]=>-.30, .15, .00 , 0.02, f2, 00, t1, 60, 1, "light button"
    l[3]=>-.20, .15, .00 , 0.02, f2, 00, t1, 70, 1, "light button"
    l[4]=>-.10, .15, .00 , 0.02, f2, 00, t1, 80, 1, "light button"
    ==========================================================================
    id=1+n
    int i
    for i=1 to 4
      c[i].id+=n 'slider
      l[i].id+=n 'light button
    next
  end if
  '
  glpushmatrix
  gltranslatef  x,y,z
  '
  gltranslatef -.25,.0,-.0005
  if sc then glscalef sc,sc,1.0
  if pick
    PickLabel id
  else
    QuadShadow .20,.20,.005,.5
    glcolor3f    .60,.50,.60 'fix alpha bug
    glcolor4f    .60,.50,.60,0.50 'box
  endif
  QuadTex      .20,.20,.0.01
  gltranslatef  .25,.0,-.0
  '
  'DISPLAY LABELS
  if lbl
    glpushmatrix
    gltranslatef -.43,-.13,.0005
    glcolor4f .9,.9,.4,.9
    float j=0.015
    'DISPLAY EACH SLIDER VALUE
    for i=1 to 4
      glpushmatrix
      gltranslatef j,0,0
      glscalef  .035,.035,.035
      if pick
        gltranslatef -.1,-.18,.0
        picklabel id+i
        PutBoxArea 2,1
        gltranslatef .1,.18,.0
      else
        if picked=id+i 'edit
          ------------
          'DATA EDITING
          color 0.9,0.9,0.9
          'box-around
          gltranslatef -.1,-.18,.0
          glBegin GL_LINE_STRIP
          glVertex2f 0,0
          glVertex2f 2,0
          glVertex2f 2,1
          glVertex2f 0,1
          glVertex2f 0,0
          glEnd
          gltranslatef .1,.18,.0
          '
          static string ss
          ss= str(50+c[i].vy*50,0) '0..100
          input ss
          c[i].vy=(val(ss)-50) *0.02
          '
          static int cpick,cy,cx
          if cpick<>picked
            cp=le+1 'place cursor at end of string
            cy=y
            cx=x
            cpick=picked
          endif
          '
          select lastkey
          case VK_UP
            c[i].vy+=0.01
          case VK_DOWN
            c[i].vy-=0.01
          case VK_PRIOR 'PGUP
            c[i].vy+=0.01
          case VK_NEXT 'PGDN
            c[i].vy-=0.01
          case 9 'tab
            if GetAsyncKeyState(VK_SHIFT)=0
              picked++
              if picked>id+4
                picked=id+4
              end if
            else 'left
              picked--
              if picked<id+1
                picked=id+1
              endif
            endif
          end select
          lastkey=0
          lastchar=0
        else 'display
          gprint str(50+c[i].vy*50,0) '0..100
          'gprint str((c[i].vy)*100 , 0) -100..100
        endif
      endif
      glpopmatrix
      j+=0.1
    next
    'DISPLAY MAIN PANEL LABEL
    gltranslatef 0,-.05,0
    glscalef  .04,.04,.04
    glcolor4f .9,.9,.0,.9
    gprint lbl
    glpopmatrix
  endif
  '
  '
  if bleft
    if picked=id
      if not lock
        drag(dx,dy,1.0/sc)
        x=xx+dx : y=yy+dy
      end if
    end if
  else
    xx=x : yy=y : zz=z 'ANCHOR
  end if
  '
  'render
  '
  int i,oi1,oi2
  for i=1 to 4
    c[i].act(1,i,oi1) 'slider
    l[i].act(1,i,oi2) 'lightbutton
  next
  glpopmatrix
  '
  'show data
  '
  'glDisable GL_TEXTURE_2D
  glDisable GL_LIGHTING
  '
  glPushMatrix
  glLoadIdentity
  if pick
    PickLabel 0
  endif
  gltranslatef -.5,.35,-1.0
  float w,h
  glscalef    .05,.05,.01
  GetWordArea  "Control:",w,h
  if pick
    PutBoxArea  w,h
  else
    /*
    glColor3f    .99,.99,.00
    gprint      "Control: "
    glColor3f    .99,.99,.99
    gprint    str(picked)
    if oi1+oi2
      gprint "  "
      if oi1 then gprint str((1.0+c[oi1].vy)*50 , 0)
      if oi2 then gprint str (l[oi2].lit)
    end if
    */
  end if
  glPopMatrix
  end method
  '
  method destructor()
  ===================
  'del this.label
  'sliders      c[4]
  'lightbuttons l[4]
  int i
  for i=1 to 4
    c[i].destructor
  next
  for i=1 to 4
    l[i].destructor
  next
  end method
  '
  end class

  '#recordof ControlPanelA
  'Keys: Esc, arrow-keys, n,m, F4

  indexbase 1
  sys      texn[16]
  sys      GdiplusToken
  float    ang1
  sys      cube,pent

  '--------------------------------------- //
  BeginScript

  procedure main() 'triangle-data example
  ================

  static single ra,ri,angi1=.5
  static sys    initscene
  sys hwnd
  static float rr=.5,gg=.5,bb=.5,aa=.8 'object color
  static float sx,sy,sz
  '
  '
'--------------------------------------------------- //
  'WaitForEvent '0 off 1 on (default on)
  static quad t1,t2

  if opening 'FIRST CALL ONLY
    timemark t1
    'picked=100
    'mbox "helo"
  end if
  '
  if closing 'FINAL CALL BEFORE SHUTDOWN
    'mbox "Bye!"
    exit sub
  end if
  cls

  subroutine ShowPolygon
  ======================
  move 0,0,-1
  shading
  UserMovement mu,1100,3 'symbol identity, count
  if opening
    mu[1].x= 0
    mu[1].y= 5
    mu[2].x=-5
    mu[2].y=-5
    mu[3].x= 5
    mu[3].y=-5
  endif
  scale 1
  picklabel 0
  int i
  for i=1 to 3
    pushstate
    mu[i].act
    color 1,.9,0,1
    scale 0.4
    go sphere
    popstate
  next
  float xa,xb,xc,ya,yb,yc 'mu[i].act
  xa=mu[1].x : ya=mu[1].y
  xb=mu[2].x : yb=mu[2].y
  xc=mu[3].x : yc=mu[3].y
  '
  static float sx,sy,sz

  'MOUSE DRAG ADJUSTMENT
  select picked
    case 1100 : xa+=mu[1].d.x : ya+=mu[1].d.y
    'print "1100"
    case 1200 : xb+=mu[2].d.x : yb+=mu[2].d.y
    case 1300 : xc+=mu[3].d.x : yc+=mu[3].d.y
  end select
  flat
  thickness 2
  '
  color 1,1,0,1
  pushstate
  move xa-.5,ya-1
  gprint "A"
  popstate
  pushstate
  move xb+1,yb+1
  gprint "B"
  popstate
  pushstate
  move xc-1,yc+1
  gprint "C"
  popstate
  '
  color rr,gg,bb,aa 'linked to slider panel 1
  'sizer sx,sy,sz

  float zp=-1.001
  glBegin GL_TRIANGLES
  glVertex3f xa,ya,zp
  glVertex3f xb,yb,zp
  glVertex3f xc,yc,zp
  glEnd
  '
  color 0,.9,.9
  glBegin GL_LINES
  glVertex2f xa,ya
  glVertex2f xb,yb
  glVertex2f xb,yb
  glVertex2f xc,yc
  glVertex2f xc,yc
  glVertex2f xa,ya
  glEnd

  move 5

  'if not pick then
    if key[49] then picked=100 'keypress '1'
    if key[50] then picked=200 'keypress  '2'
    pushstate
    move -20,12
    static sys tally
    timemark t2
    scale 1.0
    '
    int dp=3
    '
    macro pr1(a) 'PRINTING LIST
    -----------------------------
      pushstate : color .5,1,1 : print a : popstate
      printl ""
    end macro
    '
    macro pr2(a,b) 'PRINTING LIST
    -----------------------------
      pushstate : color .5,1,1 : print a : popstate
      pushstate : color 1,1,.5 : move 4 : print str(b,dp) : popstate
      printl ""
    end macro
    '
    macro pr3(a,b,c) 'PRINTING LIST
    ------------------------------
      pushstate : color .5,1,1 : print a : popstate
      pushstate : color 1,1,.5 : move 4 : print str(b,dp) : popstate
      pushstate : color 1,1,.5 : move 8 : print str(c,dp) : popstate
      printl ""
    end macro
    '
    '
    'DISPLAY INFO
    -------------
    picklabel 0

    pushstate
    scale 2
    color 1,1,1
    print "Triangle Data"
    popstate
    pr1 ""
    pr1 ""
  'pr2 "Action Code:  ", act
  'pr2 "indexbase      ", indexbase
  'pr2 "Keyboard Code: ", keyd
    pr2 "Picked ID:    ", picked
    '
    pr3 "Point A: ", str(xa,3), ya
    pr3 "Point B: ", str(xb,3), yb
    pr3 "Point C: ", str(xc,3), yc
    '
    float ab,ac,bc,ar,ht,hb
    '
    ab=hypot(xa-xb, ya-yb)
    ac=hypot(xa-xc, ya-yc)
    bc=hypot(xb-xc, yb-yc)
    '
    hb=0.5* ( ab*ab - ac*ac + bc*bc ) / bc
    ht=sqr(ab*ab-hb*hb)
    ar=0.5*bc*ht

    'ANGLES
    float na,nb,nc
    nb=deg(asin(ht/ab))
    nc=deg(asin(ht/ac))
    na=180-nb-nc

    pr1 ""
    pr2 "Angle A:",na
    pr2 "Angle B:",nb
    pr2 "Angle C:",nc
 
    pr1 ""
    pr2 "Line AB:",ab
    pr2 "Line AC:",ac
    pr2 "Line BC:",bc
    pr2 "Left base:",hb
    pr2 "Height:",ht
    pr2 "Area:", ar
    pr1 ""
    '
    picklabel 0
    popstate
  'end if
  end subroutine

  '--------------------
  'end polygon display
  '--------------------

  'PANEL DISPLAY
  ==============

  static single ra,ri,angi1=.5
  static sys    initscene
 
  '------------------------------
 'glClearColor 0.5, 0.5, 0.7, 0
 'glClearColor 0.1, 0.2, 0.1, 0
  '
  glColor4f .99,.99,.99,.99
  'glEnable GL_TEXTURE_2D
  '
  'RENDERED LOWEST FIRST (FOR TRANSPARENCY BLENDING)
  '
  %                    ordn=2'1
  static ControlPanelA cb[ordn]
  static int          ord[16]
  static int          idb[16]
  '
  if closing
    int i
    for i=1 to ordn
      cb[i].destructor
    next
    exit sub
  endif
 
  '
  'INITIAL PLACEMENT ETC
  '
  if initscene=0
    ord={1,2,3,4}
    idb={0,100,200,300}
    cb[1].x=.8 : cb[1].y=.6 : cb[1].lbl="Color"
    cb[2].x=.8 : cb[2].y=.6 : cb[2].lbl="size"
    int i
    'set scale
    for i=1 to ordn : cb[i].sc=2.5 : next
    initscene=1
  end if
  '
  'ORDER OF BUILD (SUPPORTING TRANSPARENCY)
  '
  if picked and bleft
    int a=1+trunc(picked/100)
    PlaceTop(a,ord,ordn)
  end if
  '
  'RENDER SCENE
  '
  move 0,0,-1
  gosub ShowPolygon
  move 0,0,1
  '
  UserMovement mu,1100,3

  glpushmatrix
  static float layr=.001
  static float f = -1 - layr*ordn
  glscalef 15,15,1
  gltranslatef .0, .0, f
  int i,j
  for i=1 to ordn
    j=ord[i]
    cb[j].act idb[j] 'original
    'cb[2].act mu[1].x
    'cb[j].act mu[j].x
    cb[i].act mu[j].x
    gltranslatef .0, .0, layr 'next micro-layer in front
  next
  '
  'LINK TO SLIDERS
  'COLOR
  rr=0.5+cb[1].c[1].vy*.5 'c[1] slider
  gg=0.5+cb[1].c[2].vy*.5
  bb=0.5+cb[1].c[3].vy*.5
  aa=0.5+cb[1].c[4].vy*.5
  'glpopmatrix
  '----------------------------------- // slider to triangle size how?
  '---------- problem zone here ------ //
  float xa,xb,xc,ya,yb,yc ''mu[i].act
  xa=mu[1].x : cb[1].c[1].vy : ya=mu[1].y
  xb=mu[2].x : cb[1].c[1].vy : yb=mu[2].y
  xc=mu[3].x : cb[1].c[1].vy : yc=mu[3].y
  glpopmatrix
 
  '  ang1+=angi1
  '  if ang1>=360 then ang1-=360
 
  end procedure 'main
  EndScript


#5
OxygenBasic Examples / Re: Function strMatchPattern
Last post by Charles Pegge - December 04, 2023, 02:29:47 PM
Interesting.

At first glance, it understands the algorithm well, though the optimization of early termination on an end wild-card would be incorrect for the purposes of the instrp returning a complete match-string. The en variable should also return the position following the last character of the match. My variable annotations were also omitted, with the variables stacked with colons, thereby less easy to  read.
#6
OxygenBasic Examples / Re: Function strMatchPattern
Last post by Theo Gottwald - December 04, 2023, 12:51:23 PM
Optimizations and Changes:

Wildcard Handling: Optimized the handling of the * wildcard by skipping consecutive *s and efficiently searching for the next character in the pattern.

Redundant Checks: Removed redundant length checks and streamlined the handling of edge cases like empty strings or patterns.

Character Matching Logic: Direct comparison of bytes from source and pattern strings to enhance performance.
Memory Optimization: Reduced the number of variables and their scope where possible.

Efficient Data Structures: Utilized direct memory access (byte bs at strptr(s), byte bp at strptr(p)) for potentially more efficient string processing, depending on language support.

Notes:
The code is written in a style similar to the original, assuming a Basic-like language. The actual optimization may vary based on the specific language's features and capabilities.
Profiling and testing are recommended to ensure the optimized code performs as expected and to validate improvements.


function instrp(int i, string s, p, int* en=0) as int
  ' Initialize variables
  if i < 1 then i = 1
  if not s then return 0 ' No source string
  if not p then return 1 ' No search string

  ' Pre-calculate string lengths to avoid redundant calls
  int ls = len(s)
  int lp = len(p)
  if ls = 0 or lp = 0 then return 0 ' Handle empty strings

  ' Using more efficient direct memory access (if supported by the language)
  byte bs at strptr(s)
  byte bp at strptr(p)

  ' Optimization: Preprocessing for first character of pattern
  byte ka = bp[1]
  int js = i, jp = 1, ks = i, kt = i
  int fs = 0, kf = 0, kg = 0, ok = 0

  ' Main search loop
  while js <= ls and jp <= lp
    select bp[jp]
    case 42 ' * Wildcard
      ' Skip consecutive * characters
      do while jp < lp and bp[jp+1] = 42
        jp += 1
      loop

      ' Special case: * at the end of pattern
      if jp = lp then return ks

      ' Find the next character in source string
      jp += 1
      ka = bp[jp]
      do while js <= ls and bs[js] <> ka
        js += 1
      loop
      if js > ls then return 0

      kf = jp
      kg = js

    case 63 ' ? Wildcard
      if js > ls then return 0
      if ka = bs[js] then ks = js
      js += 1

    case else ' Regular character
      if bp[jp] <> bs[js] then
        ' Mismatch, use previous wildcard positions if available
        if kf > 0 then
          jp = kf
          js = kg
          kf = 0
          kg = 0
          continue while
        else
          ' No previous wildcard, restart search
          jp = 1
          ks += 1
          js = ks
          if js > ls then return 0
        endif
      else
        ' Character match
        if fs = 0 then fs = js ' First match position
        js += 1
      endif
    end select
    jp += 1
  wend

  ' Check for match completion
  if jp > lp then
    en = js - 1
    return fs
  else
    return 0
  endif
end function

#7
OxygenBasic Examples / Re: Slider Box changes triangl...
Last post by Charles Pegge - December 03, 2023, 06:33:18 PM
Hi Frank,
I've cleaned up the previous and linked color/transparency to one slider panel. I hope this answers your questions and resolves the issues you were having.

'-------- experiment to combine triangle data with slider overlapped
  '-------- oxygenbasic, by frank brübach, 27-11-2023
  '
  '17:29 03/12/2023 CP
  #compact
 '%filename "t.exe"
 'uses RTL64
  % Title "Triangle Data:  Move points with mouse and arrow keys etc"

 '% WindowStyle WS_OVERLAPPEDWINDOW
 '% Animated
 '% ScaleUp
  % PlaceCentral
  % AnchorCentral

  '% shaders

  uses consoleG
 'uses glo2/geoplanar
  'uses ControlPanels


  uses controls
  ===================
  class ControlPanelA
  ===================
  float  x,y,z
  int    id
  float  xx,yy,zz
  float  dx,dy,dz
  float  sc
  int    lock
  int    t1,t2
  int    f1,f2
  string lbl
  ===================
  sliders      c[4]
  lightbuttons l[4]
  ===================

  method act(optional int n)
  indexbase 1
  if id=0
    f1=0 'cube
    f2=0 'pent
    ==========================================================================
    'ctrl   x    y   z     sc    shm shb tex id  lk  lbl
    --------------------------------------------------------------------------
    c[1]=>-.40,-.00, .00,  0.10, f1, 00, t1, 10, 1, "slider"
    c[2]=>-.30,-.00, .00 , 0.10, f2, 00, t1, 20, 1, "slider"
    c[3]=>-.20,-.00, .00 , 0.10, f2, 00, t1, 30, 1, "slider"
    c[4]=>-.10,-.00, .00 , 0.10, f2, 00, t1, 40, 1, "slider"
    -------------------------------------------------------------------------
    l[1]=>-.40, .15, .00,  0.02, f1, 00, t1, 50, 1, "light button"
    l[2]=>-.30, .15, .00 , 0.02, f2, 00, t1, 60, 1, "light button"
    l[3]=>-.20, .15, .00 , 0.02, f2, 00, t1, 70, 1, "light button"
    l[4]=>-.10, .15, .00 , 0.02, f2, 00, t1, 80, 1, "light button"
    ==========================================================================
    id=1+n
    int i
    for i=1 to 4
      c[i].id+=n
      l[i].id+=n
    next
  end if
  '
  glpushmatrix
  gltranslatef  x,y,z
  '
  gltranslatef -.25,.0,-.0005
  if sc then glscalef sc,sc,1.0
  if pick
    PickLabel id
  else
    QuadShadow .20,.20,.005,.5
    glcolor3f     .60,.50,.60 'fix alpha bug
    glcolor4f     .60,.50,.60,0.50 'box
  endif
  QuadTex       .20,.20,.0.01
  gltranslatef  .25,.0,-.0
  '
  'DISPLAY LABELS
  if lbl
    glpushmatrix
    gltranslatef -.43,-.13,.0005
    glcolor4f .9,.9,.4,.9
    float j=0.015
    'DISPLAY EACH SLIDER VALUE
    for i=1 to 4
      glpushmatrix
      gltranslatef j,0,0
      glscalef  .035,.035,.035
      if pick
        gltranslatef -.1,-.18,.0
        picklabel id+i
        PutBoxArea 2,1
        gltranslatef .1,.18,.0
      else
        if picked=id+i 'edit
          ------------
          'DATA EDITING
          color 0.9,0.9,0.9
          'box-around
          gltranslatef -.1,-.18,.0
          glBegin GL_LINE_STRIP
          glVertex2f 0,0
          glVertex2f 2,0
          glVertex2f 2,1
          glVertex2f 0,1
          glVertex2f 0,0
          glEnd
          gltranslatef .1,.18,.0
          '
          static string ss
          ss= str(50+c[i].vy*50,0) '0..100
          input ss
          c[i].vy=(val(ss)-50) *0.02
          '
          static int cpick,cy,cx
          if cpick<>picked
            cp=le+1 'place cursor at end of string
            cy=y
            cx=x
            cpick=picked
          endif
          '
          select lastkey
          case VK_UP
            c[i].vy+=0.01
          case VK_DOWN
            c[i].vy-=0.01
          case VK_PRIOR 'PGUP
            c[i].vy+=0.01
          case VK_NEXT 'PGDN
            c[i].vy-=0.01
          case 9 'tab
            if GetAsyncKeyState(VK_SHIFT)=0
              picked++
              if picked>id+4
                picked=id+4
              end if
            else 'left
              picked--
              if picked<id+1
                picked=id+1
              endif
            endif
          end select
          lastkey=0
          lastchar=0
        else 'display
          gprint str(50+c[i].vy*50,0) '0..100
          'gprint str((c[i].vy)*100 , 0) -100..100
        endif
      endif
      glpopmatrix
      j+=0.1
    next
    'DISPLAY MAIN PANEL LABEL
    gltranslatef 0,-.05,0
    glscalef  .04,.04,.04
    glcolor4f .9,.9,.0,.9
    gprint lbl
    glpopmatrix
  endif
  '
  '
  if bleft
    if picked=id
      if not lock
        drag(dx,dy,1.0/sc)
        x=xx+dx : y=yy+dy
      end if
    end if
  else
    xx=x : yy=y : zz=z 'ANCHOR
  end if
  '
  'render
  '
  int i,oi1,oi2
  for i=1 to 4
    c[i].act(1,i,oi1)
    l[i].act(1,i,oi2)
  next
  glpopmatrix
  '
  'show data
  '
  'glDisable GL_TEXTURE_2D
  glDisable GL_LIGHTING
  '
  glPushMatrix
  glLoadIdentity
  if pick
    PickLabel 0
  endif
  gltranslatef -.5,.35,-1.0
  float w,h
  glscalef     .05,.05,.01
  GetWordArea  "Control:",w,h
  if pick
    PutBoxArea   w,h
  else
    /*
    glColor3f    .99,.99,.00
    gprint       "Control: "
    glColor3f    .99,.99,.99
    gprint    str(picked)
    if oi1+oi2
      gprint "   "
      if oi1 then gprint str((1.0+c[oi1].vy)*50 , 0)
      if oi2 then gprint str (l[oi2].lit)
    end if
    */
  end if
  glPopMatrix
  end method
  '
  method destructor()
  ===================
  'del this.label
  'sliders      c[4]
  'lightbuttons l[4]
  int i
  for i=1 to 4
    c[i].destructor
  next
  for i=1 to 4
    l[i].destructor
  next
  end method
  '
  end class

  '#recordof ControlPanelA



  'Keys: Esc, arrow-keys, n,m, F4

  indexbase 1
  sys       texn[16]
  sys       GdiplusToken
  float     ang1
  sys       cube,pent



  BeginScript

  procedure main() 'triangle-data example
  ================

  static single ra,ri,angi1=.5
  static sys    initscene
  sys hwnd
  static float rr=.5,gg=.5,bb=.5,aa=.8 'object color
  '
  '
'--------------------------------------------------- //
  'WaitForEvent '0 off 1 on (default on)
  static quad t1,t2

  if opening 'FIRST CALL ONLY
    timemark t1
    'picked=100
    'mbox "helo"
  end if
  '
  if closing 'FINAL CALL BEFORE SHUTDOWN
    'mbox "Bye!"
    exit sub
  end if
  cls

  subroutine ShowPolygon
  ======================
  move 0,0,-1
  shading
  UserMovement mu,1100,3 'symbol identity, count
  if opening
    mu[1].x= 0
    mu[1].y= 5
    mu[2].x=-5
    mu[2].y=-5
    mu[3].x= 5
    mu[3].y=-5
  endif
  scale 1
  picklabel 0
  int i
  for i=1 to 3
    pushstate
    mu[i].act
    color 1,.9,0,1
    scale 0.4
    go sphere
    popstate
  next
  float xa,xb,xc,ya,yb,yc
  xa=mu[1].x : ya=mu[1].y
  xb=mu[2].x : yb=mu[2].y
  xc=mu[3].x : yc=mu[3].y
  '
  'MOUSE DRAG ADJUSTMENT
  select picked
    case 1100 : xa+=mu[1].d.x : ya+=mu[1].d.y
    case 1200 : xb+=mu[2].d.x : yb+=mu[2].d.y
    case 1300 : xc+=mu[3].d.x : yc+=mu[3].d.y
  end select
  flat
  thickness 2
  '
  color 1,1,0,1
  pushstate
  move xa-.5,ya-1
  gprint "A"
  popstate
  pushstate
  move xb+1,yb+1
  gprint "B"
  popstate
  pushstate
  move xc-1,yc+1
  gprint "C"
  popstate
  '
  color rr,gg,bb,aa 'linked to slider panel 1
  float zp=-1.001
  glBegin GL_TRIANGLES
  glVertex3f xa,ya,zp
  glVertex3f xb,yb,zp
  glVertex3f xc,yc,zp
  glEnd
  '
  color 0,.9,.9
  glBegin GL_LINES
  glVertex2f xa,ya
  glVertex2f xb,yb
  glVertex2f xb,yb
  glVertex2f xc,yc
  glVertex2f xc,yc
  glVertex2f xa,ya
  glEnd

  move 5

  'if not pick then
    if key[49] then picked=100 'keypress '1'
    if key[50] then picked=200 'keypress  '2'
    pushstate
    move -20,12
    static sys tally
    timemark t2
    scale 1.0
    '
    int dp=3
    '
    macro pr1(a) 'PRINTING LIST
    -----------------------------
      pushstate : color .5,1,1 : print a : popstate
      printl ""
    end macro
    '
    macro pr2(a,b) 'PRINTING LIST
    -----------------------------
      pushstate : color .5,1,1 : print a : popstate
      pushstate : color 1,1,.5 : move 4 : print str(b,dp) : popstate
      printl ""
    end macro
    '
    macro pr3(a,b,c) 'PRINTING LIST
    ------------------------------
      pushstate : color .5,1,1 : print a : popstate
      pushstate : color 1,1,.5 : move 4 : print str(b,dp) : popstate
      pushstate : color 1,1,.5 : move 8 : print str(c,dp) : popstate
      printl ""
    end macro
    '
    '
    'DISPLAY INFO
    -------------
    picklabel 0

    pushstate
    scale 2
    color 1,1,1
    print "Triangle Data"
    popstate
    pr1 ""
    pr1 ""
   'pr2 "Action Code:   ", act
   'pr2 "indexbase      ", indexbase
   'pr2 "Keyboard Code: ", keyd
    pr2 "Picked ID:     ", picked
    '
    pr3 "Point A: ", str(xa,3), ya
    pr3 "Point B: ", str(xb,3), yb
    pr3 "Point C: ", str(xc,3), yc
    '
    float ab,ac,bc,ar,ht,hb
    '
    ab=hypot(xa-xb, ya-yb)
    ac=hypot(xa-xc, ya-yc)
    bc=hypot(xb-xc, yb-yc)
    '
    hb=0.5* ( ab*ab - ac*ac + bc*bc ) / bc
    ht=sqr(ab*ab-hb*hb)
    ar=0.5*bc*ht

    'ANGLES
    float na,nb,nc
    nb=deg(asin(ht/ab))
    nc=deg(asin(ht/ac))
    na=180-nb-nc

    pr1 ""
    pr2 "Angle A:",na
    pr2 "Angle B:",nb
    pr2 "Angle C:",nc
  
    pr1 ""
    pr2 "Line AB:",ab
    pr2 "Line AC:",ac
    pr2 "Line BC:",bc
    pr2 "Left base:",hb
    pr2 "Height:",ht
    pr2 "Area:", ar
    pr1 ""
    '
    picklabel 0
    popstate
  'end if
  end subroutine

  '--------------------
  'end polygon display
  '--------------------

  'PANEL DISPLAY
  ==============

  static single ra,ri,angi1=.5
  static sys    initscene
 
  '------------------------------
 'glClearColor 0.5, 0.5, 0.7, 0
 'glClearColor 0.1, 0.2, 0.1, 0
  '
  glColor4f .99,.99,.99,.99
  'glEnable GL_TEXTURE_2D
  '
  'RENDERED LOWEST FIRST (FOR TRANSPARENCY BLENDING)
  '
  %                    ordn=1
  static ControlPanelA cb[ordn]
  static int           ord[16]
  static int           idb[16]
  '
  if closing
    int i
    for i=1 to ordn
      cb[i].destructor
    next
    exit sub
  endif
 
  '
  'INITIAL PLACEMENT ETC
  '
  if initscene=0
    ord={1,2,3}
    idb={0,100,200}
    cb[1].x=.8 : cb[1].y=.6 : cb[1].lbl="Color"
    int i
    'set scale
    for i=1 to ordn : cb[i].sc=2.5 : next
    initscene=1
  end if
  '
  'ORDER OF BUILD (SUPPORTING TRANSPARENCY)
  '
  if picked and bleft
    int a=1+trunc(picked/100)
    PlaceTop(a,ord,ordn)
  end if
  '
  'RENDER SCENE
  '
  move 0,0,-1
  gosub ShowPolygon
  move 0,0,1
  '
  glpushmatrix
  static float layr=.001
  static float f = -1 - layr*ordn
  glscalef 15,15,1
  gltranslatef .0, .0, f
  int i,j
  for i=1 to ordn
    j=ord[i]
    cb[j].act idb[j]
    gltranslatef .0, .0, layr 'next micro-layer in front
  next
  '
  'LINK TO SLIDERS
  'COLOR
  rr=0.5+cb[1].c[1].vy*.5
  gg=0.5+cb[1].c[2].vy*.5
  bb=0.5+cb[1].c[3].vy*.5
  aa=0.5+cb[1].c[4].vy*.5
  glpopmatrix
  '
  '
  '
  '
 
'  ang1+=angi1
'  if ang1>=360 then ang1-=360
 
  end procedure 'main
  EndScript
#8
OxygenBasic Examples / Re: Function strMatchPattern
Last post by Charles Pegge - December 02, 2023, 05:33:01 PM
It is an interesting algorithm with hidden complexity. Here is one of my code serpents. :) It is in the form of a instr, and as you can see, it is considerably more complex than this AI version:

'01/12/2023 CP

'01/12/2023
'
function instrp(int i,string s,p,int*en=0) as int
=================================================
'
'i   start position
's   string to search
'p   search string (with optional ? * wildcards
'en  boundary of found key string
'
if i<1
  i=1
endif
if not s
  return 0 'no source string
endif
if not p
  return 1 'no search string
endif
'
indexbase 1
byte bs at strptr(s) 'source string bytes
byte bp at strptr(p) 'search string bytes
int js=i      'source string position
int jp=1      'search string position
int ks=i      'next search start
int kt=i      'current search start
int kf=0      'prev key wild card position
int kg=0      'prev source wild card position
int fs=i      'possible found position
int ls=len(s) 'limit of source string
int lp=len(p) 'limit of search string
int ok=1      'vrification flag
byte ka=bp[1] 'first byte to search
do
  if jp>lp
    exit do
  endif
  if js>ls
    if jp<=lp
      ok=0
    endif
    exit do
  endif
  select bp[jp]
  case 42 '*
    ok=1
    while bp[jp]=42
      jp++
    wend
    do
      if js>ls 'end of string
        ok=1
        jp--
        exit do
      endif
      if ka=bs[js]
        ks=js
      endif
      if jp>lp 'end of pattern
        ok=1
        jp--
        exit do
      endif
      if bp[jp]=bs[js] 'possible match char
        ok=1
        jp--
        'these flags used for resuming wild card
        kf=jp
        kg=js+1
        exit do
      endif
      if bp[jp]=63 'possible match ? char
        ok=1
        jp--
        exit do
      endif
      js++
    loop
  case 63 '?
    if ka=bs[js]
      ks=js
    endif
    ok=1
    js++
  case else 'all other chars
    if bp[jp]=bs[js] 'byte match
      ok=1
      if ka=bs[js]
        ks=js
      endif
      js++
    else 'mismatch
      ok=0
      if kf
        'prev wildcard positions
        jp=kf-1
        js=kg
        kf=0
        kg=0
      else
        if ka=63
          ks=kt '?' was wildcard start
        endif
         if ks=kt
           ks++ 'nudge fwd
        endif
        kt=ks
        js=ks 'restart search
        fs=js
        jp=0
      endif
    endif
  end select
  jp++ 'next pattern byte
loop
if ok
  function=fs
else
  js=0
endif
en=js
end function
'
'test cases
===========
string s="aabcdefghijklmmnopqrstuvwxyz"
'print instrp 1,s,"ab"
'print instrp 1,s,"abz"
'print instrp 1,s,"xyz"
'print instrp 1,s,"mno"
'print instrp 1,s,"mm?o"
'print instrp 1,s,"m?o"
'print instrp 1,s,"m??"
'print instrp 1,s,"m??p"
'print instrp 1,s,"??m"
'print instrp 1,s,"*m"
'print instrp 1,s,"m*"
'print instrp 1,s,"m*z"
'print instrp 1,s,"m*k*z"
'print instrp 1,s,"m*n"
'print instrp 1,s,"a*b"
'print instrp 1,s,"a?*c"
'print instrp 1,s,"c?d"
'print instrp 1,s,"c*d"
'print instrp 1,s,"c?*e"
'print instrp 1,s,"c**f"
'print instrp 1,s,"c*??f" 'yes
'print instrp 1,s,"c*??g" 'no
'print instrp 1,s,"c??*g" 'yes
int en
'print instrp 1,s,"c??*g",en 'yes
'print en
uses console
s="abcdefghijklmmabcdefghijklmn"
int b
b=instrp(1,s,"d*lmm",en)
print b " - " en cr
print mid(s,b,en-b) cr
print instrp(1,s,"d*lmn",en) " - " en cr
print cr "ok" cr
wait
#9
OxygenBasic Examples / Re: Function strMatchPattern
Last post by Zlatko Vid - December 02, 2023, 05:20:12 PM
so nobody respond ...looks like a stupid question or what ?
#10
OxygenBasic / Re: GetKey
Last post by Charles Pegge - December 02, 2023, 04:30:18 PM
With a small mod the Ascii code (supporting esc) can be made available:

in console.inc
  static KEY_RECORD KeyRecord
  '
  function inkey(int c=0) as int
  ================================
  static KEY_RECORD k[8]
  static int nr
  int d
  PeekConsoleInputA ConsIn,@k,8, @nr
  if nr
    if c=0
      indexbase 1
      int i
      for i=1 to nr
        if k[i].EventType=1 'KEY_EVENT
          if k[i].bKeyDown
            KeyRecord=k[i]
            d=KeyRecord.wVirtualKeyCode
            exit for
          endif
        endif
      next
    elseif GetAsyncKeyState(c)
      d=c
    endif
    FlushConsoleInputBuffer ConsIn
    return d   
  endif
  end function

test code:
/*
  type KEY_RECORD
  ===============
    word EventType
    word wReserved
    dword bKeyDown
    word wRepeatCount
    word wVirtualKeyCode
    word wScanCode
    word wAsciiCode
    dword dwReserved
  end type
*/

uses console
string k
int a,c
do
  a=inkey
  if a
    c=KeyRecord.wAsciiCode
    k=a  ",  " c
    print k + cr
    if a=13 then break
  endif
loop

printl "end"

wait
[/cade]