IE Automation - checkbox

  • Thread starter Matthew Herbert
  • Start date
M

Matthew Herbert

All,

My question relates to the code listed in "ListCheckBoxes" below. You
should be able to simply copy and paste all the VBA code below and run
"ListCheckBoxes" in order to follow the logic of my code.

I'm looking for a "better" way of obtaining the collection of web browser
checkbox controls for the following URL:
http://www.zacks.com/screening/custom/view.php?sid=87639 (and a small sample
of the HTML is also below), so that I can check the desired check boxes based
on the text description that lines up with the checkbox. (See the website
for a visual representation).

My Desired Goal:
Since each checkbox has a description (e.g. "52 Week High", "Market Cap
(millions)", etc.), I plan on using the description as a way to identify
whether the checkbox should be checked. The user will have a list of
descriptions in the spreadsheet. The program will then loop through the
spreadsheet list, search the description text for a match (the
".parentElement.parentElement.innerText" portion below, which can be combined
with InStr to find a "match"), and check the checkbox if a match exists.

Again, I'm looking for a "better" way to do this. My IE automation
knowledge is very limited, so I don't know if there is a way to get the
object collection via the class (i.e. "tdata1", and I don't know how or if
getting a collection from the class is possible), the name (i.e.
"p_columns[]"), the tag (i.e. "input"), etc. Or, maybe there is simply a
better way than my current logic. I'm open to suggestions and general
knowledge that may help me better understand IE automation. (For example, is
adding a reference to "Microsoft HTML Object Library", opening the Object
Browser, and then searching the HTML* classes a good way to "discover/learn"
IE automation? It's probably a loaded question that doesn't have a "great"
answer.)

Thanks,

Matthew Herbert

VBA:

Private Sub ListCheckBoxes()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim objArr() As Object
Dim lngCnt As Long
Dim strURL As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
Set objIE = CreateObject("InternetExplorer.Application")
objIE.Visible = True
objIE.Navigate strURL
WaitForLoad objIE
End If

Set objTarget = objIE.document.all.tags("input")

'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")

For Each Obj In objTarget
If Obj.Type = "checkbox" Then
ReDim Preserve objArr(lngCnt)
Set objArr(lngCnt) = Obj
lngCnt = lngCnt + 1
End If
Next Obj

For lngCnt = LBound(objArr) To UBound(objArr)
Set Obj = objArr(lngCnt)
With Obj
'listed properties are some of what is viewable
' from "View Source" and what is embedded in
' the tag

'not sure how to list the "class" though
Debug.Print "lngCnt :" & lngCnt
Debug.Print " Prnt.Prnt:" & .parentElement.parentElement.innerText
Debug.Print " name :" & .Name
Debug.Print " type :" & .Type
Debug.Print " value :" & .Value
Debug.Print " id :" & .ID
Debug.Print " innerHTML:" & .innerHTML
Debug.Print " innerText:" & .innerText

'check the box
'.Checked = True
End With
Next lngCnt

End Sub

Function GetIE(strAddress As String) As Object
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' ??/??/2007, Matthew Herbert
'---------------------------------------------------------------------
Dim objShell As Object
Dim objShellWindows As Object
Dim Obj As Object
Dim objRes As Object
Dim strURL As String

Set objRes = Nothing
Set objShell = CreateObject("Shell.Application")
Set objShellWindows = objShell.Windows

'see if IE is already open
For Each Obj In objShellWindows
strURL = ""
On Error Resume Next
strURL = Obj.document.Location
On Error GoTo 0
If strURL <> "" Then
If strURL Like strAddress & "*" Then
Set objRes = Obj
Exit For
End If
End If
Next Obj
Set GetIE = objRes
End Function

Sub WaitForLoad(objIE As Object)
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' 07/08/2009, Matthew Herbert
'---------------------------------------------------------------------
Do Until objIE.Busy = False And objIE.readyState = 4
Application.Wait (Now() + TimeValue("0:00:01"))
DoEvents
Loop
End Sub


HTML Sample, which was a simple copy and paste from View Source:
<div class="restable">
<span class="nudge select_choose_header">Select Criteria</span>
<div id="criteriaBox">
<table id="table10000" class="viewCriteria" cellspacing=0 cellpadding=0>
<tr>
<td class="textB" colspan=2>Popular Items</td>
</tr>
<tr><td class=tdata1>Current Zacks Rank
<a class="hand" onclick="show('div_15005');"
onmouseout="hide('div_15005');"><img src="/images/help_q.jpg" class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_15005" onmouseover="show('div_15005');"
onmouseout="hide('div_15005');">Shortened for brevity's sake</div>
</td>

<td class=tdata1 width=20><a
href="https://www.zacks.com/registration/...ssage=&continue_to=/screening/custom/view.php"><img
src="/images/premium_small.gif" border=0></a></td>
</tr><tr><td class=tdata1>Zacks Industry Rank
<a class="hand" onclick="show('div_15025');"
onmouseout="hide('div_15025');"><img src="/images/help_q.jpg" class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_15025" onmouseover="show('div_15025');"
onmouseout="hide('div_15025');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><a
href="https://www.zacks.com/registration/...ssage=&continue_to=/screening/custom/view.php"><img
src="/images/premium_small.gif" border=0></a></td>
</tr><tr><td class=tdata1>52 Week High
<a class="hand" onclick="show('div_14010');"
onmouseout="hide('div_14010');"><img src="/images/help_q.jpg" class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_14010" onmouseover="show('div_14010');"
onmouseout="hide('div_14010');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><input type=checkbox name=p_columns[]
value="14010" onclick="javascript:checkFormForDups(this, this.checked,
14010);"></td>
</tr><tr><td class=tdata1>Market Cap (millions)
<a class="hand" onclick="show('div_12010');"
onmouseout="hide('div_12010');"><img src="/images/help_q.jpg" class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_12010" onmouseover="show('div_12010');"
onmouseout="hide('div_12010');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><input type=checkbox name=p_columns[]
value="12010" checked onclick="javascript:checkFormForDups(this,
this.checked, 12010);"></td>
</tr><tr><td class=tdata1>Last EPS Surprise (%)
<a class="hand" onclick="show('div_17005');"
onmouseout="hide('div_17005');"><img src="/images/help_q.jpg" class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_17005" onmouseover="show('div_17005');"
onmouseout="hide('div_17005');"> Shortened for brevity's sake </div>
</td>
 
T

Tim Williams

Matt,
'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")

Should work if you correct the typo in "document" ;-)

Tim



Matthew Herbert said:
All,

My question relates to the code listed in "ListCheckBoxes" below. You
should be able to simply copy and paste all the VBA code below and run
"ListCheckBoxes" in order to follow the logic of my code.

I'm looking for a "better" way of obtaining the collection of web browser
checkbox controls for the following URL:
http://www.zacks.com/screening/custom/view.php?sid=87639 (and a small
sample
of the HTML is also below), so that I can check the desired check boxes
based
on the text description that lines up with the checkbox. (See the website
for a visual representation).

