【问题标题】:Searching websites using VBA使用 VBA 搜索网站
【发布时间】:2018-05-30 07:13:51
【问题描述】:

我想做的是使用 VBA 搜索website,在左侧框中输入一些单词并在右侧获取结果。

问题是我不懂 HTML,也不知道如何引用这个框。我使用 GetElementByID 但我收到错误:

objIE.Document.GetElementByID("text-translation-video-ad").Value = "piłka".   
"Object doesn't support this property or method".

这是我的代码:

Sub www()

    Set objIE = CreateObject("InternetExplorer.Application")

    objIE.Top = 0
    objIE.Left = 0
    objIE.Width = 800
    objIE.Height = 600
    objIE.AddressBar = 0
    objIE.StatusBar = 0
    objIE.Toolbar = 0
    objIE.Visible = True
    objIE.Navigate ("https://pl.pons.com/tłumaczenie-tekstu")

    Do
        DoEvents
    Loop Until objIE.ReadyState = 4

    pagesource = objIE.Document.Body.Outerhtml
    objIE.Document.GetElementByID("text-translation-video-ad").Value = "piłka"
    objIE.Document.GetElementByID("qKeyboardInputInitiator").Click

    Do
        DoEvents
    Loop Until objIE.ReadyState = 4

End Sub

【问题讨论】:

  • “搜索网站”是什么意思?您是要在页面的 HTML 中搜索特定的字词,还是要跨多个页面进行搜索?

标签: javascript html vba web-scraping


【解决方案1】:

在不更改任何语言设置的情况下,以下翻译为“你好”

代码:

Option Explicit

Public Sub GetInfo()
    Dim IE As New InternetExplorer, html As HTMLDocument, translation As String
    Const TRANSLATION_STRING As String = "Hello"

    With IE
        .Visible = True
        .navigate "https://pl.pons.com/t%C5%82umaczenie-tekstu"

        While .Busy Or .readyState < 4: DoEvents: Wend

        Set html = .document

        With html
            .querySelector("textarea.text-translation-source.source").Value = TRANSLATION_STRING
            .querySelector("button.btn.btn-primary.submit").Click
            Application.Wait Now + TimeSerial(0, 0, 3)
            translation = .querySelector("div.translated_text").innerText
        End With

        Debug.Print translation
        'Quit '<== Remember to quit application
    End With

End Sub

查看:

在即时窗口中打印:


编辑:

后期绑定版本

Option Explicit

Public Sub GetInfo()
    Dim IE As Object, html As Object

    With CreateObject("InternetExplorer.Application")
        .Visible = True
        .navigate "https://pl.pons.com/t%C5%82umaczenie-tekstu"

        While .Busy Or .readyState < 4: DoEvents: Wend

        Set html = CreateObject("htmlfile")
        Set html = .document

        With html

            .getElementsByClassName("text-translation-source source")(0).innerText = "Translate"
            .getElementsByClassName("btn btn-primary submit")(0).Click
             Application.Wait Now + TimeSerial(0, 0, 2)

             Dim i As Long
             For i = 0 To .getElementsByClassName("text-translation-target target").Length - 1
                 Debug.Print .getElementsByClassName("text-translation-target target")(i).innerText
             Next i

            Stop
        End With
        .Quit
    End With

End Sub

【讨论】:

    【解决方案2】:

    ID 为“text-translation-video-ad”的元素是一个没有.Value 属性的 DIV。您想访问提到的 DIV 的后代文本区域。

    页面上有 2 个带有标签“textarea”的元素,您感兴趣的是第一个元素,因此 (0) 索引。 GetElementsByTagName 中的标签必须大写。

    objIE.Document.GetElementsByTagName("TEXTAREA")(0).Value = "piłka"
    

    您还可以从 IE 自动化中退出,并采用更快、更可靠的方法,无需浏览器自动化,这将为您提供 JSON 格式的响应。需要设置对 Microsoft HTML 对象库的引用。

    Option Explicit
    
    Public Sub Scrape()
    
        Dim WindHttp As Object: Set WindHttp = CreateObject("WinHTTP.WinHTTPRequest.5.1")
        Dim htmlDoc As New HTMLDocument
        Dim urlName As String, myWord As String, requestString As String
        Dim myResults() As String
        Dim resultNum As Long
    
        urlName = "https://pl.pons.com/_translate/translate"
        myWord = "piłka"
    
        requestString = "source_language=pl&target_language=en&service=deepl&text=" & _
        myWord & _
        "&lookup=true&requested_by=Web&source_language_confirmed=true"
    
        Set htmlDoc = postDocument(urlName, WindHttp, requestString)
    
        myResults = Split(Replace(Split(Split(htmlDoc.body.innerText, ",")(1), ":")(1), Chr(34), vbNullString), vbCrLf)
    
        For resultNum = LBound(myResults) To UBound(myResults)
            Debug.Print myResults(resultNum)
        Next resultNum
    
    End Sub
    
    Function postDocument(ByVal urlName As String, myRequest As Object, Optional requestString As String) As HTMLDocument
    
        Set postDocument = New HTMLDocument
    
        With myRequest
    
            .Open "POST", urlName, False
            .setRequestHeader "Cache-Control", "no-cache"
            .setRequestHeader "Pragma", "no-cache"
            .setRequestHeader "Content-type", "application/x-www-form-urlencoded"
    
            If requestString = vbNullString Then
                .send
            Else
                .send requestString
            End If
    
            postDocument.body.innerHTML = .responseText
    
        End With
    
    End Function
    

    【讨论】:

    • 太棒了!,就像我尝试单击“Przetłumacz”按钮一样,但它不起作用。 (objIE.Document.GetElementByTagName("BUTTON")(5).Click)
    • 方法名中的“元素”,第5个元素的索引是4,因为枚举从0开始。使用:objIE.Document.GetElementsByTagName("BUTTON")(4).Click
    • 原来是“元素”而不是“元素”的问题。现在我尝试将语言从默认英语更改为波兰语。我也可以使用“GetElementsByTagName”吗?我试过 objIE.Document.GetElementsByTagName("BUTTON")(0).Value = "polskiego" 但它既不返回错误也不改变语言。
    • 这是另一个帖子的材料,但是这个按钮没有任何价值。它里面有span元素。您也可以在浏览器中手动更改此文本,然后单击按钮进行翻译并查看会发生什么 - 网站不关心值被更改。您必须单击下拉列表 元素。
    • 好吧,老实说,我不知道它应该是什么样子。我已经尝试了几次,但我收到了错误或没有结果。
    猜你喜欢
    • 2012-07-31
    • 1970-01-01
    • 1970-01-01
    • 2018-12-20
    • 1970-01-01
    • 1970-01-01
    • 2011-09-03
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多