QMLアプリケーション開発時に、システムのカラー情報やアイコンを取得する必要がある場合、Win32 APIを活用することで効率的に実装できます。
プロジェクト設定ファイルに必要なライブラリを追加します。
QT += svg gui
# Windows API設定
win32:LIBS += -lUser32 -lgdi32
# OpenCV設定
win32:CONFIG(release, debug|release): {
LIBS += -L$$PWD/opencv/lib -lopencv_core451
INCLUDEPATH += $$PWD/opencv/include
}
win32:CONFIG(debug, debug|release): {
LIBS += -L$$PWD/opencv/lib -lopencv_core451d
INCLUDEPATH += $$PWD/opencv/include
}
ヘルパークラスのインターフェース定義:
#ifndef SYSTEM_UTILITY_H
#define SYSTEM_UTILITY_H
#include <QObject>
#include <QColor>
#include <QPoint>
#include <QSize>
class SystemUtility : public QObject
{
Q_OBJECT
public:
explicit SystemUtility(QObject* parent = nullptr);
Q_INVOKABLE QPoint getMousePosition() const;
Q_INVOKABLE QColor getScreenColor(int x, int y) const;
Q_INVOKABLE void saveCursorIcon(const QString& path,
const QSize& size = QSize(32, 32)) const;
};
#endif // SYSTEM_UTILITY_H
実装クラス:
#include "systemutility.h"
#include <windows.h>
#include <QSvgGenerator>
#include <QPainter>
#include <QPixmap>
SystemUtility::SystemUtility(QObject* parent) : QObject(parent) {}
QPoint SystemUtility::getMousePosition() const
{
POINT cursorPos;
GetCursorPos(&cursorPos);
return QPoint(cursorPos.x, cursorPos.y);
}
QColor SystemUtility::getScreenColor(int x, int y) const
{
HDC dc = GetDC(nullptr);
COLORREF color = GetPixel(dc, x, y);
ReleaseDC(nullptr, dc);
return QColor(GetRValue(color), GetGValue(color), GetBValue(color));
}
void SystemUtility::saveCursorIcon(const QString& path, const QSize& size) const
{
const int width = size.width();
const int height = size.height();
HDC screenDC = GetDC(nullptr);
HDC memDC = CreateCompatibleDC(screenDC);
HBITMAP bitmap = CreateCompatibleBitmap(screenDC, width, height);
HBITMAP oldBitmap = static_cast<HBITMAP>(SelectObject(memDC, bitmap));
POINT cursorPos;
GetCursorPos(&cursorPos);
BitBlt(memDC, 0, 0, width, height, screenDC,
cursorPos.x - width/2, cursorPos.y - height/2, SRCCOPY);
QImage image(width, height, QImage::Format_ARGB32);
BITMAPINFO bmi = {0};
bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
bmi.bmiHeader.biWidth = width;
bmi.bmiHeader.biHeight = -height;
bmi.bmiHeader.biPlanes = 1;
bmi.bmiHeader.biBitCount = 32;
bmi.bmiHeader.biCompression = BI_RGB;
GetDIBits(memDC, bitmap, 0, height,
image.bits(), &bmi, DIB_RGB_COLORS);
SelectObject(memDC, oldBitmap);
DeleteObject(bitmap);
DeleteDC(memDC);
ReleaseDC(nullptr, screenDC);
QSvgGenerator svg;
svg.setFileName(path);
svg.setSize(size);
svg.setViewBox(QRect(0, 0, width, height));
QPainter painter;
painter.begin(&svg);
painter.drawImage(0, 0, image);
painter.end();
}
QMLからは以下のように利用できます:
SystemUtility {
id: systemUtil
}
// マウス位置取得
var pos = systemUtil.getMousePosition();
// 画面色取得
var color = systemUtil.getScreenColor(100, 200);
// アイコン保存
systemUtil.saveCursorIcon("icon.svg");