My Desired Goal:
Since each checkbox has a description (e.g. "52 Week High", "Market Cap
(millions)", etc.), I plan on using the description as a way to identify
whether the checkbox should be checked. The user will have a list of
descriptions in the spreadsheet. The program will then loop through the
spreadsheet list, search the description text for a match (the
".parentElement.parentElement.innerText" portion below, which can be
combined
with InStr to find a "match"), and check the checkbox if a match exists.

Again, I'm looking for a "better" way to do this. My IE automation
knowledge is very limited, so I don't know if there is a way to get the
object collection via the class (i.e. "tdata1", and I don't know how or if
getting a collection from the class is possible), the name (i.e.
"p_columns[]"), the tag (i.e. "input"), etc. Or, maybe there is simply a
better way than my current logic. I'm open to suggestions and general
knowledge that may help me better understand IE automation. (For example,
is
adding a reference to "Microsoft HTML Object Library", opening the Object
Browser, and then searching the HTML* classes a good way to
"discover/learn"
IE automation? It's probably a loaded question that doesn't have a
"great"
answer.)

Thanks,

Matthew Herbert

VBA:

Private Sub ListCheckBoxes()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim objArr() As Object
Dim lngCnt As Long
Dim strURL As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
Set objIE = CreateObject("InternetExplorer.Application")
objIE.Visible = True
objIE.Navigate strURL
WaitForLoad objIE
End If

Set objTarget = objIE.document.all.tags("input")

'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")

For Each Obj In objTarget
If Obj.Type = "checkbox" Then
ReDim Preserve objArr(lngCnt)
Set objArr(lngCnt) = Obj
lngCnt = lngCnt + 1
End If
Next Obj

For lngCnt = LBound(objArr) To UBound(objArr)
Set Obj = objArr(lngCnt)
With Obj
'listed properties are some of what is viewable
' from "View Source" and what is embedded in
' the tag

'not sure how to list the "class" though
Debug.Print "lngCnt :" & lngCnt
Debug.Print " Prnt.Prnt:" & .parentElement.parentElement.innerText
Debug.Print " name :" & .Name
Debug.Print " type :" & .Type
Debug.Print " value :" & .Value
Debug.Print " id :" & .ID
Debug.Print " innerHTML:" & .innerHTML
Debug.Print " innerText:" & .innerText

'check the box
'.Checked = True
End With
Next lngCnt

End Sub

Function GetIE(strAddress As String) As Object
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' ??/??/2007, Matthew Herbert
'---------------------------------------------------------------------
Dim objShell As Object
Dim objShellWindows As Object
Dim Obj As Object
Dim objRes As Object
Dim strURL As String

Set objRes = Nothing
Set objShell = CreateObject("Shell.Application")
Set objShellWindows = objShell.Windows

'see if IE is already open
For Each Obj In objShellWindows
strURL = ""
On Error Resume Next
strURL = Obj.document.Location
On Error GoTo 0
If strURL <> "" Then
If strURL Like strAddress & "*" Then
Set objRes = Obj
Exit For
End If
End If
Next Obj
Set GetIE = objRes
End Function

Sub WaitForLoad(objIE As Object)
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' 07/08/2009, Matthew Herbert
'---------------------------------------------------------------------
Do Until objIE.Busy = False And objIE.readyState = 4
Application.Wait (Now() + TimeValue("0:00:01"))
DoEvents
Loop
End Sub


HTML Sample, which was a simple copy and paste from View Source:
<div class="restable">
<span class="nudge select_choose_header">Select Criteria</span>
<div id="criteriaBox">
<table id="table10000" class="viewCriteria" cellspacing=0 cellpadding=0>
<tr>
<td class="textB" colspan=2>Popular Items</td>
</tr>
<tr><td class=tdata1>Current Zacks Rank
<a class="hand" onclick="show('div_15005');"
onmouseout="hide('div_15005');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_15005" onmouseover="show('div_15005');"
onmouseout="hide('div_15005');">Shortened for brevity's sake</div>
</td>

<td class=tdata1 width=20><a
href="https://www.zacks.com/registration/...ssage=&continue_to=/screening/custom/view.php"><img
src="/images/premium_small.gif" border=0></a></td>
</tr><tr><td class=tdata1>Zacks Industry Rank
<a class="hand" onclick="show('div_15025');"
onmouseout="hide('div_15025');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_15025" onmouseover="show('div_15025');"
onmouseout="hide('div_15025');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><a
href="https://www.zacks.com/registration/...ssage=&continue_to=/screening/custom/view.php"><img
src="/images/premium_small.gif" border=0></a></td>
</tr><tr><td class=tdata1>52 Week High
<a class="hand" onclick="show('div_14010');"
onmouseout="hide('div_14010');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_14010" onmouseover="show('div_14010');"
onmouseout="hide('div_14010');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><input type=checkbox name=p_columns[]
value="14010" onclick="javascript:checkFormForDups(this, this.checked,
14010);"></td>
</tr><tr><td class=tdata1>Market Cap (millions)
<a class="hand" onclick="show('div_12010');"
onmouseout="hide('div_12010');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_12010" onmouseover="show('div_12010');"
onmouseout="hide('div_12010');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><input type=checkbox name=p_columns[]
value="12010" checked onclick="javascript:checkFormForDups(this,
this.checked, 12010);"></td>
</tr><tr><td class=tdata1>Last EPS Surprise (%)
<a class="hand" onclick="show('div_17005');"
onmouseout="hide('div_17005');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_17005" onmouseover="show('div_17005');"
onmouseout="hide('div_17005');"> Shortened for brevity's sake </div>
</td>
 
M

Matthew Herbert

Tim,

As always, thank you for the help. Yes, it was a matter of checking my own
spelling. You have helped me in the past, and I appreciate the help now.
When I do need to do IE automation, I usually end up doing an Advanced Search
for your posts. However, I'm still far removed from truly knowing the "best"
way to do IE automation.

For example, I don't know the best way to get the checkbox description text.
So, if you open the webpage you see the following:
52 Week High (Question Mark Picture) [checkbox] (for which the HTML can be
found in the chain).

I can tell that the <tr> tag is prior to "52 Week High" and that a <div> tag
seems to be associated with the mouseover text. In my code, the
".parentElement.parentElement.innerText" returns "52 Week High + the
mouseover text". I simply want "52 Week High". I found a previous post that
had code that I thought might be helpful:

retVal = o.Document.getElementById("member-jacket").rows[0].cells[0].innerText

However, I don't know if I'm thinking about this the right way, i.e. trying
to access the text of a specific row/cell. (I'm also assuming that HTML
tables have rows, columns, and/or cells; however, I don't know how a
rows/columns delineation -- like in an Excel spreadsheet -- is different than
the rows[0].cells[0] shown above. Logic tells me that rows[0].cells[0] is
the first row, first cell).

Do you have advice for getting the "52 Week High" portion of text? (Right
now, it appears that the <div> text is preceeded by a double space, but I
don't want to rely on using a double space as a way of separating the <tr>
text from the <div> text).

Thanks,

Matt

Set objTarget = objIE.document.getElementsByName("p_columns[]")

lngCnt = 0
For Each Obj In objTarget
Set objDesc = Obj.parentElement.parentElement

'not sure what to do here to get the <tr> text
strText = objDesc.innerText

Tim Williams said:
Matt,
'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")

Should work if you correct the typo in "document" ;-)

Tim



Matthew Herbert said:
All,

My question relates to the code listed in "ListCheckBoxes" below. You
should be able to simply copy and paste all the VBA code below and run
"ListCheckBoxes" in order to follow the logic of my code.

I'm looking for a "better" way of obtaining the collection of web browser
checkbox controls for the following URL:
http://www.zacks.com/screening/custom/view.php?sid=87639 (and a small
sample
of the HTML is also below), so that I can check the desired check boxes
based
on the text description that lines up with the checkbox. (See the website
for a visual representation).

