11Imports System.ComponentModel
22Imports System.Formats.Tar
33Imports System.IO
4+ Imports System.Text.RegularExpressions
45Imports System.Windows.Forms.VisualStyles.VisualStyleElement
6+ Imports Windows.Win32.UI.Input
57
68Public Class frmMain
79
@@ -262,13 +264,22 @@ Public Class frmMain
262264
263265 'Add only the supported files to the process queue
264266 For Each file In files
265- If file.EndsWith( ".bas" , StringComparison.OrdinalIgnoreCase) OrElse
267+ If optRenumber.Checked Then
268+ If file.EndsWith( ".bas" , StringComparison.OrdinalIgnoreCase) Then
269+ txtLog.Text &= "Renumbering " & file & vbCrLf
270+ ChangeLineNumbers(file, numStart.Value, numStep.Value, file)
271+ Else
272+ txtLog.Text &= "Unsupported " & file & vbCrLf
273+ End If
274+ Else
275+ If file.EndsWith( ".bas" , StringComparison.OrdinalIgnoreCase) OrElse
266276 file.EndsWith( ".wav" , StringComparison.OrdinalIgnoreCase) OrElse
267277 file.EndsWith( ".mp3" , StringComparison.OrdinalIgnoreCase) Then
268- filesToPrcess.Add(file)
269- txtLog.Text &= "Will process " & file & vbCrLf
270- Else
271- txtLog.Text &= "Unsupported " & file & vbCrLf
278+ filesToPrcess.Add(file)
279+ txtLog.Text &= "Will process " & file & vbCrLf
280+ Else
281+ txtLog.Text &= "Unsupported " & file & vbCrLf
282+ End If
272283 End If
273284 Next
274285
@@ -289,6 +300,9 @@ Public Class frmMain
289300
290301 'Load settings
291302 cmbPcModel.Text = My.Settings.pcModel
303+ txtFileName.Text = My.Settings.sharpFileName
304+ numStart.Value = My.Settings.startLine
305+ numStep.Value = My.Settings.stepLine
292306
293307 If My.Settings.outputFormat = 1 Then
294308 optMp3.Checked = True
@@ -305,8 +319,11 @@ Public Class frmMain
305319 Else
306320 optFromFilename.Checked = True
307321 End If
308-
309- txtFileName.Text = My.Settings.sharpFileName
322+ If My.Settings.operation = 1 Then
323+ optRenumber.Checked = True
324+ Else
325+ optConvert.Checked = True
326+ End If
310327 End Sub
311328
312329 Private Sub optUseFilename_CheckedChanged(sender As Object , e As EventArgs) Handles optUseFilename.CheckedChanged
@@ -334,6 +351,9 @@ Public Class frmMain
334351 Private Sub frmMain_Closing(sender As Object , e As CancelEventArgs) Handles MyBase .Closing
335352 'Save settings
336353 My.Settings.pcModel = cmbPcModel.Text
354+ My.Settings.sharpFileName = txtFileName.Text
355+ My.Settings.startLine = numStart.Value
356+ My.Settings.stepLine = numStep.Value
337357
338358 If optMp3.Checked Then
339359 My.Settings.outputFormat = 1
@@ -350,11 +370,134 @@ Public Class frmMain
350370 Else
351371 My.Settings.fileNamePolicy = 0
352372 End If
373+ If optRenumber.Checked Then
374+ My.Settings.operation = 1
375+ Else
376+ My.Settings.operation = 0
377+ End If
353378
354- My.Settings.sharpFileName = txtFileName.Text
355379 End Sub
356380
357381 Private Sub linkWeb_LinkClicked(sender As Object , e As LinkLabelLinkClickedEventArgs) Handles linkWeb.LinkClicked
358382 Process.Start( "explorer.exe" , "https://github.com/SilverGreen93/SharpPocketToolsGUI" )
359383 End Sub
384+
385+ ''' <summary>
386+ ''' Renumber BASIC lines in source files
387+ ''' </summary>
388+ ''' <param name="fileName">Input file name</param>
389+ ''' <param name="start">Start line number</param>
390+ ''' <param name="increment">Increment step</param>
391+ ''' <param name="finalFile">Output file name</param>
392+ Sub ChangeLineNumbers(fileName As String , start As Integer , increment As Integer , finalFile As String )
393+ Dim stream As StreamReader
394+ Dim newLines As New List( Of String )
395+ Dim changedLines As String = ""
396+ Dim matchMap As New Hashtable()
397+ Dim match As Match
398+ Dim lineIndex As Integer = start
399+
400+ 'Read the file line by line, parse each line, create a map between the old line number and the new one.
401+ 'Write each line into a list of lines.
402+ Try
403+ stream = New StreamReader(File.Open(fileName, FileMode.Open, FileAccess.Read))
404+ While Not stream.EndOfStream
405+ Dim line As String = stream.ReadLine()
406+ If lineIndex > 999 Then
407+ txtLog.Text &= vbCrLf & "Error: Line number is greater than 999! Please adjust and retry operation!" & vbCrLf & vbCrLf
408+ Return
409+ End If
410+ match = Regex.Match(line, "^ *[0-9]+" ) 'match the number at the start of the line
411+ If match.Value IsNot "" Then
412+ matchMap.Add(match.Value.Trim(), lineIndex)
413+ Dim newLine = Regex.Replace(line, "^ *[0-9]+" , lineIndex.ToString().PadLeft( 5 ))
414+ newLines.Add(newLine)
415+ lineIndex += increment
416+ Else
417+ 'If line is a comment or empty line, copy as it is.
418+ newLines.Add(line)
419+ End If
420+ End While
421+ stream.Close()
422+ Catch ex As Exception
423+ txtLog.Text &= "Error opening file: " & fileName & vbCrLf & ex.Message & vbCrLf
424+ Return
425+ End Try
426+
427+ 'Parse lines again to find GOTO or GOSUB statements to replace the line numbers
428+ For Each line In newLines
429+ match = Regex.Match(line, "^ *[']" ) 'skip lines starting with comments
430+ If match.Value IsNot "" Then
431+ changedLines &= line & vbCrLf
432+ Continue For
433+ End If
434+ 'The line is not a comment, go ahead
435+
436+ 'Find lines that contain GOTO, GOSUB or THEN
437+ match = Regex.Match(line, "(GOTO|GOSUB|THEN)" , RegexOptions.IgnoreCase)
438+ If match.Value Is "" Then
439+ changedLines &= line & vbCrLf
440+ Continue For
441+ End If
442+ 'The line contains GOTO, GOSUB or THEN, go ahead
443+
444+ match = Regex.Match(line, "(GOTO|GOSUB|THEN) *[0-9]+$" , RegexOptions.IgnoreCase)
445+ If match.Value IsNot "" Then
446+ 'The line contains GOTO, GOSUB or THEN followed by constant line number at the end of line.
447+ Dim line_no As Match = Regex.Match(match.Value, "[0-9]+$" ) 'get the original line number reference
448+ line = Regex.Replace(line, "GOTO *[0-9]+$" , "GOTO " & matchMap(line_no.Value.Trim()), RegexOptions.IgnoreCase)
449+ line = Regex.Replace(line, "GOSUB *[0-9]+$" , "GOSUB " & matchMap(line_no.Value.Trim()), RegexOptions.IgnoreCase)
450+ line = Regex.Replace(line, "THEN *[0-9]+$" , "THEN " & matchMap(line_no.Value.Trim()), RegexOptions.IgnoreCase)
451+ changedLines &= line & vbCrLf
452+ Continue For
453+ End If
454+ 'The line contains GOTO, GOSUB or THEN, but with variable, label, or plain string insted of constant line number
455+
456+ match = Regex.Match(line, "(GOTO|GOSUB|THEN) *"".*""" , RegexOptions.IgnoreCase)
457+ If match.Value IsNot "" Then
458+ 'The line contains GOTO, GOSUB or THEN with a label, it is safe to copy unchanged.
459+ changedLines &= line & vbCrLf
460+ Continue For
461+ End If
462+
463+ match = Regex.Match(line, "(GOTO|GOSUB|THEN) *.*\$" , RegexOptions.IgnoreCase)
464+ If match.Value IsNot "" Then
465+ 'The line contains GOTO, GOSUB or THEN with a string variable ($), it is safe to copy unchanged.
466+ changedLines &= line & vbCrLf
467+ Continue For
468+ End If
469+
470+ match = Regex.Match(line, "^ *[0-9]+" )
471+ txtLog.Text &= vbCrLf & "Warning: At line " & match.Value.Trim() & ": GOTO/GOSUB/THEN with non-constant line number found! Please adjust logic manually!" & vbCrLf & vbCrLf
472+
473+ changedLines &= line & vbCrLf
474+ Next
475+
476+ 'Replace the original file if the Overwrite option is checked.
477+ If optOverwrite.Checked Then
478+ My.Computer.FileSystem.WriteAllText(finalFile, changedLines, False )
479+ Else
480+ If My.Computer.FileSystem.FileExists(finalFile) Then
481+ Dim index As Integer = 1
482+ Do While My.Computer.FileSystem.FileExists( String .Concat(finalFile.AsSpan( 0 , finalFile.Length - 4 ), " (" & index & ").BAS" ))
483+ index += 1
484+ Loop
485+ My.Computer.FileSystem.WriteAllText( String .Concat(finalFile.AsSpan( 0 , finalFile.Length - 4 ), " (" & index & ").BAS" ), changedLines, False )
486+ End If
487+ End If
488+ End Sub
489+
490+ Private Sub optRenumber_CheckedChanged(sender As Object , e As EventArgs) Handles optRenumber.CheckedChanged
491+ If optRenumber.Checked Then
492+ numStart.Enabled = True
493+ numStep.Enabled = True
494+ grpOutput.Enabled = False
495+ grpFilename.Enabled = False
496+ Else
497+ numStart.Enabled = False
498+ numStep.Enabled = False
499+ grpOutput.Enabled = True
500+ grpFilename.Enabled = True
501+ End If
502+ End Sub
360503End Class
0 commit comments