SeleniumVBAを使ったグーグル翻訳のマクロです。ドライバーなどインストール不要でどの環境でも動作します。
文章の和文英文の量的判断により、動的に和英訳を行います。数値や「。」などの記号等で誤って英文解釈されることを回避しています。また、スクリプトではJSを使用しないことで、「':シングルクォーテーション」が入った文章も翻訳可能です。その他、対象翻訳文で和英文が半々の場合や、ラグによる翻訳が元の文のまま進んでしまうことも避けています。
挙動
コード
SeleniumVBAのダウンロードや使用前の準備については下記をご参照ください。(一部デバック用メモをあえて残しています)
・SeleniumVBAのダウンロード:Releases · GCuser99/SeleniumVBA
・SeleniumVBAのダウンロードからの手順:[Excel VBA]WebDriver経由でブラウザ操作(SeleniumVBA使い方メモ) #ExcelVBA - Qiita
SeleniumVBAをダウンロードし、標準フォームに2つ標準プロシージャを作成し、下記2コードを貼り付けてください。

①翻訳用コード
Option Explicit
#If VBA7 Then
Private Declare PtrSafe Function FindWindow Lib "user32" Alias "FindWindowA" ( _
ByVal lpClassName As String, ByVal lpWindowName As String) As LongPtr
Private Declare PtrSafe Function SetForegroundWindow Lib "user32" ( _
ByVal hwnd As LongPtr) As Long
#Else
Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" ( _
ByVal lpClassName As String, ByVal lpWindowName As String) As Long
Private Declare Function SetForegroundWindow Lib "user32" ( _
ByVal hwnd As Long) As Long
#End If
Sub Honyaku() '20250321更新
'570文字など日本語が半数以下の場合は和文以外と見なされ、和訳のままになってしまう
'未だ同じ文章が出るのと、フリーズで動かなくなる場合あり0402
Dim driver As SeleniumVBA.WebDriver
Dim mngr As SeleniumVBA.WebDriverManager
Dim keys As SeleniumVBA.WebKeyboard
Dim keySeq As String
Dim rlt As String
Dim timer As Long
'英訳の場合true
Dim flag As Boolean: flag = False
Set driver = SeleniumVBA.New_WebDriver
Set keys = SeleniumVBA.New_WebKeyboard
Set mngr = SeleniumVBA.New_WebDriverManager
'WebDriverを自動更新するWebDriverManagerクラスを使用する
mngr.AlignChromeDriverWithBrowser
Dim transrng As Range, rng As Range
On Error Resume Next
Set transrng = Application.InputBox("和訳したいセルを選択してください", , , , , , , 8)
If transrng Is Nothing Then Exit Sub
On Error GoTo 0
'Edgeを選択してブラウザを開く
driver.StartEdge
Dim caps As WebCapabilities, invisible As Boolean
' invisibleをなくしてもいいように見えるがなくすと画面で出てきてしまう
driver.OpenBrowser caps, invisible = True
'Google翻訳を開く
driver.NavigateTo "https://translate.google.com" '左は英訳 "https://translate.google.com"
driver.Wait 500
'訳したい文字列の右に空欄が無ければ訳の欄を作る場合は’を削除
'If Not IsEmpty(transrng.Offset(, 1)) Then
transrng.Offset(, 1).Insert xlShiftToRight
'End If
Call BringWorkbookToFront
Dim x As Long
x = 0
'翻訳文が自動判定され誤判定されるのを回避
driver.FindElement(By.ID, "i12").Click
For Each rng In transrng
x = x + 1
'空欄の場合-を入力
If Replace(rng.Value, " ", "", , , vbTextCompare) = "" Then
rng.Offset(, 1) = "-"
Else
'改行を削除し訳したい文字列を入力する
If InStr(rng.Value, vbLf) <> 0 Then
keySeq = Replace(rng.Value, vbLf, "")
Else
keySeq = rng.Value
End If
'ブラウザにおけるデフォルトの自動検出は和英混合文の場合翻訳ミスが起きるため、
'ブラウザ上での訳文を英語に設定する
'文を日本語か判断して英訳ならTrue
If isJapaneseText(keySeq) Then
flag = True
driver.FindElement(By.ID, "i16").Click
End If
driver.FindElement(By.className, "er8xn").SendKeys keySeq
'JSでやるとDOM直接操作で早く、複雑な操作可能だが、'がある場合誤判定などある為避ける
'Dim script As String
'script = "document.getElementsByClassName('er8xn')[0].value = '" & keySeq & "';"
'driver.ExecuteScript script
'driver.FindElement(By.className, "er8xn").SendKeys keys.EnterKey
'一文字でも約800は必要
driver.Wait 1000
'MsgBox driver.FindElement(By.className, "HwtZe").GetText
'文字多いと上の設問の日本語がそのまま来ることあり、
'検索対象の一個前の文章と一致している場合はさらに待つ必要あり
On Error Resume Next
rlt = driver.FindElement(By.className, "HwtZe").GetText
Do While rlt = ""
'driver.Wait 100
rlt = driver.FindElement(By.className, "HwtZe").GetText
Loop
' timer = 0
If Not flag Then
timer = 0
Do Until isJapaneseText(rlt) = True Or timer >= 5
rlt = driver.FindElement(By.className, "HwtZe").GetText
driver.Wait 1000
timer = timer + 1
Loop
End If
' MsgBox "訳文: " & rlt & vbCr & _
' "前回の翻訳文: " & rng.Offset(-1).Value & vbCr & _
' "前回翻訳: " & rng.Offset(-1, 1).Value
'If rlt = rng.Offset(-1, 1).Value Then MsgBox "訳文が前回と同じ"
'If rlt = rlt = rng.Offset(-1).Value Then MsgBox "訳対象文が転記されている"
If x >= 2 Then
timer = 0
'ラグにより、前回の翻訳と同じまま、前回の翻訳対象分が適されること回避
If rlt = rng.Offset(-1, 1).Value Or rlt = rng.Offset(-1).Value Then
Do While rlt = rng.Offset(-1, 1) Or rlt = rng.Offset(-1).Value
rlt = driver.FindElement(By.className, "HwtZe").GetText
driver.Wait 2000
timer = timer + 1
If timer >= 5 Then
Exit Do
End If
Loop
End If
End If
On Error GoTo 0
rng.Offset(, 1) = rlt
rng.Offset(, 1).WrapText = False
'rng.Offset(, 1).WrapText = True
If InStr(rng.Offset(, 1).Value, vbCrLf) <> 0 Then
rng.Offset(, 1) = Replace(rng.Offset(, 1), vbCrLf, "")
End If
If flag Then
flag = False
driver.FindElement(By.ID, "i15").Click
End If
'JSで入力していない事で訳文が残ったままになる為、削除する
driver.ExecuteScript "document.getElementsByClassName('er8xn')[0].value = '';"
End If
Next
MsgBox "完了しました"
End Sub
Sub BringWorkbookToFront()
Dim hwnd As LongPtr
Dim wb As Workbook
' 対象のワークブック
Set wb = ActiveWorkbook
' ウィンドウハンドルを取得
hwnd = FindWindow("XLMAIN", Application.caption)
If hwnd = 0 Then
MsgBox "ウィンドウハンドルが見つかりません。", vbCritical
Exit Sub
End If
' ワークブックを最前面に移動
SetForegroundWindow hwnd
End Sub
②日本語判定関数コード
Option Explicit
Function isJapaneseText(inputText As String) As Boolean
' 日本語の文字をカウントする
Dim japaneseCount As Integer
japaneseCount = CountJapaneseCharacters(inputText)
' 文字列全体の長さを取得
Dim totalLength As Integer
totalLength = Len(inputText)
' 日本語の文字が50%以上を占めているか確認
If totalLength > 0 And (japaneseCount / totalLength) >= 0.5 Then
isJapaneseText = True
Else
isJapaneseText = False
End If
End Function
' 日本語の文字をカウントする関数
Function CountJapaneseCharacters(inputText As String) As Integer
Dim regex As Object
Set regex = CreateObject("VBScript.RegExp")
' ひらがな、全角カタカナ、半角カタカナ、日本語の漢字、句読点(。、)を含める
regex.Pattern = "[\u3040-\u309F\u30A0-\u30FF\uFF61-\uFF9F\u4E00-\u9FFF々〆?、。]"
regex.IgnoreCase = True
regex.Global = True
' 一致する文字をカウントして返す
Dim matches As Object
Set matches = regex.execute(inputText)
CountJapaneseCharacters = matches.Count
End Function
SeleniumVBAをダウンロードし保存する際には下記のような表示が出ます。これはSeleniumVBAファイルによる仕様のため、無視していただいて問題はありません。

