엑셀 카카오톡 자동화 프로그램 만들기 (윈도우 API 응용)

엑셀 VBA와 Win32 API를 사용하여 카카오톡 문자보내기 자동화를 위한 전체 명령문 및 동작원리를 단계별로 살펴봅니다.

홈페이지 » 엑셀 카카오톡 자동화 프로그램 만들기 (윈도우 API 응용)

엑셀 카카오톡 자동화 프로그램 만들기 (윈도우 API 응용)

엑셀 카카오톡 자동화 목차 바로가기
영상강의
큰 화면으로 보기

.

라이브 강의 전체영상도 함께 확인해보세요!

위캔두 회원이 되시면 매주 오빠두엑셀에서 진행하는 라이브강의 풀영상을 확인하실 수 있습니다.


예제파일 다운로드

오빠두엑셀의 강의 예제파일은 여러분을 위해 자유롭게 제공하고 있습니다.

  • [VBA프로젝트] 엑셀 카카오톡 자동화 프로그램 (Win32 API 응용)
    예제파일
  • [VBA프로젝트] 엑셀 카카오톡 자동화 프로그램 (Win32 API 응용)
    E-Book
  • [VBA프로젝트] 엑셀 카카오톡 자동화 프로그램 (Win32 API 응용)
    완성파일

엑셀 x 카카오톡 문자 보내기 자동화 서식을 업데이트 하였습니다.
서식이 필요하신 회원 여러분께 도움이 되었으면 좋겠습니다.

엑셀 카카오톡 문자보내기 자동화 서식 썸네일
엑셀 x 카카오톡 문자 보내기 자동화 서식 다운로드

hWnd 란 무엇인가요?

윈도우 hwnd
윈도우에서 실행되는 모든 프로그램에는 고유한 hWnd 값이 주어집니다.

hWnd 란 'Handle to the Window"의 약자로 윈도우에서 실행중인 프로그램의 창 고유값을 이야기 합니다. 윈도우에서 실행되는 모든 프로그램의 모든 창(Window)는 각각의 고유값을 가지며, 이번 강의에서 다룰 카카오톡 또한 각 단계별로 실행되는 각각의 창 마다 고유한 값을 가지게 됩니다.

Window Detective (윈도우 hWnd 조회 프로그램) 다운로드

이번 강의 초반부에 간략히 설명해드린 hWnd(Handle to Window : 실행 중인 프로그램의 고유 창 번호)을 조회하려면 Window Detective 라는 프로그램이 필요합니다. (이 외에도 Spy++, WinSpy++ 등 여러 다른 프로그램을 사용할 수도 있습니다.)

현재 사용중인 PC에서 실행되고 있는 카카오톡 또는 다른 프로그램의 창 번호를 직접 조회하며 강의를 실습하시려면 아래 링크로 이동하여 Window Detective 프로그램을 설치한 뒤 강의를 진행해주세요.

(아래 적어드린 최종 명령문에는 카카오톡에 사용된 모든 클래스 이름 및 창 이름을 적어드렸으므로, Window Detective는 꼭 설치하지 않으시더라도 강의를 진행할 수 있습니다.)

윈도우 API 살펴보기

윈도우 API 란 마이크로소프트에서 윈도우 운영체제에서 실행되는 다양한 프로그램를 제어하기 위하여 제공하는 API(Application Programming Interfaces) 입니다. 윈도우 API는 각 윈도우 운영체제 버전에 따라 다양하게 제공되며, 현재 대표적으로 사용되는 API 버전은 Win32 API 입니다.

Win32 API는 윈도우 95 부터 제공되기 시작하였고, 2020년 기준으로 마이크로소프트에서는 Win32 대신 Win64 API 를 사용할 것을 권장하고 있습니다. 하지만 아직까지는 혹시라도 모를 호환성 문제로 인하여 VBA로 윈도우 API를 사용할 경우에는 Win32 API를 사용할 것을 권장드립니다.

윈도우 API는 윈도우 운영체제 버전에 따라 다양하게 지원됩니다.

  • Win16 / Win32 / WIn32s / Win64 / WinCE

