 Rem File: Room.bas - Cmd*.bas
 Rem $Include: 'dndbbs.inc'

Sub Add.Room(Var)
 On Local Error Goto ErrorTrap30
 Graphics.Off=True
 Strng="No room exists in that direction."
 Call IO.O
 Strng="You may create a room there."
 Call IO.O
 Graphics.Off=False
 No.Input.Out="N"
 Strng="Add new room(y/n)? "
 Call IO.I
 Var=Yes
 If Var Then
    VarZ=TempA ' store entry direction
    Call Clear.Room ' create new room
    TempX!=Next.Room ' store new room number
    Call Edit.Room ' edit room in TempX!
    TempA=VarZ ' restore entry direction
    UserRecord.ObjectsCreated(7)=UserRecord.ObjectsCreated(7)+1#
    Close #TempFile1
    Filename$=DND.Path+"created.dat"
    Open Filename$ For Append Shared As #TempFile1
    Var$=Lcase$(Rtrim$(UserRecord.CodeName))
    Mid$(Var$,1,1)=Ucase$(Mid$(Var$,1,1))
    Var$=Var$+" created room"+Str$(TempX!)+" on "
    Var$=Var$+Format$(Now,"mm-dd-yyyy")+" "+Format$(Now,"hh:mm:ss")
    Print #TempFile1, Var$
    Close #TempFile1
 Endif
ErrorResume30:
 Exit Sub
ErrorTrap30:
 Resume ErrorResume30
End Sub

Sub Edit.Room
 On Local Error Goto ErrorTrap29
 Gosub Get.Config
 VarX!=Room ' store old room
 Room=TempX! ' set to new room
 VarZ=TempA ' store direction
 Strng="Room Edit Utility Menu:"
 Call IO.O
 Call Read.Record(RoomFile,Room)
 Do While Lost.Carrier=False
    Call Display.Room2
    Graphics.Off=False
    Strng="Room Edit Utility Menu for room"+Str$(Room)+":"
    Call IO.O
    Graphics.Off=True
    If Option1 Then
       Strng="[A]ction"
    Else
       Strng="[*]ction"
    Endif
    Call IO.O
    If Option2 Then
       Strng="[C]ontainers"
    Else
       Strng="[*]ontainers"
    Endif
    Call IO.O
    If Option3 Then
       Strng="[D]escription"
    Else
       Strng="[*]escription"
    Endif
    Call IO.O
    If Option4 Then
       Strng="[M]onster class"
    Else
       Strng="[*]onster class"
    Endif
    Call IO.O
    If Option5 Then
       Strng="[O]bject edit"
    Else
       Strng="[*]bject edit"
    Endif
    Call IO.O
    If Option6 Then
       Strng="[T]reasure edit"
    Else
       Strng="[*]reasure edit"
    Endif
    Call IO.O
    Graphics.Off=False
    Strng="Room edit option(q to quit)? "
    No.Input.Out="Q"
    Call IO.I
    Select Case Ucase$(Out2)
    Case "A"
       If Option1=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option1 Then
          Call Add.Action
       Endif
    Case "C"
       If Option2=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option2 Then
          Call Edit.Room.Containers
       Endif
    Case "D"
       If Option3=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option3 Then
          Call Edit.Description
       Endif
    Case "M"
       If Option4=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option4 Then
          Call Edit.Monclass
       Endif
    Case "O"
       If Option5=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option5 Then
          Call Edit.Objects
       Endif
    Case "T"
       If Option6=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option6 Then
          Call Edit.Treasure
       Endif
    Case "Q"
       Exit Do
    End Select
 Loop
 Call Write.Record(RoomFile,Room)
 If VarZ Then ' check direction
    ' write new direction from old room
    Call Read.Record(RoomFile,VarX!)
    RoomRecord.Direct(VarZ)=Room
    Call Write.Record(RoomFile,VarX!)
    ' write return direction
    Call Find.Back.Link(VarZ)
    If Temp4 Then
       No.Input.Out="Y"
       Strng="Link new room to previous(y/n)? "
       Call IO.I
       If Yes Then
          Call Read.Record(RoomFile,Room)
          RoomRecord.Direct(Temp4)=VarX!
          Call Write.Record(RoomFile,Room)
       Endif
    Endif
 Endif
 Room=VarX! ' restore old room
 Exit Sub
Get.Config:
 Option1=-1
 Option2=-1
 Option3=-1
 Option4=-1
 Option5=-1
 Option6=-1
 Do
    VarX=VarX+1
    If VarX>Options.Lines Then
       Exit Do
    Endif
    Var$=Ltrim$(Rtrim$(Options.Array(VarX)))
    If Ucase$(Var$)="[ROOM]" Then
       Do
          VarX=VarX+1
          If VarX>Options.Lines Then
             Return
          Endif
          Var$=Ltrim$(Rtrim$(Options.Array(VarX)))
          If Ucase$(Var$)="[END]" Then
             Return
          Endif
          Var=Instr(Var$,"=")
          If Var Then
             Var2$=Lcase$(Ltrim$(Rtrim$(Left$(Var$,Var-1))))
             Var3$=Lcase$(Ltrim$(Rtrim$(Mid$(Var$,Var+1))))
             Select Case Var2$
             Case "edit.action"
                Select Case Var3$
                Case "0", "false", "off"
                   Option1=0
                End Select
             Case "edit.container"
                Select Case Var3$
                Case "0", "false", "off"
                   Option2=0
                End Select
             Case "edit.descrip"
                Select Case Var3$
                Case "0", "false", "off"
                   Option3=0
                End Select
             Case "edit.monclass"
                Select Case Var3$
                Case "0", "false", "off"
                   Option4=0
                End Select
             Case "edit.objects"
                Select Case Var3$
                Case "0", "false", "off"
                   Option5=0
                End Select
             Case "edit.treasure"
                Select Case Var3$
                Case "0", "false", "off"
                   Option6=0
                End Select
             End Select
          Endif
       Loop
    Endif
 Loop
 Return
ErrorResume29:
 Exit Sub
ErrorTrap29:
 Resume ErrorResume29
End Sub

