Display a drop-down/combo box in VB Script - scripting

I'm trying to create a drop-down/combo box in VB Script. As per my understanding we need to create an instance for Internet Explorer and create a drop-down/combo box, something like this:
set oIE = createObject("InternetExplorer.Application")
with oIE
.Navigate "about:blank"
Do until .ReadyState = 4 : WScript.Sleep 100 : Loop
set oDoc = .document
.Visible = true
end with
with oDoc
.open
.writeln "<html><head><title>ComboBox Example</title></head>"
.writeln "<body scroll=no><object "
.writeln "classid=clsid:8BD21D30-EC42-11CE-9E0D-00AA006002F3"
.writeln "id=ComboBox1 width=400></object><p>"
.writeln "</body></html>"
.close
Do until .ReadyState = "complete" : WScript.Sleep 100 : Loop
set oComboBox1 = .all.ComboBox1
end with
with oComboBox1
.List = Array("One", "Two", "Three", "Four")
.AutoWordSelect = true
.focus
end with
oDoc.parentWindow.opener = "Me"
bClosing = false
on error resume next
do until bclosing: wsh.sleep 100 : loop
oIE.quit
sub Closing : bClosing = True : end sub
Is it possible to create an dorp-down/combo box without using IE, similar to Message Box or Input Box?

I'm quite sure many users here will glad to answer on this question, and their reply may hold varied details, but for sure the answer w'd been the same - No. At least not with pure VBScript and without programming your own ActiveX component, which then to instantinate with CreateObject inside your .vbs script.
But if you looking for alternative then may consider HTA as an option for your own custom GUI.

Related

Object required when using GetElementByName in VBscript

Im using the following code but get object required on my getelementbyname field. Does anyone know what is going on here?
I tried so many variations:
WScript.Quit Main
Call Main
Function Main
Set IE = CreateObject("InternetExplorer.Application")
IE.Visible = True
IE.Navigate "myurlsamle"
WScript.Sleep 8000
With IE
.document.getElementsByName("UsernameTextBox").value = "myusername"
.document.getElementsByName("PasswordTextBox").value = "mypassword"
End With
End Function

Unable to switch to a new tab in an efficient manner

I've written a script in vba which is able to click on a certain link (Draw a map) of a webpage. When the clicking is done, a new tab opens up containing information I would like to grab from. My script can do all these errorlessly. Upon running the script it scrapes the title visible as Make a Google Map from a GPS file from the new tab.
My question: is there any alternative way to switch to new tab other than using hardcoded search like If IE.LocationURL Like "*" & "output_geocoder" Then?
This is my script:
Sub FetchInfo()
Const url As String = "http://www.gpsvisualizer.com/geocoder/"
Dim IE As New InternetExplorer, Html As HTMLDocument, R&
Dim winShell As New Shell
With IE
.Visible = True
.navigate url
While .Busy = True Or .readyState < 4: DoEvents: Wend
Set Html = .document
End With
Html.querySelector("input[value$='map']").Click
For Each IE In winShell.Windows
If IE.LocationURL Like "*" & "output_geocoder" Then
IE.Visible = True
While IE.Busy = True Or IE.readyState < 4: DoEvents: Wend
Set Html = IE.document
Exit For
End If
Next
Set post = Html.querySelector("h1")
MsgBox post.innerText
IE.Quit
End Sub
To execute the above script, add this reference to the library:
Microsoft Shell Controls And Automation
Microsoft Internet Controls
Microsoft HTML Object Library
Btw, there is nothing wrong with the above script. I only wish to know any better way to do the same.
This is the best I have so far with selenium
Option Explicit
Public Sub GetInfo()
Dim d As WebDriver
Set d = New ChromeDriver
Const url = "http://www.gpsvisualizer.com/geocoder/"
With d
.Start "Chrome"
.get url
.FindElementByCss("input[value$='map']").Click
.SwitchToNextWindow
.FindElementByCss("input.gpsv_submit").Click
MsgBox .Title
Stop
.Quit
End With
End Sub
The more fixed with title is:
.SwitchToWindowByTitle("GPS Visualizer: Draw a map from a GPS data file").Activate
.FindElementByCss("input.gpsv_submit").Click
tl;dr;
I will need to read up more on how robust .SwitchToNextWindow is.
FYI, you can get handles info with:
Dim hwnds As List
Set hwnds = driver.Send("GET", "/window_handles")

VBA IE change dropdown value

Tried the below code for following URL Scripture look up. Please how to change drop down value from WEB to RV1909?
Dim Doc As HTMLDocument
Set Doc = IEApp.document
TestV2 = ""
TestV3 = ""
TestV2 = Doc.getElementsByClassName("app-list text-list")(0).innerText
Debug.Print "4b of 5: " & TestV2
IEApp.Doc.getElementsByClassName("app-list text-list").selectedIndex = 1
IEApp.Doc.getElementsByClassName("app-list text-list").FireEvent ("onchange")
TestV3 = Doc.getElementsByClassName("app-list text-list")(0).innerText
Debug.Print "4c of 5: " & TestV3
Tried many approaches from other posts, the following does not work:
IEApp.Doc.getElementsByClassName("app-list text-list")(0).innerHTML = "RV1909"
Here is the screenshot of Chrome Inspector:
In this case it's not enough just change div.app-list.text-list element innerText, as you can see that element is simple div, but not even ul. It should be changed by scripts which are called on click events. So, first of all you need to click on div to display the entire list, and then click on the RV1909 item. The below example shows how that could be done:
Sub Test()
Dim oIE As Object
Dim oDiv As Object
Set oIE = CreateObject("InternetExplorer.Application")
With oIE
.Visible = True
.Navigate "http://ebible.org/study/"
Do While .readyState <> 4 Or .Busy
DoEvents
Loop
With .Document
Do While .readyState <> "complete"
DoEvents
Loop
Set oDiv = .getElementsByClassName("app-list text-list")(0)
oDiv.Click
Do While .readyState <> "complete"
DoEvents
Loop
For Each oNode In .getElementsByClassName("text-chooser-main")(0).getElementsByClassName("text-chooser-abbr")
If oNode.innerText = "RV1909" Then
oNode.Click
Do While oDiv.innerText <> "RV1909"
DoEvents
Loop
Exit For
End If
Next
End With
End With
End Sub
Change the html div element <div class=app-list text-list>WEB</div> to <div class=app-list text-list>RV1909</div>