윈도우 API 에서 제공되는 함수는 크게 8개의 카테고리로 구분할 수 있습니다. 특히 엑셀 VBA에서 자주 사용되는 윈도우 API 라이브러리는 User32.dll 이며, 이번 강의에서도 user32.dll 라이브러리에서 제공되는 함수만 사용하였습니다.

  1. Base Service (kernel32.dll) :
    파일 시스템, 장치, 스레드, 오류처리 등의 중요 리소스 접근에 사용됩니다.
  2. Advanced Service (advapi32.dll) :
    윈도우 레지스트리, 시스템 재부팅, 시작, 종료, 계정 생성 등 부가기능 접근에 사용됩니다.
  3. Graphics Device Service (gdi32.dll) :
    모니터, 프린터, 출력장치 접근에 사용됩니다.
  4. ★ User Interface (user32.dll) :
    화면, 마우스, 키보드, 윈도우 GUI 연동 등 대부분의 엑셀과 외부 프로그램 연동 시 사용되는 라이브러리입니다.
  5. Common Dialog Box Library (comdlg32.dll) :
    응용프로그램 실행, 파일 저장 등을 위한 대화상자 접근에 사용됩니다.
  6. Common Control Library (comctl32.dll) :
    상태표시줄, 도구모음 등 일부 프로그램에서 제공하는 옵션 컨트롤에 접근에 사용됩니다.
  7. Windows Shell (shell32.dll) :
    셸(Shell) 접근에 사용됩니다. 다양한 명령문을 통한 프로그램 제어에 사용됩니다.
  8. Network Services :
    인터넷 익스프롤러, FTP 접속 등 네트워킹 기능 제어에 사용됩니다.

강의에 사용된 전체 명령문

Option Explicit
 
#If VBA7 Then
' https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-findwindowa
Private Declare PtrSafe Function FindWindow Lib "user32.dll" Alias "FindWindowA" _
                                                        (ByVal lpClassName As String, _
                                                        ByVal lpWindowName As String) As Long
' https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-findwindowexa
Private Declare PtrSafe Function FindWindowEx Lib "user32.dll" Alias "FindWindowExA" _
                                                            (ByVal hwndParent As Long, _
                                                            ByVal hwndChildAfter As Long, _
                                                            ByVal lpszClass As String, _
                                                            ByVal lpszWindow As String) As Long
' https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-sendmessagea
Private Declare PtrSafe Function SendMessage Lib "user32" Alias "SendMessageA" _
                                                            (ByVal hwnd As Long, _
                                                            ByVal wMsg As Long, _
                                                            ByVal wParam As Long, _
                                                            ByRef lParam As Any) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-postmessagea
Private Declare PtrSafe Function PostMessage Lib "user32" Alias "PostMessageA" _
                                                            (ByVal hwnd As Long, _
                                                            ByVal wMsg As Long, _
                                                            ByVal wParam As Long, _
                                                            ByRef lParam As Any) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-keybd_event
Private Declare PtrSafe Sub keybd_event Lib "user32.dll" _
                                                            (ByVal bVk As Byte, _
                                                            ByVal bScan As Byte, _
                                                            ByVal dwFlags As Long, _
                                                            ByVal dwExtraInfo As Long)
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-getkeystate
Private Declare PtrSafe Function GetKeyState Lib "user32" ( _
                                                            ByVal nVirtKey As Long) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-getwindow
Public Declare PtrSafe Function GetWindow _
                                                        Lib "user32" _
                                                        (ByVal hwnd As Long, _
                                                        ByVal wCmd As Long) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-getclassname
Private Declare PtrSafe Function GetClassName Lib "user32" Alias "GetClassNameA" _
                                                            (ByVal hwnd As Long, _
                                                            ByVal lpClassName As String, _
                                                            ByVal nMaxCount As Long) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-getwindowtexta
Private Declare PtrSafe Function GetWindowText Lib "user32" Alias "GetWindowTextA" _
                                                            (ByVal hwnd As Long, _
                                                            ByVal lpString As String, _
                                                            ByVal cch As Long) As Long
#Else
' https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-findwindowa
Private Declare Function FindWindow Lib "user32.dll" Alias "FindWindowA" _
                                                        (ByVal lpClassName As String, _
                                                        ByVal lpWindowName As String) As Long
' https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-findwindowexa
Private Declare Function FindWindowEx Lib "user32.dll" Alias "FindWindowExA" _
                                                            (ByVal hwndParent As Long, _
                                                            ByVal hwndChildAfter As Long, _
                                                            ByVal lpszClass As String, _
                                                            ByVal lpszWindow As String) As Long
' https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-sendmessagea
Private Declare Function SendMessage Lib "user32" Alias "SendMessageA" _
                                                            (ByVal hwnd As Long, _
                                                            ByVal wMsg As Long, _
                                                            ByVal wParam As Long, _
                                                            ByRef lParam As Any) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-postmessagea
Private Declare Function PostMessage Lib "user32" Alias "PostMessageA" _
                                                            (ByVal hwnd As Long, _
                                                            ByVal wMsg As Long, _
                                                            ByVal wParam As Long, _
                                                            ByRef lParam As Any) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-keybd_event
Private Declare Sub keybd_event Lib "user32.dll" _
                                                            (ByVal bVk As Byte, _
                                                            ByVal bScan As Byte, _
                                                            ByVal dwFlags As Long, _
                                                            ByVal dwExtraInfo As Long)
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-getkeystate
Private Declare Function GetKeyState Lib "user32" ( _
                                                            ByVal nVirtKey As Long) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-getwindow