Sub Display.Room2
 On Local Error Goto Error.Trap0a
 Graphics.Off=False
 Strng="Room number"+Str$(Room)+":"
 Call IO.O
 Strng="Room short description:"
 Call IO.O
 Strng=RoomRecord.ShortDesc
 Strng=Rtrim$(Strng)
 If Instr(Strng,Chr$(0)) Then
    Strng=Nul
 Endif
 If Strng=Nul Then
    Strng="<none>"
 Endif
 Graphics.Off=True
 Call IO.O
 Strng="Room long description:"
 TempZ=False
 For TempQ=19 To 1 Step -1
    If RoomRecord.LongDesc(TempQ)>SFalse Then
       TempZ=TempQ
       Exit For
    Endif
 Next
 Select Case TempZ
 Case False
    Strng=Strng+" <none>"
 Case 1
    Strng=Strng+" 1 line."
 Case Else
    Strng=Strng+Str$(TempZ)+" lines."
 End Select
 Graphics.Off=False
 Call IO.O
 Graphics.Off=True
 Strng="Room monster class:"+Str$(RoomRecord.MonClass)+"."
 Call IO.O
 Strng="Room action number:"+Str$(RoomRecord.Action)+"."
 Call IO.O
 Temp3!=SFalse
 Temp2!=RoomRecord.First
 If Temp2! Then
    Do While Lost.Carrier=False
       Call Read.Record(RoomInvFile,Temp2!)
       If MessWorkRecord6.Room=SFalse Then
          Exit Do
       Endif
       Temp6!=MessWorkRecord6.Next
       VarX!=MessWorkRecord6.Index
       If VarX!<SFalse Then
          VarX!=Abs(VarX!)
          If VarX!>SFalse And VarX!<=Lof(ObjectFile)/ObjectRecLen Then
             Temp3!=Temp3!+1!
          Endif
       Endif
       If Temp6!=SFalse Then
          Exit Do
       Endif
       Temp2!=Temp6!
    Loop
 Endif
 Strng="Objects:"+Str$(Temp3!)+"."
 Call IO.O
 Temp3!=SFalse
 Temp2!=RoomRecord.First
 If Temp2! Then
    Do While Lost.Carrier=False
       Call Read.Record(RoomInvFile,Temp2!)
       If MessWorkRecord6.Room=SFalse Then
          Exit Do
       Endif
       Temp6!=MessWorkRecord6.Next
       VarX!=MessWorkRecord6.Index
       If VarX!>SFalse Then
          If VarX!>SFalse And VarX!<=Lof(TreasureFile)/TreasureRecLen Then
             Temp3!=Temp3!+1!
          Endif
       Endif
       If Temp6!=SFalse Then
          Exit Do
       Endif
       Temp2!=Temp6!
    Loop
 Endif
 Strng="Treasure:"+Str$(Temp3!)+"."
 Call IO.O
 Temp3!=SFalse
 Temp5!=RoomRecord.First2
 If Temp5! Then
    Do While Lost.Carrier=False
       Call Read.Record(ContainerFile,Temp5!)
       Var6!=ContainerRecord.Next
       If ContainerRecord.WithinContainer=SFalse Then
          If ContainerRecord.DeletedContainer=False Then
             Temp3!=Temp3!+1!
          Endif
       Endif
       If Var6!=SFalse Then
          Exit Do
       Endif
       Temp5!=Var6!
    Loop
 Endif
 Strng="Containers:"+Str$(Temp3!)+"."
 Call IO.O
 Call More.Prompt
Error.Resume0a:
 Exit Sub
Error.Trap0a:
 Resume Error.Resume0a
End Sub

Sub Add.Action
 On Local Error Goto Error.Trap0b
 Strng="Enter action number(0-"+ _
 Mid$(Str$(Lof(ActionFile)/ActionRecLen),2)+")? "
 Call IO.I
 Temp2!=Int(Val(Out2))
 If Temp2!=0! Then
    RoomRecord.Action=0!
    Strng="Action removed from room"+Str$(Room)+"."
 Else
    If Temp2!>SFalse And Temp2!<=Lof(ActionFile)/ActionRecLen Then
       RoomRecord.Action=Temp2!
       Strng="Action number"+Str$(Temp2!)+" added to room"+Str$(Room)+"."
    Else
       Strng="Action number not found."
    Endif
 Endif
 Call IO.O
Error.Resume0b:
 Exit Sub
Error.Trap0b:
 Resume Error.Resume0b
End Sub

Sub Edit.Description
 On Local Error Goto Error.Trap0c
 Gosub Get.Config2
 Do While Lost.Carrier=False
    Graphics.Off=False
    Strng="Room description edit options:"
    Call IO.O
    Graphics.Off=True
    If Option1 Then
       Strng="[D]isplay description"
    Else
       Strng="[*]isplay description"
    Endif
    Call IO.O
    If Option2 Then
       Strng="[L]ong description"
    Else
       Strng="[*]ong description"
    Endif
    Call IO.O
    If Option3 Then
       Strng="[S]hort description"
    Else
       Strng="[*]hort description"
    Endif
    Call IO.O
    Graphics.Off=False
    Strng="Room description option(q to quit)? "
    No.Input.Out="Q"
    Call IO.I
    Select Case Ucase$(Out2)
    Case "D"
       If Option1=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option1 Then
          Graphics.Off=False
          Strng="Current short description:"
          Call IO.O
          Graphics.Off=True
          Strng=RoomRecord.ShortDesc
          Var=Instr(Strng,Chr$(0))
          If Var Then
             Strng=Left$(Strng,Var-1)
          Endif
          Strng=Rtrim$(Strng)
          If Strng=Nul Then
             Strng="<none>"
          Endif
          Call IO.O
          Call More.Prompt
          Graphics.Off=False
          Strng="Current long description:"
          Call IO.O
          TempZ=False
          Graphics.Off=True
          For TempQ=19 To 1 Step -1
             If RoomRecord.LongDesc(TempQ)>SFalse Then
                Exit For
             Endif
          Next
          For TempY=1 To TempQ
             TempR!=RoomRecord.LongDesc(TempY)
             If TempR!>SFalse And TempR!<=Lof(RoomDescFile)/RoomDescLen Then
                Call Read.Record(RoomDescFile,TempR!)
                Strng=BufferRecord.Buffer
                Strng=Rtrim$(Strng)
                TempZ=True
                Call IO.O
             Endif
          Next
          If TempZ=False Then
             Strng="<none>"
             Call IO.O
          Endif
          Call More.Prompt
       Endif
    Case "L"
       If Option2=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option2 Then
          No.Input.Out=Nul
          Line.Length=TempD
          Graphics.Off=False
          Strng="Edit long description(y/n)? "
          Call IO.I
          If Yes Then
             Redim Temp.ArrayS(1 To 19) As String
             For TempY=1 To 19
                Temp.ArrayS(TempY)=Nul
             Next
             Message.Length=False
             For TempY=1 To 19
                TempQ!=RoomRecord.LongDesc(TempY)
                If TempQ!>SFalse And TempQ!<=Lof(RoomDescFile)/RoomDescLen Then
                   Call Read.Record(RoomDescFile,TempQ!)
                   Strng=BufferRecord.Buffer
                   Strng=Rtrim$(Strng)
                   Message.Length=TempY
                   Temp.ArrayS(TempY)=Strng
                Endif
             Next
             Do While Lost.Carrier=False
                Temp0=19
                Call Edit.Message(VarX)
                Select Case VarX
                Case -1 ' continue
                   If Message.Length=19 Then
                      Strng="Description buffer full."
                      Call IO.O
                   Else
                      Strng="Continue editing. Press "+Enter$+" on a blank line to edit."
                      Call IO.O
                      Do While Lost.Carrier=False
                         Graphics.Off=True
                         If Message.Length<19 Then
                            Word.Wrap=True
                         Else
                            Word.Wrap=False
                         Endif
                         Strng="?"
                         Call IO.I
                         If No.Input Then
                            Exit Do
                         Endif
                         Message.Length=Message.Length+1
                         Temp.ArrayS(Message.Length)=Out2
                         If Message.Length=19 Then
                            Strng="Description buffer full."
                            Call IO.O
                            Exit Do
                         Endif
                      Loop
                   Endif
                Case 0 ' abort
                   Exit Do
                Case 1 ' store
                   If Message.Length=0 Then
                      Strng="No message text to store."
                   Else
                      Call Store.Description
                      Strng="Lines written:"+Str$(Message.Length)+"."
                   Endif
                   Call IO.O
                   Exit Do
                End Select
             Loop
          Endif
       Endif
    Case "S"
       If Option3=False Then
          Strng="Option restricted."
          Call IO.O
       Endif
       If Option3 Then
          Graphics.Off=False
          Strng="Enter short description(80 characters):"
          Call IO.O
          Graphics.Off=True
          Strng="Press "+Enter$+" to leave unchanged."
          Call IO.O
          Line.Length=80
          Strng="?"
          Call IO.I
          If No.Input=False Then
             RoomRecord.ShortDesc=Out2
          Endif
       Endif
    Case "Q"
       Exit Do
    End Select
 Loop
 Call Write.Record(RoomFile,Room)
 Exit Sub