ポイント機能
使用前にエクセルの参照設定が下記の設定と過不足がないか確認してください。不足しているとうまく動作しない可能性があります。

- 翻訳対象文の右側に空欄を開け、訳文を転記
- 和英文の量的判定(②日本語判定関数)
- 翻訳対象の文章が英文なら訳結果が訳文になるまで待機
- エラー回避(JS記載を避け、シングルクォーテーション時のエラー、動作遅延による一つ前の文章訳を回避)
翻訳対象文の右側に空欄を開け、訳文を転記
今マクロでは翻訳対象文を選択した後、翻訳文を記載する空欄を左に作成します。そして上から順に訳文をFor each で取得、Google翻訳に転記&翻訳後の文章を空欄に転記しています。
和英文の量的判定(②日本語判定関数)
和文の定義は、「ひらがな、全角カタカナ、半角カタカナ、日本語の漢字、句読点(。、)を含めた文章が全体の内半数以上の場合」
としています。
全角/半角のひらがな、カタカナ、漢字が入っている場合は日本語と判定して英訳、それ以外は英訳するようになっています。
句読点等の記号でも日本語の判定は可能ですが、全角コロン「:」などの記号は日本語になってしまい、例えば英語の文でも記号が入っていると和文と認識してしまうため、和文判定基準からは除外しています。
関数は2つあり、
①日本語の割合から和文を判断する関数と、
②日本語の量を数える関数です。①から②を呼び出し、①で割合を計算し和英判断をしています。
②では引数を受け取り、標準表現Regexを使用することで和文を数えます。

