Excel VBA: 如何从 Internet Explorer 复制字段值

Excel VBA: How to copy value of a field from Internet Explorer

我正在尝试访问 Internet Explorer 上的表单,然后复制某些字段的值(我知道名称和 ID)并将这些值复制到 Excel sheet .那是我正在尝试做的简化版本。所以现在我可以打开我的网页,然后打开其中包含的子表单。但是当我开始复制我感兴趣的字段的值时。我无法设置变量,因此我可以将其复制回 Excel.
下面是我的代码。我的评论之间的问题。

Private Sub Open_multiple_sub_pages_from_main_page()

    Dim i As Long
    Dim IE As Object
    Dim Doc As Object
    Dim objElement As Object
    Dim objCollection As Object

    ' Create InternetExplorer Object
    Set IE = CreateObject("InternetExplorer.Application")

    ' You can uncoment Next line To see form results
    IE.Visible = True

    ' Send the form data To URL As POST binary request
    IE.navigate "http://webpage.com/"

    ' Wait while IE loading...
    While IE.Busy
            DoEvents
    Wend

    Set objCollection = IE.Document.getElementsByTagName("input")

    i = 0
    While i < objCollection.Length
        If objCollection(i).Name = "txtUserName" Then

            ' Set text for search
            objCollection(i).Value = "1234"
        End If
        If objCollection(i).Name = "txtPwd" Then

            ' Set text for search
            objCollection(i).Value = "password"
        End If

        If objCollection(i).Type = "submit" And objCollection(i).Name = "btnSubmit" Then ' submit button if found and set
            Set objElement = objCollection(i)
        End If
        i = i + 1
    Wend
    objElement.Click    ' click button to load page

    ' Wait while IE re-loading...
    While IE.Busy
            DoEvents
    Wend

    ' Show IE
    IE.Visible = True
    Set Doc = IE.Document

    Dim links, link, value_to_copy

    Dim j As Integer                                                                    'variable to count items
    j = 0
    Set links = IE.Document.getelementbyId("dgTime").getElementsByTagName("a")
    n = links.Length
    While j <= n                                    'loop to go thru all "a" item so it loads next page
        links(j).Click
        While IE.Busy
            DoEvents
        Wend
        '------------THE PROBLEM IS HERE---------------------------
        Set value_to_copy = IE.Document.getelementbyId("mainTable").getElementsByTagName("txtProject").innerText
        '----------VALUE_TO_COPY WILL REMAIN AT "" VALUE

        IE.Document.getelementbyId("DetailToolbar1_lnkBtnSave").Click              'save
        Do While IE.Busy
            Application.Wait DateAdd("s", 1, Now)                                   'wait
        Loop
        IE.Document.getelementbyId("DetailToolbar1_lnkBtnCancel").Click            'close
        Do While IE.Busy
            Application.Wait DateAdd("s", 1, Now)                                   'wait
        Loop
        Set links = IE.Document.getelementbyId("dgTime").getElementsByTagName("a")
        j = j + 2
    Wend
End Sub

下面是我试图从中检索 "txtProject" 值的页面的 html 代码。在该特定情况下,该值为“0000001”。这就是我需要复制的价值。

<table width="100%" class="Form" id="mainTable" border="0" cellspacing="0" cellpadding="0">
    <tbody><tr id="TRCustomer">
        <td class="titleLabel"><span id="lblCustomer">
<u>C</u>lient : </span></td>
<td><input name="txtCustomer" id="txtCustomer" accesskey="C"
   language="javascript" onchange="__doPostBack('txtCustomer','')"  
   type="text"></td>
<td><a class="Button" id="lnkBtnCustomer" href="javascript:__doPostBack('lnkBtnCustomer','')">
<img id="imgCustomer" alt="" src="images/toolbar/b_preview.gif"  
   border="0"></a></td>
<td class="tdDescriptionLabel"><span class="DescriptionLabel" 
    id="lblCustomerDescription">&nbsp;</span></td>
    </tr>
<tr id="TRProject">
<td width="110" class="titleLabel">
  <span id="lblProject">Pro<u>j</u>et : </span></td>