Get.Config2:
 Option1=-1
 Option2=-1
 Option3=-1
 Do
    VarX=VarX+1
    If VarX>Options.Lines Then
       Exit Do
    Endif
    Var$=Ltrim$(Rtrim$(Options.Array(VarX)))
    If Ucase$(Var$)="[ROOM]" Then
       Do
          VarX=VarX+1
          If VarX>Options.Lines Then
             Return
          Endif
          Var$=Ltrim$(Rtrim$(Options.Array(VarX)))
          If Ucase$(Var$)="[END]" Then
             Return
          Endif
          Var=Instr(Var$,"=")
          If Var Then
             Var2$=Lcase$(Ltrim$(Rtrim$(Left$(Var$,Var-1))))
             Var3$=Lcase$(Ltrim$(Rtrim$(Mid$(Var$,Var+1))))
             Select Case Var2$
             Case "display.desc"
                Select Case Var3$
                Case "0", "false", "off"
                   Option1=0
                End Select
             Case "edit.long.desc"
                Select Case Var3$
                Case "0", "false", "off"
                   Option2=0
                End Select
             Case "edit.short.desc"
                Select Case Var3$
                Case "0", "false", "off"
                   Option3=0
                End Select
             End Select
          Endif
       Loop
    Endif
 Loop
 Return
Error.Resume0c:
 Exit Sub
Error.Trap0c:
 Resume Error.Resume0c
End Sub

Sub Edit.Monclass
 On Local Error Goto Error.Trap0d
 Strng="Enter monster class(0-"+ _
 Mid$(Str$(Lof(MonClassFile)/MonClassRecLen),2)+")? "
 Call IO.I
 Temp2!=Int(Val(Out2))
 If Temp2!=0! Then
    RoomRecord.MonClass=0!
    Strng="Monster class removed from room."
 Else
    If Temp2!>SFalse And Temp2!<=Lof(MonClassFile)/MonClassRecLen Then
       RoomRecord.MonClass=Temp2!
       Strng="Monster class"+Str$(Temp2!)+" added to room"+Str$(Room)+"."
    Else
       Strng="Monster class not found."
    Endif
 Endif
 Call IO.O
Error.Resume0d:
 Exit Sub
Error.Trap0d:
 Resume Error.Resume0d
End Sub

Sub Edit.Objects
 On Local Error Goto Error.Trap0e
 Do While Lost.Carrier=False
    Graphics.Off=True
    Strng="[A]dd"
    Call IO.O
    Strng="[D]elete"
    Call IO.O
    Strng="[L]ist"
    Call IO.O
    Graphics.Off=False
    Strng="Room object edit option(q to quit)? "
    No.Input.Out="Q"
    Call IO.I
    Select Case Ucase$(Out2)
    Case "A"
       VarQ=False
       Call Find.Object
       If TempD! Then
          Temp2!=Lof(RoomInvFile)/MessWorkRecLen6+1!
          MessWorkRecord6.Room=Room
          MessWorkRecord6.User=SFalse
          MessWorkRecord6.Index=-TempD!
          MessWorkRecord6.Charges=False
          MessWorkRecord6.Plus=False
          Call Add.List.Node(Temp2!)
          VarQ=True
       Endif
       If VarQ=True Then
          Strng="Object added to room."
       Else
          Strng="Object not added to room."
       Endif
       Call IO.O
    Case "D"
       Strng="Object number to delete? "
       No.Input.Out="1"
       Call IO.I
       VarQ=False
       Temp2!=Int(Val(Out2))
       TempX!=SFalse
       If Temp2!>SFalse And Temp2!<=Lof(RoomInvFile)/MessWorkRecLen6 Then
          Var4!=RoomRecord.First
          If Var4! Then
             Do While Lost.Carrier=False
                Call Read.Record(RoomInvFile,Var4!)
                Var5!=MessWorkRecord6.Next
                If MessWorkRecord6.Index<SFalse Then
                   TempX!=TempX!+1!
                   If TempX!=Temp2! Then
                      Call Delete.List.Node(Var4!)
                      Call Clear.List.Node
                      Call Write.Record(RoomInvFile,Var4!)
                      VarQ=True
                      Exit Do
                   Endif
                Endif
                If Var5!=SFalse Then
                   Exit Do
                Endif
                Var4!=Var5!
             Loop
          Endif
       Endif
       If VarQ=True Then
          Strng="Object deleted from room."
       Else
          Strng="Object not deleted from room."
       Endif
       Call IO.O
    Case "L"
       Allow.Break=True
       Break=False
       Continuous=False
       Graphics.Off=True
       Temp8=False
       Temp4!=RoomRecord.First
       TempX!=SFalse
       If Temp4! Then
          Do While Lost.Carrier=False
             Call Read.Record(RoomInvFile,Temp4!)
             If MessWorkRecord6.Room=SFalse Then
                Exit Do
             Endif
             Temp6!=MessWorkRecord6.Next
             Temp2!=MessWorkRecord6.Index
             If Temp2!<SFalse Then
                Temp2!=Abs(Temp2!)
                If Temp2!>SFalse And Temp2!<=Lof(ObjectFile)/ObjectRecLen Then
                   Call Read.Record(ObjectFile,Temp2!)
                   Out3=Rtrim$(ObjectRecord.ObjectName)
                   TempX!=TempX!+1!
                   Strng=Mid$(Str$(TempX!),2)+"."+Out3
                   If ObjectRecord.Invisible Then
                      Strng=Strng+" [inv]"
                   Endif
                   Call IO.O
                   If Break Then
                      Exit Do
                   Endif
                   Temp8=Temp8+1
                   If Temp8>=User.Pagelength-2 Then
                      Temp8=False
                      If Continuous=False Then
                         Call More.Prompt
                         If No Or Quit Then
                            Exit Do
                         Endif
                      Endif
                   Endif
                Endif
             Endif
             If Temp6!=SFalse Then
                Exit Do
             Endif
             Temp4!=Temp6!
          Loop
       Endif
       Allow.Break=False
       Break=False
       If Temp8 Then
          Call More.Prompt
       Endif
    Case "Q"
       Exit Do
    End Select
 Loop