My Desired Goal:
Since each checkbox has a description (e.g. "52 Week High", "Market Cap
(millions)", etc.), I plan on using the description as a way to identify
whether the checkbox should be checked. The user will have a list of
descriptions in the spreadsheet. The program will then loop through the
spreadsheet list, search the description text for a match (the
".parentElement.parentElement.innerText" portion below, which can be
combined
with InStr to find a "match"), and check the checkbox if a match exists.

Again, I'm looking for a "better" way to do this. My IE automation
knowledge is very limited, so I don't know if there is a way to get the
object collection via the class (i.e. "tdata1", and I don't know how or if
getting a collection from the class is possible), the name (i.e.
"p_columns[]"), the tag (i.e. "input"), etc. Or, maybe there is simply a
better way than my current logic. I'm open to suggestions and general
knowledge that may help me better understand IE automation. (For example,
is
adding a reference to "Microsoft HTML Object Library", opening the Object
Browser, and then searching the HTML* classes a good way to
"discover/learn"
IE automation? It's probably a loaded question that doesn't have a
"great"
answer.)

Thanks,

Matthew Herbert

VBA:

Private Sub ListCheckBoxes()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim objArr() As Object
Dim lngCnt As Long
Dim strURL As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
Set objIE = CreateObject("InternetExplorer.Application")
objIE.Visible = True
objIE.Navigate strURL
WaitForLoad objIE
End If

Set objTarget = objIE.document.all.tags("input")

'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")

For Each Obj In objTarget
If Obj.Type = "checkbox" Then
ReDim Preserve objArr(lngCnt)
Set objArr(lngCnt) = Obj
lngCnt = lngCnt + 1
End If
Next Obj

For lngCnt = LBound(objArr) To UBound(objArr)
Set Obj = objArr(lngCnt)
With Obj
'listed properties are some of what is viewable
' from "View Source" and what is embedded in
' the tag

'not sure how to list the "class" though
Debug.Print "lngCnt :" & lngCnt
Debug.Print " Prnt.Prnt:" & .parentElement.parentElement.innerText
Debug.Print " name :" & .Name
Debug.Print " type :" & .Type
Debug.Print " value :" & .Value
Debug.Print " id :" & .ID
Debug.Print " innerHTML:" & .innerHTML
Debug.Print " innerText:" & .innerText

'check the box
'.Checked = True
End With
Next lngCnt

End Sub

Function GetIE(strAddress As String) As Object
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' ??/??/2007, Matthew Herbert
'---------------------------------------------------------------------
Dim objShell As Object
Dim objShellWindows As Object
Dim Obj As Object
Dim objRes As Object
Dim strURL As String

Set objRes = Nothing
Set objShell = CreateObject("Shell.Application")
Set objShellWindows = objShell.Windows

'see if IE is already open
For Each Obj In objShellWindows
strURL = ""
On Error Resume Next
strURL = Obj.document.Location
On Error GoTo 0
If strURL <> "" Then
If strURL Like strAddress & "*" Then
Set objRes = Obj
Exit For
End If
End If
Next Obj
Set GetIE = objRes
End Function

Sub WaitForLoad(objIE As Object)
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' 07/08/2009, Matthew Herbert
'---------------------------------------------------------------------
Do Until objIE.Busy = False And objIE.readyState = 4
Application.Wait (Now() + TimeValue("0:00:01"))
DoEvents
Loop
End Sub


HTML Sample, which was a simple copy and paste from View Source:
<div class="restable">
<span class="nudge select_choose_header">Select Criteria</span>
<div id="criteriaBox">
<table id="table10000" class="viewCriteria" cellspacing=0 cellpadding=0>
<tr>
<td class="textB" colspan=2>Popular Items</td>
</tr>
<tr><td class=tdata1>Current Zacks Rank
<a class="hand" onclick="show('div_15005');"
onmouseout="hide('div_15005');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_15005" onmouseover="show('div_15005');"
onmouseout="hide('div_15005');">Shortened for brevity's sake</div>
</td>

<td class=tdata1 width=20><a
href="https://www.zacks.com/registration/...ssage=&continue_to=/screening/custom/view.php"><img
src="/images/premium_small.gif" border=0></a></td>
</tr><tr><td class=tdata1>Zacks Industry Rank
<a class="hand" onclick="show('div_15025');"
onmouseout="hide('div_15025');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_15025" onmouseover="show('div_15025');"
onmouseout="hide('div_15025');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><a
href="https://www.zacks.com/registration/...ssage=&continue_to=/screening/custom/view.php"><img
src="/images/premium_small.gif" border=0></a></td>
</tr><tr><td class=tdata1>52 Week High
<a class="hand" onclick="show('div_14010');"
onmouseout="hide('div_14010');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_14010" onmouseover="show('div_14010');"
onmouseout="hide('div_14010');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><input type=checkbox name=p_columns[]
value="14010" onclick="javascript:checkFormForDups(this, this.checked,
14010);"></td>
</tr><tr><td class=tdata1>Market Cap (millions)
<a class="hand" onclick="show('div_12010');"
onmouseout="hide('div_12010');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_12010" onmouseover="show('div_12010');"
onmouseout="hide('div_12010');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><input type=checkbox name=p_columns[]
value="12010" checked onclick="javascript:checkFormForDups(this,
this.checked, 12010);"></td>
</tr><tr><td class=tdata1>Last EPS Surprise (%)
<a class="hand" onclick="show('div_17005');"
onmouseout="hide('div_17005');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_17005" onmouseover="show('div_17005');"
onmouseout="hide('div_17005');"> Shortened for brevity's sake </div>
</td>


.
 
M

Matthew Herbert

Tim,

Well, this is more of a reply to myself, but I've listed the code below that
I'm currently using to get the description text for the checkbox. I'll use
this unless there is a "better" way.

Best,

Matt

Private Sub ListCheckBoxDescriptionText()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim strURL As String
Dim objDesc As Object
Dim strText As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
Set objIE = CreateObject("InternetExplorer.Application")
objIE.Visible = True
objIE.Navigate strURL
WaitForLoad objIE
End If

Set objTarget = objIE.document.getElementsByName("p_columns[]")

For Each Obj In objTarget
Set objDesc = Obj.parentElement.parentElement
strText = GetFirstInnerText(objDesc.innerHTML)
Debug.Print strText
Next Obj

End Sub

Private Function GetFirstInnerText(strInnerHTML As String) As String
'---------------------------------------------------------------------
'INFO: 01/05/2010, Matthew Herbert
'---------------------------------------------------------------------
'PURPOSE: Get the first available innerText from strInnerHTML.
' Search for the ">" and then the "<" and get the
' text in the middle.
'
'strInnerHTML A text string of the .innerHTML property.
'
'RETURN: - An empty string, i.e. "", if no innerText is found.
' - The string between the ">" and "<".
'---------------------------------------------------------------------
'NOTES: THIS IS HARDLY TESTED! BE CAREFUL WHEN YOU USE THIS!
' Intended to deal with at least the following 2
' situations:
' (1) <tr><td class=tdata1>52 Week High<...
' (2) <td class=tdata1>52 Week High<...
'---------------------------------------------------------------------
Dim lngPosStart As Long
Dim lngPosEnd As Long
Dim strTemp As String

'initialize the position for the first time in the loop
' in order to get the InStr function to behave correctly
lngPosStart = 1
lngPosEnd = lngPosStart

Do
lngPosStart = InStr(lngPosEnd, strInnerHTML, ">", vbTextCompare)
If lngPosStart = 0 Then
GetFirstInnerText = ""
Exit Function
End If