<td width="152"><input name="txtProject" tabindex="2" id="txtProject"
    accesskey="J" language="javascript" 
    onkeypress="return LookupButton(event,'lnkBtnProject')" 
    onchange="__doPostBack('txtProject','')" type="text"
     value="0000001"></td>
<td width="20"><a class="Button" id="lnkBtnProject" 
    href="javascript:__doPostBack('lnkBtnProject','')">
    <img id="imgProject" alt="" src="images/toolbar/b_preview.gif"
    border="0"></a></td><td class="tdDescriptionLabel">
   <span class="DescriptionLabel" 

任何帮助将不胜感激。
提前Tx.

Set关键字用于对象,这里有一个变量。从赋值语句中删除 Setvalue_to_copy = IE.Document.getelementbyId("mainTable").getElementsByTagName("txtProject").innerText

innerText属性returns一String类型。这意味着,您不需要关键字 Set 而是用于将变量设置为指向特定对象的指针。字符串是原生类型,所以不要使用关键字 Set。试试这个:

'------------THE PROBLEM IS HERE---------------------------
            value_to_copy = IE.Document.getelementbyId("mainTable").getElementsByTagName("txtProject").innerText
            '----------VALUE_TO_COPY WILL REMAIN AT "" VALUE

在文档中 id 应该是唯一的,因此您可以直接使用它:

value_to_copy = IE.Document.getelementbyId("txtProject").Value

getElementsByTagName() 不用于通过 id 定位元素,并且在任何情况下 return 是一个 匹配集合 ,而不是单个元素,所以你不能像那样分配它的 return 值。这就是您通常使用它的方式:

value_to_copy = IE.Document.getelementsbyTagName("input")(0).Value

这是一个微妙的问题。简而言之,您不应该使用 innertext 属性。相反,您想检索 txtProject element.

childNodes 属性 返回的 "value" node 的值

您检索的数据实际上不是 "innertext."Innertext 是出现在开始和结束标记之间的文本。来自 MSDN https://msdn.microsoft.com/en-us/library/ie/ms533899(v=vs.85).aspx:

The innerText property is valid for block elements only. By definition, elements that do not have both an opening and closing tag cannot have an innerText property.

例如,在以下代码段中:

<h1>Header Text</h1>

<h1> 标签的内文是 "Header text"

在您的代码段中,标签实际上没有任何内部文本。您有一个带有属性的 td 元素,但 <td...></td>:

之间没有任何内容
<td width="152"><input name="txtProject" tabindex="2" id="txtProject"
accesskey="J" language="javascript" 
onkeypress="return LookupButton(event,'lnkBtnProject')" 
onchange="__doPostBack('txtProject','')" type="text"
 value="0000001"></td>'

这就是 innertext 属性 失败的原因。您的代码段 getElementsByTagName("txtProject") returns 一个 Element 对象。元素是 nodes 的集合。您的元素具有名为 nametabindexidaccesskeylanguageonkeypressonchange、[=33 的节点=] 和 value。这些节点中的每一个都有一个与之关联的值。您需要访问 value 节点并查询其值。

我怀疑以下方法或类似方法会起作用。

set txtProject = IE.Document.getelementbyID("mainTable").getElementsByTagName("txtProject")
    ' returns a `<td..></td>` element

value_to_copy = txtProject.childNodes("value")
    'Should return the default property of the node "value".  
    'The default property should be the string "00000001".  
    'But I'm not sure so you might want to do more 
    'research on `childNodes` and `nodes`

或者,但不太直观:

value_to_copy = IE.Document.getelementbyID("mainTable") _
                           .getElementsByTagName("txtProject") _
                           .childNodes("value")

我从 https://msdn.microsoft.com/en-us/library/ms757053(v=vs.85).aspx 上的以下代码片段改编而来。所以如果我上面的建议不起作用,也许这会有所帮助。

The following script example uses the childNodes property (collection) to return an IXMLDOMNodeList, and then iterates through the collection, displaying the value of each item's xml property.

root = xmlDoc.documentElement;
oNodeList = root.childNodes;
for (var i=0; i<oNodeList.length; i++) {
  Item = oNodeList.item(i);
  WScript.Echo(Item.xml);
  }