/*
 * Copyright (C) 2020 Uniontech Technology Co., Ltd.
 *
 * Author:     gl di <diguoliang@uniontech.com>
 *
 * Maintainer: gl di <diguoliang@uniontech.com>
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

#ifndef POLKIT_QT_EXAMPLE_DBUS_H
#define POLKIT_QT_EXAMPLE_DBUS_H

#include <QtCore/QObject>
#include <QtDBus/QDBusContext>
#include <QMap>
#include <QSet>
#include <QTimer>

#include "../config/screenshotconfig.h"

/*! \file dbus.h */

/*! \class PolkitProhibitedDBus
 *  \brief set window be protected or not(either root window) by dbus
 *  \author xinbo wang
 *  \date 2023
 */
class PolkitProhibitedDBus : public QObject, protected QDBusContext
{
    Q_OBJECT
    Q_CLASSINFO("D-Bus Interface", "deepin.prohibitscreenshot.interface")

public:
    explicit PolkitProhibitedDBus(QObject* parent = nullptr);
    virtual ~PolkitProhibitedDBus();

public Q_SLOTS:
    /**
     * @brief set root window be protected or not, only be used by ICBC
     * @param bProhibited Whether or not to Set protected
     * @return 0 means set succeed, otherwise failed.
    */
    int setProhibited(bool bProhibited);

    /**
     * @brief get current prohibited status
     * @return true or false if current is prohibited
    */
    bool prohibited();

    /**
     * @brief register the Window that need be protected
     * @param window id of the window
     * @return 0 means set succeed, otherwise failed.
    */
    int registerProhibitedWindow(int window);

    /**
     * @brief unregister the Window that need be protected
     * @param window id of the window
     * @return 0 means set succeed, otherwise failed.
    */
    int unRegisterProhibitedWindow(int window);

    /**
     * @brief query Window protect State
     * @param window id of the window
     * @return true or false if the window is protected
    */
    bool queryProhibitWindowState(int window);

    /**
     * @brief update x11 ProhibitedScreenshotWindow atom
     * @param isActive window is registerd or not
     * @param window id of the window
     * @return void
    */
    void doUpdateX11Atom(bool isActive, int window);
    void protectedRootWindow(bool isActive);
    QString getOffClient();

public Q_SLOTS:
    void timerCheckProhibitedWindowPid();
    void checkNeedProhibitScreenshot();
    void dealWithSystemdbus(int pid, bool bProhibited);

    //deal with kwin signals
    void toggleActiveMinimize(int window, bool isMinimize);
    void clientToDesktop(int window, int desk);
    void workspaceSwitched(int from, int to);
    void destroyWindow(int window);
    void showingDesktop(bool isShowingDesktop);
    void sessionRemoved();
    void tabboxClosed();
    void clientMoveResize(bool moving, int window);

Q_SIGNALS:
    void ProhibitedChanged(bool);

public:
    int doProtectedWindow(bool bProhibited, int window = -1);
    int doGetWindowPid(int window);

private:
    bool checkSenderWhiteList(uint pid);
    bool checkIsExistsOtherOpenProhibitedSwitchPid(uint pid);
    bool checkWindowAttribute(int targetWindow, QString attribute);
    bool checkWindowText(int nWindow);

    /*
     * 只记录有接口调用记录的防截图程序
    */
    QMap<uint, bool> m_mapAccessInterfaceProhibitedPidStatus;

private:
    bool isNeed = false;

    QMap<int, bool> windowInfo;
    bool isCalledByUs = false;
    int m_nProtectedWindowCount = 0;
    bool isWayland = false;
    ScreenShotConfig *m_pScreenShotConfig = NULL;
};


#endif //POLKIT_QT_EXAMPLE_DBUS_H
