1168 lines
53 KiB
VB.net
1168 lines
53 KiB
VB.net
|
'BEGIN LICENCE "Lynnecence V1"
|
|||
|
'1. pls no bully
|
|||
|
'2. don't pass this software off as your own (covered by clause 1)
|
|||
|
' a. also, don't sell this software (also covered by clause 1)
|
|||
|
'3. if you decide to modify this for others to use, note the following:
|
|||
|
' a. you must change the name and the icon (idk why you'd even want to keep the icon)
|
|||
|
' b. you must express that the initial version is called notepad ultra and is made by lynnear software, and provide a link to the original
|
|||
|
' c. feel free to include the original credits, you don't have to though
|
|||
|
' d. use whatever licence you want for your version
|
|||
|
' e. i'd appreciate being notified of the modified version's existence, but it's not necessary to do so. if you do want to, email me at thecoolone3@hotmail.com
|
|||
|
'4. if you modify it for personal use, then go ahead and do whatever you want, but you still can't sell it
|
|||
|
'5. feel free to rehost this, but provide a link to the original location
|
|||
|
'6. if something is technically allowed by the licence, but it is against the spirit of the licence, don't do it (also covered by clause 1)
|
|||
|
'7. you can't hold me liable if there's damages or whatever (unless you are pet)
|
|||
|
|
|||
|
'if you feel that this licence is too stupid/vague/memeish, use MPL 2.0 instead since that's pretty much what i was going for (sans the whole "YOU MUST INHERIT THIS LICENCE" rubbish)
|
|||
|
'END LICENCE
|
|||
|
|
|||
|
Imports System.IO
|
|||
|
Imports System.Text.RegularExpressions
|
|||
|
Imports System.Text 'saves precious, precious bytes. also it makes my code look cleaner! ~u0
|
|||
|
|
|||
|
Public Class NPUWindow 'NPU is short for Notepad Ultra
|
|||
|
|
|||
|
'i know that "it's self commenting" is a copout, but... well, it kinda is. UpdateFilePicker() obviously updates the file picker. still, i've left comments here and there.
|
|||
|
|
|||
|
'DELICIOUS, DELICIOUS GLOBAL VARIABLES! AAAAHAHAHAHAHAHA! I AM THE BEST PROGRAMMER TO EVER LIIIIIVE!
|
|||
|
|
|||
|
Dim npuLocation As String = Application.StartupPath() 'i'm lazy, sue me
|
|||
|
Dim currentFile As String = ""
|
|||
|
Dim rightClickedFile As String = ""
|
|||
|
Dim Bullet As String
|
|||
|
Dim showSidebar, unsaved, ShowRightClick, AutoBullets, FirstTabPress As Boolean
|
|||
|
Dim checkPrint, IndentLevel As Integer
|
|||
|
|
|||
|
'Dim trueDpiX As Single = CreateGraphics.DpiX 'dpi shit
|
|||
|
'Dim trueDpiY As Single = CreateGraphics.DpiY
|
|||
|
'Dim dpiX = trueDpiX / 100 'for multiplication
|
|||
|
'Dim dpiY = trueDpiY / 100
|
|||
|
Dim MenuBarWidth = 10 'temp
|
|||
|
|
|||
|
Dim encType As System.Text.Encoding
|
|||
|
Dim unableToDetermineEncType As Boolean = False
|
|||
|
|
|||
|
Dim notifyStack As Queue(Of Notification) = New Queue(Of Notification) 'don't remove this, it'll make mustard gas. seriously though it causes notifystack to equal nothing, which gives us a nullreferenceexception at runtime
|
|||
|
|
|||
|
Dim UndoList As LinkedList(Of String) = New LinkedList(Of String) 'oh boy, here we go
|
|||
|
Dim UndoPos As Integer = 0
|
|||
|
|
|||
|
Private basedirectory As String
|
|||
|
Private newfilebg As Boolean = False
|
|||
|
|
|||
|
Public Property basedir() As String
|
|||
|
Get
|
|||
|
Return basedirectory
|
|||
|
End Get
|
|||
|
Private Set(ByVal value As String)
|
|||
|
basedirectory = value
|
|||
|
BaseDirWatch.Path = value
|
|||
|
StatDirectory.ToolTipText = value
|
|||
|
My.Settings.WorkingDirectory = value
|
|||
|
End Set
|
|||
|
End Property
|
|||
|
|
|||
|
Public Property NewFile() As Boolean
|
|||
|
Get
|
|||
|
Return newfilebg
|
|||
|
End Get
|
|||
|
Set(value As Boolean)
|
|||
|
newfilebg = value
|
|||
|
FileInfoToolStripMenuItem.Enabled = Not value
|
|||
|
DuplicateToolStripMenuItem.Enabled = Not value
|
|||
|
DeleteToolStripMenuItem2.Enabled = Not value
|
|||
|
End Set
|
|||
|
End Property
|
|||
|
|
|||
|
Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
|
|||
|
Icon = ProgramIcon()
|
|||
|
NewFile = True
|
|||
|
UndoList.AddLast(TextFileHolder.Text)
|
|||
|
SetDefaultThemes()
|
|||
|
Try
|
|||
|
basedir = My.Settings.WorkingDirectory
|
|||
|
FilePicker.Width = ViewToolStripMenuItem.Width + ViewToolStripMenuItem.Bounds.X + 15
|
|||
|
Find.npu = Me
|
|||
|
FindReplace.npu = Me
|
|||
|
FindCommon.npu = Me 'visual studio will try to tell you that the name can be shortened, but it's a nest of lies
|
|||
|
Settings.npu = Me
|
|||
|
chocolatePuddingOvenTimer.Start()
|
|||
|
|
|||
|
SaveDialogue.InitialDirectory = basedir
|
|||
|
FontPicker.Font = TextFileHolder.Font
|
|||
|
Redraw()
|
|||
|
UpdateFilePicker()
|
|||
|
updateStatusBar()
|
|||
|
RedrawStatusBar()
|
|||
|
|
|||
|
Notify("Welcome!", 3)
|
|||
|
Catch ex As Exception
|
|||
|
If Not My.Computer.FileSystem.DirectoryExists(basedir) Then
|
|||
|
MsgBox("Your working directory is unavailable! Press OK to select a new working directory. For reference, your working directory is currently set as" & vbNewLine & basedir & ".")
|
|||
|
FolderPicker.ShowDialog()
|
|||
|
basedir = FolderPicker.SelectedPath
|
|||
|
My.Settings.WorkingDirectory = basedir
|
|||
|
If basedir = "" Then
|
|||
|
MsgBox("Don't play me like this")
|
|||
|
'GoTo fug 'shhhh... it's our little secret! c;
|
|||
|
End
|
|||
|
End If
|
|||
|
My.Settings.WorkingDirectory = basedir
|
|||
|
UpdateFilePicker()
|
|||
|
Else
|
|||
|
MsgBox("Whoops!" & vbNewLine & "We've run into a bit of a fuckup." & vbNewLine & ex.Message & vbNewLine & "Press F to pay respects, then click OK.", MsgBoxStyle.OkOnly, "You've gone and busted, my good man")
|
|||
|
End If
|
|||
|
Finally
|
|||
|
BaseDirWatch.Path = basedir
|
|||
|
TextFileHolder.Font = My.Settings.Font
|
|||
|
TextFileHolder.WordWrap = My.Settings.WordWrap
|
|||
|
WordWrapToolStripMenuItem.Checked = My.Settings.WordWrap
|
|||
|
showSidebar = Not My.Settings.ShowSidebar
|
|||
|
SidebarToolStripMenuItem_Click(sender, e)
|
|||
|
reloadCurrentTheme()
|
|||
|
CleanOutTextFileHolder()
|
|||
|
Splash_Screen.Hide()
|
|||
|
Splash_Screen.ShowInTaskbar = False
|
|||
|
Splash_Screen.TopMost = False
|
|||
|
Activate()
|
|||
|
SplashKillTimer.Start()
|
|||
|
|
|||
|
If FileToOpen <> "" And FileToOpen IsNot Nothing Then 'for opening files directly (open with ==> npu)
|
|||
|
Dim SelectMe As String = GetFile(FileToOpen)
|
|||
|
For fileIndex = 0 To FilePicker.Items.Count - 1
|
|||
|
If FilePicker.Items(fileIndex).ToString = SelectMe Then
|
|||
|
If My.Computer.FileSystem.FileExists(basedir & SelectMe) Then FilePicker.SelectedIndex = fileIndex
|
|||
|
Exit For
|
|||
|
End If
|
|||
|
Next
|
|||
|
Open_Passed_File.Hide()
|
|||
|
Open_Passed_File.ShowInTaskbar = False
|
|||
|
OPFKillTimer.Start()
|
|||
|
End If
|
|||
|
End Try
|
|||
|
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub UpdateFilePicker()
|
|||
|
FilePicker.Items.Clear()
|
|||
|
Dim filenames = My.Computer.FileSystem.GetFiles(basedir, FileIO.SearchOption.SearchTopLevelOnly, "*.anusberries") 'don't edit this. it's temporary, and avoids the NullReferenceException meme
|
|||
|
If Not basedir.EndsWith("\") Then basedir &= "\" 'basedir *needs* to end with a backslash. if it somehow doesn't, it does now
|
|||
|
Dim files As Boolean = False
|
|||
|
For i = 0 To My.Settings.SupportedExtensions.Count - 1
|
|||
|
Dim ext As String = My.Settings.SupportedExtensions(i)
|
|||
|
filenames = My.Computer.FileSystem.GetFiles(basedir, FileIO.SearchOption.SearchTopLevelOnly, "*." & ext)
|
|||
|
For Each fileName As String In filenames
|
|||
|
If fileName.ToLower.EndsWith(ext) Then FilePicker.Items.Add(fileName.Remove(0, Len(basedir))) 'if the user only wants to open txt files, files with extensions like "txt1" and such will also open. this fixes that.
|
|||
|
files = True 'TODO: not this
|
|||
|
Next
|
|||
|
Next
|
|||
|
FilePicker.Items.Add(" ..\")
|
|||
|
If Not files Then
|
|||
|
'Notify("Directory contains no compatible files", 2)
|
|||
|
StatStatus.Text = "No compatible files"
|
|||
|
End If
|
|||
|
|
|||
|
Dim directoryNames = My.Computer.FileSystem.GetDirectories(basedir, FileIO.SearchOption.SearchTopLevelOnly)
|
|||
|
For Each dirName As String In directoryNames
|
|||
|
FilePicker.Items.Add(" " & dirName.Remove(0, Len(basedir)) & "\") 'add every subdirectory in basedir, and put a space in front of them so they show up first
|
|||
|
Next
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub Redraw() Handles Me.Resize, Me.ResizeEnd 'FIX THIS FOR WEIRD DPI SETTINGS! ensures that everything's the right size to fit in the window.
|
|||
|
Dim TitleBarHeight As Integer = RectangleToScreen(ClientRectangle).Top - Top
|
|||
|
|
|||
|
If showSidebar Then
|
|||
|
FilePicker.Height = ClientRectangle.Height - MenuBar.Height - Notification.Bounds.Height - 3 'thanks to http://stackoverflow.com/a/41018091/4480824 for this one weird ClientRectangle trick
|
|||
|
FilePicker.Top = MenuBar.Height
|
|||
|
TextFileHolder.Height = FilePicker.Height + MenuBar.Height + 3
|
|||
|
TextFileHolder.Width = Width - FilePicker.Width - 15 '*shrugs knowingly*
|
|||
|
TextFileHolder.Left = FilePicker.Width - 1
|
|||
|
TextFileHolder.Top = -1
|
|||
|
TextFileHolder.BorderStyle = BorderStyle.FixedSingle
|
|||
|
Else
|
|||
|
TextFileHolder.Height = ClientRectangle.Height - MenuBar.Height - Notification.Bounds.Height - 3
|
|||
|
TextFileHolder.Width = Width - 15
|
|||
|
TextFileHolder.Left = 0
|
|||
|
TextFileHolder.Top = MenuBar.Height
|
|||
|
TextFileHolder.BorderStyle = BorderStyle.None
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Async Sub ListBox1_SelectedIndexChanged(sender As Object, e As EventArgs) Handles FilePicker.SelectedIndexChanged 'when the user clicks on a file/directory in the filepicker
|
|||
|
If unsaved Then
|
|||
|
BaseDirWatch.EnableRaisingEvents = False ' turn basedirwatch off because it'll try to reselect the file we just saved while it's still saving, which will cause bad things to take place
|
|||
|
Dim response As MsgBoxResult = MsgBox("Save changes made to " & If(NewFile, "new file", """" & currentFile & """") & "?", MsgBoxStyle.YesNoCancel)
|
|||
|
If response = MsgBoxResult.Yes Then
|
|||
|
SaveToolStripMenuItem.PerformClick() 'the save function ends up reenabling basedirwatch, don't worry
|
|||
|
ElseIf response = MsgBoxResult.No Then
|
|||
|
BaseDirWatchReenabler.Start() 'if they don't wanna save, then reenable basedirwatch
|
|||
|
Else
|
|||
|
BaseDirWatch.EnableRaisingEvents = True
|
|||
|
Exit Sub
|
|||
|
'handle cancel
|
|||
|
End If
|
|||
|
End If
|
|||
|
|
|||
|
If IsNothing(FilePicker.SelectedItem) Or FilePicker.SelectedItem = "" Or FilePicker.SelectedItem Is Nothing Then
|
|||
|
Notify("Please select a file or directory.", 2) 'if the user clicks on the blank space at the bottom of the filepicker (which is possible for some reason), shoo them
|
|||
|
reselectCurrentFile() 'already checks to make sure it's not empty
|
|||
|
Else
|
|||
|
Cursor = Cursors.WaitCursor
|
|||
|
Enabled = False
|
|||
|
StatStatus.Text = "Loading..."
|
|||
|
'MsgBox(basedir & FilePicker.SelectedItem.ToString.Substring(1))
|
|||
|
|
|||
|
If FilePicker.SelectedItem.ToString = " ..\" Then 'if you clicked the ..\ item (which means go up)...
|
|||
|
Enabled = True
|
|||
|
Cursor = Cursors.Default
|
|||
|
StatStatus.Text = "No file loaded"
|
|||
|
GoUpToolStripMenuItem.PerformClick() '...click the go up button! ;p
|
|||
|
Else
|
|||
|
If FilePicker.SelectedItem.ToString.EndsWith("\") Then 'if you clicked on a directory
|
|||
|
Try
|
|||
|
If Not My.Computer.FileSystem.DirectoryExists(basedir & FilePicker.SelectedItem.ToString.Substring(1)) Then Throw New DirectoryNotFoundException
|
|||
|
BaseDirWatch.Path = basedir + FilePicker.SelectedItem.ToString.Substring(1) 'cd into it!
|
|||
|
basedir = BaseDirWatch.Path
|
|||
|
CleanOutTextFileHolder()
|
|||
|
Notify("Directory changed", 3)
|
|||
|
ResetUndoList()
|
|||
|
Catch ex As Exception
|
|||
|
Notify("Failed to load directory!", 1)
|
|||
|
CleanOutTextFileHolder()
|
|||
|
ResetUndoList()
|
|||
|
End Try
|
|||
|
Enabled = True
|
|||
|
Cursor = Cursors.Default
|
|||
|
|
|||
|
ElseIf My.Computer.FileSystem.FileExists(basedir & FilePicker.SelectedItem.ToString) Then 'or, if you clicked a file...
|
|||
|
Dim chosenFile As StreamReader
|
|||
|
currentFile = FilePicker.SelectedItem
|
|||
|
Dim fileToLoad As String = basedir & currentFile
|
|||
|
|
|||
|
Dim p As New Process
|
|||
|
p.StartInfo.UseShellExecute = False
|
|||
|
p.StartInfo.RedirectStandardOutput = True
|
|||
|
p.StartInfo.FileName = "dependencies\file\bin\file.exe"
|
|||
|
p.StartInfo.CreateNoWindow = True
|
|||
|
p.StartInfo.Arguments = "-b --mime-encoding """ & basedir & currentFile & """"
|
|||
|
p.Start()
|
|||
|
Dim output As String = p.StandardOutput.ReadToEnd()
|
|||
|
p.WaitForExit() 'firstly, get the encoding.
|
|||
|
unableToDetermineEncType = False
|
|||
|
|
|||
|
output = output.ToLower() 'just to be 1000% sure
|
|||
|
'MsgBox(output)
|
|||
|
|
|||
|
'and now we load that encoding!
|
|||
|
Select Case True 'call the cops, i don't give a fuck
|
|||
|
Case output.Contains("utf-8") 'TODO: find better way of doing this, it's disgusting
|
|||
|
encType = Encoding.UTF8
|
|||
|
Case output.Contains("utf-32")
|
|||
|
encType = Encoding.UTF32
|
|||
|
Case output.Contains("utf-7")
|
|||
|
encType = Encoding.UTF7
|
|||
|
Case output.Contains("unicode") Or output.Contains("utf-16") 'microsoft, the absolute madmen
|
|||
|
encType = Encoding.Unicode
|
|||
|
Case output.Contains("ansi") Or output.Contains("iso-8859") 'fucking apple i swear to god
|
|||
|
encType = Encoding.Default 'idk why but there's no System.Text.Encoding.ANSI.
|
|||
|
Case output.Contains("ascii")
|
|||
|
encType = Encoding.ASCII
|
|||
|
Case output.Contains("no read permission") Or output.Contains("no such file") 'basedirwatch tries to reload the file immediately after it's saved, which causes errors. it also causes the "couldn't determine encoding" notification to pop erroneously. this "fixes" that.
|
|||
|
encType = Encoding.UTF8
|
|||
|
Case Else
|
|||
|
Notify("Unsupported encoding: " & output.Replace(vbCrLf, "").Replace(vbNewLine, "") & ". Saving will convert to UTF-8.", 2) 'TODO: replace utf-8 with the user's default
|
|||
|
encType = Encoding.Default
|
|||
|
unableToDetermineEncType = True
|
|||
|
End Select
|
|||
|
|
|||
|
Try 'you never know what'll happen with IO
|
|||
|
chosenFile = New StreamReader(fileToLoad, encoding:=encType) 'schnik the file into a streamreader
|
|||
|
LoadTimeWarningTimer.Start() 'start waiting for it to load. if it takes more than 10 seconds, bad things are taking place.
|
|||
|
TextFileHolder.Text = Await chosenFile.ReadToEndAsync 'When building for Windows XP, remove the "async" bit, as .Net 4.0 (the last version XP supports, rip ;u;7) doesn't support it
|
|||
|
LoadTimeWarningTimer.Stop() 'it's over, isn't it? isn't it? isn't it over?
|
|||
|
Text = currentFile & " - Notepad Ultra" 'just in case the user forgets that they're using THE BEST PROGRAM EVER WRITTEN BY MORTAL HANDS
|
|||
|
TextFileHolder.Select(0, 0)
|
|||
|
TextFileHolder.ScrollToCaret() 'jump to the top of the file
|
|||
|
chosenFile.Close() 'close the streamreader
|
|||
|
ResetUndoList() 'clear the undo list, because it'd be stupid if you could undo file2.txt so it becomes file1.txt
|
|||
|
NewFile = False 'we're not using a new file
|
|||
|
'reset the font because certain characters (like AESTHETIC) fuck things up
|
|||
|
TextFileHolder.Font = New Font("FUCK", 10) 'unless the user actually has a font called FUCK, and is using it for notepad ultra, it'll be fine
|
|||
|
TextFileHolder.Font = My.Settings.Font
|
|||
|
updateStatusBar()
|
|||
|
StatStatus.Text = "Loaded"
|
|||
|
Cursor = Cursors.Default
|
|||
|
Enabled = True
|
|||
|
'FilePicker.Visible = True
|
|||
|
Catch ex As Exception
|
|||
|
'FilePicker.Visible = False
|
|||
|
'I don't know why, but that fucks things up BADLY
|
|||
|
Notify("Failed to load file!", 1)
|
|||
|
Enabled = True
|
|||
|
Cursor = Cursors.Default
|
|||
|
CleanOutTextFileHolder()
|
|||
|
End Try
|
|||
|
'reselectCurrentFile()
|
|||
|
unsaved = False
|
|||
|
Else
|
|||
|
Enabled = True
|
|||
|
Cursor = Cursors.Default
|
|||
|
Notify("Failed to load selected object!", 1) 'just in case things go terribly wrong
|
|||
|
CleanOutTextFileHolder()
|
|||
|
End If
|
|||
|
End If
|
|||
|
End If 'you know it's good code when the subroutine ends with 3 "end if" statements
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub WordWrapToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles WordWrapToolStripMenuItem.Click 'TODO: fucking hell
|
|||
|
Select Case WordWrapToolStripMenuItem.Checked
|
|||
|
Case False
|
|||
|
WordWrapToolStripMenuItem.Checked = True
|
|||
|
TextFileHolder.WordWrap = True
|
|||
|
Case True
|
|||
|
WordWrapToolStripMenuItem.Checked = False
|
|||
|
TextFileHolder.WordWrap = False
|
|||
|
End Select
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub DeleteToolStripMenuItem2_Click(sender As Object, e As EventArgs) Handles DeleteToolStripMenuItem2.Click
|
|||
|
If currentFile = "" Or NewFile Then
|
|||
|
MsgBox("You can't delete the current file when there isn't a current file, you dunce!" & vbNewLine & "(This message box should never appear! If it does, invest everything you have in gold and move out of the country)")
|
|||
|
Else
|
|||
|
If MsgBox("Are you sure you want to delete " & currentFile & "?", MsgBoxStyle.YesNo) = MsgBoxResult.Yes Then
|
|||
|
Dim DeleteOption As FileIO.RecycleOption = 3
|
|||
|
If My.Settings.UseRecycleBin Then
|
|||
|
DeleteOption = 2 'if the user wants to use the recycle bin because they're afraid of commitment, then so be it
|
|||
|
End If
|
|||
|
Enabled = False
|
|||
|
My.Computer.FileSystem.DeleteFile(basedir & currentFile, FileIO.UIOption.OnlyErrorDialogs, DeleteOption)
|
|||
|
CleanOutTextFileHolder()
|
|||
|
Enabled = True
|
|||
|
End If
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub NewToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles NewToolStripMenuItem.Click
|
|||
|
currentFile = "New file"
|
|||
|
NewFile = True 'TODO: a LOT of stuff (probably) breaks with new files. fix it all!
|
|||
|
Text = "Notepad Ultra: New file"
|
|||
|
TextFileHolder.Clear()
|
|||
|
Redraw()
|
|||
|
UpdateFilePicker() 'it's really quick, and deselects any files
|
|||
|
ResetUndoList()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub SaveToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles SaveToolStripMenuItem.Click
|
|||
|
If NewFile Then
|
|||
|
SaveAsToolStripMenuItem_Click(sender, e) 'if you try to save a new file, bring up the Save As dialogue instead
|
|||
|
Else
|
|||
|
StatStatus.Text = "Saving..."
|
|||
|
Enabled = False
|
|||
|
BaseDirWatch.EnableRaisingEvents = False
|
|||
|
If unableToDetermineEncType Then encType = Encoding.UTF8
|
|||
|
My.Computer.FileSystem.WriteAllText(basedir & currentFile, TextFileHolder.Text.Replace(vbLf, vbCrLf), False, encType) 'TODO: make this an async streamwriter?
|
|||
|
'While Not My.Computer.FileSystem.FileExists(basedir & currentFile) 'wait for the file to exist before continuing
|
|||
|
' Threading.Thread.Sleep(25) 'pause briefly to make sure we aren't thrashing the disk
|
|||
|
'End While
|
|||
|
Enabled = True
|
|||
|
Notify("Saved!", 3)
|
|||
|
StatStatus.Text = "Loaded"
|
|||
|
unsaved = False
|
|||
|
If Text.EndsWith(" (Unsaved)") Then Text = Text.RemoveLast(10) 'get rid of the (Unsaved) bit
|
|||
|
BaseDirWatchReenabler.Start() 'TODO: does this really need to be a timer?
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub SaveAsToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles SaveAsToolStripMenuItem.Click
|
|||
|
'all new files save as utf-8 at the moment, and that's probably for the best
|
|||
|
SaveDialogue.Filter = "Text files (*.txt)|*.txt|All files (*.*)|*.*"
|
|||
|
SaveDialogue.FilterIndex = 1
|
|||
|
SaveDialogue.RestoreDirectory = True
|
|||
|
SaveDialogue.InitialDirectory = basedir
|
|||
|
If NewFile Then encType = Encoding.UTF8 'TODO: load this from My.Settings.DefaultEncoding
|
|||
|
If IsNothing(encType) Then encType = Encoding.UTF8
|
|||
|
If SaveDialogue.ShowDialog() = DialogResult.OK Then
|
|||
|
My.Computer.FileSystem.WriteAllText(SaveDialogue.FileName, TextFileHolder.Text.Replace(vbLf, vbCrLf), False, encType)
|
|||
|
StatStatus.Text = "Saving..."
|
|||
|
End If
|
|||
|
currentFile = SaveDialogue.FileName.Split("\")(SaveDialogue.FileName.Split("\").Length - 1)
|
|||
|
If Text.EndsWith(" (Unsaved)") Then Text = Text.RemoveLast(10)
|
|||
|
If NewFile Then
|
|||
|
NewFile = False
|
|||
|
reselectCurrentFile()
|
|||
|
End If
|
|||
|
'BaseDirWatch will take over from here
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub OneDriveTextFilesToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles OneDriveTextFilesToolStripMenuItem.Click
|
|||
|
basedir = "F:\OneDrive\Documents\Other\Text files"
|
|||
|
UpdateFilePicker()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ChangeTheme(sender As Object, e As EventArgs, Optional ByVal silent As Boolean = False) Handles NightTheme.Click, StandardTheme.Click, TertiaryTheme.Click
|
|||
|
StandardTheme.Checked = False
|
|||
|
NightTheme.Checked = False
|
|||
|
TertiaryTheme.Checked = False
|
|||
|
sender.checked = True
|
|||
|
Dim themeName As String = sender.Name.ToString.Replace("Theme", "").Replace("Night", "Nite")
|
|||
|
|
|||
|
TextFileHolder.BackColor = CallByName(My.Settings, themeName & "TextBG", CallType.Get)
|
|||
|
TextFileHolder.ForeColor = CallByName(My.Settings, themeName & "TextFG", CallType.Get)
|
|||
|
FilePicker.BackColor = CallByName(My.Settings, themeName & "SidebarBG", CallType.Get)
|
|||
|
FilePicker.ForeColor = CallByName(My.Settings, themeName & "SidebarFG", CallType.Get)
|
|||
|
StatusBar.BackColor = CallByName(My.Settings, themeName & "StatBG", CallType.Get)
|
|||
|
StatusBar.ForeColor = CallByName(My.Settings, themeName & "StatFG", CallType.Get)
|
|||
|
|
|||
|
If Not silent Then Notify("Applied " & sender.Name.ToString.Replace("Theme", " Theme") & "!", 3) 'have some sort of cooldown?
|
|||
|
Dim themeToSet As Integer = 0
|
|||
|
Select Case sender.name
|
|||
|
Case "StandardTheme"
|
|||
|
themeToSet = 0
|
|||
|
Case "NightTheme"
|
|||
|
themeToSet = 1
|
|||
|
Case "TertiaryTheme"
|
|||
|
themeToSet = 2
|
|||
|
Case Else 'you never know when shit will hit the fan
|
|||
|
themeToSet = 0
|
|||
|
End Select
|
|||
|
|
|||
|
My.Settings.CurrentTheme = themeToSet
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ExitToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles ExitToolStripMenuItem.Click
|
|||
|
saveSettings()
|
|||
|
End
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub SidebarToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles SidebarToolStripMenuItem.Click 'TODO: i'm pretty sure this doesn't really do anything except waste cycles
|
|||
|
Select Case SidebarToolStripMenuItem.Checked
|
|||
|
Case False
|
|||
|
SidebarToolStripMenuItem.Checked = True
|
|||
|
showSidebar = True
|
|||
|
FilePicker.Visible = True
|
|||
|
TextFileHolder.Left = MenuBarWidth + 25 '*shrugs knowingly*
|
|||
|
Case True
|
|||
|
SidebarToolStripMenuItem.Checked = False
|
|||
|
showSidebar = False
|
|||
|
FilePicker.Visible = False
|
|||
|
TextFileHolder.Left = 0
|
|||
|
End Select
|
|||
|
Redraw()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub updateStatusBar() Handles TextFileHolder.TextChanged 'TODO: wait for user to stop typing before updating? this could murder slow computers, or any computer working with a fucking MASSIVE text file
|
|||
|
UndoTimer.Stop()
|
|||
|
StatChars.Text = "Characters: " & TextFileHolder.Text.Length
|
|||
|
'MsgBox(unsaved)
|
|||
|
If Not IsNothing(encType) Then StatBytes.Text = encType.GetByteCount(TextFileHolder.Text) & " Bytes"
|
|||
|
If My.Settings.UndoSteps <> 0 Then UndoTimer.Start()
|
|||
|
End Sub
|
|||
|
|
|||
|
Public Sub unsavedCheck(sender As Object, e As EventArgs) Handles TextFileHolder.KeyPress
|
|||
|
If Not My.Computer.Keyboard.CtrlKeyDown Then 'don't mark as unsaved if you only press ctrl-a, ctrl-c, etc. TODO: handle ctrl v, ctrl, x...
|
|||
|
If Not unsaved Then
|
|||
|
Text = Text + " (Unsaved)"
|
|||
|
unsaved = True
|
|||
|
End If
|
|||
|
If Text.EndsWith("(Unsaved) (Unsaved)") Then Text = Text.RemoveLastInstanceOf(" (Unsaved)") 'just to be sure. this will break if the user is editing a file with the extension ".(Unsaved) (Unsaved)", but, i mean... come on.
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub opacify() Handles Me.Move
|
|||
|
If My.Settings.MoveTransparency Then Opacity = 0.5 'fade on move!
|
|||
|
If Not IsNothing(chocolatePuddingOvenTimer) Then
|
|||
|
chocolatePuddingOvenTimer.Stop()
|
|||
|
chocolatePuddingOvenTimer.Start()
|
|||
|
Else
|
|||
|
Opacity = 1
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub chocolatePuddingOvenTimer_Tick(sender As Object, e As EventArgs) Handles chocolatePuddingOvenTimer.Tick
|
|||
|
Opacity = 1 'stop being faded on stopped being moved!
|
|||
|
chocolatePuddingOvenTimer.Stop()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ToolStripSplitButton1_ButtonClick(sender As Object, e As EventArgs) Handles StatDirectory.ButtonClick
|
|||
|
Process.Start(basedir)
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub toggleSidebar(sender As Object, e As EventArgs)
|
|||
|
SidebarToolStripMenuItem.PerformClick()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub RestartToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles RestartToolStripMenuItem.Click
|
|||
|
saveSettings() 'better safe than sorry!
|
|||
|
Application.Restart()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub saveSettings()
|
|||
|
My.Settings.Font = TextFileHolder.Font
|
|||
|
My.Settings.WordWrap = TextFileHolder.WordWrap
|
|||
|
My.Settings.ShowSidebar = showSidebar
|
|||
|
My.Settings.WorkingDirectory = basedir
|
|||
|
My.Settings.Save()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub emergencySave(ByVal sender As System.Object, ByVal e As System.Windows.Forms.FormClosingEventArgs) Handles Me.FormClosing
|
|||
|
Try
|
|||
|
My.Computer.Clipboard.SetText(My.Computer.Clipboard.GetText)
|
|||
|
saveSettings()
|
|||
|
If unsaved Then
|
|||
|
Dim response As MsgBoxResult = MsgBox("Save changes made to " & If(NewFile, "new file", """" & currentFile & """") & "?", MsgBoxStyle.YesNoCancel)
|
|||
|
If response = MsgBoxResult.Yes Then
|
|||
|
SaveToolStripMenuItem_Click(SaveToolStripMenuItem, EventArgs.Empty)
|
|||
|
ElseIf response = MsgBoxResult.Cancel Then
|
|||
|
e.Cancel = True
|
|||
|
Exit Sub
|
|||
|
End If
|
|||
|
End If
|
|||
|
End
|
|||
|
Catch ex As Exception
|
|||
|
MsgBox(ex.Message)
|
|||
|
End Try
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub SHOWRECENTSHEREToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles SHOWRECENTSHEREToolStripMenuItem.Click '???
|
|||
|
currentFile = ""
|
|||
|
FolderPicker.ShowDialog()
|
|||
|
basedir = FolderPicker.SelectedPath
|
|||
|
UpdateFilePicker()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ChangeToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles ChangeToolStripMenuItem.Click '?????
|
|||
|
SHOWRECENTSHEREToolStripMenuItem_Click(sender, e)
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub UndoToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles UndoToolStripMenuItem.Click
|
|||
|
If My.Settings.UndoSteps <> 0 Then
|
|||
|
Try
|
|||
|
If UndoPos <> 0 Then
|
|||
|
UndoPos -= 1
|
|||
|
TextFileHolder.Text = UndoList(UndoPos).ToString
|
|||
|
UndoTimer.Stop()
|
|||
|
Else
|
|||
|
Notify("Nothing to undo", 2)
|
|||
|
End If
|
|||
|
Catch ex As Exception 'better safe than sorry
|
|||
|
Notify("Undo error: " & ex.Message, 1)
|
|||
|
End Try
|
|||
|
Else
|
|||
|
Notify("Undo disabled by user.", 2) 'just in case the user's being a silly billy and forgets that they've turned off undo
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub RedoToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles RedoToolStripMenuItem.Click 'TODO: consider merge with undo
|
|||
|
If My.Settings.UndoSteps <> 0 Then
|
|||
|
Try
|
|||
|
If UndoPos <> UndoList.Count - 1 Then
|
|||
|
UndoPos += 1
|
|||
|
TextFileHolder.Text = UndoList(UndoPos).ToString
|
|||
|
UndoTimer.Stop()
|
|||
|
Else
|
|||
|
Notify("Nothing to redo", 2)
|
|||
|
End If
|
|||
|
Catch ex As Exception
|
|||
|
Notify("Undo error: " & ex.Message, 1)
|
|||
|
End Try
|
|||
|
Else
|
|||
|
Notify("Undo disabled by user.", 2)
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub FindToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles FindToolStripMenuItem.Click
|
|||
|
Find.npu = Me 'ensure that the find menu can access npu's main window
|
|||
|
Find.Show(Me)
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub CustomToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles CustomToolStripMenuItem.Click
|
|||
|
FontPicker.ShowDialog()
|
|||
|
TextFileHolder.Font = FontPicker.Font
|
|||
|
My.Settings.Font = TextFileHolder.Font
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub AboutToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles AboutToolStripMenuItem.Click
|
|||
|
'MsgBox("NotePad Ultra (Version 0.10 Alpha)" & vbNewLine & vbNewLine & "An advanced Notepad for advanced minds." & vbNewLine & vbNewLine & "© 2016 Lynnear Software" & vbNewLine & "QA: Petra Morse")
|
|||
|
About.Show()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ArialToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles ArialToolStripMenuItem.Click
|
|||
|
My.Settings.Font = New Font("Arial", My.Settings.Font.SizeInPoints, My.Settings.Font.Style)
|
|||
|
TextFileHolder.Font = My.Settings.Font
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub GoUpToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles GoUpToolStripMenuItem.Click
|
|||
|
If basedir.Length <> 3 And Not Regex.IsMatch(basedir, "^\\\\[^?:+\\<>]+\\[^?:\\<>*""|/]+\\$", RegexOptions.None) Then basedir = StrReverse(Replace(Replace(StrReverse(basedir), StrReverse(basedir.Split("\")(basedir.Split("\").Length - 2)), "",, 1), "\\", "\",, 1)) Else Notify("Already at root!", 2) 'wew lady
|
|||
|
'HOW THIS WORKS:
|
|||
|
'>check to make sure that we're not at the root path (either C:\, D:\ etc OR \\server\folder)
|
|||
|
'>start with basedir (C:\Path\Folder\)
|
|||
|
'>split it into an array using backslash as a separator ("C:", "Path", "Folder", "")
|
|||
|
'>select the second last string in this array ("Folder")
|
|||
|
'>reverse it ("redloF")
|
|||
|
'>reverse the whole basedir string (\redloF\htaP\:C)
|
|||
|
'>replace the first instance of the reversed second-last item in the array inside the reversed basedir with nothing (replace the first instance of "redloF" with "", giving "\\htaP\:C")
|
|||
|
'>replace the first instance of "\\" with "\" (\htaP\:C)
|
|||
|
'>reverse the whole thing ("C:\Path\")
|
|||
|
|
|||
|
'a few weeks after writing this, i found out about My.Computer.FileSystem.ParentPath. but i'm not fucking changing it.
|
|||
|
|
|||
|
Text = "Notepad Ultra"
|
|||
|
If My.Computer.FileSystem.DirectoryExists(basedir) Then
|
|||
|
'Notify("Directory changed", 3) 'Notification stack is FIFO, we gotta get in there first
|
|||
|
UpdateFilePicker()
|
|||
|
CleanOutTextFileHolder()
|
|||
|
Else
|
|||
|
Notify("Failed to change directory!", 1)
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub GoUpToolStripMenuItem1_Click(sender As Object, e As EventArgs) Handles GoUpToolStripMenuItem1.Click 'TODO: why are there two separate subs for this, what the fuck?
|
|||
|
GoUpToolStripMenuItem_Click(sender, e)
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub FileInfoToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles FileInfoToolStripMenuItem.Click
|
|||
|
Dim p As New Process
|
|||
|
p.StartInfo.UseShellExecute = False
|
|||
|
p.StartInfo.RedirectStandardOutput = True
|
|||
|
p.StartInfo.FileName = "dependencies\file\bin\file.exe"
|
|||
|
p.StartInfo.CreateNoWindow = True
|
|||
|
p.StartInfo.Arguments = "-b """ & basedir & currentFile & """"
|
|||
|
p.Start()
|
|||
|
Dim output As String = p.StandardOutput.ReadToEnd()
|
|||
|
p.WaitForExit()
|
|||
|
Dim q As New Process
|
|||
|
q.StartInfo.UseShellExecute = False
|
|||
|
q.StartInfo.RedirectStandardOutput = True
|
|||
|
q.StartInfo.FileName = "dependencies\file\bin\file.exe"
|
|||
|
q.StartInfo.CreateNoWindow = True
|
|||
|
q.StartInfo.Arguments = "-b --mime-encoding """ & basedir & currentFile & """"
|
|||
|
q.Start()
|
|||
|
Dim output2 As String = q.StandardOutput.ReadToEnd()
|
|||
|
q.WaitForExit()
|
|||
|
Try
|
|||
|
MsgBox("Detected type: " & output & "Detected encoding: " & output2 & "Approximate file size (on save): " & encType.GetByteCount(TextFileHolder.Text) & " Bytes" & vbNewLine & "Creation date: " & My.Computer.FileSystem.GetFileInfo(basedir & currentFile).CreationTime)
|
|||
|
Catch ex As Exception
|
|||
|
If ex.Message = "Object reference not set to an instance of an object." Then MsgBox("Failed to get file info: " & ex.Message & vbNewLine & "This almost certainly means that the file does not exist.") Else MsgBox("Failed to get file info: " & ex.Message)
|
|||
|
|
|||
|
End Try
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub SoftwareUsedToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles SoftwareUsedToolStripMenuItem.Click
|
|||
|
MsgBox("Notepad Ultra makes use of the following open-source software:" & vbNewLine & vbNewLine & "GNU file" & vbNewLine & "http://www.darwinsys.com/file/" & vbNewLine & "http://gnuwin32.sourceforge.net/packages/file.htm" & "(Used for detecting file encoding)") 'i looked for a windows tool that could do the job of "file" for so fucking long! anyone who cares enough to open the software used box should know about it!
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub EDocumentsToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles EDocumentsToolStripMenuItem.Click 'tempura
|
|||
|
basedir = "E:\Documents"
|
|||
|
UpdateFilePicker()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub autoFPUpdate() Handles BaseDirWatch.Deleted, BaseDirWatch.Created, BaseDirWatch.Renamed ', Me.Activated, Me.Deactivate, Me.GotFocus, Me.LostFocus
|
|||
|
UpdateFilePicker()
|
|||
|
reselectCurrentFile()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub MakeFontLarger_Click(sender As Object, e As EventArgs) Handles MakeFontLarger.Click 'TODO: merge with vvv
|
|||
|
If My.Settings.Font.SizeInPoints < 500 Then
|
|||
|
My.Settings.Font = New Font(My.Settings.Font.FontFamily, My.Settings.Font.SizeInPoints + 1, My.Settings.Font.Style)
|
|||
|
TextFileHolder.Font = My.Settings.Font
|
|||
|
Else
|
|||
|
Notify("Maximum font size!", 2)
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub MakeFontSmaller_Click(sender As Object, e As EventArgs) Handles MakeFontSmaller.Click 'TODO: merge with ^^^
|
|||
|
If My.Settings.Font.SizeInPoints > 4 Then
|
|||
|
My.Settings.Font = New Font(My.Settings.Font.FontFamily, My.Settings.Font.SizeInPoints - 1, My.Settings.Font.Style)
|
|||
|
TextFileHolder.Font = My.Settings.Font
|
|||
|
Else
|
|||
|
Notify("Minimum font size!", 2)
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub RefreshFileList_Click(sender As Object, e As EventArgs) Handles RefreshFileList.Click
|
|||
|
UpdateFilePicker()
|
|||
|
reselectCurrentFile()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub SegoeUIToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles SegoeUIToolStripMenuItem.Click 'TODO: merge this with the following 3
|
|||
|
My.Settings.Font = New Font("Segoe UI", My.Settings.Font.SizeInPoints, My.Settings.Font.Style)
|
|||
|
TextFileHolder.Font = My.Settings.Font
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ConsolasToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles ConsolasToolStripMenuItem.Click
|
|||
|
My.Settings.Font = New Font("Consolas", My.Settings.Font.SizeInPoints, My.Settings.Font.Style)
|
|||
|
TextFileHolder.Font = My.Settings.Font
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub LucidaConsoleToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles LucidaConsoleToolStripMenuItem.Click
|
|||
|
My.Settings.Font = New Font("Lucida Console", My.Settings.Font.SizeInPoints, My.Settings.Font.Style)
|
|||
|
TextFileHolder.Font = My.Settings.Font
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub SettingsToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles SettingsToolStripMenuItem.Click
|
|||
|
Settings.npu = Me
|
|||
|
Settings.Show(Me)
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub CleanOutTextFileHolder()
|
|||
|
UpdateFilePicker()
|
|||
|
ResetUndoList()
|
|||
|
NewFile = True
|
|||
|
unsaved = False
|
|||
|
Text = "Notepad Ultra"
|
|||
|
StatStatus.Text = "No file loaded"
|
|||
|
TextFileHolder.Text = "Welcome to Notepad Ultra! Select a file from the left." 'get everything nice and phresh
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub TimeDateToolStripMenuItem1_Click(sender As Object, e As EventArgs) Handles TimeDateToolStripMenuItem1.Click
|
|||
|
'Dim timeAndDate As String = My.Computer.Clock.LocalTime.ToShortTimeString & " " & My.Computer.Clock.LocalTime.ToShortDateString
|
|||
|
TextFileHolder.SelectionLength = 0
|
|||
|
TextFileHolder.SelectedText = My.Computer.Clock.LocalTime.ToShortTimeString & " " & My.Computer.Clock.LocalTime.ToShortDateString 'schnick the current time in
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub Notification_Click(sender As Object, e As EventArgs) Handles Notification.MouseDown
|
|||
|
Notification.Visible = False
|
|||
|
ShowNotificationTimer.Interval = 1
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub Notify(notifyText As String, category As Integer)
|
|||
|
notifyStack.Enqueue(New Notification() With {.Text = notifyText, .Category = category})
|
|||
|
ShowNotificationTimer.Start()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ShowNotificationTimer_Tick(sender As Object, e As EventArgs) Handles ShowNotificationTimer.Tick
|
|||
|
If notifyStack.Count = 0 Then
|
|||
|
ShowNotificationTimer.Stop()
|
|||
|
Notification.Visible = False
|
|||
|
ShowNotificationTimer.Interval = 1 'The next time the timer is called after showing all pending notifications, it should appear immediately.
|
|||
|
Else
|
|||
|
Dim PoppedNotify As Notification = notifyStack.Dequeue()
|
|||
|
Notification.Text = PoppedNotify.Text
|
|||
|
ShowNotificationTimer.Interval = 3000
|
|||
|
|
|||
|
Select Case PoppedNotify.Category
|
|||
|
Case 1 'Critical: Something critical has gone wrong
|
|||
|
Notification.BackColor = ReturnThemeSettingsAsThemeObject(My.Settings.CurrentTheme).NotificationCriticalBG
|
|||
|
Notification.ForeColor = ReturnThemeSettingsAsThemeObject(My.Settings.CurrentTheme).NotificationCriticalFG
|
|||
|
Case 2 'Warning: Something minor has gone wrong, or an action is unavailable
|
|||
|
imSorryCLU:
|
|||
|
Notification.BackColor = ReturnThemeSettingsAsThemeObject(My.Settings.CurrentTheme).NotificationWarningBG
|
|||
|
Notification.ForeColor = ReturnThemeSettingsAsThemeObject(My.Settings.CurrentTheme).NotificationWarningFG
|
|||
|
Case 3 'Just letting you know...
|
|||
|
Notification.BackColor = ReturnThemeSettingsAsThemeObject(My.Settings.CurrentTheme).NotificationInfoBG
|
|||
|
Notification.ForeColor = ReturnThemeSettingsAsThemeObject(My.Settings.CurrentTheme).NotificationInfoFG
|
|||
|
ShowNotificationTimer.Interval = 1500
|
|||
|
Case Else
|
|||
|
GoTo imSorryCLU 'apparently, you can't say "Case 2, Else" :c
|
|||
|
End Select
|
|||
|
Notification.Visible = True
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub BaseDirWatchPathToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles BaseDirWatchPathToolStripMenuItem.Click
|
|||
|
MsgBox(BaseDirWatch.Path)
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub reselectCurrentFile()
|
|||
|
Dim RestoreOnReload As Boolean = False
|
|||
|
Dim TempFileHolder As String = "An error occurred while switching files. Any unsaved changes made to this document have been lost. We apologise for the inconvenience." 'let's hope this shit never happens
|
|||
|
If currentFile IsNot "" And currentFile IsNot Nothing Then
|
|||
|
RestoreOnReload = unsaved
|
|||
|
If RestoreOnReload Then
|
|||
|
TempFileHolder = TextFileHolder.Text 'try to set tempfileholder to the textbox's text
|
|||
|
unsaved = False
|
|||
|
End If
|
|||
|
For fileIndex = 0 To FilePicker.Items.Count - 1
|
|||
|
If FilePicker.Items(fileIndex).ToString = currentFile Then
|
|||
|
If My.Computer.FileSystem.FileExists(basedir & currentFile) Then FilePicker.SelectedIndex = fileIndex
|
|||
|
Exit For
|
|||
|
End If
|
|||
|
Next
|
|||
|
If RestoreOnReload Then
|
|||
|
TextFileHolder.Text = TempFileHolder
|
|||
|
unsaved = True
|
|||
|
Text = Text + " (Unsaved)"
|
|||
|
End If
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub BaseDirWatchReenabler_Tick(sender As Object, e As EventArgs) Handles BaseDirWatchReenabler.Tick
|
|||
|
BaseDirWatch.EnableRaisingEvents = True
|
|||
|
'updateFilePicker()
|
|||
|
'reselectCurrentFile()
|
|||
|
BaseDirWatchReenabler.Stop()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub DuplicateToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles DuplicateToolStripMenuItem.Click
|
|||
|
Dim response As String = InputBox("Duplicate """ & currentFile & """ with name:", "Duplicate", "Copy of " & currentFile)
|
|||
|
If response IsNot "" And Not NewFile Then
|
|||
|
If My.Computer.FileSystem.FileExists(basedir & response) Then
|
|||
|
If MsgBox("A file with the name """ & response & """ already exists. Please choose a different name.", MsgBoxStyle.OkCancel) = MsgBoxResult.Ok Then
|
|||
|
DuplicateToolStripMenuItem.PerformClick() 'reprompt the user for a new name if it's already taken here
|
|||
|
End If
|
|||
|
Else
|
|||
|
Dim ValidExt As Boolean = False
|
|||
|
For i = 0 To My.Settings.SupportedExtensions.Count - 1
|
|||
|
If response.EndsWith("." & My.Settings.SupportedExtensions(i)) Then ValidExt = True 'if the user only wants npu to work with txt files, and they save it as a cfg, schnick a .txt on the end
|
|||
|
If ValidExt Then Exit For
|
|||
|
Next
|
|||
|
If Not ValidExt Then response &= ".txt" 'default to the txt ending
|
|||
|
Dim OldCurrentFile As String = currentFile
|
|||
|
currentFile = response
|
|||
|
My.Computer.FileSystem.CopyFile(basedir & OldCurrentFile, basedir & response)
|
|||
|
Notify("Duplicated!", 3)
|
|||
|
End If
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Public Sub reloadCurrentTheme()
|
|||
|
Select Case My.Settings.CurrentTheme
|
|||
|
Case 0
|
|||
|
ChangeTheme(StandardTheme, EventArgs.Empty, True)
|
|||
|
Case 1
|
|||
|
ChangeTheme(NightTheme, EventArgs.Empty, True)
|
|||
|
Case 2
|
|||
|
ChangeTheme(TertiaryTheme, EventArgs.Empty, True)
|
|||
|
End Select
|
|||
|
End Sub
|
|||
|
|
|||
|
Public Sub RedrawStatusBar()
|
|||
|
Dim StatBarSettings As String() = {"Chars", "Date", "Dir", "FontSize", "Size", "Status", "Mode"}
|
|||
|
For i = 0 To 6
|
|||
|
GetStatBarObject(i).visible = CallByName(My.Settings, "StatBar" & StatBarSettings(i), CallType.Get) 'only show the ones that the user wants
|
|||
|
Next
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ReplaceToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles ReplaceToolStripMenuItem.Click
|
|||
|
FindReplace.npu = Me
|
|||
|
FindReplace.Show(Me)
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub GoToToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles GoToToolStripMenuItem.Click
|
|||
|
MsgBox("Not yet supported") 'TODO: make it supported
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub GoUpValidatorToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles GoUpValidatorToolStripMenuItem.Click
|
|||
|
Dim benis As String = InputBox("String to check:")
|
|||
|
If benis IsNot Nothing And benis <> "" Then
|
|||
|
If benis.Length <> 3 And Not Regex.IsMatch(benis, "^\\\\[^?:+\\<>]+\\[^?:\\<>*""|/]+\\$", RegexOptions.None) Then MsgBox("Valid!") Else MsgBox("Invalid!") ' ensure it's a valid filename (ignoring stuff like AUX and COM, which windows should catch anyway... right?)
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub ShowInExplorer_Click(sender As Object, e As EventArgs) Handles ShowInExplorer.Click
|
|||
|
Process.Start("explorer.exe", "/select, " & basedir & rightClickedFile)
|
|||
|
End Sub
|
|||
|
|
|||
|
Public Sub GetFileToShowMenuFor(sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles FilePicker.MouseDown
|
|||
|
If e.Button = MouseButtons.Right Then
|
|||
|
Try
|
|||
|
rightClickedFile = FilePicker.Items(FilePicker.IndexFromPoint(e.X, e.Y)).ToString 'try to show the right-click menu with the right-clicked file as the target
|
|||
|
Catch fug As System.ArgumentOutOfRangeException 'if the user right-clicks that blank bit at the bottom of the filepicker...
|
|||
|
Notify("Invalid selection!", 2) '...tell them to fuck off.
|
|||
|
rightClickedFile = ""
|
|||
|
End Try
|
|||
|
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub DeleteToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles DeleteToolStripMenuItem.Click
|
|||
|
Dim DeleteOption As FileIO.RecycleOption = 3
|
|||
|
If My.Settings.UseRecycleBin Then DeleteOption = 2
|
|||
|
If MsgBox("Delete """ & rightClickedFile & """?", MsgBoxStyle.YesNo) = MsgBoxResult.Yes Then
|
|||
|
My.Computer.FileSystem.DeleteFile(basedir & rightClickedFile, FileIO.UIOption.OnlyErrorDialogs, DeleteOption)
|
|||
|
UpdateFilePicker()
|
|||
|
If rightClickedFile = currentFile Then
|
|||
|
CleanOutTextFileHolder()
|
|||
|
currentFile = ""
|
|||
|
End If
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
'Printing stuff (courtesy of https://support.microsoft.com/en-us/kb/811401)
|
|||
|
Private Sub PrintDocument1_BeginPrint(ByVal sender As Object, ByVal e As System.Drawing.Printing.PrintEventArgs) Handles PrintDocumentThingy.BeginPrint
|
|||
|
checkPrint = 0
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub PrintDocument1_PrintPage(ByVal sender As Object, ByVal e As System.Drawing.Printing.PrintPageEventArgs) Handles PrintDocumentThingy.PrintPage
|
|||
|
' Print the content of the RichTextBox. Store the last character printed.
|
|||
|
checkPrint = TextFileHolder.Print(checkPrint, TextFileHolder.TextLength, e)
|
|||
|
|
|||
|
' Look for more pages
|
|||
|
If checkPrint < TextFileHolder.TextLength Then
|
|||
|
e.HasMorePages = True
|
|||
|
Else
|
|||
|
e.HasMorePages = False
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub PrintToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles PrintToolStripMenuItem.Click
|
|||
|
Try
|
|||
|
PrintDocumentThingy.DocumentName = currentFile
|
|||
|
If PrintPreviewDialog1.ShowDialog() > -1 Then 'wait for the user to close the preview before continuing
|
|||
|
If PrintDialogue.ShowDialog() = DialogResult.OK Then
|
|||
|
PrintDocumentThingy.Print()
|
|||
|
End If
|
|||
|
End If
|
|||
|
Catch ex As Exception
|
|||
|
MsgBox("Failed to print file!" & vbNewLine & ex.Message)
|
|||
|
End Try
|
|||
|
|
|||
|
End Sub
|
|||
|
|
|||
|
Public Function GetStatBarObject(index)
|
|||
|
Select Case index
|
|||
|
Case 0
|
|||
|
Return StatChars
|
|||
|
Case 1
|
|||
|
Return StatDate
|
|||
|
Case 2
|
|||
|
Return StatDirectory
|
|||
|
Case 3
|
|||
|
Return StatFontSize
|
|||
|
Case 4
|
|||
|
Return StatBytes
|
|||
|
Case 5
|
|||
|
Return StatStatus
|
|||
|
Case 6
|
|||
|
Return StatMode
|
|||
|
Case Else
|
|||
|
Throw New Exception("GetStatBarObject: Invalid index!")
|
|||
|
End Select
|
|||
|
End Function
|
|||
|
|
|||
|
Private Sub LoadTimeWarning_Tick(sender As Object, e As EventArgs) Handles LoadTimeWarningTimer.Tick
|
|||
|
LoadTimeWarning.Show() 'if it takes more than 10s to load the file, something's gone wrong
|
|||
|
LoadTimeWarningTimer.Stop()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub SplashKillTimer_Tick(sender As Object, e As EventArgs) Handles SplashKillTimer.Tick
|
|||
|
Splash_Screen.Close() 'the program crashes unless you give it some time to do its thing
|
|||
|
SplashKillTimer.Stop()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub OPFKillTimer_Tick(sender As Object, e As EventArgs) Handles OPFKillTimer.Tick
|
|||
|
Open_Passed_File.Close()
|
|||
|
OPFKillTimer.Stop()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub FilePickerMenu_Opening(sender As Object, e As System.ComponentModel.CancelEventArgs) Handles FilePickerMenu.Opening
|
|||
|
FilePickerMenu.Enabled = False
|
|||
|
If rightClickedFile = "" Then
|
|||
|
FilenametxtToolStripMenuItem.Text = "Invalid selection"
|
|||
|
Else
|
|||
|
FilePickerMenu.Enabled = True
|
|||
|
FilenametxtToolStripMenuItem.Text = rightClickedFile
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub UndoTimer_Tick(sender As Object, e As EventArgs) Handles UndoTimer.Tick
|
|||
|
Dim UndoListTooBig As Boolean = False
|
|||
|
If My.Settings.UndoMemoryLimit Then
|
|||
|
Dim UndoListSize As Long
|
|||
|
Dim ms As New IO.MemoryStream
|
|||
|
Dim bf As New Runtime.Serialization.Formatters.Binary.BinaryFormatter()
|
|||
|
bf.Serialize(ms, UndoList)
|
|||
|
UndoListSize = ms.Position
|
|||
|
If UndoListSize / (1024 * 1024) >= My.Settings.UndoMaxMemory Then UndoListTooBig = True 'divide by 1024 to make bytes into kb, then again to make into mb
|
|||
|
End If
|
|||
|
If Not (UndoList.Count < My.Settings.UndoSteps OrElse My.Settings.UndoUnlimitedSteps) OrElse UndoListTooBig Then
|
|||
|
UndoList.RemoveFirst()
|
|||
|
'Notify("Undo limit reached, removing oldest entries", 3)
|
|||
|
End If
|
|||
|
If UndoList.Count > 0 And UndoPos > 0 And UndoList.Count > UndoPos Then
|
|||
|
While UndoPos <> UndoList.Count - 1
|
|||
|
UndoList.RemoveLast()
|
|||
|
End While
|
|||
|
End If
|
|||
|
UndoList.AddLast(TextFileHolder.Text)
|
|||
|
UndoPos = UndoList.Count - 1
|
|||
|
UndoTimer.Stop()
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub PageSetup_Click(sender As Object, e As EventArgs) Handles PageSetup.Click
|
|||
|
PageSetupDialog1.ShowDialog()
|
|||
|
End Sub
|
|||
|
|
|||
|
Public Sub ThrobberToggler() Handles Me.EnabledChanged
|
|||
|
'this subroutine ensures that whenever the form is disabled, the throbber is visible. the throbber's throbbing animation is designed to let the user know that things are happening in the background and that the program is not frozen. after all, who /doesn't/ love throbbers? i know i do!
|
|||
|
'for more about throbbers, visit https://en.wikipedia.org/wiki/Throbber. if you are still interested, and your desire for throbbers is not quenched by this page, the internet contains an astronomical amount of images, posts, videos, games, and more, all revolving around the concept of throbbers.
|
|||
|
Try
|
|||
|
Throbber.Visible = Not Enabled
|
|||
|
Catch ex As Exception
|
|||
|
'could not toggle throbber! throbber must be untoggleable.
|
|||
|
Notify("Throbber toggling failed: " & ex.Message, 1) 'notify the user of their untoggleable throbber. they'll want to know why their throbber isn't throbbing away down there!
|
|||
|
End Try
|
|||
|
'keep things short, we don't want the program sitting around toggling its throbber all day!
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub RenameToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles RenameToolStripMenuItem.Click 'nearly identical to the duplicate sub
|
|||
|
Dim response As String = InputBox("Enter new name for """ & currentFile & """:", "Rename", currentFile)
|
|||
|
If response IsNot "" And Not NewFile Then
|
|||
|
If My.Computer.FileSystem.FileExists(basedir & response) Then
|
|||
|
If MsgBox("A file with the name """ & response & """ already exists. Please choose a different name.", MsgBoxStyle.OkCancel) = MsgBoxResult.Ok Then
|
|||
|
RenameToolStripMenuItem.PerformClick()
|
|||
|
End If
|
|||
|
Else
|
|||
|
Dim ValidExt As Boolean = False
|
|||
|
For i = 0 To My.Settings.SupportedExtensions.Count - 1
|
|||
|
If response.EndsWith("." & My.Settings.SupportedExtensions(i)) Then ValidExt = True
|
|||
|
If ValidExt Then Exit For
|
|||
|
Next
|
|||
|
If Not ValidExt Then response &= ".txt"
|
|||
|
Dim OldCurrentFile As String = currentFile
|
|||
|
currentFile = response
|
|||
|
My.Computer.FileSystem.RenameFile(basedir & OldCurrentFile, response)
|
|||
|
currentFile = response
|
|||
|
Notify("Renamed!", 3)
|
|||
|
For fileIndex = 0 To FilePicker.Items.Count - 1
|
|||
|
If FilePicker.Items(fileIndex).ToString = currentFile Then
|
|||
|
If My.Computer.FileSystem.FileExists(basedir & currentFile) Then
|
|||
|
FilePicker.SelectedIndex = fileIndex
|
|||
|
NewFile = False
|
|||
|
End If
|
|||
|
Exit For
|
|||
|
End If
|
|||
|
Next
|
|||
|
End If
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub MoveToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles MoveToolStripMenuItem.Click 'also nearly identical to the duplicate sub
|
|||
|
MoveFileDialogue.InitialDirectory = basedir
|
|||
|
If MoveFileDialogue.ShowDialog() = DialogResult.OK Then
|
|||
|
Dim response As String = MoveFileDialogue.FileName
|
|||
|
If response IsNot "" And Not NewFile Then
|
|||
|
Dim ValidExt As Boolean = False
|
|||
|
For i = 0 To My.Settings.SupportedExtensions.Count - 1
|
|||
|
If response.EndsWith("." & My.Settings.SupportedExtensions(i)) Then ValidExt = True
|
|||
|
If ValidExt Then Exit For
|
|||
|
Next
|
|||
|
If Not ValidExt Then response &= ".txt"
|
|||
|
Dim OldCurrentFile As String = currentFile
|
|||
|
currentFile = response
|
|||
|
My.Computer.FileSystem.MoveFile(basedir & OldCurrentFile, response)
|
|||
|
basedir = GetPath(response)
|
|||
|
currentFile = GetFile(response)
|
|||
|
Notify("Moved!", 3)
|
|||
|
For fileIndex = 0 To FilePicker.Items.Count - 1
|
|||
|
If FilePicker.Items(fileIndex).ToString = currentFile Then
|
|||
|
If My.Computer.FileSystem.FileExists(basedir & currentFile) Then
|
|||
|
FilePicker.SelectedIndex = fileIndex
|
|||
|
NewFile = False
|
|||
|
End If
|
|||
|
Exit For
|
|||
|
End If
|
|||
|
Next
|
|||
|
End If
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub RenameToolStripMenuItem1_Click(sender As Object, e As EventArgs) Handles RenameToolStripMenuItem1.Click
|
|||
|
Dim response As String = InputBox("Enter new name for """ & rightClickedFile & """:", "Rename", currentFile)
|
|||
|
If response IsNot "" Then
|
|||
|
If My.Computer.FileSystem.FileExists(basedir & response) Then
|
|||
|
If MsgBox("A file with the name """ & response & """ already exists. Please choose a different name.", MsgBoxStyle.OkCancel) = MsgBoxResult.Ok Then
|
|||
|
RenameToolStripMenuItem1_Click(sender, e)
|
|||
|
End If
|
|||
|
Else
|
|||
|
Dim ValidExt As Boolean = False
|
|||
|
For i = 0 To My.Settings.SupportedExtensions.Count - 1
|
|||
|
If response.EndsWith("." & My.Settings.SupportedExtensions(i)) Then ValidExt = True
|
|||
|
If ValidExt Then Exit For
|
|||
|
Next
|
|||
|
If Not ValidExt Then response &= ".txt"
|
|||
|
My.Computer.FileSystem.RenameFile(basedir & rightClickedFile, response)
|
|||
|
Notify("Renamed!", 3)
|
|||
|
UpdateFilePicker()
|
|||
|
If currentFile = rightClickedFile Then
|
|||
|
currentFile = response
|
|||
|
reselectCurrentFile()
|
|||
|
End If
|
|||
|
End If
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub EncryptToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles EncryptToolStripMenuItem.Click
|
|||
|
'If MsgBox("Create an encrypted copy of this file?") = MsgBoxResult.Yes Then
|
|||
|
|
|||
|
'End If
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub OvertypeToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles OvertypeToolStripMenuItem.Click
|
|||
|
My.Computer.Keyboard.SendKeys(Keys.Insert) 'just schnick the insert key
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub DashesToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles DashesToolStripMenuItem.Click
|
|||
|
Bullet = "-"
|
|||
|
BulletPointsToolStripMenuItem.Checked = False
|
|||
|
AutoBullets = sender.Checked
|
|||
|
TextFileHolder.Focus()
|
|||
|
My.Computer.Keyboard.SendKeys("{END}")
|
|||
|
My.Computer.Keyboard.SendKeys("~") 'TODO: fix weird DING noise
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub BulletPointsToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles BulletPointsToolStripMenuItem.Click
|
|||
|
Bullet = "•"
|
|||
|
DashesToolStripMenuItem.Checked = False
|
|||
|
AutoBullets = sender.Checked
|
|||
|
TextFileHolder.Focus()
|
|||
|
My.Computer.Keyboard.SendKeys("{END}")
|
|||
|
My.Computer.Keyboard.SendKeys("~")
|
|||
|
End Sub
|
|||
|
|
|||
|
Public Sub ResetUndoList()
|
|||
|
UndoList.Clear()
|
|||
|
UndoPos = 0
|
|||
|
UndoList.AddLast(TextFileHolder.Text)
|
|||
|
End Sub
|
|||
|
|
|||
|
Private Sub rtb_KeyDown(sender As Object, e As KeyEventArgs) Handles TextFileHolder.KeyDown
|
|||
|
Dim Spaces As String = String.Concat(Enumerable.Repeat(" ", IndentLevel)) & " " 'put two spaces in for every level the user is indented up to, as well as an initial space
|
|||
|
TextFileHolder.Focus() 'sometimes the tab key changes menu settings instead of inserting a tab, this should fix it
|
|||
|
If e.Control AndAlso e.KeyCode = Keys.V Then 'stops people pasting in rich text
|
|||
|
DirectCast(sender, RichTextBox).Paste(DataFormats.GetFormat("Text"))
|
|||
|
e.Handled = True
|
|||
|
End If
|
|||
|
If AutoBullets Then 'handle automatic bullet points
|
|||
|
If e.KeyCode = Keys.Enter Then
|
|||
|
TextFileHolder.SelectedText = vbNewLine & Spaces & Bullet & " "
|
|||
|
My.Computer.Keyboard.SendKeys(vbBack) ':/
|
|||
|
ElseIf e.KeyCode = Keys.Tab Then 'if they pressed tab, they want to increase the indent level
|
|||
|
e.Handled = True 'this should stop a tab being inserted but it doesn't
|
|||
|
Dim WordWrap As Boolean = TextFileHolder.WordWrap
|
|||
|
TextFileHolder.WordWrap = False 'TODO: try to find a better way of doing this
|
|||
|
Dim Lines As String() = TextFileHolder.Lines()
|
|||
|
Dim OldPos As Integer = TextFileHolder.SelectionStart
|
|||
|
If e.Shift Then 'if they pressed shift tab
|
|||
|
IndentLevel -= 1 'unindent
|
|||
|
If Lines(TextFileHolder.GetLineFromCharIndex(TextFileHolder.SelectionStart - 1)).StartsWith(" ") Then
|
|||
|
Lines(TextFileHolder.GetLineFromCharIndex(TextFileHolder.SelectionStart - 1)) = Lines(TextFileHolder.GetLineFromCharIndex(TextFileHolder.SelectionStart - 1)).RemoveFirst(2) 'if the line starts with 2 spaces, get rid of them
|
|||
|
End If
|
|||
|
|
|||
|
If IndentLevel < 0 Then
|
|||
|
Notify("AutoBullets disabled", 3) 'turn off autobullets if they unindent when on the lowest level
|
|||
|
AutoBullets = False
|
|||
|
IndentLevel = 0
|
|||
|
DashesToolStripMenuItem.Checked = False
|
|||
|
BulletPointsToolStripMenuItem.Checked = False
|
|||
|
End If
|
|||
|
Else
|
|||
|
IndentLevel += 1
|
|||
|
Lines(TextFileHolder.GetLineFromCharIndex(TextFileHolder.SelectionStart)) = " " & Lines(TextFileHolder.GetLineFromCharIndex(TextFileHolder.SelectionStart)) 'add the spaces
|
|||
|
End If
|
|||
|
TextFileHolder.Lines = Lines
|
|||
|
If e.Shift Then
|
|||
|
If OldPos > 2 Then TextFileHolder.SelectionStart = OldPos - 2 'move the cursor back 2 spaces because we just deleted 2 characters
|
|||
|
Else
|
|||
|
TextFileHolder.SelectionStart = OldPos + 2
|
|||
|
End If
|
|||
|
My.Computer.Keyboard.SendKeys(vbBack) ':\
|
|||
|
If WordWrap Then
|
|||
|
TextFileHolder.WordWrap = True
|
|||
|
My.Computer.Keyboard.SendKeys(" ")
|
|||
|
End If
|
|||
|
End If
|
|||
|
End If
|
|||
|
End Sub
|
|||
|
|
|||
|
End Class
|