/***************************************************************************
 *   Copyright (C) 2005 by Karye   *
 *   karye@users.sourceforge.net   *
 *                                                                         *
 *   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 2 of the License, or     *
 *   (at your option) 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, write to the                         *
 *   Free Software Foundation, Inc.,                                       *
 *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
 ***************************************************************************/

#include <cstddef>                 // for NULL
#include <klocalizedstring.h>       // for i18n
#include <ktreewidgetsearchline.h>  // for KTreeWidgetSearchLine
#include <qabstractitemview.h>      // for QAbstractItemView, QAbstractItemV...
#include <qcursor.h>                // for QCursor
#include <qdebug.h>                 // for QDebug
#include <qicon.h>                  // for QIcon
#include <qpushbutton.h>            // for QPushButton
#include <qstringlist.h>            // for QStringList
#include <qstringliteral.h>         // for QStaticStringData, QStringLiteral
#include <qtreewidget.h>            // for QTreeWidgetItem
#include <qwhatsthis.h>             // for QWhatsThis

#include "common.h"                 // for EtcUpdateSingleton, DEBUG_LINE_INFO
#include "emerge.h"                 // for Emerge
#include "etcupdate.h"              // for EtcUpdate
#include "mergelistview.h"          // for MergeListView, MergeListView::Mer...
#include "mergetab.h"

/**
 * @class MergeTab
 * @short Tabpage for emerge log browser.
 */
MergeTab::MergeTab( QWidget* parent )
    : QWidget( parent )
{
	setupUi( this );

	// Connect What's this button
	connect(pbWhatsThis, &QPushButton::clicked, this, &MergeTab::slotWhatsThis);

	pbClearFilter->setIcon( QIcon::fromTheme(QStringLiteral("edit-clear-locationbar-ltr")) );

	mergeFilter->setTreeWidget( mergeView );

	connect( EtcUpdateSingleton::Instance(), &EtcUpdate::signalScanCompleted, this, &MergeTab::slotLoadConfFiles );
	connect( EtcUpdateSingleton::Instance(), &EtcUpdate::signalEtcFileMerged, this, &MergeTab::slotReload );

	// When all packages are emerged...
	connect( EmergeSingleton::Instance(), &Emerge::signalEmergeComplete, this, &MergeTab::slotReload );

	connect(unmergeView, &MergeListView::itemSelectionChanged, this, &MergeTab::slotButtonMerge);
	connect(mergeView, &MergeListView::itemSelectionChanged, this, &MergeTab::slotButtonView);

	connect(pbMerge, &QPushButton::clicked, this, &MergeTab::slotMergeFile);
	connect(pbView, &QPushButton::clicked, this, &MergeTab::slotViewFile);

	slotInit();
}

/**
 * Save splitters and listview geometry.
 */
MergeTab::~MergeTab()
= default;

/**
 * Initialize geometry and content.
 */
void MergeTab::slotInit()
{
	pbWhatsThis->setIcon( QIcon::fromTheme(QStringLiteral("help-about")) );
	unmergeView->setHeaderLabel( i18n("New Configuration file") );
	mergeView->setHeaderLabel( i18n("Merged Configuration file") );
	mergeView->setSelectionMode(QAbstractItemView::SingleSelection);
	unmergeView->setSelectionMode(QAbstractItemView::SingleSelection);
	pbMerge->setDisabled( true );
	pbView->setDisabled( true );
	slotReload();
}

/**
 * What's this info explaning this tabs functionality.
 */
void MergeTab::slotWhatsThis()
{
	QWhatsThis::showText( QCursor::pos(), i18n( "<qt>"
			"This tab keeps track of all configuration files that need to be merged.<br/>"
			"Your system is scanned automatically for configuration files after completed installation.<br/>"
			"Select a file to merge and press 'Merge changes'. Kompare will then open with old and new files. "
			"After saving changes in Kompare the configuration file will be removed. "
			"Old merged changes can then be reviewed in the right list.</qt>" ), this );
}

/**
 * Reload history view.
 */
void MergeTab::slotReload()
{
	DEBUG_LINE_INFO;
	EtcUpdateSingleton::Instance()->slotEtcUpdate();
}

/**
 * List new configuration files in mergeView.
 */
void MergeTab::slotLoadConfFiles()
{
	DEBUG_LINE_INFO;
	QStringList confFilesList = EtcUpdateSingleton::Instance()->confFilesList();
	unmergeView->loadConfFiles( confFilesList );

	QStringList backupFilesList = EtcUpdateSingleton::Instance()->backupFilesList();
	mergeView->loadBackupFiles( backupFilesList );

	Q_EMIT signalMergeChanged();
}

void MergeTab::slotClearFilter()
{
	mergeFilter->clear();
}

/**
 * Activate buttons only when file is selected.
 */
void MergeTab::slotButtonView()
{
	QTreeWidgetItem *item = mergeView->currentItem();
	if ( item && item->parent() ) {
		unmergeView->clearSelection();
		pbView->setDisabled( false );
		pbMerge->setDisabled( true );
	}
	else {
		pbMerge->setDisabled( true );
		pbView->setDisabled( true );
	}
}

/**
 * Activate buttons only when file is selected.
 */
void MergeTab::slotButtonMerge()
{
	QTreeWidgetItem *item = unmergeView->currentItem();
	if ( item ) {
		mergeView->clearSelection();
		pbMerge->setDisabled( false );
		pbView->setDisabled( true );
	}
	else {
		pbMerge->setDisabled( true );
		pbView->setDisabled( true );
	}
}

/**
 * View merged changes in diff tool.
 */
void MergeTab::slotViewFile()
{
    auto *item = dynamic_cast<MergeListView::MergeItem*>( mergeView->currentItem() );
	if ( nullptr != item && nullptr != item->parent() )
		EtcUpdateSingleton::Instance()->runDiff( item->source(), item->destination()/*, false */);
}

/**
 * Launch diff tool to merge changes.
 */
void MergeTab::slotMergeFile()
{
	auto *item = dynamic_cast<MergeListView::MergeItem*>( unmergeView->currentItem() );
	if ( nullptr != item )
		EtcUpdateSingleton::Instance()->runDiff( item->source(), item->destination()/*, true */);
}