Error.Resume0e:
 Exit Sub
Error.Trap0e:
 Resume Error.Resume0e
End Sub

Sub Edit.Treasure
 On Local Error Goto Error.Trap0f
 Do While Lost.Carrier=False
    Graphics.Off=True
    Strng="[A]dd"
    Call IO.O
    Strng="[D]elete"
    Call IO.O
    Strng="[L]ist
    Call IO.O
    Graphics.Off=False
    Strng="Room treasure edit option(q to quit)? "
    No.Input.Out="Q"
    Call IO.I
    Select Case Ucase$(Out2)
    Case "A"
       VarQ=False
       Call Find.Treasure
       If TempC! Then
          If TreasureRecord.Container=False Then
             Temp!=Lof(RoomInvFile)/MessWorkRecLen6+1!
             MessWorkRecord6.Room=Room
             MessWorkRecord6.User=SFalse
             MessWorkRecord6.Index=TempC!
             MessWorkRecord6.Charges=TreasureRecord.Charges
             MessWorkRecord6.Plus=False
             Call Add.List.Node(Temp!)
             VarQ=True
          Endif
       Endif
       If VarQ Then
          Strng="Treasure added to room."
       Else
          Strng="Treasure not added to room."
       Endif
       Call IO.O
    Case "D"
       Strng="Treasure number to delete? "
       No.Input.Out="1"
       Call IO.I
       VarQ=False
       Temp2!=Int(Val(Out2))
       TempX!=SFalse
       If Temp2!>SFalse And Temp2!<=Lof(RoomInvFile)/MessWorkRecLen6 Then
          Var4!=RoomRecord.First
          If Var4! Then
             Do While Lost.Carrier=False
                Call Read.Record(RoomInvFile,Var4!)
                Var5!=MessWorkRecord6.Next
                If MessWorkRecord6.Index>SFalse Then
                   TempX!=TempX!+1!
                   If TempX!=Temp2! Then
                      Call Delete.List.Node(Var4!)
                      Call Clear.List.Node
                      Call Write.Record(RoomInvFile,Var4!)
                      VarQ=True
                      Exit Do
                   Endif
                Endif
                If Var5!=SFalse Then
                   Exit Do
                Endif
                Var4!=Var5!
             Loop
          Endif
       Endif
       If VarQ=True Then
          Strng="Treasure deleted from room."
       Else
          Strng="Treasure not deleted from room."
       Endif
       Call IO.O
    Case "L"
       Allow.Break=True
       Break=False
       Continuous=False
       Graphics.Off=True
       Temp8=False
       Temp4!=RoomRecord.First
       TempX!=SFalse
       If Temp4! Then
          Do While Lost.Carrier=False
             Call Read.Record(RoomInvFile,Temp4!)
             If MessWorkRecord6.Room=SFalse Then
                Exit Do
             Endif
             Temp6!=MessWorkRecord6.Next
             Temp2!=MessWorkRecord6.Index
             If Temp2!>SFalse And Temp2!<=Lof(TreasureFile)/TreasureRecLen Then
                Call Read.Record(TreasureFile,Temp2!)
                TempX!=TempX!+1!
                Out3=Rtrim$(TreasureRecord.TreasureName)
                Strng=Mid$(Str$(TempX!),2)+"."+Out3
                If TreasureRecord.Plus Then
                   Strng=Strng+" (+"+Mid$(Str$(TreasureRecord.Plus),2)+")"
                Endif
                If MessWorkRecord6.Charges Then
                   Strng=Strng+" (charges:"+Str$(MessWorkRecord6.Charges)+")"
                Endif
                If TreasureRecord.Invisible Then
                   Strng=Strng+" [inv]"
                Endif
                Call IO.O
                If Break Then
                   Exit Do
                Endif
                Temp8=Temp8+1
                If Temp8>=User.Pagelength-2 Then
                   Temp8=False
                   If Continuous=False Then
                      Call More.Prompt
                      If No Or Quit Then
                         Exit Do
                      Endif
                   Endif
                Endif
             Endif
             If Temp6!=SFalse Then
                Exit Do
             Endif
             Temp4!=Temp6!
          Loop
       Endif
       Allow.Break=False
       Break=False
       If Temp8 Then
          Call More.Prompt
       Endif
    Case "Q"
       Exit Do
    End Select
 Loop
Error.Resume0f:
 Exit Sub
Error.Trap0f:
 Resume Error.Resume0f
End Sub