lngPosEnd = InStr(lngPosStart + 1, strInnerHTML, "<", vbTextCompare)
If lngPosEnd = 0 Then
GetFirstInnerText = ""
Exit Function
End If
Loop Until lngPosEnd > lngPosStart + 1

'---------------------------------------------------------------------
'get the text in between the ">" and "<"

'want the position after the ">"
lngPosStart = lngPosStart + 1

'want the position before the "<"
lngPosEnd = lngPosEnd - 1

'guard against the following
If lngPosStart >= lngPosEnd Then
GetFirstInnerText = ""
Exit Function
End If

strTemp = Mid(strInnerHTML, lngPosStart, lngPosEnd - lngPosStart)
'---------------------------------------------------------------------

'replace any "&" with ""
strTemp = Replace(strTemp, "&", "")

'trim off any spaces
strTemp = Trim(strTemp)

GetFirstInnerText = strTemp

End Function



Matthew Herbert said:
Tim,

As always, thank you for the help. Yes, it was a matter of checking my own
spelling. You have helped me in the past, and I appreciate the help now.
When I do need to do IE automation, I usually end up doing an Advanced Search
for your posts. However, I'm still far removed from truly knowing the "best"
way to do IE automation.

For example, I don't know the best way to get the checkbox description text.
So, if you open the webpage you see the following:
52 Week High (Question Mark Picture) [checkbox] (for which the HTML can be
found in the chain).

I can tell that the <tr> tag is prior to "52 Week High" and that a <div> tag
seems to be associated with the mouseover text. In my code, the
".parentElement.parentElement.innerText" returns "52 Week High + the
mouseover text". I simply want "52 Week High". I found a previous post that
had code that I thought might be helpful:

retVal = o.Document.getElementById("member-jacket").rows[0].cells[0].innerText

However, I don't know if I'm thinking about this the right way, i.e. trying
to access the text of a specific row/cell. (I'm also assuming that HTML
tables have rows, columns, and/or cells; however, I don't know how a
rows/columns delineation -- like in an Excel spreadsheet -- is different than
the rows[0].cells[0] shown above. Logic tells me that rows[0].cells[0] is
the first row, first cell).

Do you have advice for getting the "52 Week High" portion of text? (Right
now, it appears that the <div> text is preceeded by a double space, but I
don't want to rely on using a double space as a way of separating the <tr>
text from the <div> text).

Thanks,

Matt

Set objTarget = objIE.document.getElementsByName("p_columns[]")

lngCnt = 0
For Each Obj In objTarget
Set objDesc = Obj.parentElement.parentElement

'not sure what to do here to get the <tr> text
strText = objDesc.innerText

Tim Williams said:
Matt,
'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")

Should work if you correct the typo in "document" ;-)

Tim



Matthew Herbert said:
All,

My question relates to the code listed in "ListCheckBoxes" below. You
should be able to simply copy and paste all the VBA code below and run
"ListCheckBoxes" in order to follow the logic of my code.

I'm looking for a "better" way of obtaining the collection of web browser
checkbox controls for the following URL:
http://www.zacks.com/screening/custom/view.php?sid=87639 (and a small
sample
of the HTML is also below), so that I can check the desired check boxes
based
on the text description that lines up with the checkbox. (See the website
for a visual representation).

My Desired Goal:
Since each checkbox has a description (e.g. "52 Week High", "Market Cap
(millions)", etc.), I plan on using the description as a way to identify
whether the checkbox should be checked. The user will have a list of
descriptions in the spreadsheet. The program will then loop through the
spreadsheet list, search the description text for a match (the
".parentElement.parentElement.innerText" portion below, which can be
combined
with InStr to find a "match"), and check the checkbox if a match exists.

Again, I'm looking for a "better" way to do this. My IE automation
knowledge is very limited, so I don't know if there is a way to get the
object collection via the class (i.e. "tdata1", and I don't know how or if
getting a collection from the class is possible), the name (i.e.
"p_columns[]"), the tag (i.e. "input"), etc. Or, maybe there is simply a
better way than my current logic. I'm open to suggestions and general
knowledge that may help me better understand IE automation. (For example,
is
adding a reference to "Microsoft HTML Object Library", opening the Object
Browser, and then searching the HTML* classes a good way to
"discover/learn"
IE automation? It's probably a loaded question that doesn't have a
"great"
answer.)

Thanks,

Matthew Herbert

VBA:

Private Sub ListCheckBoxes()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim objArr() As Object
Dim lngCnt As Long
Dim strURL As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
Set objIE = CreateObject("InternetExplorer.Application")
objIE.Visible = True
objIE.Navigate strURL
WaitForLoad objIE
End If

Set objTarget = objIE.document.all.tags("input")

'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")

For Each Obj In objTarget
If Obj.Type = "checkbox" Then
ReDim Preserve objArr(lngCnt)
Set objArr(lngCnt) = Obj
lngCnt = lngCnt + 1
End If
Next Obj

For lngCnt = LBound(objArr) To UBound(objArr)
Set Obj = objArr(lngCnt)
With Obj
'listed properties are some of what is viewable
' from "View Source" and what is embedded in
' the tag

'not sure how to list the "class" though
Debug.Print "lngCnt :" & lngCnt
Debug.Print " Prnt.Prnt:" & .parentElement.parentElement.innerText
Debug.Print " name :" & .Name
Debug.Print " type :" & .Type
Debug.Print " value :" & .Value
Debug.Print " id :" & .ID
Debug.Print " innerHTML:" & .innerHTML
Debug.Print " innerText:" & .innerText

'check the box
'.Checked = True
End With
Next lngCnt

End Sub

Function GetIE(strAddress As String) As Object
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' ??/??/2007, Matthew Herbert
'---------------------------------------------------------------------
Dim objShell As Object
Dim objShellWindows As Object
Dim Obj As Object
Dim objRes As Object
Dim strURL As String

Set objRes = Nothing
Set objShell = CreateObject("Shell.Application")
Set objShellWindows = objShell.Windows

'see if IE is already open
For Each Obj In objShellWindows
strURL = ""
On Error Resume Next
strURL = Obj.document.Location
On Error GoTo 0
If strURL <> "" Then
If strURL Like strAddress & "*" Then
Set objRes = Obj
Exit For
End If
End If
Next Obj
Set GetIE = objRes
End Function

Sub WaitForLoad(objIE As Object)
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' 07/08/2009, Matthew Herbert
'---------------------------------------------------------------------
Do Until objIE.Busy = False And objIE.readyState = 4
Application.Wait (Now() + TimeValue("0:00:01"))
DoEvents
Loop
End Sub


HTML Sample, which was a simple copy and paste from View Source:
<div class="restable">
<span class="nudge select_choose_header">Select Criteria</span>
<div id="criteriaBox">
<table id="table10000" class="viewCriteria" cellspacing=0 cellpadding=0>
<tr>
<td class="textB" colspan=2>Popular Items</td>
</tr>
<tr><td class=tdata1>Current Zacks Rank
<a class="hand" onclick="show('div_15005');"
onmouseout="hide('div_15005');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_15005" onmouseover="show('div_15005');"
onmouseout="hide('div_15005');">Shortened for brevity's sake</div>
</td>

<td class=tdata1 width=20><a
href="https://www.zacks.com/registration/...ssage=&continue_to=/screening/custom/view.php"><img
src="/images/premium_small.gif" border=0></a></td>
</tr><tr><td class=tdata1>Zacks Industry Rank
<a class="hand" onclick="show('div_15025');"
onmouseout="hide('div_15025');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_15025" onmouseover="show('div_15025');"
onmouseout="hide('div_15025');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><a
href="https://www.zacks.com/registration/...ssage=&continue_to=/screening/custom/view.php"><img
src="/images/premium_small.gif" border=0></a></td>
</tr><tr><td class=tdata1>52 Week High
<a class="hand" onclick="show('div_14010');"
onmouseout="hide('div_14010');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_14010" onmouseover="show('div_14010');"
onmouseout="hide('div_14010');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><input type=checkbox name=p_columns[]
value="14010" onclick="javascript:checkFormForDups(this, this.checked,
14010);"></td>
</tr><tr><td class=tdata1>Market Cap (millions)
<a class="hand" onclick="show('div_12010');"
onmouseout="hide('div_12010');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_12010" onmouseover="show('div_12010');"
onmouseout="hide('div_12010');"> Shortened for brevity's sake </div>
</td>

