How do I center text of a cell vertically in a table using VBScript and a word document? - vbscript

I tried using
With myTable.Rows(1)
.Height = 20
.Cells.VerticalAlignment = wdAlignVerticalTop
End With
But it doesn't seem to work for VBScript, does someone know how to do what I want to do?

If you are using vbscript, then vbscript does not know the values of your word enumerated constants. So, either assign values to these constants or just use the numbers/constants directly as shown below:
With myTable.Rows(1)
.Height = 20
.Cells.VerticalAlignment = 1 '1 means WdCellVerticalAlignment(see link below)
End With
Click here -- Word Enumerated constants
Also, If you are using Word VBA and not vbscript, then you should mention the correct enumerated constant. In your case, It should not be wdAlignVerticalTop. Instead, it should be WdCellVerticalAlignment.

Related

Scripting Word from vbs

I'm trying to get Word to fill in cells in a table. The script works when run as a macro from within Word, but fails when saved as a .vbs file and double-clicked, or run with wscript. This is a part of it.
set obj = GetObject(,"Word.Application)
With obj
With .Selection
MsgBox .text
If (.Information(wdWithInTable) = True) Then
.Collapse Direction:=wdCollapseStart
tCols = .Tables(1).Columns.Count
tRow = .Information(wdStartOfRangeRowNumber)
tCol = .Information(wdStartOfRangeColumnNumber)
For I = 2 To 5
.Tables(1).Cell(tRow, I).Range.Text = "fred" & Str(I)
Next
` now make new row
For I = 1 To tCols - tCol + 1
.MoveRight unit:=wdCell
Next
End If
End With
End With
I have three problems. First, it won't compile unless I comment out the .Collapse and .MoveRight lines. Second, although the MsgBox .text displays the selected text, I get "out of range" errors if I try to access any .Information property.
I'm sure I'm missing something very simple: I usually write software for Macs, and I'd do this using AppleScript. This is my first attempt at getting anything done under Windows.
VBScript and VBA are different languages.
They are a bit similar, but not very. Moreover, VBScript is not like AppleScript; it doesn't let you easily interface with running programs.
The interfaces you'll get from VBScript can behave subtly differently in VBA and VBScript. However, I think you've got two problems here:
:= is invalid syntax in VBScript; you'll need to find an alternative way of calling the function. Try just using positional arguments.
You've no guarantee that this will open the expected file; there could be another instance of Word that it's interacting with instead.
Since your code is not running within the Word environment it would require a reference to the Word object library in order to use enumeration constants (those things that start with wd).
VBScript, however, cannot work with references, which means the only possibility is to use the long value equivalents of the enumerations. You'll find these in the Word Language References. Simplest to use is probably the Object Browser in Word's VBA Editor. (In Word: Alt+F11 to open the VBA Editor; F2 to start the Object Browser; type in the term in the "Search" box, click on the term, then look in the bottom bar.)
The code in the question uses, for example:
wdWithInTable
wdCollapseStart
wdStartOfRangeRowNumber
wdStartOfRangeColumnNumber
wdCell
The reason you get various kinds of errors depends on where these are used.
Also, VBScript can't used named parameters such as Unit:=. Any parameters must be passed in comma-delimited format, if there's more than one, in the order specified by the method or property. If there are optional parameters you don't want to use these should be left "blank":
MethodName parameter, parameter, , , parameter

Missing events in properties for VB6

I am a self taught amateur Visual Basic programmer. My programs are for myself, friends and some non-profit organizations. I have a situation that I thought would be reasonably simple but doesn't seems the case.
I have a text box array of 6 elements (1 -6) named "txtBilled" .When the value is entered into any but element 6 I want to add the values in 1-5 and put result in element 6. My problems start due to the fact that the properties for the text array does not provide for a lost focus option. Searching the inter provides statements that this is normal, others say the "Lost Focus" should always be there.
As a second approach I tried to use the validate element. Never used this before created a sub as follows that I found on the web.
Private sub txtBilled__Validate(Cancel as Boolean)
Found that the Validate event is also not included in the properties for the array
I am using VB6 version 8176 under Windows 10.
Any ideal as to what I am doing incorrectly would be appreciated.
Can you not create your own LostFocus sub using the Index of the textbox array?
Private Sub txtBilled_LostFocus(Index As Integer)
Dim i As Integer
dim sngTotal As Single
' Calculate sum only if not in last textbox
If Index <> uBound(txtBilled) Then
For i = LBound(txtBilled) to UBound(txtBilled) - 1
sngTotal = sngTotal + txtBilled(i)
Next i
txtBilled(uBound(txtBilled)) = sngTotal
End If
End Sub

VB6, Adding an integer to a control name in a for loop

I am currently trying you learn VB6 and came across this issue.
I wanted to loop through a for loop and adding a number to a control name.
Dim I As Integer
For I = 1 To 5
S = CStr(I)
If TextS.Text = "" Then
LabelS.ForeColor = &HFF&
Else
LabelS.ForeColor = &H80000012
End If
Next I
This S needs to be added to Text and Label so the colour will be changed without needing to use 5 If Else statements
I hope you can help me with this.
From your comment below:
What i mean is this: If Text1.text = "" Then I need this 1 to be replaced with the variable I, so the for loop can loop through my 5 textboxes and the same for my Labels.
You can't do that (look up a variable using an expression to create its name) in VB6. (Edit: While that statement is true, it's not true that you can't look up form controls using a name from an expression. See "alternative" below.)
What you can do is make an array of your textboxes, and then index into that array. The dev env even helps you do that: Open your form in the dev env and click the first textbox. Change its name to the name you want the array to have (perhaps TextBoxes). Then click the next textbox and change its name to the same thing (TextBoxes). The dev env will ask you:
(Don't ask me why I have a VM lying around with VB6 on it...)
Click Yes, and then you can rename your other textboxes TextBoxes to add them to the array. Then do the same for your labels.
Then your code should look like this:
For I = TextBoxes.LBound To TextBoxes.UBound
If TextBoxes(I).Text = "" Then
Labels(I).ForeColor = &HFF&
Else
Labels(I).ForeColor = &H80000012
End If
Next
LBound is the lowest index of the control array, UBound is the highest. (You can't use the standard LBound and Ubound that take the array as an argument, because control arrays aren't quite normal arrays.) Note also that there's no need to put I on the Next line, that hasn't been required since VB4 or VB5. You can, though, if you like being explicit.
Just make sure that you have exactly the same number of TextBoxes as Labels. Alternately, you could create a user control that consisted of a label and a textbox, and then have a control array of your user control.
Alternative: : You can use the Controls array to look up a control using a name resulting from an expression, like this:
For I = 1 To 5
If Me.Controls("Text" & I).Text = "" Then
Me.Controls("Label" & I).ForeColor = &HFF&
Else
Me.Controls("Label" & I).ForeColor = &H80000012
End If
Next
This has the advantage of mapping over to a very similar construct in VB.Net, should you migrate at some point.
Side note:
I am currently trying you learn VB6...
(tl;dr - I'd recommend learning something else instead, VB6 is outdated and the dev env hasn't been supported in years.)
VB6's development environment has been discontinued and unsupported for years (since 2008). The runtime is still (I believe) supported because of the sheer number of apps that use it, although the most recent patch seems to be from 2012. But FWIW, you'd get a better return on your study time learning VB.net or C#.Net (or any of several non-Microsoft languages), rather than VB6...

VB6 control iteration: one control gives me an error; which one?

I am trying to loop through all controls in a form:
For Each ctrl in Me.Controls
in order enable/disable the control based on some conditions.
But there is a control on the form that gives an error when I try to access it. What kind of control does that, and how do I find it?
When you get your error and click Debug, is the error on the line setting a control's Enabled property?
If so, add a Debug.Print statement writing out the control's name. Do so on the line before setting the Enabled property.
Here's what I mean:
Dim ctrl As Control
For Each ctrl In Me.Controls
Debug.Print ctrl.Name
ctrl.Enabled = True
Next
The Debug.Print statement will write out to the Immediate Window the name of the control that was last processed in the loop, presumably the one that caused your error.
EDIT
This might work. Put this control in a Panel control and set the Panel's Enabled property to False. If I recall correctly, in VB6 setting a container control's Enabled property to False will also set the container's child controls Enabled to False. If your control's Enabled property really is read-only, I'm curious what would happen.
Try this:
Dim ctr As Control
Dim CtrStatus Boolean
CtrStatus = False
For Each ctr In Me.Controls
If (SSTab.hwnd = GetParent(ctr.hwnd)) Then
Call CallByName(ctr, "Enabled", VbLet, CtrStatus)
else
ctr.Enabled = CtrStatus
End If
Next
Another approach is as follows, that also works at runtime (as opposed to just in the IDE):
private sub SetEnabled()
on error goto errHandle
Dim ctrl As Control
For Each ctrl In Me.Controls
ctrl.Enabled = True
Next
exitPoint:
exit sub
errHandle:
MsgBox "Error " & err.Description & " with Control " & ctrl.Name
resume exitPoint
end sub
Suppress the error reports before the loop and then set it back to standard error handling:
On Error Resume Next
For Each ctrl In Me.Controls
ctrl.Enabled = lIsEnabled
Next
On Error GoTo 0
OR name your controls with a standard prefix/suffix that you can check by name and skip in the loop.
For Each ctrl In Me.Controls
If Left(ctrl.Name, 3) = "sst" Then
ctrl.Enabled = lIsEnabled
End If
Next
Tosa: from your comment on AngryHacker's answer, I think you are checking the container incorrectly.
Your code is like this
' BAD CODE '
If ctrl.Container = fraMovies Then
For me that gives error 450 Wrong number of arguments or invalid property assignment. Do you get the same error?
The code should use Is rather than =, like this
' GOOD CODE '
If ctrl.Container Is fraMovies Then
Explanation. You want to check whether two variables "point" to the same control. Controls are objects: you must use Is not = to check whether two object variables "point" to the same object. This is a classic pitfall in VB6.
One last word. Next time, could you try to post 10 lines or less of actual code, reproducing the error, and give the exact error number and message and the exact line on which it occurs? It really does make it much easier for us to solve your problem - I know it's work for you to shorten the code, but you'll get better answers that way.
EDIT Welcome back! :) You said some controls don't have a Container property. You could try wrapping the test in On Error Resume Next, something like this.
' GOOD CODE '
Dim bMatch As Boolean
Dim ctrl As Control
For Each ctrl In Me.Controls
bMatch = False
On Error Resume Next
bMatch = (ctrl.Container Is fraMovies)
On Error Goto 0
If bMatch Then
ctrl.Enabled = True
End If
Next
To avoid such problems follow the given rules while naming contols
When you name an element in your Visual Basic application, the first character of that name must be an alphabetic character or an underscore.
**Begin each separate word in a name with a capital letter, as in FindLastRecord and RedrawMyForm.
Begin function and method names with a verb, as in InitNameArray or CloseDialog.
Begin class, structure, module, and property names with a noun, as in EmployeeName or CarAccessory.
Begin interface names with the prefix "I", followed by a noun or a noun phrase, like IComponent, or with an adjective describing the interface's behavior, like IPersistable. Do not use the underscore, and use abbreviations sparingly, because abbreviations can cause confusion.
Begin event handler names with a noun describing the type of event followed by the "EventHandler" suffix, as in "MouseEventHandler".
In names of event argument classes, include the "EventArgs" suffix.
If an event has a concept of "before" or "after," use a suffix in present or past tense, as in "ControlAdd" or "ControlAdded".
For long or frequently used terms, use abbreviations to keep name lengths reasonable, for example, "HTML", instead of "Hypertext Markup Language". In general, variable names greater than 32 characters are difficult to read on a monitor set to a low resolution. Also, make sure your abbreviations are consistent throughout the entire application. Randomly switching in a project between "HTML" and "Hypertext Markup Language" can lead to confusion.
Avoid using names in an inner scope that are the same as names in an outer scope. Errors can result if the wrong variable is accessed. If a conflict occurs between a variable and the keyword of the same name, you must identify the keyword by preceding it with the appropriate type library. For example, if you have a variable called Date, you can use the intrinsic Date function only by calling DateTime.Date.

How to add connection points in Visio 2013 using Vbscript

I am trying to add connection points to a shape via Vbscript code. The following lines are the only ones I have tried that don't cause an error but they actually don't create the connection point I am looking for.
Set Vapp = GetObject(,"visio.application")
Set VP = Vapp.activewindow
VP.Page.Shapes.ItemFromID(26).CellsSRC(VisSectionConnectionPts,0, VisCnnctX).FormulaU = ".0815"
VP.Page.Shapes.ItemFromID(26).CellsSRC(visSectionConnectionPts, 0, visCnnctY).FormulaU = ".0710"
It's noteworthy that using "vis" does not work in such commands as:
VP.Shapes.ItemFromID(26).CellsU("LineColor").Formula = "rgb(255,192,0)"
And notice that I had to enclose LineColor in parentheses, but that does not work with the connection point commands. What am I missing?
I found my answer (http://www.activecallcenter.com/manual/306.htm).
Since Vbscript does not know what Visio constants such as VisSectionConnectionPts are, I have to look up the index number for VisSectionConnectionPts in the Visio object library. Using the index numbers for these constants works just fine.

Resources