Sub Edit.Room.Containers
 On Local Error Goto ErrResume18a
 Do While Lost.Carrier=False
    Graphics.Off=True
    If TempC=False Then
       Strng="[A]dd"
       Call IO.O
       Strng="[D]elete"
       Call IO.O
       Strng="[L]ist"
       Call IO.O
       Graphics.Off=False
    Endif
    Strng="Room container edit option(q to quit)? "
    Line.Length=TempD
    No.Input.Out="Q"
    Call IO.I
    Select Case Ucase$(Out2)
    Case "A"
       VarQ=False
       Call Find.Treasure
       If TempC! Then
          If TreasureRecord.Container Then
             Temp!=Room
             Call Add.Container.Room(TempC!)
             VarQ=True
          Endif
       Endif
       If VarQ=True Then
          Strng="Container added to room."
       Else
          Strng="Container not added to room."
       Endif
       Call IO.O
    Case "D"
       Strng="Number to delete? "
       No.Input.Out="0"
       Call IO.I
       VarQ=False
       Temp2!=Int(Val(Out2))
       TempX!=SFalse
       If Temp!>=SFalse And Temp!<=Lof(ContainerFile)/ContainerRecLen Then
          Var4!=RoomRecord.First2
          If Var4! Then
             Do While Lost.Carrier=False
                Call Read.Record(ContainerFile,Var4!)
                Var5!=ContainerRecord.Next
                If ContainerRecord.WithinContainer=SFalse Then
                   If ContainerRecord.DeletedContainer=False Then
                      TempX!=TempX!+1!
                      If TempX!=Temp2! Then
                         Call Delete.Room.Container(Var4!,Room)
                         Call Clear.Container.Node
                         Call Write.Record(ContainerFile,Var4!)
                         VarQ=True
                         Exit Do
                      Endif
                   Endif
                Endif
                If Var5!=SFalse Then
                   Exit Do
                Endif
                Var4!=Var5!
             Loop
          Endif
       Endif
       If VarQ=True Then
          Strng="Container deleted from room."
       Else
          Strng="Container not deleted from room."
       Endif
       Call IO.O
    Case "L"
       Graphics.Off=True
       VarZ=False
       Allow.Break=True
       Break=False
       Continuous=False
       Temp5!=RoomRecord.First2
       TempX!=SFalse
       If Temp5! Then
          Do While Lost.Carrier=False
             Call Read.Record(ContainerFile,Temp5!)
             Var6!=ContainerRecord.Next
             If ContainerRecord.WithinContainer=SFalse Then
                If ContainerRecord.DeletedContainer=False Then
                   Out3=ContainerRecord.ContainerName
                   Out3=Rtrim$(Out3)
                   Out3=Lcase$(Out3)
                   TempX!=TempX!+1!
                   Strng=Mid$(Str$(TempX!),2)+"."+Out3
                   If ContainerRecord.InvisibleContainer Then
                      Strng=Strng+" [inv]"
                   Endif
                   Call IO.O
                   If Break Then
                      Exit Do
                   Endif
                   VarZ=VarZ+1
                   If VarZ>=User.Pagelength-2 Then
                      VarZ=False
                      If Continuous=False Then
                         Call More.Prompt
                         If No Or Quit Then
                            Exit Do
                         Endif
                      Endif
                   Endif
                Endif
             Endif
             If Var6!=SFalse Then
                Exit Do
             Endif
             Temp5!=Var6!
          Loop
       Endif
       Allow.Break=False
       If VarZ Then
          Call More.Prompt
       Endif
    Case "Q"
       Exit Do
    End Select
 Loop
ErrExit18a:
 Exit Sub
ErrResume18a:
 Resume ErrExit18a
End Sub

Sub Find.Treasure
 On Local Error Goto ErrResume103
 TempC!=SFalse
 Strng="Treasure name, or number"
 Strng=Strng+"(1-"+Mid$(Str$(Lof(TreasureFile)/TreasureRecLen),2)+")? "
 No.Input.Out="0"
 Call IO.I
 If Out2=Nul Then
    Exit Sub
 Endif
 Out2=Lcase$(Out2)
 Temp7!=SFalse
 If Instr(Out2,"#") Then
    Temp7!=Val(Mid$(Out2,Instr(Out2,"#")+1))
    Out2=Left$(Out2,Instr(Out2,"#")-1)
 Endif
 TempQ!=SFalse
 For Var2!=1! To Lof(TreasureFile)/TreasureRecLen
    Call Read.Record(TreasureFile,Var2!)
    Strng=Rtrim$(TreasureRecord.TreasureName)
    Var3$=Out2
    Call InstrSUB4(VarX,Var3$,0)
    If VarX Then
       TempQ!=TempQ!+1!
       If Temp7!=SFalse Or TempQ!=Temp7! Then
          Goto Exit103
       Endif
    Endif
 Next
 Var2!=Int(Val(Out2))
 If Var2!<=SFalse Or Var2!>Lof(TreasureFile)/TreasureRecLen Then
    Var2!=SFalse
    Strng="Treasure name not found."
    Call IO.O
 Else
    Call Read.Record(TreasureFile,Var2!)
 Endif
Exit103:
 TempC!=Var2!
ErrExit103:
 Exit Sub
ErrResume103:
 Resume ErrExit103
End Sub

Sub Find.Object
 On Local Error Goto ErrResume105
 TempD!=SFalse
 Strng="Object name, or number"
 Strng=Strng+"(1-"+Mid$(Str$(Lof(ObjectFile)/ObjectRecLen),2)+")? "
 No.Input.Out="0"
 Call IO.I
 If Out2=Nul Then
    Exit Sub
 Endif
 Out2=Lcase$(Out2)
 Temp7!=SFalse
 If Instr(Out2,"#") Then
    Temp7!=Val(Mid$(Out2,Instr(Out2,"#")+1))
    Out2=Left$(Out2,Instr(Out2,"#")-1)
 Endif
 TempQ!=SFalse
 For Var2!=1! To Lof(ObjectFile)/ObjectRecLen
    Call Read.Record(ObjectFile,Var2!)
    Strng=Rtrim$(ObjectRecord.ObjectName)
    Var3$=Out2
    Call InstrSUB4(VarX,Var3$,0)
    If VarX Then
       TempQ!=TempQ!+1!
       If Temp7!=SFalse Or TempQ!=Temp7! Then
          Goto Exit105
       Endif
    Endif
 Next
 Var2!=Int(Val(Out2))
 If Var2!<=SFalse Or Var2!>Lof(ObjectFile)/ObjectRecLen Then
    Var2!=SFalse
    Strng="Object name not found."
    Call IO.O
 Else
    Call Read.Record(ObjectFile,Var2!)
 Endif
Exit105:
 TempD!=Var2!
ErrExit105:
 Exit Sub
ErrResume105:
 Resume ErrExit105