Public Declare Function GetWindow _
                                                        Lib "user32" _
                                                        (ByVal hwnd As Long, _
                                                        ByVal wCmd As Long) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-getclassname
Private Declare Function GetClassName Lib "user32" Alias "GetClassNameA" _
                                                            (ByVal hwnd As Long, _
                                                            ByVal lpClassName As String, _
                                                            ByVal nMaxCount As Long) As Long
'https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-getwindowtexta
Private Declare Function GetWindowText Lib "user32" Alias "GetWindowTextA" _
                                                            (ByVal hwnd As Long, _
                                                            ByVal lpString As String, _
                                                            ByVal cch As Long) As Long
#End If
 
'######################################
' 공통 상수 선언
'######################################
' 가상키 ASCII 코드
Public Const WM_SETTEXT = &HC
Public Const WM_KEYDOWN = &H100
Public Const WM_KEYUP = &H101
Public Const VK_RETURN = &HD
Public Const VK_CONTROL = &H11
Public Const VK_ESC = &H1B
Public Const KEYEVENTF_KEYUP As Long = 2
Public Const VK_A = &H41
Public Const VK_V = &H56
Public Const VK_C = &H43
Public Const VK_DOWN = &H28
Public Const VK_UP = &H26
 
'######################################
' 친구에게 카카오톡 메세지를 전송합니다.
'######################################
Function SendKakao(Target As String, Message As String, Optional ChatRoomSearch As Boolean = False, Optional iDelay As Long = 1) As Boolean
 
' 변수 선언
Dim hwnd_RichEdit As Long       ' 채팅입력창 hwnd
 
' 친구 채팅입력창 hwnd 찾기
hwnd_RichEdit = FindRecepientHwnd(Target, ChatRoomSearch, iDelay)
'▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
 
'보낼 대상의 채팅창 없을 경우 안내메세지 출력 후 종료
If hwnd_RichEdit = 0 Then MsgBox "보낼 대상의 카카오톡 대화창을 찾을 수 없습니다.": Exit Function
 
' 메세지 보내기
Send_TextMsg Message, hwnd_RichEdit
 
End Function
 
'######################################
' 카카오톡 메세지를 전송합니다.
'######################################
Sub Send_TextMsg(Message As String, hwnd_RichEdit As Long)
 
' 대화상대 채팅 입력창 hWnd 에 메세지 입력
Call SendMessage(hwnd_RichEdit, WM_SETTEXT, 0, ByVal Message)
'▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
' 사용자 Ctrl 키 입력여부 확인
If IsCtrlKeyDown = False Then
    ' Ctrl 키 미입력 시, 메세지 전송
    Call PostMessage(hwnd_RichEdit, WM_KEYDOWN, VK_RETURN, 0)
Else
    ' Ctrl 키 입력중일 경우, 강제로 Ctrl 키 올림 -> 메세지 전송 -> Ctrl 키 재입력
    keybd_event VK_CONTROL, 0, KEYEVENTF_KEYUP, 0
    Call PostMessage(hwnd_RichEdit, WM_KEYDOWN, VK_RETURN, 0)
    keybd_event VK_CONTROL, 0, 0, 0
End If
 
End Sub
 
'######################################
' 보낼 대상의 hWnd 값을 찾습니다.
' 보낼 대상의 채팅창이 없을 경우 False를 반환합니다.
'######################################
Function FindRecepientHwnd(Target As String, ChatRoomSearch As Boolean, iDelay As Long) As Long
 
' 변수 선언
Dim dStart As Double
Dim hwnd_KakaoTalk As Long   ' 친구 채팅창 hwnd
Dim hwnd_RichEdit As Long       ' 채팅입력창 hwnd
 
' 보낼대상의 카톡창 실행
ActiveChat Target, iDelay, ChatRoomSearch
'▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
 
' 보낼대상의 카톡창 Hwnd 찾기
hwnd_KakaoTalk = FindWindow(vbNullString, Target)
'▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
 
dStart = Now
While hwnd_KakaoTalk = 0
    hwnd_KakaoTalk = FindWindow(vbNullString, Target)
    ' 1초 지날때까지 창을 못찾으면 함수 결과로 False 반환 후 종료
    If DateDiff("s", dStart, Now) > 1 Then FindRecepientHwnd = 0: Exit Function
Wend
 
' 친구의 채팅입력창 hWnd 찾기
hwnd_RichEdit = FindWindowEx(hwnd_KakaoTalk, 0, "RichEdit50W", vbNullString)  '카카오톡 버전에 따른 RichEdit ClassName 차이
If hwnd_RichEdit = 0 Then hwnd_RichEdit = FindWindowEx(hwnd_KakaoTalk, 0, "RichEdit20W", vbNullString)
 