Regexの使用では参照設定で事前バインディングを行います。これをすることでピリオドを押すとIntelliSenseが機能し入力しやすくなります。

Regex(正規表現)とは、特定のパターンに一致する文字列を検索・置換・抽出するための表記法です。プログラミングやデータ処理で広く使用されます。数値や日本語など様々な文字は正規表現を使うことでより細かく、包括的に操作することが可能です。
例えば日本語であれば、平仮名などの其々の形態ごとに正規表現があり、簡単に操作が可能です。
- ひらがな →
[ぁ-ゖ]
- カタカナ(全角) →
[ァ-ヶ]
- カタカナ(半角) →
[ヲ-゚]
- 漢字 →
[々〇〻\u3400-\u9FFF\uF900-\uFAFF]
Regexを使った文字カウントでは基本的なスクリプトが決まっています。オブジェクト変数にRegexを割り当て、Patternに対象にしたい文字や記号を指定、IgnoreCaseで大文字小文字区別するかを指定し、Globalで対象の文字列すべてを検索するか、最初に見つけるまでとするかを設定します。今回は、ひらがな~句読点まで日本語に現れ、英語には表れない表現を指定し、IgnoreCace、GlobalをTrueにしたことで、大文字に関係なく、対象文章からすべての日本語を捜査対象にしています。

上記条件での該当がどれくらいあるかは、Countメソッドで取得できます。変数matchesに上記のRegexをexecute(引数)を設定し、捜査実施後、Countをすることで指定文字列の数を取得できます。