End Sub

Sub Clear.Container.Node
 On Local Error Goto ErrorTrp32c
 ContainerRecord.UserNumber=SFalse
 ContainerRecord.RoomNumber=SFalse
 ContainerRecord.DeletedContainer=True
 ContainerRecord.Prev=SFalse
 ContainerRecord.Next=SFalse
ErrorRsm32c:
 Exit Sub
ErrorTrp32c:
 Resume ErrorRsm32c
End Sub

Sub Add.Container.Room(Var2!)
 On Local Error Goto ErrResume141f
 VarA!=Lof(ContainerFile)/ContainerRecLen+1!
 Call Clear.Container
 Strng="Invisible container(y/n)? "
 No.Input.Out="N"
 Call IO.I
 ContainerRecord.InvisibleContainer=Yes
 For VarR=1 To 3
    ContainerRecord.RestrictItem(VarR)=TreasureRecord.RestrictItem(VarR)
 Next
 ContainerRecord.ContainerName=TreasureRecord.TreasureName
 ContainerRecord.ContainerShort=TreasureRecord.ShortName
 ContainerRecord.ContainerMax=TreasureRecord.ContainerMax
 ContainerRecord.NamePrefix=TreasureRecord.ContainerPrefix
 ContainerRecord.Prefix1=TreasureRecord.Prefix1
 ContainerRecord.Size=TreasureRecord.ContainerSize
 ContainerRecord.Material=TreasureRecord.ContainerMaterial
 If TreasureRecord.KeyNumber Then
    ContainerRecord.KeyNumber=TreasureRecord.KeyNumber
    ContainerRecord.Closed=True
    ContainerRecord.Locked=True
 Endif
 If TreasureRecord.Locked Then
    ContainerRecord.Closed=True
    ContainerRecord.Locked=True
 Endif
 ContainerRecord.RoomNumber=Room
 ContainerRecord.UserNumber=SFalse
 ContainerRecord.WithinContainer=SFalse
 ContainerRecord.Weight=TreasureRecord.Weight
 ContainerRecord.ContainerIndex=Var2!
 ContainerRecord.Disappears=TreasureRecord.ContainerDisappears
 ContainerRecord.SelfImplodes=TreasureRecord.ContainerSelfImplodes
 ContainerRecord.Permanent=TreasureRecord.Permanent
 ContainerRecord.First=SFalse
 ContainerRecord.Last=SFalse
 ContainerRecord.SwapFlag=SFalse
 ContainerRecord.Scanned=False
 Call Write.Record(ContainerFile,VarA!)
 ' add container to rooms.dat list
 Call Read.Record(RoomFile,Temp!)
 If RoomRecord.First2=SFalse Then
    RoomRecord.First2=VarA!
    RoomRecord.Last2=VarA!
    Call Write.Record(RoomFile,Temp!)
    ContainerRecord.Prev=SFalse
    ContainerRecord.Next=SFalse
    Call Write.Record(ContainerFile,VarA!)
 Else
    ContainerRecord.Prev=RoomRecord.Last2
    ContainerRecord.Next=SFalse
    Call Write.Record(ContainerFile,VarA!)
    Call Read.Record(ContainerFile,RoomRecord.Last2)
    ContainerRecord.Next=VarA!
    Call Write.Record(ContainerFile,RoomRecord.Last2)
    Call Read.Record(ContainerFile,VarA!)
    RoomRecord.Last2=VarA!
    Call Write.Record(RoomFile,Temp!)
 Endif
ErrExit141f:
 Exit Sub
ErrResume141f:
 Resume ErrExit141f
End Sub

Sub Edit.Message(Var)
 On Local Error Goto Error.Trap44
 Do While Lost.Carrier=False
    Graphics.Off=True
    Strng="[A]bort edit"
    Call IO.O
    Strng="[C]ontinue edit"
    Call IO.O
    Strng="[D]elete lines"
    Call IO.O
    Strng="[E]dit line"
    Call IO.O
    Strng="[H]elp with edit"
    Call IO.O
    Strng="[I]nsert lines"
    Call IO.O
    Strng="[L]ist text"
    Call IO.O
    Strng="[P]refix description"
    Call IO.O
    Strng="[R]eplace line"
    Call IO.O
    Strng="[S]tore text"
    Call IO.O
    Strng="[T]ext search"
    Call IO.O
    Graphics.Off=False
    Strng="Edit option? "
    No.Input.Out="?"
    Call IO.I
    Out2=Ucase$(Out2)
    Select Case Out2
    Case "A"
       Strng="Abort. Are you sure(y/n)? "
       No.Input.Out="N"
       Call IO.I
       If Yes Then
          Var=False
          Exit Do
       Endif
    Case "C"
       Var=True
       Exit Do
    Case "D"
       If Message.Length=False Then
          Strng="Message buffer empty."
          Call IO.O
       Else
          Call Delete.Line
       Endif
    Case "E"
       If Message.Length=False Then
          Strng="Message buffer empty."
          Call IO.O
       Else
          Call Edit.Line
       Endif
    Case "H", "?"
       Stored.Parsed.Command1="MAILEDIT"
       Call Read.Help
    Case "I"
       If Message.Length=False Then
          Strng="Message buffer empty."
          Call IO.O
       Else
          Call Insert.Lines
       Endif
    Case "L"
       If Message.Length=False Then
          Strng="Message buffer empty."
          Call IO.O
       Else
          Call List.Lines
       Endif
    Case "P"
       Graphics.Off=True
       Call Display.ANSI.Prefixes
    Case "R"
       If Message.Length=False Then
          Strng="Message buffer empty."
          Call IO.O
       Else
          Call Replace.Line
       Endif
    Case "S"
       Var=1
       Exit Do
    Case "T"
       If Message.Length=False Then
          Strng="Message buffer empty."
          Call IO.O
       Else
          Call Search.Mess.Text
       Endif
    End Select
 Loop
Error.Resume44:
 Exit Sub
Error.Trap44:
 Resume Error.Resume44
End Sub

Sub List.Lines
 On Local Error Goto ErrResume77
 Line.Length=1
 No.Input.Out="Y"
 Strng="Display line numbers(y/n)? "
 Call IO.I
 TempX=Yes
 Graphics.Off=True
 Allow.Break=True
 Break=False
 For Temp=1 To Message.Length
    Strng=Nul
    If TempX Then
       Strng=Mid$(Str$(Temp),2)+":"
    Endif
    Strng=Strng+Temp.ArrayS(Temp)
    Strng=Left$(Strng,79)
    Call IO.O
    If Break Then
       Exit For
    Endif
 Next
 Allow.Break=False
 Break=False
 Call More.Prompt
