/**************************************************************************
 *  This file is part of QXmlEdit                                         *
 *  Copyright (C) 2011 by Luca Bellonda and individual contributors       *
 *    as indicated in the AUTHORS file                                    *
 *  lbellonda _at_ gmail.com                                              *
 *                                                                        *
 * This library is free software; you can redistribute it and/or          *
 * modify it under the terms of the GNU Library General Public            *
 * License as published by the Free Software Foundation; either           *
 * version 2 of the License, or (at your option) any later version.       *
 *                                                                        *
 * This library 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      *
 * Library General Public License for more details.                       *
 *                                                                        *
 * You should have received a copy of the GNU Library General Public      *
 * License along with this library; if not, write to the                  *
 * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,       *
 * Boston, MA  02110-1301  USA                                            *
 **************************************************************************/

#ifndef XMLEDITWIDGET_H
#define XMLEDITWIDGET_H

#include "libQXmlEdit_global.h"

#include <QWidget>
#include <QDomDocument>

#include "xmlEdit.h"
#include "xmleditglobals.h"

#include "qxmleditdata.h"
#include "navigation.h"
#include "regola.h"

// Forward declaration : do not remove, it is usefull for third party applications to include only this file
class XSDSchema;
class Element;
class XSchemaLoader;
class UIDelegate;
class QAttributeDelegate;
class PaintInfo;

namespace Ui
{
class XmlEditWidget;
}

class XmlEditWidgetPrivate;

class LIBQXMLEDITSHARED_EXPORT XmlEditWidget : public QWidget
{
    Q_OBJECT
    Q_PROPERTY(bool enabled READ isEnabled WRITE setEnabled)
    Q_PROPERTY(bool encodingLabelVisible READ isEncodingLabelVisible WRITE setEncodingLabelVisible)
    Q_PROPERTY(bool viewAsXSDButtonVisible READ isViewAsXSDButtonVisible WRITE setViewAsXSDButtonVisible)
    Q_PROPERTY(bool moveButtonsVisible READ areMoveButtonsVisible WRITE setMoveButtonsVisible)
    Q_PROPERTY(ulong versionNumber READ versionNumber)

    friend class XmlEditWidgetPrivate ;

private:
    XmlEditWidgetPrivate *d;


public:
    explicit XmlEditWidget(QWidget *parent = 0);
    ~XmlEditWidget();

    bool isReady();

    ulong versionNumber();
    XmlEditWidgetPrivate *getPrivate();

    bool editElement(QTreeWidgetItem *item);

    bool init();
    void setData(QApplication *newApplication, QXmlEditData *newData, const bool newIsSlave, UIDelegate *newUiDelegate);

    Element *getSelectedItem();
    QTreeWidgetItem *getSelItem();
    void deleteSchema();

    void display();
    void repaint();
    void resetTree();
    void computeSelectionState();

    PaintInfo *getPaintInfo();

    void doLoadFileXplore(const QString &filePath);
    void openProva();
    QString getContentAsText();
    qxmledit::EDisplayMode displayMode();

    bool isCDATA();
    void setCDATA(const bool isCData);
    void doNew();

    Regola *getRegola();

    void autoLoadValidation();
    //void triggersWelcomeDialog();

    void error(const QString& message) ;
    void warning(const QString& message) ;
    void message(const QString& message) ;
    bool askYN(const QString & message) ;

    QTreeWidget *getMainTreeWidget();
    void addChild();
    void addBrother();

    void errorNoRule();
    void setClipBoardItem(Element *pElement);
    void cleanClipBoard();
    Element * getClipBoardItem() const ;

    bool isActionMode();
    bool isActionNoScanMode();
    void setDisplayMode(const qxmledit::EDisplayMode value);

    void setDocument(QDomDocument &document, const QString &filePath, const bool isSetState);
    void setNavigationDataAndEnable(const int minFragment, const int maxFragment);
    void showNavigationBox();
    void loadText(const QString &text, const bool isChangeState = true, const bool isAskForReview = false);
    void insertSnippet(Regola *newRegola);
    void insertAllowedElements(Element *element);
    void validateWithFile(const QString &filePath);
    XSDSchema *schema();
    bool isUndoPossible();
    bool isRedoPossible();
    void undo();
    void redo();
    void onActionCompareXSD(const QString &folderPath);
    void onActionExportSiblingsAttributesAsCSVClipboard();

private:
    Ui::XmlEditWidget *ui;

