291 lines
11 KiB
Diff
291 lines
11 KiB
Diff
From 28943e130d80c183d40df77bc17c64f4593b6aca Mon Sep 17 00:00:00 2001
|
||
From: wangyucheng <wangyucheng@kylinsec.com.cn>
|
||
Date: Sun, 23 Apr 2023 14:29:42 +0800
|
||
Subject: [PATCH] feature: add windows capture mode
|
||
MIME-Version: 1.0
|
||
Content-Type: text/plain; charset=UTF-8
|
||
Content-Transfer-Encoding: 8bit
|
||
|
||
- 增加截图时代码捕获的功能
|
||
---
|
||
.gitignore | 2 +
|
||
flameshot.pro | 4 +
|
||
src/core/controller.cpp | 2 +-
|
||
src/widgets/capture/capturewidget.cpp | 98 +++++++++++++++++++++-
|
||
src/widgets/capture/capturewidget.h | 6 ++
|
||
src/widgets/capture/thicknesswidget.cpp | 1 +
|
||
src/widgets/capture/toowidget.cpp | 1 +
|
||
translations/Internationalization_zh_CN.ts | 6 +-
|
||
8 files changed, 114 insertions(+), 6 deletions(-)
|
||
|
||
diff --git a/.gitignore b/.gitignore
|
||
index e69de29..5acb669 100644
|
||
--- a/.gitignore
|
||
+++ b/.gitignore
|
||
@@ -0,0 +1,2 @@
|
||
+build
|
||
+.vscode
|
||
diff --git a/flameshot.pro b/flameshot.pro
|
||
index 0f368db..cec798d 100644
|
||
--- a/flameshot.pro
|
||
+++ b/flameshot.pro
|
||
@@ -5,6 +5,7 @@
|
||
#-------------------------------------------------
|
||
|
||
win32:LIBS += -luser32 -lshell32
|
||
+QMAKE_CXXFLAGS += -Wno-deprecated-declarations
|
||
|
||
TAG_VERSION = $$system(git --git-dir $$PWD/.git --work-tree $$PWD describe --always --tags)
|
||
isEmpty(TAG_VERSION){
|
||
@@ -16,12 +17,15 @@ DEFINES += WNCK_I_KNOW_THIS_IS_UNSTABLE
|
||
CONFIG += console
|
||
|
||
QT += core gui widgets network svg
|
||
+QT += x11extras
|
||
|
||
unix:!macx {
|
||
QT += dbus
|
||
}
|
||
|
||
CONFIG += c++11 link_pkgconfig
|
||
+
|
||
+PKGCONFIG += x11
|
||
PKGCONFIG += klog-qt5
|
||
PKGCONFIG += kiran-style-helper
|
||
|
||
diff --git a/src/core/controller.cpp b/src/core/controller.cpp
|
||
index ab46a4b..36abfbf 100644
|
||
--- a/src/core/controller.cpp
|
||
+++ b/src/core/controller.cpp
|
||
@@ -325,4 +325,4 @@ void Controller::doLater(int msec, QObject *receiver, lambda func) {
|
||
[timer, func](){ func(); timer->deleteLater(); });
|
||
timer->setInterval(msec);
|
||
timer->start();
|
||
-}
|
||
+}
|
||
\ No newline at end of file
|
||
diff --git a/src/widgets/capture/capturewidget.cpp b/src/widgets/capture/capturewidget.cpp
|
||
index 5985d21..5f05b25 100644
|
||
--- a/src/widgets/capture/capturewidget.cpp
|
||
+++ b/src/widgets/capture/capturewidget.cpp
|
||
@@ -240,7 +240,6 @@ void CaptureWidget::initOriginUI()
|
||
|
||
m_zoomIndicator = new ZoomIndicator(this);
|
||
m_zoomIndicator->hide();
|
||
-
|
||
m_isFirstReleaseButton = false;
|
||
}
|
||
|
||
@@ -406,7 +405,8 @@ void CaptureWidget::paintEvent(QPaintEvent *) {
|
||
QString helpTxt = tr("Press Enter to capture the screen."
|
||
"\nUse the Mouse Wheel to change the thickness of your tool."
|
||
"\nUse ctrl+c to save the picture to the clipboard."
|
||
- "\nUse ctrl+s to save the picture to the set location.");
|
||
+ "\nUse ctrl+s to save the picture to the set location."
|
||
+ "\nUse ctrl+d open capture window mode.");
|
||
|
||
// We draw the white contrasting background for the text, using the
|
||
//same text and options to get the boundingRect that the text will have.
|
||
@@ -566,7 +566,35 @@ void CaptureWidget::mouseMoveEvent(QMouseEvent *e) {
|
||
//QRect m_backgroundRect = m_selection->geometry();
|
||
QPoint topLeft = m_backgroundRect.topLeft() * devicePixelRatioF();
|
||
|
||
- if(curPos.x() + INDICATOR_WIDTH > m_context.desktop->screenGeometry().width() - 120)
|
||
+ //Active windows select mode
|
||
+ if (activeWindowSelectMode)
|
||
+ {
|
||
+ // new rect for active window
|
||
+ int minWith = INT_MAX;
|
||
+ int minHeight = INT_MAX;
|
||
+ int windowX = 0;
|
||
+ int windowY = 0;
|
||
+
|
||
+ for (auto win : m_wnds)
|
||
+ {
|
||
+ if (win.contains(curPos))
|
||
+ {
|
||
+ if (minWith > win.width() && minHeight > win.height())
|
||
+ {
|
||
+ minWith = win.width();
|
||
+ minHeight = win.height();
|
||
+ windowX = win.x();
|
||
+ windowY = win.y();
|
||
+ }
|
||
+ //new m_selection
|
||
+ }
|
||
+ m_selection->setVisible(true);
|
||
+ m_selection->setGeometry(QRect(windowX, windowY, minWith, minHeight).normalized());
|
||
+ update();
|
||
+ }
|
||
+ }
|
||
+
|
||
+ if (curPos.x() + INDICATOR_WIDTH > m_context.desktop->screenGeometry().width() - 120)
|
||
{
|
||
tmpPos.setX(curPos.x() - INDICATOR_WIDTH);
|
||
}
|
||
@@ -971,6 +999,8 @@ void CaptureWidget::initSelection() {
|
||
});
|
||
m_selection->setVisible(false);
|
||
m_selection->setGeometry(QRect());
|
||
+ // 初始化要捕获的窗口
|
||
+ getActiveWindow();
|
||
}
|
||
|
||
void CaptureWidget::setState(CaptureButton *b) {
|
||
@@ -1187,6 +1217,7 @@ void CaptureWidget::initShortcuts() {
|
||
new QShortcut(QKeySequence(Qt::CTRL + Qt::Key_S), this, SLOT(saveScreenshot()));
|
||
new QShortcut(QKeySequence(Qt::CTRL + Qt::Key_C), this, SLOT(copyScreenshot()));
|
||
new QShortcut(QKeySequence(Qt::CTRL + Qt::Key_Z), this, SLOT(undo()));
|
||
+ new QShortcut(QKeySequence(Qt::CTRL + Qt::Key_D), this, SLOT(setActiveWindowSelectMode()));
|
||
new QShortcut(QKeySequence(Qt::CTRL + Qt::SHIFT + Qt::Key_Z), this, SLOT(redo()));
|
||
new QShortcut(QKeySequence(Qt::SHIFT + Qt::Key_Right), this, SLOT(rightResize()));
|
||
new QShortcut(QKeySequence(Qt::SHIFT + Qt::Key_Left), this, SLOT(leftResize()));
|
||
@@ -1419,3 +1450,64 @@ void CaptureWidget::saveFullScreen()
|
||
{
|
||
saveScreenshot();
|
||
}
|
||
+
|
||
+void CaptureWidget::setActiveWindowSelectMode()
|
||
+{
|
||
+ activeWindowSelectMode = true;
|
||
+ m_showInitialMsg = false;
|
||
+ update();
|
||
+}
|
||
+
|
||
+void CaptureWidget::getActiveWindow()
|
||
+{
|
||
+ auto display = XOpenDisplay(nullptr);
|
||
+ // todo: 只获取了默认的屏幕,在多屏幕下无法获取到其他屏幕的窗口
|
||
+ auto root_window = DefaultRootWindow(display);
|
||
+
|
||
+ Window root_return, parent_return;
|
||
+ Window* child_list = nullptr;
|
||
+ unsigned int child_num = 0;
|
||
+ // 按z-order顺序获取根屏幕的所有子屏幕,也就是所有的窗口
|
||
+ XQueryTree(display, root_window, &root_return, &parent_return, &child_list, &child_num);
|
||
+ // 绝大部分窗口可以排除,也许可以给出一个常量,比如20(20个需要关注的可见窗口)
|
||
+ m_wnds.reserve(child_num);
|
||
+ for (auto i = child_num; (int)i >= 0; i--)
|
||
+ {
|
||
+ XWindowAttributes attrs;
|
||
+ // 获取窗口相关数据
|
||
+ XGetWindowAttributes(display, child_list[i], &attrs);
|
||
+ int screenX = 0;
|
||
+ int screenY = 0;
|
||
+ Window childWin;
|
||
+ // 坐标系转换
|
||
+ XTranslateCoordinates(display, child_list[i], root_window, 0, 0, &screenX, &screenY, &childWin);
|
||
+ // 过滤掉不可见的窗口
|
||
+ if (attrs.map_state != IsViewable)
|
||
+ {
|
||
+ continue;
|
||
+ }
|
||
+ auto cur_wnd = QRect(screenX, screenY, attrs.width, attrs.height);
|
||
+ auto is_coverd = false;
|
||
+ // 只能判断是否被一个窗口遮挡,如果被两个窗口拼接遮挡则判断不了
|
||
+ if (m_wnds.isEmpty())
|
||
+ {
|
||
+ m_wnds.append(cur_wnd);
|
||
+ }
|
||
+ for (auto wnd : m_wnds)
|
||
+ {
|
||
+ if (wnd.contains(cur_wnd, true))
|
||
+ {
|
||
+ is_coverd = true;
|
||
+ break;
|
||
+ }
|
||
+ }
|
||
+ if (is_coverd)
|
||
+ {
|
||
+ is_coverd = false;
|
||
+ continue;
|
||
+ }
|
||
+ m_wnds.append(cur_wnd);
|
||
+ }
|
||
+ XFree(display);
|
||
+ XFree(child_list);
|
||
+}
|
||
\ No newline at end of file
|
||
diff --git a/src/widgets/capture/capturewidget.h b/src/widgets/capture/capturewidget.h
|
||
index 79246e4..d08aa4b 100644
|
||
--- a/src/widgets/capture/capturewidget.h
|
||
+++ b/src/widgets/capture/capturewidget.h
|
||
@@ -123,6 +123,7 @@ private slots:
|
||
void setDrawThickness(const int &t);
|
||
void setDrawRectStyle(const int &s);
|
||
void setDrawLineStyle(const int &l);
|
||
+ void setActiveWindowSelectMode();
|
||
|
||
protected:
|
||
void paintEvent(QPaintEvent *);
|
||
@@ -156,6 +157,10 @@ protected:
|
||
bool m_adjustmentButtonPressed;
|
||
bool m_inselection = true;
|
||
bool m_flag = false;
|
||
+ bool activeWindowSelectMode = false; //select active window
|
||
+
|
||
+ // save active window
|
||
+ QVector<QRect> m_wnds;
|
||
|
||
private:
|
||
void initSecondUI();
|
||
@@ -169,6 +174,7 @@ private:
|
||
void pushToolToStack();
|
||
void makeChild(QWidget *w);
|
||
void updateToolBar(QString toolName);
|
||
+ void getActiveWindow();
|
||
|
||
QRect extendedSelection() const;
|
||
QRect extendedRect(QRect *r) const;
|
||
diff --git a/src/widgets/capture/thicknesswidget.cpp b/src/widgets/capture/thicknesswidget.cpp
|
||
index 3f6360b..5046201 100644
|
||
--- a/src/widgets/capture/thicknesswidget.cpp
|
||
+++ b/src/widgets/capture/thicknesswidget.cpp
|
||
@@ -97,6 +97,7 @@ QVector<QRect> ThicknessWidget::handleMask() const {
|
||
spacing += i*4;
|
||
QRect *rect = new QRect(8 + i * 10 + spacing , 13 - i * 2 , (i+1)*4, (i+1)*4);
|
||
areas.append(*rect);
|
||
+ delete rect;
|
||
}
|
||
return areas;
|
||
}
|
||
diff --git a/src/widgets/capture/toowidget.cpp b/src/widgets/capture/toowidget.cpp
|
||
index 96d5fed..33428cf 100644
|
||
--- a/src/widgets/capture/toowidget.cpp
|
||
+++ b/src/widgets/capture/toowidget.cpp
|
||
@@ -127,6 +127,7 @@ QVector<QRect> Toowidget::handleMask() const {
|
||
for (int i = 0; i < m_colorList.size(); ++i) {
|
||
QRect *rect = new QRect(102 + i * 22, 9, 12, 12);
|
||
areas.append(*rect);
|
||
+ delete rect;
|
||
}
|
||
return areas;
|
||
}
|
||
diff --git a/translations/Internationalization_zh_CN.ts b/translations/Internationalization_zh_CN.ts
|
||
index f8bbbe5..3bfd5d5 100644
|
||
--- a/translations/Internationalization_zh_CN.ts
|
||
+++ b/translations/Internationalization_zh_CN.ts
|
||
@@ -156,7 +156,8 @@
|
||
<source>Press Enter to capture the screen.
|
||
Use the Mouse Wheel to change the thickness of your tool.
|
||
Use ctrl+c to save the picture to the clipboard.
|
||
-Use ctrl+s to save the picture to the set location.</source>
|
||
+Use ctrl+s to save the picture to the set location.
|
||
+Use ctrl+d open capture window mode.</source>
|
||
<translatorcomment>按 Enter 键捕捉屏幕。
|
||
使用鼠标滚轮来改变绘画工具的宽度。
|
||
使用ctrl+c将图片保存到剪贴板。
|
||
@@ -164,7 +165,8 @@ Use ctrl+s to save the picture to the set location.</source>
|
||
<translation>按 Enter 键捕捉屏幕。
|
||
使用鼠标滚轮来改变绘画工具的宽度。
|
||
使用ctrl+c将图片保存到剪贴板。
|
||
-使用ctrl+s将图片保存至设定位置。</translation>
|
||
+使用ctrl+s将图片保存至设定位置。
|
||
+使用ctrl+d打开窗口捕获模式。</translation>
|
||
</message>
|
||
<message>
|
||
<location filename="../src/widgets/capture/capturewidget.cpp" line="1009"/>
|
||
--
|
||
2.33.0
|
||
|