Error received when downloading a file from web when only submit button is present

I need to download a file from web, but only a submit button is present.
There is no url for reaching the file directly.
I tried to catch the button by its id, but VBA drops run-time error '424' (Object required).
Here is the code:
Sub keler_submit()
Application.ScreenUpdating = False
Set IE = CreateObject("InternetExplorer.Application")
IE.navigate "https://www.keler.hu/T%C3%A1rsas%C3%A1gi%20esem%C3%A9nyek/"
While IE.Busy
DoEvents
Wend
Set doc = IE.document
gomb = doc.getElementById("ctl00_wpm_UserControlPortlet1682286671_ctl00_wpm_UserControlPortlet1682286671_userControlPortlet_DownloadButton1")
gomb.submit
Set IE = Nothing
Application.ScreenUpdating = True
End Sub
Thank you in advance
These lines are incorrect:
gomb = doc.getElementById("ctl00_wpm_UserControlPortlet1682286671_ctl00_wpm_UserControlPortlet1682286671_userControlPortlet_DownloadButton1")
gomb.submit
doc.getElementById returns an object type so you need to use Set to assign it to a variable. The element you are trying to access should then be clicked instead of submitted. There's a high probability that IE will display a "Do you wish to open or save this file" dialog so start by making the IE object visible to show this:
IE.visible = True
Set gomb = doc.getElementById("ctl00_wpm_UserControlPortlet1682286671_ctl00_wpm_UserControlPortlet1682286671_userControlPortlet_DownloadButton1")
gomb.click
You need a loop in there as well to ensure page has loaded. The following works:
Option Explicit
Public Sub GetInfo()
Dim IE As New InternetExplorer
With IE
.Visible = True
.navigate "https://www.keler.hu/T%C3%A1rsas%C3%A1gi%20esem%C3%A9nyek/"
While .Busy Or .readyState < 4: DoEvents: Wend
Do
Dim b As Object
On Error Resume Next
Set b = .document.getElementById("ctl00_wpm_UserControlPortlet1682286671_ctl00_wpm_UserControlPortlet1682286671_userControlPortlet_DownloadButton1")
On Error GoTo 0
Loop While b Is Nothing
b.Click
'Handle save button
'Quit '<== Remember to quit application
End With
End Sub

VBA Object Required Error Trying To Get InnerText

I am trying to create a code that will go to a website, put in data, submit it, and then return the answer to a cell in excel. When I step through it, it works fine, but when I just try to run it, I get run-time error 424; Object Required.
I tried looking for a good answer, but I am just not grasping on how to quite fix this. Where is my issue? How do I correct it?
Sub Distance()
Dim IE As Object
' Create InternetExplorer Object
Set IE = CreateObject("InternetExplorer.Application")
' Make visible
IE.Visible = True
' Go to site
IE.Navigate "http://www.distance-cities.com/"
' Wait while IE loading...
Do Until IE.READYSTATE = 4
DoEvents
Loop
IE.Document.getelementbyId("from").Value = "Stillwater, OK"
IE.Document.getelementbyId("to").Value = "Hollis, OK"
IE.Document.forms(0).submit
Do Until IE.READYSTATE = 4
DoEvents
Loop
'*Below is where I get my error
Sheet1.Range("E5").Value = IE.Document.getelementbyId("routemi").InnerText
IE.Quit
End Sub
I apologize if this is a bit messy.
Thanks for you help!
Something like this (untested):
Dim el as object
'...
Set el = WaitForElement(IE.Document, "routemi", 1)
If Not el is Nothing Then
Sheet1.Range("E5").Value = el.innerText
Else
Msgbox "Element 'routemi' not found!"
Exit Sub
End if
Utility function to get an element by id, waiting until it appears:
Function WaitForElement(doc As Object, id As String, maxWaitSec As Double) As Object
Dim rv As Object, t
t = Timer
Do
Set rv = doc.getElementById(id)
DoEvents
Loop While rv Is Nothing And (Timer - t) < maxWaitSec
Set WaitForElement = rv
End Function
You need to leave proper waits at each point (after .Navigate2 and .Click) to allow for page loading. I use CSS selectors to target ids as modern browsers are optimized for CSS. Also, I updated method for page navigation to .Navigate2.
Option Explicit
Public Sub Distance()
Dim ie As New InternetExplorer
With ie
.Visible = True
.Navigate2 "http://www.distance-cities.com/"
While .Busy Or .readyState < 4: DoEvents: Wend
With .document
.querySelector("#from").Value = "Stillwater, OK"
.querySelector("#to").Value = "Hollis, OK"
.querySelector("[type=submit]").Click
End With
While .Busy Or .readyState < 4: DoEvents: Wend
Debug.Print .document.querySelector("#routemi").innerText
.Quit
End With
End Sub