FindRecepientHwnd = hwnd_RichEdit
 
End Function
 
'############################
' 친구 채팅창이 열려있지 않을 경우 채팅창을 검색 후 활성화합니다.
'############################
Function ActiveChat(Target As String, iDelay As Long, ChatRoomSearch As Boolean)
 
' 변수 설정
Dim hWndMain As Long: Dim hWndChild1 As Long: Dim hWndChild2 As Long: Dim hWndEdit As Long
Dim i As Long
 
' 대화상대 창 이미 열려있을 시 명령문 종료
If FindWindow(vbNullString, Target) > 0 Then Exit Function
'▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
 
' 카카오톡 메인 hWnd 검색 [▶▶▶▶▶F5키]
hWndMain = FindHwndEVA
' 카카오톡 메인 창 없으면 카톡 실행 안됨 -> 함수 False 반환 후 명령문 종료
If hWndMain = 0 Then ActiveChat = False: Exit Function
 
' 메인 [▶▶▶▶▶F5키]
hWndChild1 = FindWindowEx(hWndMain, 0, "EVA_ChildWindow", vbNullString)
'▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
' 연락처 목록 검색 -> EVA_Window 첫번째 항목
hWndChild2 = FindWindowEx(hWndChild1, 0, "EVA_Window", vbNullString)
' 채팅창 목록 검색 -> EVA_Window 두번째 항목
If ChatRoomSearch = True Then hWndChild2 = FindWindowEx(hWndChild1, hWndChild2, "EVA_Window", vbNullString)
' EVA_Window의 대화상대 검색창
hWndEdit = FindWindowEx(hWndChild2, 0, "Edit", vbNullString)
 
' 검색창에 대화상대 복사/붙여넣기
Call SendMessage(hWndEdit, WM_SETTEXT, 0, ByVal Target): MyDelay iDelay
' 채팅창 목록 검색일 경우 윗쪽방향키 눌러서 첫번째 항목 활성화
If ChatRoomSearch = True Then Call PostMessage(hWndEdit, WM_KEYDOWN, VK_UP, 0): MyDelay iDelay
' 엔터키로 채팅창 열기
Call PostMessage(hWndEdit, WM_KEYDOWN, VK_RETURN, 0): MyDelay iDelay
 
End Function
 
'############################
' 카카오톡 실행여부 확인 후, 실행중일 시 메인창의 hWnd 를 반환합니다.
'############################
Private Function FindHwndEVA() As Long
 
' 변수 설정
Dim hwnd As Long: Dim lngT As Long: Dim strT As String
 
' 현재 Desktop에서 실행중인 첫번째 프로그램 hWnd
hwnd = FindWindowEx(0, 0, vbNullString, vbNullString)
 
' 모든 hWnd 를 돌아가며 검색
While hwnd <> 0
    ' hWnd를 돌아가며 ClassName을 확인
    strT = String(100, Chr(0))
    lngT = GetClassName(hwnd, strT, 100)
    ' hWnd 의 ClassName 에 "EVA_Window_DblClk"이 포함될 경우
    If InStr(1, Left(strT, lngT), "EVA_Window_Dblclk") > 0 Then
        ' 해당 hWnd의 채팅창이름을 받아옵니다.
        strT = String(100, Chr(0))
        lngT = GetWindowText(hwnd, strT, 100)
        ' 채팅창 이름이 "카카오톡" 또는 "KakaoTalk"(영문OS 사용시)일 경우, hWnd 을 함수 결과로 반환 후 종료
        If InStr(1, Left(strT, lngT), "카카오톡") > 0 Or InStr(1, Left(strT, lngT), "KakaoTalk") > 0 Then FindHwndEVA = hwnd: Exit Function
    End If
hwnd = FindWindowEx(0, hwnd, vbNullString, vbNullString)
Wend
 
End Function
 
'###############################################################
'오빠두엑셀 VBA 사용자지정함수 (https://www.oppadu.com)
'▶ MyDelay 함수
'▶ 임시 지연 코드
'▶ ______________iDelay    : 지연 속도 조절 (클수록 많은 지연, 1 ≒ 4ms)
'###############################################################
Sub MyDelay(Optional iDelay As Long = 1)
 
Dim i As Long
For i = 1 To iDelay * 10000000:        i = i + 1:        Next
 
End Sub
 
