This commit is contained in:
恍兮惚兮 2024-06-06 20:58:53 +08:00
parent 36e690ca76
commit 9825bf0119
4 changed files with 89 additions and 18 deletions

View File

@ -1,30 +1,29 @@
import time import time
from textsource.textsourcebase import basetext from textsource.textsourcebase import basetext
from myutils.config import globalconfig from myutils.config import globalconfig
import winsharedutils, os import winsharedutils, os, queue
import windows import windows
class copyboard(basetext): class copyboard(basetext):
def __init__(self) -> None:
self.last_paste_str = ""
def end(self):
winsharedutils.clipboard_callback_stop(self.__hwnd)
super().end()
def __callback(self, string, ismy):
if globalconfig["excule_from_self"] and ismy:
return
return self.__queue.put(string)
def __init__(self) -> None:
self.__ref = winsharedutils.clipboard_callback_type(self.__callback)
self.__hwnd = winsharedutils.clipboard_callback(self.__ref)
self.__queue = queue.Queue()
super(copyboard, self).__init__("0", "copy") super(copyboard, self).__init__("0", "copy")
def gettextthread(self): def gettextthread(self):
return self.__queue.get()
time.sleep(0.1)
paste_str = winsharedutils.clipboard_get()
if self.last_paste_str != paste_str:
self.last_paste_str = paste_str
if (
globalconfig["excule_from_self"]
and windows.GetWindowThreadProcessId(windows.GetClipboardOwner())
== os.getpid()
):
return
return paste_str
def gettextonce(self): def gettextonce(self):
return winsharedutils.clipboard_get() return winsharedutils.clipboard_get()

View File

@ -409,3 +409,10 @@ get_ZoomFactor.argtypes = (c_void_p,)
get_ZoomFactor.restype = c_double get_ZoomFactor.restype = c_double
put_ZoomFactor = utilsdll.put_ZoomFactor put_ZoomFactor = utilsdll.put_ZoomFactor
put_ZoomFactor.argtypes = c_void_p, c_double put_ZoomFactor.argtypes = c_void_p, c_double
clipboard_callback = utilsdll.clipboard_callback
clipboard_callback.argtypes = (c_void_p,)
clipboard_callback.restype = HWND
clipboard_callback_stop = utilsdll.clipboard_callback_stop
clipboard_callback_stop.argtypes = (HWND,)
clipboard_callback_type = CFUNCTYPE(None, c_wchar_p, c_bool)

View File

@ -29,7 +29,7 @@ include(generate_product_version)
set(VERSION_MAJOR 3) set(VERSION_MAJOR 3)
set(VERSION_MINOR 2) set(VERSION_MINOR 2)
set(VERSION_PATCH 2) set(VERSION_PATCH 3)
add_library(pch pch.cpp) add_library(pch pch.cpp)
target_precompile_headers(pch PUBLIC pch.h) target_precompile_headers(pch PUBLIC pch.h)

View File

@ -65,3 +65,68 @@ bool clipboard_set(HWND hwnd, wchar_t *text)
CloseClipboard(); CloseClipboard();
return success; return success;
} }
static void clipboard_callback_1(void (*callback)(wchar_t *, bool), HANDLE hsema, HWND *hwnd)
{
const wchar_t CLASS_NAME[] = L"LunaClipboardListener";
WNDCLASS wc = {};
wc.lpfnWndProc = [](HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
if (WM_CLIPBOARDUPDATE == message)
{
auto data = clipboard_get();
auto callback_ = reinterpret_cast<decltype(callback)>(GetWindowLongPtrW(hWnd, GWLP_USERDATA));
if (data && callback_)
{
auto ohwnd = GetClipboardOwner();
DWORD pid;
GetWindowThreadProcessId(ohwnd, &pid);
callback_(data, pid == GetCurrentProcessId());
delete data;
}
}
return DefWindowProc(hWnd, message, wParam, lParam);
};
wc.hInstance = GetModuleHandle(0);
wc.lpszClassName = CLASS_NAME;
static auto _ = RegisterClass(&wc);
HWND hWnd = CreateWindowEx(
WS_EX_CLIENTEDGE, CLASS_NAME, CLASS_NAME, WS_OVERLAPPEDWINDOW,
0, 0, 0, 0,
NULL, NULL, GetModuleHandle(0), 0);
SetWindowLongPtrW(hWnd, GWLP_USERDATA, (LONG_PTR)callback);
*hwnd = hWnd;
ReleaseSemaphore(hsema, 1, 0);
MSG msg = {};
while (GetMessage(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
DECLARE HWND clipboard_callback(void (*callback)(wchar_t *, bool))
{
HANDLE hsema = CreateSemaphoreW(0, 0, 10, 0);
HWND hwnd;
std::thread(std::bind(clipboard_callback_1, callback, hsema, &hwnd)).detach();
WaitForSingleObject(hsema, INFINITE);
CloseHandle(hsema);
if (AddClipboardFormatListener(hwnd))
return hwnd;
else
return NULL;
}
DECLARE void clipboard_callback_stop(HWND hwnd)
{
if (!hwnd)
return;
RemoveClipboardFormatListener(hwnd);
DestroyWindow(hwnd);
}