<td class=tdata1 width=20><input type=checkbox name=p_columns[]
value="12010" checked onclick="javascript:checkFormForDups(this,
this.checked, 12010);"></td>
</tr><tr><td class=tdata1>Last EPS Surprise (%)
<a class="hand" onclick="show('div_17005');"
onmouseout="hide('div_17005');"><img src="/images/help_q.jpg"
class="qPlace"
border="0"></a>
<div class=qdiv style="visibility: hidden; border: 1px solid black;"
id="div_17005" onmouseover="show('div_17005');"
onmouseout="hide('div_17005');"> Shortened for brevity's sake </div>
</td>


.
 
R

ron

Tim,

Well, this is more of a reply to myself, but I've listed the code below that
I'm currently using to get the description text for the checkbox.  I'lluse
this unless there is a "better" way.

Best,

Matt

Private Sub ListCheckBoxDescriptionText()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim strURL As String
Dim objDesc As Object
Dim strText As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
    Set objIE = CreateObject("InternetExplorer.Application")
    objIE.Visible = True
    objIE.Navigate strURL
    WaitForLoad objIE
End If

Set objTarget = objIE.document.getElementsByName("p_columns[]")

For Each Obj In objTarget
    Set objDesc = Obj.parentElement.parentElement
    strText = GetFirstInnerText(objDesc.innerHTML)
    Debug.Print strText
Next Obj

End Sub

Private Function GetFirstInnerText(strInnerHTML As String) As String
'---------------------------------------------------------------------
'INFO:          01/05/2010, Matthew Herbert
'---------------------------------------------------------------------
'PURPOSE:       Get the first available innerText from strInnerHTML..
'               Search for the ">" and then the "<" and getthe
'               text in the middle.
'
'strInnerHTML   A text string of the .innerHTML property.
'
'RETURN:        - An empty string, i.e. "", if no innerText is found.
'               - The string between the ">" and "<".
'---------------------------------------------------------------------
'NOTES:         THIS IS HARDLY TESTED!  BE CAREFUL WHEN YOU USETHIS!
'               Intended to deal with at least the following 2
'               situations:
'               (1) <tr><td class=tdata1>52 Week High<...
'               (2)     <td class=tdata1>52 Week High<...
'---------------------------------------------------------------------
Dim lngPosStart As Long
Dim lngPosEnd As Long
Dim strTemp As String

'initialize the position for the first time in the loop
'   in order to get the InStr function to behave correctly
lngPosStart = 1
lngPosEnd = lngPosStart

Do
    lngPosStart = InStr(lngPosEnd, strInnerHTML, ">", vbTextCompare)
    If lngPosStart = 0 Then
        GetFirstInnerText = ""
        Exit Function
    End If

    lngPosEnd = InStr(lngPosStart + 1, strInnerHTML, "<", vbTextCompare)
    If lngPosEnd = 0 Then
        GetFirstInnerText = ""
        Exit Function
    End If
Loop Until lngPosEnd > lngPosStart + 1

'---------------------------------------------------------------------
'get the text in between the ">" and "<"

'want the position after the ">"
lngPosStart = lngPosStart + 1

'want the position before the "<"
lngPosEnd = lngPosEnd - 1

'guard against the following
If lngPosStart >= lngPosEnd Then
    GetFirstInnerText = ""
    Exit Function
End If

strTemp = Mid(strInnerHTML, lngPosStart, lngPosEnd - lngPosStart)
'---------------------------------------------------------------------

'replace any "&" with ""
strTemp = Replace(strTemp, "&", "")

'trim off any spaces
strTemp = Trim(strTemp)

GetFirstInnerText = strTemp

End Function



Matthew Herbert said:
As always, thank you for the help.  Yes, it was a matter of checking my own
spelling.  You have helped me in the past, and I appreciate the help now.  
When I do need to do IE automation, I usually end up doing an Advanced Search
for your posts.  However, I'm still far removed from truly knowing the "best"
way to do IE automation.
For example, I don't know the best way to get the checkbox description text.
 So, if you open the webpage you see the following:
52 Week High (Question Mark Picture) [checkbox] (for which the HTML canbe
found in the chain).  
I can tell that the <tr> tag is prior to "52 Week High" and that a <div> tag
seems to be associated with the mouseover text.  In my code, the
".parentElement.parentElement.innerText" returns "52 Week High + the
mouseover text".  I simply want "52 Week High".  I found a previouspost that
had code that I thought might be helpful:
retVal = o.Document.getElementById("member-jacket").rows[0].cells[0].innerText
However, I don't know if I'm thinking about this the right way, i.e. trying
to access the text of a specific row/cell.  (I'm also assuming that HTML
tables have rows, columns, and/or cells; however, I don't know how a
rows/columns delineation -- like in an Excel spreadsheet -- is different than
the rows[0].cells[0] shown above.  Logic tells me that rows[0].cells[0] is
the first row, first cell).
Do you have advice for getting the "52 Week High" portion of text?  (Right
now, it appears that the <div> text is preceeded by a double space, butI
don't want to rely on using a double space as a way of separating the <tr>
text from the <div> text).

Set objTarget = objIE.document.getElementsByName("p_columns[]")
lngCnt = 0
For Each Obj In objTarget
    Set objDesc = Obj.parentElement.parentElement
    'not sure what to do here to get the <tr> text
    strText = objDesc.innerText
Matt,
 'thought the following might work, but I get an error
 'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")
Should work if you correct the typo  in "document"  ;-)
Tim
messageAll,
My question relates to the code listed in "ListCheckBoxes" below.  You
should be able to simply copy and paste all the VBA code below and run
"ListCheckBoxes" in order to follow the logic of my code.
I'm looking for a "better" way of obtaining the collection of web browser
checkbox controls for the following URL:
http://www.zacks.com/screening/custom/view.php?sid=87639(and a small
sample
of the HTML is also below), so that I can check the desired check boxes
based
on the text description that lines up with the checkbox.  (See the website
for a visual representation).
My Desired Goal:
Since each checkbox has a description (e.g. "52 Week High", "MarketCap
(millions)", etc.), I plan on using the description as a way to identify
whether the checkbox should be checked.  The user will have a list of
descriptions in the spreadsheet.  The program will then loop through the
spreadsheet list, search the description text for a match (the
".parentElement.parentElement.innerText" portion below, which can be
combined
with InStr to find a "match"), and check the checkbox if a match exists.
Again, I'm looking for a "better" way to do this.  My IE automation
knowledge is very limited, so I don't know if there is a way to getthe
object collection via the class (i.e. "tdata1", and I don't know how or if
getting a collection from the class is possible), the name (i.e.
"p_columns[]"), the tag (i.e. "input"), etc.  Or, maybe there is simply a
better way than my current logic.  I'm open to suggestions and general
knowledge that may help me better understand IE automation.  (Forexample,
is
adding a reference to "Microsoft HTML Object Library", opening the Object
Browser, and then searching the HTML* classes a good way to
"discover/learn"
IE automation?  It's probably a loaded question that doesn't havea
"great"
answer.)
Thanks,
Matthew Herbert
VBA:
Private Sub ListCheckBoxes()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim objArr() As Object
Dim lngCnt As Long
Dim strURL As String
strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)
If objIE Is Nothing Then
   Set objIE = CreateObject("InternetExplorer.Application")
   objIE.Visible = True
   objIE.Navigate strURL
   WaitForLoad objIE