'###############################################################
'오빠두엑셀 VBA 사용자지정함수 (https://www.oppadu.com)
'▶ IsCtrlKeyDown 함수
'▶ 키보드 Ctrl 키 누름여부를 확인합니다.
'▶ 인수 설명
'_____________LeftRightKey : 왼쪽/오른쪽 Ctrl 키 누름여부를 정합니다.
' 1 : 왼쪽 Ctrl키 입력시 TRUE
' 2 : 오른쪽 Ctrl키 입력시 TRUE
' 3 : 양쪽 Ctrl키 동시 입력시 TRUE
' 0 : 둘 중 하나라도 입력시 TRUE
'###############################################################
 
Private Function IsCtrlKeyDown(Optional LeftRightKey As Long = 0) As Boolean
 
Const VK_LCTRL = &HA2: Const VK_RCTRL = &HA3: Const KEY_MASK As Integer = &HFF80
 
Dim Result As Long
 
Select Case LeftRightKey
    '왼쪽 CTRL 키 입력여부 확인
    Case 1:        Result = GetKeyState(VK_LCTRL) And KEY_MASK
    '오른쪽 CTRL 키 입력여부 확인
    Case 2:        Result = GetKeyState(VK_RCTRL) And KEY_MASK
    '양쪽 CTRL 키 동시 입력여부 확인
    Case 3:        Result = GetKeyState(VK_LCTRL) And GetKeyState(VK_RCTRL) And KEY_MASK
    'CTRL 키 둘중 하나의 입력여부 확인
    Case Else:    Result = GetKeyState(vbKeyControl) And KEY_MASK
End Select
 
IsCtrlKeyDown = CBool(Result)
 
End Function

강의에 사용된 보조 명령문 목록

엑셀 카카오톡 자동화 명령문 순서
엑셀 카카오톡 자동화 명령문에는 크게 4개의 보조명령문이 사용되었습니다.