    //-----------------------
    void emitReevaluateSelectionState();
    void emitDocumentIsModified(const bool isModified);// TODO: emit this
    void emitTreeContextMenuRequested(const QPoint &);
    void emitSignalSetClipBoardActionsState(const bool isAction);
    void emitOkClicked();
    void emitCancelClicked();
    void emitEnableZoom();
    void emitViewAsXsdRequested();
    void emitSchemaLabelChanged(const QString &newLabel);
    void emitShowStatusMessage(const QString &message, const bool isLongTimeout);
    void emitDataReadyMessage(const QString &newLabel);
    void emitLoadCurrentPage(const int page);
    //-----------------------

protected:
    virtual void changeEvent(QEvent *e);
    virtual bool eventFilter(QObject *obj, QEvent *event);
public:
    // Show/Hide Move buttons
    void setMoveButtonsVisible(bool isShow);
    bool areMoveButtonsVisible();
    // Show/Hide ViewAsXsd
    void setViewAsXSDButtonVisible(bool isShow);
    bool isViewAsXSDButtonVisible();
    // Show/Hide encoding label at the top of the right layout
    void setEncodingLabelVisible(bool isShow);
    bool isEncodingLabelVisible();
    // Show/Hide doc type label
    void setDocTypeVisible(bool isShow);
    bool isDocTypeVisible();
    //
    void resizeTreeColumns();
    void onAddBrother();
    void onDeleteItem();
    void onActionPaste();
    void onActionCopy();
    void onActionCut();
    void onActionExpandAll();
    void onActionShowAttrLine(const bool state);
    void onActionAppendComment();
    void onActionAddComment();
    void onActionAppendProcessingInstruction();
    void onActionAddProcessingInstruction();
    void onActionResizeToContents();
    void onActionAddChildElement();
    void onActionAppendChildElement();
    void onActionEdit();
    void onActionFind();
    void onActionDelete();
    void onActionMoveUp();
    void onActionMoveDown();
    void onActionGoToParent();
    void onActionGoToPreviousBrother();
    void onActionGoToNextBrother();
    void onActionClearBookmarks();
    void onActionToggleBookmark();
    void onActionGotoNextBookmark();
    void onActionGotoPreviousBookmark();
    void onActionShowChildIndex(const bool isChecked);
    void onActionCloseThisAllBrothers();
    void onActionNewFromClipboard();
    void onActionCompactView(const bool isChecked);
    void onActionHideBrothers();
    void onActionFixedSizeAttributes(const bool isChecked);
    void onActionShowAttributesLength(const bool isChecked);
    void onActionShowCurrentElementTextBase64(const bool isChecked);
    void onActionShowBase64(const bool isChecked);
    void onActionEditInnerXML();
    void onActionEditInnerXMLBase64();
    void onActionEditInnerBase64Text();
    void onActionZoomIn();
    void onActionZoomOut();
    void onActionCopyPathToClipboard();
    void onActionValidate();
    void onActionValidateFile();
    void onActionValidateNewFile();
    void onActionInsertSnippet();
    void onActionShowElementTextLength(const bool isChecked);
    void onActionShowElementSize(const bool isChecked);
    void onActionDeleteBookmarked();
    void onActionCleanBookmarkedContent();
    void onActionHideView(const bool isChecked);
    void onActionViewAsXsd();
    void onActionAllowedSchemaElements();
    void onActionPasteAndSubstituteText();
    void onActionNewUsingXMLSchema(const QString &schemaURL);
    void onActionTransformInComment();
    void onActionExtractElementsFromComment();
    void onActionInsertNoNamespaceSchemaReferenceAttributes();
    void onActionInsertSchemaReferenceAttributes();
    Element* onActionHideLeafChildren();
    void onActionHideAllLeafChildren();
    Element* onActionShowLeafChildren();
    void onActionShowAllLeafChildren();
    bool isValidXsd();
    void loadSchema(const QString &schemaURL);
    void setCurrentItem(Element *newSelection);

    void viewNodes();

    //-----------------------

    //------------------- slots
signals:
    void reevaluateSelectionState();
    void documentIsModified(const bool isModified);// TODO: emit this
    void treeContextMenuRequested(const QPoint &);
    void signalSetClipBoardActionsState(const bool isAction);
    void okClicked();
    void cancelClicked();
    void enableZoom();
    void viewAsXsdRequested();
    void schemaLabelChanged(const QString &newLabel);
    void showStatusMessage(const QString &message, const bool isLongTimeout);
    void dataReadyMessage(const QString &newLabel);
    void loadCurrentPage(const int page);
    void undoStateUpdated(const bool undoPossible, const bool redoPossible);
    //--------------- signals
};

#endif // XMLEDITWIDGET_H