End If
Set objTarget = objIE.document.all.tags("input")
'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")
For Each Obj In objTarget
   If Obj.Type = "checkbox" Then
       ReDim Preserve objArr(lngCnt)
       Set objArr(lngCnt) = Obj
       lngCnt = lngCnt + 1
   End If
Next Obj
For lngCnt = LBound(objArr) To UBound(objArr)
   Set Obj = objArr(lngCnt)
   With Obj
       'listed properties are some of what is viewable
       '   from "View Source" and what is embedded in
       '   the tag
       'not sure how to list the "class" though
       Debug.Print "lngCnt     :" & lngCnt
       Debug.Print "  Prnt.Prnt:" & .parentElement.parentElement.innerText
       Debug.Print "  name     :" & .Name
       Debug.Print "  type     :" & .Type
       Debug.Print "  value    :" & .Value
       Debug.Print "  id       :" & .ID
       Debug.Print "  innerHTML:" & .innerHTML
       Debug.Print "  innerText:" & .innerText
       'check the box
       '.Checked = True
   End With
Next lngCnt
End Sub
Function GetIE(strAddress As String) As Object
'---------------------------------------------------------------------
'INFO:      Original from Tim Williams
'           ??/??/2007, Matthew Herbert
'---------------------------------------------------------------------
Dim objShell As Object
Dim objShellWindows As Object
Dim Obj As Object
Dim objRes As Object
Dim strURL As String

...

read more »- Hide quoted text -

- Show quoted text -

Hi Matt...I think something like the following will allow you to
capture the desired information...Ron

Sub ckbx()
' Open IE to the desired webpage
strURL = "http://www.zacks.com/screening/custom/view.php?
sid=87639"

Set IE = CreateObject("InternetExplorer.Application")
With IE
.Visible = True
.Navigate strURL
.Top = 50
.Left = 530
.Height = 400
.Width = 400
End With

' Loop until the page is fully loaded
Do Until Not IE.Busy And IE.ReadyState = 4
DoEvents
Loop

' Get the checkbox descriptions; the first 9 elements
' in objTarget represent the checkboxes of interest
Set objTarget = IE.document.getElementsByName("p_columns[]")

For x = 1 To 9
Set objDesc = objTarget(x).parentElement.parentElement
mytext = objDesc.innertext
mytext = Left(mytext, InStr(1, mytext, " ", vbTextCompare))
' Do something here to store this information
Next
End Sub
 
T

Tim Williams

Matt,

This seemed to work for me.

Set objTarget = objIE.document.getElementsByName("p_columns[]")

For Each Obj In objTarget
Debug.Print Obj.parentElement.previousSibling.getAdjacentText
("afterBegin")
Next Obj

Reference:
http://msdn.microsoft.com/en-us/library/ms533053(VS.85).aspx


Tim


Tim,

Well, this is more of a reply to myself, but I've listed the code below that
I'm currently using to get the description text for the checkbox.  I'lluse
this unless there is a "better" way.

Best,

Matt

Private Sub ListCheckBoxDescriptionText()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim strURL As String
Dim objDesc As Object
Dim strText As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
    Set objIE = CreateObject("InternetExplorer.Application")
    objIE.Visible = True
    objIE.Navigate strURL
    WaitForLoad objIE
End If

Set objTarget = objIE.document.getElementsByName("p_columns[]")

For Each Obj In objTarget
    Set objDesc = Obj.parentElement.parentElement
    strText = GetFirstInnerText(objDesc.innerHTML)
    Debug.Print strText
Next Obj

End Sub

Private Function GetFirstInnerText(strInnerHTML As String) As String
'---------------------------------------------------------------------
'INFO:          01/05/2010, Matthew Herbert
'---------------------------------------------------------------------
'PURPOSE:       Get the first available innerText from strInnerHTML..
'               Search for the ">" and then the "<" and getthe
'               text in the middle.
'
'strInnerHTML   A text string of the .innerHTML property.
'
'RETURN:        - An empty string, i.e. "", if no innerText is found.
'               - The string between the ">" and "<".
'---------------------------------------------------------------------
'NOTES:         THIS IS HARDLY TESTED!  BE CAREFUL WHEN YOU USETHIS!
'               Intended to deal with at least the following 2
'               situations:
'               (1) <tr><td class=tdata1>52 Week High<...
'               (2)     <td class=tdata1>52 Week High<...
'---------------------------------------------------------------------
Dim lngPosStart As Long
Dim lngPosEnd As Long
Dim strTemp As String

'initialize the position for the first time in the loop
'   in order to get the InStr function to behave correctly
lngPosStart = 1
lngPosEnd = lngPosStart

Do
    lngPosStart = InStr(lngPosEnd, strInnerHTML, ">", vbTextCompare)
    If lngPosStart = 0 Then
        GetFirstInnerText = ""
        Exit Function
    End If

    lngPosEnd = InStr(lngPosStart + 1, strInnerHTML, "<", vbTextCompare)
    If lngPosEnd = 0 Then
        GetFirstInnerText = ""
        Exit Function
    End If
Loop Until lngPosEnd > lngPosStart + 1

'---------------------------------------------------------------------
'get the text in between the ">" and "<"

'want the position after the ">"
lngPosStart = lngPosStart + 1

'want the position before the "<"
lngPosEnd = lngPosEnd - 1

'guard against the following
If lngPosStart >= lngPosEnd Then
    GetFirstInnerText = ""
    Exit Function
End If

strTemp = Mid(strInnerHTML, lngPosStart, lngPosEnd - lngPosStart)
'---------------------------------------------------------------------

'replace any "&" with ""
strTemp = Replace(strTemp, "&", "")

'trim off any spaces
strTemp = Trim(strTemp)

GetFirstInnerText = strTemp

End Function



Matthew Herbert said:
As always, thank you for the help.  Yes, it was a matter of checking my own
spelling.  You have helped me in the past, and I appreciate the help now.  
When I do need to do IE automation, I usually end up doing an Advanced Search
for your posts.  However, I'm still far removed from truly knowing the "best"
way to do IE automation.
For example, I don't know the best way to get the checkbox description text.
 So, if you open the webpage you see the following:
52 Week High (Question Mark Picture) [checkbox] (for which the HTML canbe
found in the chain).  
I can tell that the <tr> tag is prior to "52 Week High" and that a <div> tag
seems to be associated with the mouseover text.  In my code, the
".parentElement.parentElement.innerText" returns "52 Week High + the
mouseover text".  I simply want "52 Week High".  I found a previouspost that
had code that I thought might be helpful:
retVal = o.Document.getElementById("member-jacket").rows[0].cells[0].innerText
However, I don't know if I'm thinking about this the right way, i.e. trying
to access the text of a specific row/cell.  (I'm also assuming that HTML
tables have rows, columns, and/or cells; however, I don't know how a
rows/columns delineation -- like in an Excel spreadsheet -- is different than
the rows[0].cells[0] shown above.  Logic tells me that rows[0].cells[0] is
the first row, first cell).
Do you have advice for getting the "52 Week High" portion of text?  (Right
now, it appears that the <div> text is preceeded by a double space, butI
don't want to rely on using a double space as a way of separating the <tr>
text from the <div> text).