이번 강의에서 제작한 SendKakao 명령문은 크게 4개의 보조 명령문으로 나뉘어 제작되었으며 각 보조 명령문의 구성은 아래와 같습니다.

  1. FindHwndEVA 함수 : 카카오톡 실행여부 확인 및 카카오톡 메인 윈도우의 hWnd 를 반환합니다.
    '############################
    ' 카카오톡 실행여부 확인 후, 실행중일 시 메인창의 hWnd 를 반환합니다.
    '############################
    Private Function FindHwndEVA() As Long
     
    ' 변수 설정
    Dim hwnd As Long: Dim lngT As Long: Dim strT As String
     
    ' 현재 Desktop에서 실행중인 첫번째 프로그램 hWnd
    hwnd = FindWindowEx(0, 0, vbNullString, vbNullString)
     
    ' 모든 hWnd 를 돌아가며 검색
    While hwnd <> 0
        ' hWnd를 돌아가며 ClassName을 확인
        strT = String(100, Chr(0))
        lngT = GetClassName(hwnd, strT, 100)
        ' hWnd 의 ClassName 에 "EVA_Window_DblClk"이 포함될 경우
        If InStr(1, Left(strT, lngT), "EVA_Window_Dblclk") > 0 Then
            ' 해당 hWnd의 채팅창이름을 받아옵니다.
            strT = String(100, Chr(0))
            lngT = GetWindowText(hwnd, strT, 100)
            ' 채팅창 이름이 "카카오톡" 또는 "KakaoTalk"(영문OS 사용시)일 경우, hWnd 을 함수 결과로 반환 후 종료
            If InStr(1, Left(strT, lngT), "카카오톡") > 0 Or InStr(1, Left(strT, lngT), "KakaoTalk") > 0 Then FindHwndEVA = hwnd: Exit Function
        End If
    hwnd = FindWindowEx(0, hwnd, vbNullString, vbNullString)
    Wend
     
    End Function
  2. ActiveChat 함수 : 카카오톡의 친구목록에서 친구 검색 후, 엔터키를 입력하여 친구 채팅창을 활성화합니다.
    인수 설명
    Target As String 친구목록에서 검색할 친구 이름입니다.
    iDelay As Long 친구목록 검색 시 적용할 지연 시간입니다. (1 = 약 0.04s)
    ChatRoomSearch As Boolean TRUE 일 경우 대화목록에서 검색합니다.
    '############################
    ' 친구 채팅창이 열려있지 않을 경우 채팅창을 검색 후 활성화합니다.
    '############################
    Function ActiveChat(Target As String, iDelay As Long, ChatRoomSearch As Boolean)
     
    ' 변수 설정
    Dim hWndMain As Long: Dim hWndChild1 As Long: Dim hWndChild2 As Long: Dim hWndEdit As Long
    Dim i As Long
     
    ' 대화상대 창 이미 열려있을 시 명령문 종료
    If FindWindow(vbNullString, Target) > 0 Then Exit Function
    '▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
     
    ' 카카오톡 메인 hWnd 검색 [▶▶▶▶▶F5키]
    hWndMain = FindHwndEVA
    ' 카카오톡 메인 창 없으면 카톡 실행 안됨 -> 함수 False 반환 후 명령문 종료
    If hWndMain = 0 Then ActiveChat = False: Exit Function
     
    ' 메인 [▶▶▶▶▶F5키]
    hWndChild1 = FindWindowEx(hWndMain, 0, "EVA_ChildWindow", vbNullString)
    '▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
    ' 연락처 목록 검색 -> EVA_Window 첫번째 항목
    hWndChild2 = FindWindowEx(hWndChild1, 0, "EVA_Window", vbNullString)
    ' 채팅창 목록 검색 -> EVA_Window 두번째 항목
    If ChatRoomSearch = True Then hWndChild2 = FindWindowEx(hWndChild1, hWndChild2, "EVA_Window", vbNullString)
    ' EVA_Window의 대화상대 검색창
    hWndEdit = FindWindowEx(hWndChild2, 0, "Edit", vbNullString)
     
    ' 검색창에 대화상대 복사/붙여넣기
    Call SendMessage(hWndEdit, WM_SETTEXT, 0, ByVal Target): MyDelay iDelay
    ' 채팅창 목록 검색일 경우 윗쪽방향키 눌러서 첫번째 항목 활성화
    If ChatRoomSearch = True Then Call PostMessage(hWndEdit, WM_KEYDOWN, VK_UP, 0): MyDelay iDelay
    ' 엔터키로 채팅창 열기
    Call PostMessage(hWndEdit, WM_KEYDOWN, VK_RETURN, 0): MyDelay iDelay
     
    End Function
  3. FindRecepientHwnd 함수 : 친구채팅창의 채팅입력창 hWnd 를 반환합니다.
    인수 설명
    Target As String 친구목록에서 검색할 친구 이름입니다.
    iDelay As Long 친구목록 검색 시 적용할 지연 시간입니다. (1 = 약 0.04s)
    ChatRoomSearch As Boolean TRUE 일 경우 친구이름을 대화목록에서 검색합니다.
    '######################################
    ' 보낼 대상의 hWnd 값을 찾습니다.
    ' 보낼 대상의 채팅창이 없을 경우 False를 반환합니다.
    '######################################
    Function FindRecepientHwnd(Target As String, ChatRoomSearch As Boolean, iDelay As Long) As Long
     
    ' 변수 선언
    Dim dStart As Double
    Dim hwnd_KakaoTalk As Long   ' 친구 채팅창 hwnd
    Dim hwnd_RichEdit As Long       ' 채팅입력창 hwnd
     
    ' 보낼대상의 카톡창 실행
    ActiveChat Target, iDelay, ChatRoomSearch
    '▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
     
    ' 보낼대상의 카톡창 Hwnd 찾기
    hwnd_KakaoTalk = FindWindow(vbNullString, Target)
    '▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
     
    dStart = Now
    While hwnd_KakaoTalk = 0
        hwnd_KakaoTalk = FindWindow(vbNullString, Target)
        ' 1초 지날때까지 창을 못찾으면 함수 결과로 False 반환 후 종료
        If DateDiff("s", dStart, Now) > 1 Then FindRecepientHwnd = 0: Exit Function
    Wend
     
    ' 친구의 채팅입력창 hWnd 찾기
    hwnd_RichEdit = FindWindowEx(hwnd_KakaoTalk, 0, "RichEdit50W", vbNullString)  '카카오톡 버전에 따른 RichEdit ClassName 차이
    If hwnd_RichEdit = 0 Then hwnd_RichEdit = FindWindowEx(hwnd_KakaoTalk, 0, "RichEdit20W", vbNullString)
     
    FindRecepientHwnd = hwnd_RichEdit
     
    End Function
  4. Send_TextMsg 함수 : 채팅입력창에 메시지를 입력 후 엔터키를 눌러 메시지를 전송합니다.
    인수 설명
    Message As String 친구에게 보낼 메시지입니다.
    hwnd_RichEdit As Long 보낼 메시지를 입력할 채팅입력창의 hWnd 입니다.
    '######################################
    ' 카카오톡 메세지를 전송합니다.
    '######################################
    Sub Send_TextMsg(Message As String, hwnd_RichEdit As Long)
     
    ' 대화상대 채팅 입력창 hWnd 에 메세지 입력
    Call SendMessage(hwnd_RichEdit, WM_SETTEXT, 0, ByVal Message)
    '▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
    ' 사용자 Ctrl 키 입력여부 확인
    If IsCtrlKeyDown = False Then
        ' Ctrl 키 미입력 시, 메세지 전송
        Call PostMessage(hwnd_RichEdit, WM_KEYDOWN, VK_RETURN, 0)
    Else
        ' Ctrl 키 입력중일 경우, 강제로 Ctrl 키 올림 -> 메세지 전송 -> Ctrl 키 재입력
        keybd_event VK_CONTROL, 0, KEYEVENTF_KEYUP, 0
        Call PostMessage(hwnd_RichEdit, WM_KEYDOWN, VK_RETURN, 0)
        keybd_event VK_CONTROL, 0, 0, 0
    End If
     
    End Sub
  5. SendKakao 함수 : 지정한 친구에게 메시지를 전송합니다.
    인수 설명
    Target As String 메시지를 보낼 친구 이름입니다.
    Message As Long 친구에게 보낼 메시지입니다.
    ChatRoomSearch As Boolean TRUE 일 경우 친구이름을 대화목록에서 검색합니다.
    iDelay As Long 친구이름 검색 시 적용할 지연시간입니다.
    '######################################
    ' 친구에게 카카오톡 메세지를 전송합니다.
    '######################################
    Function SendKakao(Target As String, Message As String, Optional ChatRoomSearch As Boolean = False, Optional iDelay As Long = 1) As Boolean
     
    ' 변수 선언
    Dim hwnd_RichEdit As Long       ' 채팅입력창 hwnd
     
    ' 친구 채팅입력창 hwnd 찾기
    hwnd_RichEdit = FindRecepientHwnd(Target, ChatRoomSearch, iDelay)
    '▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶▶
     
    '보낼 대상의 채팅창 없을 경우 안내메세지 출력 후 종료
    If hwnd_RichEdit = 0 Then MsgBox "보낼 대상의 카카오톡 대화창을 찾을 수 없습니다.": Exit Function
     
    ' 메세지 보내기
    Send_TextMsg Message, hwnd_RichEdit
     
    End Function