エラー回避(動作遅延や空欄時等)
今回のVBAでは、①翻訳対象文と②翻訳後の文を変数に入れ、翻訳をしています。また、複数の翻訳文がある場合、③一つ前の翻訳対象文と、④一つ前の翻訳後の文も比較をしています。これにより、意図しない翻訳を回避しています。
プロシージャのテストでは、
①一つ前と今回の翻訳対象文が英語の場合、今回の翻訳対象文を読み込ませても一つ前の翻訳後の文を取得して一つ前の翻訳後の文で処理されてしまうエラーと、
②一つ前の翻訳対象文が、今回の翻訳対象文の翻訳後の文として処理されてしまうエラーの2つがありました。
それぞれを変数として判断することで、これら翻訳エラーを回避しています。
Google翻訳での翻訳は、訳文貼り付け→翻訳と、ブラウザ上で翻訳までに多少の遅延があります。また、PCのスペックやネット接続状況でも遅延が起きてしまいます。これにより①、②のエラーが起きます。
①については、一つ前の翻訳後の文が英語であり、その次の翻訳対象文が日本語で訳文の場合、一つ前の翻訳後の文がブラウザに残っていた場合、日本語の文が一つ前の翻訳文にもかかわらず処理が進んでしまいます。(つまり、一つ前の翻訳後の文が和文であり、今回は英訳したい場合、前回の翻訳後の文がブラウザ上に残っている為、今回の翻訳対象文をブラウザの要素に送っても翻訳されているようになってしまう)
JSによるエラー
ウェブの捜査といえばJSで、使うことはできるのですが、英文訳時にシングルクォーテーションがある場合エラーとなります。
これはJSの実行時にシングルクォーテーションを使うため、例えばIt’sのような訳文があった場合にはエラーとなってしまいます。
今回はコメントアウトとして記載しています。

最初に実行した際、訳文によっては前文との判定がうまくいかず、同じ訳文が記載されることがあります。その場合は同じようにマクロを再度実行するとうまくいきます。

その他関連機能について
- SeleniumVBAによるブラウザ操作
- Google翻訳の言語自動検出について
SeleniumVBAによるブラウザ操作
使用するメソッドやプロパティは下記が参考になります。
【SeleniumVBA】スクレイピングをする為のメソッド一覧表
基本的には、SeleniumVBAのサンプルを参考に、ブラウザのIDを自分で指定し、メソッド等を追加していくことで目的に合うスクレイピングを実施できます。
Google翻訳の言語自動検出について
苦労な点はGoogle翻訳の言語自動検出アルゴリズム。和英混合文の場合、意図した判定がされない場合があります。
下記は日本語が2文字含まれる文章です。一部に和文が入っている英文で和訳したい場合下記は英語判定する必要がありますが、Google翻訳上では日本語と認識されています。どうやら単なる量的判断ではないようです。

そこでどこで英語判定されるのかと「a」を追加すると、何度英語判定になります。英文としては不完全で、また1文字しか追加していないのに英文になりました。

AIの判定でもなく、量的な判定でもない微妙な判定アルゴリズムのため、今マクロではあらかじめ英語の部分の要素をクリックし、翻訳文を英語にセットしています。

訳出分のちょっとした例外

自動検出の場合、一部文字が日本語として認識される場合があります。
Gakuでやるとどうしても日本語と認識されてしまいます。Gakuiにしても日本語でしたが、Gakueにしてみるとうまく和訳されます。

ちなみにGokuだと悟空になります。あのアニメの主人公ですが、ブラウザ内の知識によって把握する言語が変わるのでしょうか。
上記の場合、英語と判定して和訳し、和訳された文章が日本語になるまで待つ処理をしています。
このような日本語と認識される場合を考慮し、5秒間経っても訳が日本語ではない場合そのまま転記するようにしています。
Flagにより、訳対象の言語が日本語化それ以外化に分けて判定し、英訳の場合はflagがtrueになり、同時に翻訳ブラウザ画面の訳出言語を英語に設定します。
ブラウザやPCの状態、訳したい言語等によって訳出に変動が生まれるため、ブラウザから訳出分を変数に代入し、空欄の場合は訳が取得できるまでWhile文でLoopする処理をしています。