Set objTarget = objIE.document.getElementsByName("p_columns[]")
lngCnt = 0
For Each Obj In objTarget
    Set objDesc = Obj.parentElement.parentElement
    'not sure what to do here to get the <tr> text
    strText = objDesc.innerText
Matt,
 'thought the following might work, but I get an error
 'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")
Should work if you correct the typo  in "document"  ;-)
Tim
 
M

Matthew Herbert

Ron,

I appreciate the input, but as I mentioned in my previous post "I don't want
to rely on using a double space as a way of separating the text." Hence my
GetFirstInnerText function in the prior post (because the double space is
highly unreliable, especially if the webpage design changes and the input
text doesn't have the ending and leading space). I'm more interested in
determining whether there is an existing IE method/property to use in
combination with the object for returning the text, rather than using my
custom GetFirstInnerText function.

Best,

Matt

ron said:
Tim,

Well, this is more of a reply to myself, but I've listed the code below that
I'm currently using to get the description text for the checkbox. I'll use
this unless there is a "better" way.

Best,

Matt

Private Sub ListCheckBoxDescriptionText()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim strURL As String
Dim objDesc As Object
Dim strText As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
Set objIE = CreateObject("InternetExplorer.Application")
objIE.Visible = True
objIE.Navigate strURL
WaitForLoad objIE
End If

Set objTarget = objIE.document.getElementsByName("p_columns[]")

For Each Obj In objTarget
Set objDesc = Obj.parentElement.parentElement
strText = GetFirstInnerText(objDesc.innerHTML)
Debug.Print strText
Next Obj

End Sub

Private Function GetFirstInnerText(strInnerHTML As String) As String
'---------------------------------------------------------------------
'INFO: 01/05/2010, Matthew Herbert
'---------------------------------------------------------------------
'PURPOSE: Get the first available innerText from strInnerHTML..
' Search for the ">" and then the "<" and get the
' text in the middle.
'
'strInnerHTML A text string of the .innerHTML property.
'
'RETURN: - An empty string, i.e. "", if no innerText is found.
' - The string between the ">" and "<".
'---------------------------------------------------------------------
'NOTES: THIS IS HARDLY TESTED! BE CAREFUL WHEN YOU USE THIS!
' Intended to deal with at least the following 2
' situations:
' (1) <tr><td class=tdata1>52 Week High<...
' (2) <td class=tdata1>52 Week High<...
'---------------------------------------------------------------------
Dim lngPosStart As Long
Dim lngPosEnd As Long
Dim strTemp As String

'initialize the position for the first time in the loop
' in order to get the InStr function to behave correctly
lngPosStart = 1
lngPosEnd = lngPosStart

Do
lngPosStart = InStr(lngPosEnd, strInnerHTML, ">", vbTextCompare)
If lngPosStart = 0 Then
GetFirstInnerText = ""
Exit Function
End If

lngPosEnd = InStr(lngPosStart + 1, strInnerHTML, "<", vbTextCompare)
If lngPosEnd = 0 Then
GetFirstInnerText = ""
Exit Function
End If
Loop Until lngPosEnd > lngPosStart + 1

'---------------------------------------------------------------------
'get the text in between the ">" and "<"

'want the position after the ">"
lngPosStart = lngPosStart + 1

'want the position before the "<"
lngPosEnd = lngPosEnd - 1

'guard against the following
If lngPosStart >= lngPosEnd Then
GetFirstInnerText = ""
Exit Function
End If

strTemp = Mid(strInnerHTML, lngPosStart, lngPosEnd - lngPosStart)
'---------------------------------------------------------------------

'replace any "&" with ""
strTemp = Replace(strTemp, "&", "")

'trim off any spaces
strTemp = Trim(strTemp)

GetFirstInnerText = strTemp

End Function



Matthew Herbert said:
As always, thank you for the help. Yes, it was a matter of checking my own
spelling. You have helped me in the past, and I appreciate the help now.
When I do need to do IE automation, I usually end up doing an Advanced Search
for your posts. However, I'm still far removed from truly knowing the "best"
way to do IE automation.
For example, I don't know the best way to get the checkbox description text.
So, if you open the webpage you see the following:
52 Week High (Question Mark Picture) [checkbox] (for which the HTML can be
found in the chain).
I can tell that the <tr> tag is prior to "52 Week High" and that a <div> tag
seems to be associated with the mouseover text. In my code, the
".parentElement.parentElement.innerText" returns "52 Week High + the
mouseover text". I simply want "52 Week High". I found a previous post that
had code that I thought might be helpful:
retVal = o.Document.getElementById("member-jacket").rows[0].cells[0].innerText
However, I don't know if I'm thinking about this the right way, i.e. trying
to access the text of a specific row/cell. (I'm also assuming that HTML
tables have rows, columns, and/or cells; however, I don't know how a
rows/columns delineation -- like in an Excel spreadsheet -- is different than
the rows[0].cells[0] shown above. Logic tells me that rows[0].cells[0] is
the first row, first cell).
Do you have advice for getting the "52 Week High" portion of text? (Right
now, it appears that the <div> text is preceeded by a double space, but I
don't want to rely on using a double space as a way of separating the <tr>
text from the <div> text).

Set objTarget = objIE.document.getElementsByName("p_columns[]")
lngCnt = 0
For Each Obj In objTarget
Set objDesc = Obj.parentElement.parentElement
'not sure what to do here to get the <tr> text
strText = objDesc.innerText

'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")
Should work if you correct the typo in "document" ;-)