4.7 19 투표
게시글평점
guest
41 댓글
Inline Feedbacks
모든 댓글 보기
SEANPAUL
SEANPAUL
2020년 12월 3일 9:17 오전
게시글평점 :
     

감히 천재라고 인정합니다

영혼의때를위하여
영혼의때를위하여
2020년 12월 3일 2:36 오후
게시글평점 :
     

오빠두엑셀 님 최고

mone****
mone****
2020년 12월 3일 3:01 오후
게시글평점 :
     

항상 유용하고 멋진 강의 감사합니다.
제가 못 찾는 건지 모르겠는데 완성파일에 실제 입력하는 시트가 없어서요

군자소프
군자소프
2020년 12월 8일 9:24 오전
답글 남기기  오빠두엑셀

엑셀 시트에서 보내는 방법은 어디서 배울수 있는지 궁금 합니다 *^_^*

군자소프
군자소프
2020년 12월 8일 9:23 오전
게시글평점 :
     

엑셀 시트에서 보내는 방법은 어디서 배울수 있는지 궁금 합니다 *^_^*

군자소프
군자소프
2020년 12월 11일 1:22 오전
답글 남기기  오빠두엑셀

감사 합니다 *^_^*

군자소프
군자소프
2020년 12월 11일 1:26 오전
답글 남기기  오빠두엑셀

완성파일에서와 같이 만드려고 합니다 그런데 아무리 찾아 봐도 알수가 없어서요 위 링크는 엑셀 시트에서 vba 와 연동해서 카톡 보내는거와 틀려 솔직히 모르겠습니다 ㅠㅠ 완성 파일과 같이 하려면 어디를 봐야 할까요… 더보기 »

군자소프
군자소프
2020년 12월 11일 7:41 오후
게시글평점 :
     

