Word input from one line in the textbox to another - vb.net

I have 5 text boxes marked with NX1, NX2, NX3 .... NX5.
I have a Textbox marked with Textbox2 that contains lines like:
2 4 6 8 11
1 2 3 4 12
3 4 7 9 13
4 5 7 9 14
Is there a possibility to enter the first word / number from TextBox2 Lines (0) in NX1? i.e. First Word (number 2 in NX1), (Second Word) number 4 in NX2, number 6 in NX3 and number 8 in NX4. and so on.
I tried this:
Dim mytext As String
Dim counter As Integer
mytext = TextBox1.Text
For counter = 1 To Len(TextBox1.Text)
If Mid$(mytext, counter, 1) = " " Then
GoTo NextPart
End If
Next counter
NextPart:
MsgBox("'" + Mid$(mytext, 1, counter - 1) + "'")
MsgBox("'" + Mid$(mytext, 2, counter - 1) + "'")

Get the TextBox.Lines(0). That's the first line of text. If the text parts are separated by a white space, just Split() the text (white space is the default separator).
If it's not, specify the separator: Split("[SomeChar]"c).
You'll get 5 strings in a String() array. Assing String(0) to NX1 etc.
Dim FirstLine As String = TextBox2.Lines(0)
Dim AllParts As String() = FirstLine.Split()
NX1.Text = AllParts(0)
NX2.Text = AllParts(1)
'(...)
Repeat the same procedure if you need the other text lines.
You could also use LINQ to perform the string assignments:
AllParts.Select(Function(s, i) Me.Controls("NX" & (i + 1)).Text = s).ToList()
Or, assemble everything in one expression:
TextBox2.Lines(0).Split().Select(Function(s, i) Me.Controls("NX" & (i + 1)).Text = s).ToList()
A description of this method:
[TextBox].Lines(0) => Returns the first line of text in a TextBoxBase control
Split() => Splits the text content using the default separator.
Returns an array of String
Select((string, int)) => Selects each string returned by the Split() method and updates
the index of each iteration.
Performs an action: sets a control`s Text property.
ToList() => Materializes the Enumerable collection returned by Select()
If omitted, in this case, the iteration is performed just once
Me.Controls("NX" & (i + 1)).Text = s:
Returns a Form's Control which name is "NX" + a number and assigns a string to its Text property.

You can use String.Split() to split the string.
Dim columns = TextBox2.Lines(0).Split()
For i = 0 To columns.Length - 1
Controls.Item("NX" & (i + 1)).Text = columns(i)
Next
The Lines property of the TextBox returns a string array containing the lines of the entered text.
String.Split() with no parameters splits a string at white spaces and returns a string array containing the parts (the columns of the first lines in this case).
The Controls property of the form returns a controls collection. The indexed Item property of the controls collection accepts either an Integer index or a control name as String.

Related

ppt vba multiple slide selection macro error

When multiple PowerPoint slide numbers are entered in the input box (ex: 3, 5, 6), I want to create a macro that selects the slides of the entered number, but an error occurs.
Sub test()
Dim strresponse2 As String
Dim iresponse2 As String
strresponse2 = InputBox("page number" & vbCr & "ex) 2,4,11,5")
If IsNumeric(strresponse2) Then
iresponse2 = strresponse2
End If
ActiveWindow.Selection.Unselect
ActivePresentation.slides.Range(Array(iresponse2)).Select
'error here
'How to fix it so it doesn't get an error
'ActivePresentation.Slides.Range(Array(2, 4, 11,5)).Select
'no error
End Sub
Several issues here.
a) If you enter 2, 4, 5, the check for IsNumeric(strresponse2) will fail because the function tries to convert the whole string into one single number.
b) Array(iresponse2) will not convert the string into an array (of 3 numbers). It will convert the single string 2, 4, 5 into an string array with 1 (not 3) member.
In your case, you can use the Split-function to split the input string into an array of strings.
c) If you want to access the slides by number, the input needs to be of a numeric type, not of string (even if the strings contain numbers). You will need to convert the string array into a numeric array (if you pass a string or an array of strings as parameter, VBA will look for members with the name, not the index).
Have a look to the following piece of code and check if it does what you need - it's only half tested (as I have no Powerpoint VBA available, only Excel, but the priniple is the same)
Dim answer As String
answer = InputBox("page number" & vbCr & "ex) 2,4,11,5")
Dim pagesS() As String
pagesS = Split(answer, ",") ' Split the answer into an array of strings.
ReDim pagesN(0 To UBound(pagesS)) As Long ' Create an empty numeric array
Dim countS As Long, countN As Long
For countS = 0 To UBound(pagesS) ' Loop over all strings
If IsNumeric(pagesS(countS)) Then ' String is Numeric
Dim pageNo As Long
pageNo = Val(pagesS(countS)) ' Convert string to number
If pageNo > 0 And pageNo <= ActivePresentation.slides.Count Then
pagesN(countN) = pageNo ' When number is within valid range, copy it
countN = countN + 1 ' Count the number of valid page numbers
End If
End If
Next countS
If countN > 0 Then ' At least one number found
ReDim Preserve pagesN(0 To countN - 1) ' Get rid of unused elements
ActivePresentation.Slides.Range(pagesN).Select
End If

What is the simplest way to display an aligned table from an Array of Strings in a TextBox using just Tabs (not using Tabstops)

I have an array of strings with 5 entries, where each string consists of 7 fields separated by comma's.
Those fields are of different lengths. I'm using a monospace font, so I can align things with tabs.
I had build a loop that goes through the string array, splitting the strings in the array, to determine which string in each "column" is the longest.
Then another loop, where I assemble a string with fields followed by a vbTab, and if the current field is a multiple of 8 shorter than the maximum length I add extra vbTabs (so if it's 8 shorter, add an extra vbTab, 16 = 2 vbTabs, etc).
But I have trouble getting things properly aligned in some cases.
Code:
Sub WriteTidyBlockH_layoutissues(list As List(Of String))
'Takes a list of strings as argument
'Writes it out as a table
'Assumes first line is a header (will be bolded)
'Go through list, split table fields and determine their lengths
Dim strLineFields As String() 'string array to hold the fields in a single line
Dim strLineField As String 'an individual field in a line
Dim FieldMaxLengths As New List(Of Integer)() 'list that will hold max length of each column
Dim i, j, k, intLines, intColumns As Integer
Dim strLine As String 'string to build a tabbed line in
Dim Tabs As Byte
'determine number of lines
intLines = list.Count - 1
'determine number of columns by counting the commas
intColumns = list(0).Count(Function(c As Char) c = ",")
For i = 0 To intColumns
FieldMaxLengths.Add(0)
Next
Dim strFields(intLines, intColumns) As String '2 dimensional array of strings, containing ALL fields
i = 0
For Each strListElement As String In list
j = 0
strLineFields = Split(strListElement, ",")
For Each strLineField In strLineFields
strFields(i, j) = strLineFields(j)
If strLineFields(j).Length > FieldMaxLengths(j) Then
FieldMaxLengths(j) = strLineFields(j).Length
End If
j += 1
Next
i += 1
Next
For i = 0 To intLines
strLine = ""
For j = 0 To intColumns
If Not j = intColumns Then
strLine += strFields(i, j) + vbTab 'one tab is always needed for every field, except the last
If strFields(i, j).Length <= FieldMaxLengths(j) Then
'strLine += strFields(i, j) + vbTab
'figure out how many additional tabs necessary
Tabs = (FieldMaxLengths(j) - strFields(i, j).Length) \ 8 'Div
For k = 1 To Tabs
strLine += vbTab
Next
End If
Else
'last column, don't add tabs
strLine += strFields(i, j)
End If
Next
If i = 0 Then
WriteOut(strLine, 0, True)
Else
WriteOut(strLine)
End If
Next
End Sub
Output currently looks like this:
Bank Location Capacity Speed Manufacturer Part Number Serial Number
BANK 0 ChannelA-DIMM0 8GB 1600 Kingston 99U5471-066.A00LF 24E8D583
BANK 1 ChannelA-DIMM1 8GB 1600 Kingston 99U5471-054.A00LF 30269BB7
BANK 2 ChannelB-DIMM0 8GB 1600 Kingston 99U5471-058.A00LF 182C9113
BANK 3 ChannelB-DIMM1 8GB 1600 Kingston 99U5471-054.A00LF D63F4C11
N.B. I'm having some trouble with formatting. In the actual output, only Capacity and Serial Number are misaligned (too far left), while Spped, Manufacturer and Part Number are correctly aligned with the data under them.
N.B.: WriteOut is just a sub that writes a single string to the textbox and appends a vbCrLf. The other two arguments are optional (color and bold).

MS Access VBA: Split string into pre-defined width

I have MS Access form where the user pastes a string into a field {Vars}, and I want to reformat that string into a new field so that (a) it retains whole words, and (b) "fits" within 70 columns.
Specifically, the user will be cutting/pasting variable names from SPSS. So the string will go into the field as whole names---no spaces allowed---with line breaks between each variable. So the first bit of VBA code looks like this:
Vars = Replace(Vars, vbCrLf, " ")
which removes the line breaks. But from there, I'm stumped---ultimately I want the long string that is pasted in the Vars field to be put on consecutive multiple lines that each are no longer than 70 columns.
Any help is appreciated!
Okay, for posterity, here is a solution:
The field name on the form that captures the user input is VarList. The call to the SPSS_Syntax function below returns the list of variable names (in "Vars") that can then be used elsewhere:
Vars = SPSS_Syntax(me.VarList)
Recall that user input into Varlist comes in as each variable (word) with a line break in between each. The problem is that we want the list to be on one line (horizontal, not vertical) AND a line can be no more than 256 characters in length (I'm setting it to 70 characters below). Here's the function:
Public Function SPSS_Syntax(InputString As String)
InputString = Replace(InputString, vbNewLine, " ") 'Puts the string into one line, separated by a space.
MyLength = Len(InputString) 'Computes length of the string
If MyLength < 70 Then 'if the string is already short enough, just returns it as is.
SPSS_Syntax = InputString
Exit Function
End If
MyArray = Split(InputString, " ") 'Creates the array
Dim i As Long
For i = LBound(MyArray) To UBound(MyArray) 'for each element in the array
MyString = MyString & " " & MyArray(i) 'combines the string with a blank space in between
If Len(MyString) > 70 Then 'when the string gets to be more than 70 characters
Syntax = Syntax & " " & vbNewLine & MyString 'saves the string as a new line
MyString = "" 'erases string value for next iteration
End If
Next
SPSS_Syntax = Syntax
End Function
There's probably a better way to do it but this works. Cheers.

Mods and ASCII in VB Caesar Shift

I have this code which shifts the alphabet by a certain amount. The size of the alphabet is 26. When I enter a larger size shift (for example 22) I get some weird characters displaying. I think I need to mod the ASCII alphabet to 26 to get it working but Im not quite sure which bit to mod.
Basically I need to wrap around the alphabet (once it reaches Z it goes back to letter A) Do I have to create a dictionary for the mod to work (like A = 0... Z = 26) or can I stick with using the normal ASCII table? Here is the code below:
Public Function encrypt(ByVal input As String) 'input is a variable within the funcion
Dim n as Integer
Dim i As Integer
n = key.Text Mod 26 'gets what is in the text box of 'key' and sets it as n
' the key is a multiple of 26 so 26 will = 0
'need to remove white spaces
While input.Contains(" ") 'when the input text contains a space
input = input.Replace(" ", "") 'replaces it with no space.
End While
For i = 1 To Len(input) 'find the length of the input
Mid(input, i, 1) = Chr(Asc(Mid(input, i, 1)) + n) 'chr returns the character associated with the specified character code
'
Next
encrypt = input
End Function
Look at this code:
For i = 1 To Len(input) 'find the length of the input
Mid(input, i, 1) = Chr(Asc(Mid(input, i, 1)) + n) 'chr returns the character associated with the specified character code
'
Next
String indexes are 0-based. Your first index is 0, not 1! Also, you are assigning to the result of a function call. You need to instead construct a new string.
You didn't say, but the way you used the Replace and Contains methods indicates .Net, and if that's the case, I would do it like this:
Public Function encrypt(ByVal key As Integer, ByVal input As String) As String 'Don't forget the return type on the function
key = key Mod 26
Return New String(input.Replace(" ", "").ToUpper().Select(Function(c) Chr(((Asc(c) + key - Asc("A"c)) Mod 26) + Asc("A"c))).ToArray())
End Function
Just like that, and it's almost a one-liner. I can see this works now by calling it this way:
Encrypt("C"c, "the quick brown fox jumps over the lazy dog")
Encrypt("D"c, "the quick brown fox jumps over the lazy dog")
The results:
BPMYCQKSJZWEVNWFRCUXMLWDMZBPMTIHGLWOA
CQNZDRLTKAXFWOXGSDVYNMXENACQNUJIHMXPB
Look for the results mapped for the word "lazy", and you will see that the 'a' wraps to 'z' and 'y' correctly, and that the 'D' key results are one letter off of the 'C' results.

Textbox Hell - Delete 3 Lines, Skip 1, Repeat

I have a textbox that reads like so:
Line 1
Line 2
Line 3
**Line 4**
Line 1
Line 2
Line 3
**Line 4**
(repeats...)
How can I use VB to loop through the textbox, deleting Lines 1, 2, and 3, skipping the fourth, and repeat? Or, rather, record every fourth line into a new textarea?
I'd probably get the contents, split on the newline character to create an array of strings (one string per line), then loop through the array outputting only the ones i wanted.
If this is VB6 then bear in mind that the variable length String type is a reference type meaning that operations will involve taking a deep copy i.e. concatenation is expensive.
Dim lines() As String
lines = VBA.Split(TextBox1.Text, vbCrLf)
Dim counter As Long
For counter = 3 To UBound(lines) Step 4
lines(counter) = Chr$(22)
Next
TextBox1.Text = _
Replace$( _
Replace$( _
VBA.Join(lines, vbCrLf), _
vbCrLf & Chr$(22), vbNullString), _
Chr$(22) & vbCrLf, vbNullString, 1)
This is code for the previous answer.
Private Function EveryFourthLine(ByVal input As String) As String
Dim newtxt As String = ""
Dim oldtxt As String() = input.Split(vbCrLf)
For i As Integer = 1 To oldtxt.Count
If i Mod 4 = 0 Then
newtxt = newtxt & oldtxt(i - 1)
If i <> oldtxt.Count Then
'add a vbcrlf to all but the last line
newtxt = newtxt & vbCrLf
End If
End If
Next
Return newtxt
End Function
If this is VB.Net and you are using a Textbox - you don't need to split anything yourself. You can just access the .Lines property. You'll get back an array of strings
You certainly can loop through the rows, like others have shown; but another approach is to use LINQ to do that work for you.
txtBox1.Lines = (From curLine In txtBox1.Lines _
Where Array.IndexOf(txtBox1.Lines, curLine) Mod 4 = 3).ToArray
What you are saying here is that you want the Lines in the textbox to be equal to all of the lines that are already in the text box - as long as the index of that particular line, divided by 4 has a remainder of three.
That sounds complicated when you type it out like that, but really, all it's going to do is give you every fourth line, and set that back into the textbox.