messageAll,
My question relates to the code listed in "ListCheckBoxes" below. You
should be able to simply copy and paste all the VBA code below and run
"ListCheckBoxes" in order to follow the logic of my code.
I'm looking for a "better" way of obtaining the collection of web browser
checkbox controls for the following URL:
http://www.zacks.com/screening/custom/view.php?sid=87639(and a small
sample
of the HTML is also below), so that I can check the desired check boxes
based
on the text description that lines up with the checkbox. (See the website
for a visual representation).
My Desired Goal:
Since each checkbox has a description (e.g. "52 Week High", "Market Cap
(millions)", etc.), I plan on using the description as a way to identify
whether the checkbox should be checked. The user will have a list of
descriptions in the spreadsheet. The program will then loop through the
spreadsheet list, search the description text for a match (the
".parentElement.parentElement.innerText" portion below, which can be
combined
with InStr to find a "match"), and check the checkbox if a match exists.
Again, I'm looking for a "better" way to do this. My IE automation
knowledge is very limited, so I don't know if there is a way to get the
object collection via the class (i.e. "tdata1", and I don't know how or if
getting a collection from the class is possible), the name (i.e.
"p_columns[]"), the tag (i.e. "input"), etc. Or, maybe there is simply a
better way than my current logic. I'm open to suggestions and general
knowledge that may help me better understand IE automation. (For example,
is
adding a reference to "Microsoft HTML Object Library", opening the Object
Browser, and then searching the HTML* classes a good way to
"discover/learn"
IE automation? It's probably a loaded question that doesn't have a
"great"
answer.)

Matthew Herbert

Private Sub ListCheckBoxes()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim objArr() As Object
Dim lngCnt As Long
Dim strURL As String
If objIE Is Nothing Then
Set objIE = CreateObject("InternetExplorer.Application")
objIE.Visible = True
objIE.Navigate strURL
WaitForLoad objIE
End If
Set objTarget = objIE.document.all.tags("input")
'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")
For Each Obj In objTarget
If Obj.Type = "checkbox" Then
ReDim Preserve objArr(lngCnt)
Set objArr(lngCnt) = Obj
lngCnt = lngCnt + 1
End If
Next Obj
For lngCnt = LBound(objArr) To UBound(objArr)
Set Obj = objArr(lngCnt)
With Obj
'listed properties are some of what is viewable
' from "View Source" and what is embedded in
' the tag
'not sure how to list the "class" though
Debug.Print "lngCnt :" & lngCnt
Debug.Print " Prnt.Prnt:" & .parentElement.parentElement.innerText
Debug.Print " name :" & .Name
Debug.Print " type :" & .Type
Debug.Print " value :" & .Value
Debug.Print " id :" & .ID
Debug.Print " innerHTML:" & .innerHTML
Debug.Print " innerText:" & .innerText
'check the box
'.Checked = True
End With
Next lngCnt
Function GetIE(strAddress As String) As Object
'---------------------------------------------------------------------
'INFO: Original from Tim Williams
' ??/??/2007, Matthew Herbert
'---------------------------------------------------------------------
Dim objShell As Object
Dim objShellWindows As Object
Dim Obj As Object
Dim objRes As Object
Dim strURL As String

...

read more »- Hide quoted text -

- Show quoted text -

Hi Matt...I think something like the following will allow you to
capture the desired information...Ron

Sub ckbx()
' Open IE to the desired webpage
strURL = "http://www.zacks.com/screening/custom/view.php?
sid=87639"

Set IE = CreateObject("InternetExplorer.Application")
With IE
 
M

Matthew Herbert

Tim,

Jack pot! That does it. Again, thanks for the help, and thanks for the
link to the DHTML methods (for getAdjacentText). I'm sure this site will
come in handy later on.

Best,

Matt

Tim Williams said:
Matt,

This seemed to work for me.

Set objTarget = objIE.document.getElementsByName("p_columns[]")

For Each Obj In objTarget
Debug.Print Obj.parentElement.previousSibling.getAdjacentText
("afterBegin")
Next Obj

Reference:
http://msdn.microsoft.com/en-us/library/ms533053(VS.85).aspx


Tim


Tim,

Well, this is more of a reply to myself, but I've listed the code below that
I'm currently using to get the description text for the checkbox. I'll use
this unless there is a "better" way.

Best,

Matt

Private Sub ListCheckBoxDescriptionText()
Dim objIE As Object
Dim objTarget As Object
Dim Obj As Object
Dim strURL As String
Dim objDesc As Object
Dim strText As String

strURL = "http://www.zacks.com/screening/custom/view.php?sid=87639"
Set objIE = GetIE(strURL)

If objIE Is Nothing Then
Set objIE = CreateObject("InternetExplorer.Application")
objIE.Visible = True
objIE.Navigate strURL
WaitForLoad objIE
End If

Set objTarget = objIE.document.getElementsByName("p_columns[]")

For Each Obj In objTarget
Set objDesc = Obj.parentElement.parentElement
strText = GetFirstInnerText(objDesc.innerHTML)
Debug.Print strText
Next Obj

End Sub

Private Function GetFirstInnerText(strInnerHTML As String) As String
'---------------------------------------------------------------------
'INFO: 01/05/2010, Matthew Herbert
'---------------------------------------------------------------------
'PURPOSE: Get the first available innerText from strInnerHTML..
' Search for the ">" and then the "<" and get the
' text in the middle.
'
'strInnerHTML A text string of the .innerHTML property.
'
'RETURN: - An empty string, i.e. "", if no innerText is found.
' - The string between the ">" and "<".
'---------------------------------------------------------------------
'NOTES: THIS IS HARDLY TESTED! BE CAREFUL WHEN YOU USE THIS!
' Intended to deal with at least the following 2
' situations:
' (1) <tr><td class=tdata1>52 Week High<...
' (2) <td class=tdata1>52 Week High<...
'---------------------------------------------------------------------
Dim lngPosStart As Long
Dim lngPosEnd As Long
Dim strTemp As String

'initialize the position for the first time in the loop
' in order to get the InStr function to behave correctly
lngPosStart = 1
lngPosEnd = lngPosStart

Do
lngPosStart = InStr(lngPosEnd, strInnerHTML, ">", vbTextCompare)
If lngPosStart = 0 Then
GetFirstInnerText = ""
Exit Function
End If

lngPosEnd = InStr(lngPosStart + 1, strInnerHTML, "<", vbTextCompare)
If lngPosEnd = 0 Then
GetFirstInnerText = ""
Exit Function
End If
Loop Until lngPosEnd > lngPosStart + 1

'---------------------------------------------------------------------
'get the text in between the ">" and "<"

'want the position after the ">"
lngPosStart = lngPosStart + 1

'want the position before the "<"
lngPosEnd = lngPosEnd - 1

'guard against the following
If lngPosStart >= lngPosEnd Then
GetFirstInnerText = ""
Exit Function
End If

strTemp = Mid(strInnerHTML, lngPosStart, lngPosEnd - lngPosStart)
'---------------------------------------------------------------------

'replace any "&" with ""
strTemp = Replace(strTemp, "&", "")

'trim off any spaces
strTemp = Trim(strTemp)

GetFirstInnerText = strTemp

End Function



Matthew Herbert said:
As always, thank you for the help. Yes, it was a matter of checking my own
spelling. You have helped me in the past, and I appreciate the help now.
When I do need to do IE automation, I usually end up doing an Advanced Search
for your posts. However, I'm still far removed from truly knowing the "best"
way to do IE automation.
For example, I don't know the best way to get the checkbox description text.
So, if you open the webpage you see the following:
52 Week High (Question Mark Picture) [checkbox] (for which the HTML can be
found in the chain).
I can tell that the <tr> tag is prior to "52 Week High" and that a <div> tag
seems to be associated with the mouseover text. In my code, the
".parentElement.parentElement.innerText" returns "52 Week High + the
mouseover text". I simply want "52 Week High". I found a previous post that
had code that I thought might be helpful:
retVal = o.Document.getElementById("member-jacket").rows[0].cells[0].innerText
However, I don't know if I'm thinking about this the right way, i.e. trying
to access the text of a specific row/cell. (I'm also assuming that HTML
tables have rows, columns, and/or cells; however, I don't know how a
rows/columns delineation -- like in an Excel spreadsheet -- is different than
the rows[0].cells[0] shown above. Logic tells me that rows[0].cells[0] is
the first row, first cell).
Do you have advice for getting the "52 Week High" portion of text? (Right
now, it appears that the <div> text is preceeded by a double space, but I
don't want to rely on using a double space as a way of separating the <tr>
text from the <div> text).

Set objTarget = objIE.document.getElementsByName("p_columns[]")
lngCnt = 0
For Each Obj In objTarget
Set objDesc = Obj.parentElement.parentElement
'not sure what to do here to get the <tr> text
strText = objDesc.innerText

'thought the following might work, but I get an error
'Set objTarget = objIE.docmument.getElementsByName("p_columns[]")
Should work if you correct the typo in "document" ;-)
.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top