인수설명  Target As String메시지를 보낼 친구 이름입니다.  Message As Long친구에게 보낼 메시지입니다.  ChatRoomSearch As Boolean TRUE 일 경우 친구이름을 대화목록에서 검색합니다.  iDelay As Long친구이름 검색 시 적용할 지연시간입니다. SendKakao(Target As String, Message As String,… 더보기 »

Last edited 11 월 전 by 군자소프
열공
열공
2020년 12월 28일 4:06 오후
게시글평점 :
     

안녕하세요? 멋진 오빠두엑셀님 여기 있는 전체 명령문을 이용하여 카톡을 보내보니 대화상대에게 채팅창을 띄워 메시지를 전송하고 메시지 창이 열린 상태로 다음 상대에게 보내는데. 대기시간이 짧을 경우 이미 보낸 이전 상대에게 다음… 더보기 »

june
june
2020년 12월 31일 7:27 오후
게시글평점 :
     

안녕하세요 영상 잘 보고 있습니다. 감사합니다.
예제파일을 보고 있는데요
visual basic에서 트리부분에 하나의 트리만 보이고
프로젝트가 잠겨있다고 나와 있는데요
어떻게 해야하나요?

푸른나무
푸른나무
2021년 1월 3일 6:18 오후
게시글평점 :
     

강의 너무 유익했습니다. 실습해보려는데 Window Detective 이제 다운받을 수 없나요?

푸른나무
푸른나무
2021년 1월 8일 8:40 오전
답글 남기기  오빠두엑셀

감사합니다~

파이어폭스
2021년 1월 13일 12:20 오후
게시글평점 :
     

대단하십니다!!! 혹시 시트의 특정영역을 이미지로 카톡에 넣는 방법도 알려주실수 있으실까요?

EXCELCHOBO
EXCELCHOBO
2021년 1월 14일 1:07 오후
게시글평점 :
     

유용한 기능 감사합니다!!

혹시 사진을 다수의 인원에게 동시에 개인톡으로 발송하려고 하는데 어떻게 하면 되는지 여쭤볼 수 있을까요?

파이어폭스
2021년 1월 14일 6:29 오후
게시글평점 :
     

이틀 기달렸는데 답변이 없으셔서 그냥 제가 만들었습니다! 감사합니당

나나나
나나나
2021년 2월 7일 3:02 오전
게시글평점 :
     

실습해보겠습니다.감사합니다.

Last edited 9 월 전 by 나나나
열혈
열혈
2021년 2월 27일 11:44 오전
게시글평점 :
     

감사합니다

오마이길
오마이길
2021년 4월 7일 11:57 오전
게시글평점 :
     

궁금한게 있습니다. 혹시 이런 API가 윈도우 말고, 웹에도 적용이 가능할까요?

retyr
retyr
2021년 4월 12일 12:08 오전
게시글평점 :
     

안녕하세요! 우선 이렇게 상세한 설명 해주셔서 감사합니다. ㅜㅜ 많은 도움이 되었어요! 저는 Zoom 프로그램(요새 핫한 비대면 회의 솔루션)에 있는 참가자 목록을 엑셀 vba를 통해 엑셀 시트로 바로 옮기고 싶은데요.. Zoom… 더보기 »

윤종진
윤종진
2021년 4월 18일 6:21 오후
게시글평점 :
     

예제 파일을 찾아보고 열심히 배우고잇습니다.
궁금한점있어서 그림파일로는 전송을 클릭해야만 가지더라고요

PG열공맨
PG열공맨
2021년 4월 22일 7:18 오후
게시글평점 :
     

덕분에 대단한 프로그램을 감사하게 잘 사용하고 있습니다. 그런데 사용하다 보니 추가 되었으면 하는 부분이 있어 문의 드립니다. 입력한 셀에 메세지를 전송하는데 전송된 메세지 뒤에 일정한 문자를 추가해서 보낼 수 는… 더보기 »

행복이음
행복이음
2021년 4월 27일 4:31 오후
게시글평점 :
     

깜짝 놀래고 갑니다. 감사해요~

강호석
강호석
2021년 5월 26일 12:02 오전
게시글평점 :
     

안녕하세요 저는 완전 초보라.... 저희는 학원인데 무료로 풀어주신 프로그램에서 딱 변경할 값이 여러개 생기고... 변경할 값이 여러개만 있는식으로 엑셀을 만들수는 없을까요? 예를 들어 변경할값의 항목(지금 올려주신 파일에서는 1개만 가능한데) 만… 더보기 »

멋진바람
멋진바람
2021년 6월 7일 9:47 오전
게시글평점 :
     

너무 유용한 기능입니다.

3sung
3sung
2021년 7월 12일 12:05 오후
게시글평점 :
     

대단 하십니다, 최고 입니다. 짱입니다요

saranghappiness
saranghappiness
2021년 7월 26일 2:51 오후
게시글평점 :
     

안녕하세요. 오빠두엑셀 덕분에 카카오톡 자동 보내기 정말 잘 사용하고 있습니다! 그런데 지연시간을 늘려도 카톡창 닫히는 시간은 동일하다보니 카톡창이 계속 남아있어 카카오톡 자체가 버벅거리네요. 사진이 보내지기도 전에 창이 닫히려해 카톡창에 계속… 더보기 »

비딩이
비딩이
2021년 9월 30일 6:05 오후
게시글평점 :
     

안녕하세요?
항상 응원합니다.^^
여러개의 카톡을 for 문으로 돌면서 보내고 싶은데요...

문자발송시작 버튼을 자동으로 클릭하게 할수는 없나요?
아니면 다른 방법이 있는지 궁금합니다.

비딩이
비딩이
2021년 10월 2일 9:56 오후
답글 남기기  오빠두엑셀

첨부된 파일에는 매크로 옵션 선택이 되질 않아요..ㅠㅠ

ar****
ar****
2021년 11월 11일 2:23 오전
게시글평점 :
     

최고입니다!!

41
0
여러분의 생각을 댓글로 남겨주세요.x