仕事中に文書の整形がしたくなって、ワードのマクロを調べてみたのでその備忘録
やりたかったのは、特定の文字列を一気に削除すること
文字列をコピーして、 置換のダイアログでターゲットにペーストして、 一気に置換を実行するだけなんだけど、 この作業を簡素化したかった
マクロを記録すれば自動でコードは書いてくれる、 しかしコードを見たらターゲットの文字列は記録したときのものに 固定されてしまっていた
そこでこの文字列を都度クリップボードから取得するようにしたく てちょっと調べてみたら、方法は2種類あった
① DataObjectを使用
Dim buf2 As String, CB As New DataObject
With CB
.GetFromClipboard ''クリップボードからDataObjectにデータを取得する
buf2 = .GetText ''DataObjectのデータを変数に取得する
End With
' MsgBox buf2
結構簡単、DataObjectってのを使うだけ
ただ私のワード環境ではこれがエラーになってしまい、 DataObjectを使用するためには Microsoft Forms 2.0 Object Libralyを標準モジュールに追加しなくてはいけないことが わかった
VisualBasic を開いて「ツール」「参照設定」
しかしこれでも見つからず、 そういう場合は直接これを参照すれば良い
system32\\FM20.dll
② win32apiを直接使う
VisualBasic を開いて左のツリーから「標準モジュール」を右クリ →「挿入」→「標準モジュール」として以下をコピペ
Declare Function OpenClipboard Lib "User32" (ByVal hwnd As Long) _ As Long
Declare Function CloseClipboard Lib "User32" () As Long
Declare Function GetClipboardData Lib "User32" (ByVal wFormat As _ Long) As Long
Declare Function GlobalAlloc Lib "kernel32" (ByVal wFlags&, ByVal _ dwBytes As Long) As Long
Declare Function GlobalLock Lib "kernel32" (ByVal hMem As Long) _ As Long
Declare Function GlobalUnlock Lib "kernel32" (ByVal hMem As Long) _ As Long
Declare Function GlobalSize Lib "kernel32" (ByVal hMem As Long) _ As Long
Declare Function lstrcpy Lib "kernel32" (ByVal lpString1 As Any, _ ByVal lpString2 As Any) As Long
Public Const GHND = &H42
Public Const CF_TEXT = 1
Public Const MAXSIZE = 4096
Function ClipBoard_GetData()
Dim hClipMemory As Long
Dim lpClipMemory As Long
Dim MyString As String
Dim RetVal As Long
If OpenClipboard(0&) = 0 Then
MsgBox "Cannot open Clipboard. Another app. may have it open"
Exit Function
End If
' Obtain the handle to the global memory
' block that is referencing the text.
hClipMemory = GetClipboardData(CF_TEXT)
If IsNull(hClipMemory) Then
MsgBox "Could not allocate memory"
GoTo OutOfHere
End If
' Lock Clipboard memory so we can reference
' the actual data string.
lpClipMemory = GlobalLock(hClipMemory)
If Not IsNull(lpClipMemory) Then
MyString = Space$(MAXSIZE)
RetVal = lstrcpy(MyString, lpClipMemory)
RetVal = GlobalUnlock(hClipMemory)
' Peel off the null terminating character.
MyString = Mid(MyString, 1, InStr(1, MyString, Chr$(0), 0) - 1)
Else
MsgBox "Could not lock memory to copy string from."
End If
OutOfHere:
RetVal = CloseClipboard()
ClipBoard_GetData = MyString
End Function
あとは自分のマクロで ClipBoard_GetData() を実行すれば文字列が帰ってくる
③ 考察
DataObjectってのは多分VBのwin32ラッパーです ね
それよりも②の書き方が参考になります
これでwin32のapiが自由に使えるって事だと思う
使いたい関数を冒頭でDeclare Functionするだけなんだね
これを標準モジュールの中で書いておくってあたりは良く仕組みが わかんないけど、応用が利きそうでうれしい
ワードマクロについてはエクセルとほとんど変わりませんな
いずれもVBだから当たり前なのか?
文字列をコピーして、
マクロを記録すれば自動でコードは書いてくれる、
そこでこの文字列を都度クリップボードから取得するようにしたく
① DataObjectを使用
Dim buf2 As String, CB As New DataObject
With CB
.GetFromClipboard ''クリップボードからDataObjectにデータを取得する
buf2 = .GetText ''DataObjectのデータを変数に取得する
End With
' MsgBox buf2
結構簡単、DataObjectってのを使うだけ
ただ私のワード環境ではこれがエラーになってしまい、
VisualBasic を開いて「ツール」「参照設定」
しかしこれでも見つからず、
system32\\FM20.dll
② win32apiを直接使う
VisualBasic を開いて左のツリーから「標準モジュール」を右クリ →「挿入」→「標準モジュール」として以下をコピペ
Declare Function OpenClipboard Lib "User32" (ByVal hwnd As Long) _ As Long
Declare Function CloseClipboard Lib "User32" () As Long
Declare Function GetClipboardData Lib "User32" (ByVal wFormat As _ Long) As Long
Declare Function GlobalAlloc Lib "kernel32" (ByVal wFlags&, ByVal _ dwBytes As Long) As Long
Declare Function GlobalLock Lib "kernel32" (ByVal hMem As Long) _ As Long
Declare Function GlobalUnlock Lib "kernel32" (ByVal hMem As Long) _ As Long
Declare Function GlobalSize Lib "kernel32" (ByVal hMem As Long) _ As Long
Declare Function lstrcpy Lib "kernel32" (ByVal lpString1 As Any, _ ByVal lpString2 As Any) As Long
Public Const GHND = &H42
Public Const CF_TEXT = 1
Public Const MAXSIZE = 4096
Function ClipBoard_GetData()
Dim hClipMemory As Long
Dim lpClipMemory As Long
Dim MyString As String
Dim RetVal As Long
If OpenClipboard(0&) = 0 Then
MsgBox "Cannot open Clipboard. Another app. may have it open"
Exit Function
End If
' Obtain the handle to the global memory
' block that is referencing the text.
hClipMemory = GetClipboardData(CF_TEXT)
If IsNull(hClipMemory) Then
MsgBox "Could not allocate memory"
GoTo OutOfHere
End If
' Lock Clipboard memory so we can reference
' the actual data string.
lpClipMemory = GlobalLock(hClipMemory)
If Not IsNull(lpClipMemory) Then
MyString = Space$(MAXSIZE)
RetVal = lstrcpy(MyString, lpClipMemory)
RetVal = GlobalUnlock(hClipMemory)
' Peel off the null terminating character.
MyString = Mid(MyString, 1, InStr(1, MyString, Chr$(0), 0) - 1)
Else
MsgBox "Could not lock memory to copy string from."
End If
OutOfHere:
RetVal = CloseClipboard()
ClipBoard_GetData = MyString
End Function
あとは自分のマクロで ClipBoard_GetData() を実行すれば文字列が帰ってくる
③ 考察
DataObjectってのは多分VBのwin32ラッパーです
それよりも②の書き方が参考になります
これでwin32のapiが自由に使えるって事だと思う
使いたい関数を冒頭でDeclare Functionするだけなんだね
これを標準モジュールの中で書いておくってあたりは良く仕組みが
ワードマクロについてはエクセルとほとんど変わりませんな
いずれもVBだから当たり前なのか?
0 件のコメント:
コメントを投稿