ErrExit77:
 Exit Sub
ErrResume77:
 Resume ErrExit77
End Sub

Sub Search.Mess.Text
 On Local Error Goto ErrResume77a
 Strng="Enter search text(?, * allowed): "
 Call IO.I
 If Out2=Nul Then
    Exit Sub
 Endif
 Var3$=Out2
 Strng="Case sensitive(y/n)? "
 Call IO.I
 TmpS=Yes
 If Last.Command.Number=23 Then
    Eat$=""
 Else
    Strng=Rtrim$(RoomRecord.ShortDesc)
    If Len(Strng) Then
       Call InstrSUB4(VarX,Var3$,TmpS)
       If VarX Then
          Strng="Text found in short description."
          Call IO.O
       Endif
    Endif
 Endif
 TempX=False
 Graphics.Off=True
 For Temp=1 To Message.Length
    Strng=Rtrim$(Temp.ArrayS(Temp))
    If Len(Strng) Then
       Call InstrSUB4(VarX,Var3$,TmpS)
       If VarX>0 Then
          Strng2="Text found in line"+Str$(Temp)+" in position"+Str$(VarX)+"."
       Endif
       If VarX=-1 Then
          Strng2="Text found in line"+Str$(Temp)+"."
       Endif
       If VarX Then
          If Last.Command.Number=23 Then
             Eat$=""
          Else
             If TempX=False Then
                Strng="Long description:"
                Call IO.O
             Endif
          Endif
          Strng=Strng2
          TempX=True
          Call IO.O
       Endif
    Endif
 Next
 If TempX=False Then
    If Last.Command.Number=23 Then
       Strng="Text not found."
    Else
       Strng="Long description: Text not found."
    Endif
    Call IO.O
 Endif
 Call More.Prompt
ErrExit77a:
 Exit Sub
ErrResume77a:
 Resume ErrExit77a
End Sub

Sub Replace.Line
 On Local Error Goto ErrResume78
 Strng="Line number"
 Call Get.Range2(1,Message.Length,Temp)
 If Temp Then
    Strng="Replacement line:"
    Call IO.O
    Strng="?"
    Call IO.I
    Var$=Out2
    If Var$=Nul Then
       Strng="Erase line(y/n)? "
       No.Input.Out="N"
       Call IO.I
       If No Then
          Exit Sub
       Endif
    Endif
    Temp.ArrayS(Temp)=Var$
    If Var$=Nul Then
       Strng="Line number"+Str$(Temp)+" erased."
    Else
       Strng="Line number"+Str$(Temp)+" replaced."
    Endif
    Call IO.O
 Endif
ErrExit78:
 Exit Sub
ErrResume78:
 Resume ErrExit78
End Sub

Sub Edit.Line
 On Local Error Goto ErrResume79
 Strng="Line number"
 Call Get.Range2(1,Message.Length,Temp)
 If Temp=0 Then
    Exit Sub
 Endif
 Strng="Replace what word? "
 Call IO.I
 Temp$=Out2
 If No.Input Then
    Strng="No changes made."
    Call IO.O
    Exit Sub
 Endif
 Strng="Replace with what word? "
 Call IO.I
 Temp2$=Out2
 If Temp$=Nul Or Temp$=Temp2$ Then
    Strng="No changes made."
    Call IO.O
    Exit Sub
 Endif
 Strng="Replace all occurences(y/n)? "
 No.Input.Out="Y"
 Call IO.I
 Var$=Temp.ArrayS(Temp)
 Var$=Rtrim$(Var$)
 Temp1=1
 Temp2=False
 Temp3=Yes
 Do While Lost.Carrier=False
    If Var$=Nul Then
       Exit Do
    Endif
    Var1=Instr(Temp1,Var$,Temp$)
    If Var1=False Then
       Exit Do
    Endif
    Var$=Left$(Var$,Var1-1)+Temp2$+Mid$(Var$,Var1+Len(Temp$))
    Var$=Left$(Var$,80)
    Temp1=Temp1+Len(Temp2$)
    Temp2=Temp2+1
    If Temp2=1 Then
       If Temp3=False Then
          Exit Do
       Endif
    Endif
 Loop
 Temp.ArrayS(Temp)=Var$
 If Temp2 Then
    If Temp2=1 Then
       Strng=Mid$(Str$(Temp2),2)+" change made."
    Else
       Strng=Mid$(Str$(Temp2),2)+" changes made."
    Endif
 Else
    Strng="No changes made."
 Endif
 Call IO.O
ErrExit79:
 Exit Sub
ErrResume79:
 Resume ErrExit79
End Sub

Sub Delete.Line
 On Local Error Goto ErrResume80
 Call Get.Range(Temp,Temp2,Message.Length)
 For Temp3=1 To Temp2-Temp+1
    Message.Length=Message.Length-1
    For Temp1=Temp To Message.Length
       Temp.ArrayS(Temp1)=Temp.ArrayS(Temp1+1)
    Next
 Next
 If Message.Length=False Then
    Strng="No message left."
    Call IO.O
    Exit Sub
 Endif
 Strng="Line numbers"+Str$(Temp)+" to"+Str$(Temp2)+" deleted."
 Call IO.O
ErrExit80:
 Exit Sub
ErrResume80:
 Resume ErrExit80
End Sub

' fixed for casino 04/10/2020
Sub Insert.Lines
 On Local Error Goto ErrResume81
 If Last.Command.Number=23 Then
    Var1=Temp0
    If Var1<=0 Or Var1>19 Then
       Var1=19
    Endif
 Else
    Var1=19
 Endif
 If Message.Length>=Var1 Then
    Strng="Message buffer full."
    Call IO.O
    Exit Sub
 Endif
 VarX=0
 Strng="Before line number"
 Call Get.Range2(1,Message.Length,Temp)
 Graphics.Off=True
 Do While Lost.Carrier=False
    If Message.Length>=Var1 Then
       Exit Do
    Endif
    Strng="?"
    Call IO.I
    If No.Input Then
       Exit Do
    Endif
    For Temp1=Message.Length To Temp Step -1
       Temp.ArrayS(Temp1+1)=Temp.ArrayS(Temp1)
    Next
    VarX=VarX+1
    Temp.ArrayS(Temp)=Out2
    Temp=Temp+1
    Message.Length=Message.Length+1
 Loop
 Strng="Inserted"+Str$(VarX)+" lines."
 Call IO.O
 Graphics.Off=False
 If Message.Length>=Var1 Then
    Strng="Message buffer full."
    Call IO.O
 Endif
 Call More.Prompt
ErrExit81:
 Exit Sub
ErrResume81:
 Resume ErrExit81
End Sub

Sub Store.Description
 On Local Error Goto ErrResume16a
 For TempZ=1 To Message.Length
    TempQ!=RoomRecord.LongDesc(TempZ)
    If TempQ!>SFalse And TempQ!<=Lof(RoomDescFile)/RoomDescLen Then
       Call Read.Record(RoomDescFile,TempQ!)
       BufferRecord.Buffer=Temp.ArrayS(TempZ)
       Call Write.Record(RoomDescFile,TempQ!)
    Else
       TempQ!=Lof(RoomDescFile)/RoomDescLen+1!
       RoomRecord.LongDesc(TempZ)=TempQ!
       BufferRecord.Buffer=Temp.ArrayS(TempZ)
       Call Write.Record(RoomDescFile,TempQ!)
    Endif
 Next
ErrExit16a:
 Exit Sub
ErrResume16a:
 Resume ErrExit16a
End Sub

Sub Get.Range(Var1,Var2,VarX)
 On Local Error Goto ErrResume134
 Strng="Enter range:"
 Call IO.O
 Var$=Mid$(Str$(VarX),2)
 If VarX=False Then
    Strng="From(0-"+Var$+")? "
 Else
    Strng="From(1-"+Var$+")? "
 Endif
 No.Input.Out="1"
 Call IO.I
 Var1=Int(Val(Out2))
 If Var1<1 Then
    Var1=1
 Endif
 If Var1>VarX Then
    Var1=VarX
 Endif
 Strng="To("+Mid$(Str$(Var1),2)+"-"+Var$+")? "
 No.Input.Out=Var$
 Call IO.I
 Var2=Int(Val(Out2))
 If Var2<Var1 Then
    Var2=Var1
 Endif
 If Var2>VarX Then
    Var2=VarX
 Endif
ErrExit134:
 Exit Sub
ErrResume134:
 Resume ErrExit134
End Sub

Sub Get.Range2(Var1,Var2,VarX)
 On Local Error Goto ErrResume135
 Var1$=Mid$(Str$(Var1),2)
 Var2$=Mid$(Str$(Var2),2)
 Strng=Strng+"("+Var1$+"-"+Var2$+")? "
 No.Input.Out=Var1$
 Call IO.I
 VarX=Int(Val(Out2))
 If VarX<Var1 Then
    VarX=Var1
 Endif
 If VarX>Var2 Then
    VarX=Var2
 Endif
ErrExit135:
 Exit Sub
ErrResume135:
 Resume ErrExit135
End Sub

Sub Read.Help
 On Local Error Goto Error.Trap30a
 Graphics.Off=True
 Temp$=Stored.Parsed.Command1
 Temp$=Rtrim$(Temp$)
 Temp$=Ucase$(Temp$)
 Temp$=Left$(Temp$,8)
 Close #HelpFile2
 Open Help.FileName2 For Random Shared As #HelpFile2 Len=Len(HelpRecord2)
 Temp=1
 Temp5=False
 Allow.Break=True
 Break=False
 Continuous=False
 Do While Lost.Carrier=False
    Temp=Temp+1
    Call Read.Helpfile(HelpFile2,Temp)
    Temp2$=HelpRecord2.CommandName
    Temp2$=Rtrim$(Temp2$)
    If Left$(Temp2$,Len(Temp$))=Temp$ Then
       Strng=HelpRecord2.Text
       Strng=Rtrim$(Strng)
       Call IO.O
       If Break Then
          Exit Do
       Endif
       Temp5=Temp5+1
       If Temp5>=User.Pagelength-2 Then
          Temp5=False
          If Continuous=False Then
             Call More.Prompt
             If No Or Quit Then
                Exit Do
             Endif
          Endif
       Endif
    Endif
    If Temp>Lof(HelpFile2)/HelpRecLen2 Then
       Exit Do
    Endif
 Loop
 If Temp5 Then
    Call More.Prompt
 Endif
 Allow.Break=False
 Break=False
 Graphics.Off=False
Error.Resume30a:
 Exit Sub
Error.Trap30a:
 Resume Error.Resume30a
End Sub

' function to match case-sensitive substring with ?, * characters in substring
SUB InstrSUB4(Var,Var$,VarQ)

' see if Var$ matches in Strng
On Local Error Goto ErrorTrap24x5

' store case-sensitive string match variables
If VarQ Then
   S2$ = Var$
   S3$ = Strng
Else
   S2$ = Lcase$(Var$)
   S3$ = Lcase$(Strng)
Endif

' check default instr
IF INSTR(S2$, "*") = 0 THEN
   IF INSTR(S2$, "?") = 0 THEN
      Var = INSTR(S3$, S2$)
      EXIT SUB
   END IF
END IF

Var = -1 ' assume match

' see if S2$ matches in S3$ with substrings
FOR S3 = 1 TO LEN(S3$)
   S1$ = MID$(S3$, S3)
   P1 = 1 ' pointer to S1$
   P2 = 1 ' pointer to S2$
   P3 = S3 ' position match
   DO
      ' check match
      IF P2 > LEN(S2$) THEN
         Var = P3
         EXIT SUB
      END IF

      ' check character in S2$ at P2
      V$ = MID$(S2$, P2, 1)
      SELECT CASE V$
      CASE "*" ' global character
         ' scan to next char
         IF P2 > LEN(S2$) THEN
            EXIT DO
         END IF
         S4$ = MID$(S2$, P2 + 1, 1)
         SELECT CASE S4$
         CASE "*", "?"
            P2 = P2 + 1
         CASE ELSE
            DO
               IF MID$(S1$, P1, 1) = S4$ THEN
                  EXIT DO
               END IF
               IF P1 >= LEN(S1$) THEN
                  EXIT DO
               END IF
               P1 = P1 + 1
            LOOP
            P3 = P1
            P2 = P2 + 1
         END SELECT
      CASE "?" ' wildcard character
         P1 = P1 + 1
         P2 = P2 + 1
      CASE ELSE ' ascii character
         IF MID$(S1$, P1, 1) <> V$ THEN ' no match
            EXIT DO
         END IF
         P1 = P1 + 1
         P2 = P2 + 1
      END SELECT
   LOOP
NEXT
Var = 0 ' no match
EXIT SUB
ErrorResume24x5:
 Exit Sub
ErrorTrap24x5:
 Resume ErrorResume24x5
End Sub
