9#include "alkonlinequoteswidget.h"
12#include "alknewstuffwidget.h"
13#include "alkonlinequote.h"
14#include "alkonlinequotesmodel.h"
15#include "alkonlinequotesource.h"
16#include "alkonlinequotesprofile.h"
17#include "alkonlinequotesprofilemanager.h"
18#include "alkonlinequoteuploaddialog.h"
19#include "alkwebpage.h"
20#include "alkwebview.h"
24#include <QDesktopServices>
26#include <QSortFilterProxyModel>
29#include <QTreeWidgetItem>
31#if QT_VERSION >= QT_VERSION_CHECK(5, 0, 0)
33#include <KMessageWidget>
37#include <KComponentData>
42#if QT_VERSION > QT_VERSION_CHECK(5, 0, 0)
44#define initLocale() QLocale()
47#define initLocale() KGlobal::locale()
52#include <ui_alkonlinequotedetails.h>
53#include <ui_alkonlinequoteslist.h>
54#include <ui_alkonlinequotesdebug.h>
55#include <ui_alkonlinequotesprofiledetails.h>
56#include <ui_alkonlinequotesprofiles.h>
58#if QT_VERSION < QT_VERSION_CHECK(5, 0, 0)
60static KLocale _locale(TRANSLATION_DOMAIN);
61#define i18nc(context, text) ki18nc(context, text).toString(&_locale)
62#define i18n(text) ki18n(text).toString(&_locale)
63#define tr2i18n(text, context) ki18nc(context, text).toString(&_locale)
66class AlkOnlineQuotesWidget::Private
68 ,
public Ui::AlkOnlineQuoteDetailsWidget
69 ,
public Ui::AlkOnlineQuotesDebugWidget
70 ,
public Ui::AlkOnlineQuotesProfileDetailsWidget
71 ,
public Ui::AlkOnlineQuotesProfilesWidget
72 ,
public Ui::AlkOnlineQuotesListWidget
76 QString m_acceptLanguage;
77 QList<AlkOnlineQuoteSource> m_resetList;
78 AlkOnlineQuoteSource m_currentItem;
79 bool m_quoteInEditing;
80 AlkOnlineQuotesProfile *m_profile;
81 AlkWebView *m_webView;
90 QPixmap m_unknownIcon;
91 QDialog *m_webPageDialog;
92#if QT_VERSION >= QT_VERSION_CHECK(5, 0, 0)
93 KMessageWidget* m_infoMessage;
95 AlkOnlineQuotesModel *m_model;
96 AlkOnlineQuotesWidget *m_p;
98 Private(
bool showProfiles,
bool showUpload, AlkOnlineQuotesWidget *
parent);
102 void slotNewProfile();
103 void slotDeleteProfile();
104 void slotSelectProfile();
105 void slotLoadProfile();
107 void slotDeleteEntry();
108 void slotDuplicateEntry();
109 void slotAcceptEntry();
110 void slotCopySettingsToClipboard();
111 void slotAddReferenceButton();
112 void slotLoadQuoteSource(
const QModelIndex &index = QModelIndex());
113 void slotEntryChanged();
115 void slotCheckEntry();
116 void slotLogStatus(
const QString &s);
117 void slotLogError(
const QString &s);
118 void slotLogFailed(
const QString &
id,
const QString &symbol);
119 void slotLogQuote(
const QString &
id,
const QString &symbol,
const QDate &date,
double price);
120 void slotLogQuotes(
const QString &
id,
const QString &symbol,
const AlkDatePriceMap &prices);
121 void slotInstallEntries();
122 void slotResetQuotesList();
123 void slotUploadEntry();
124 void slotShowButton();
128 void loadQuotesList(
const bool updateResetList =
false);
131 void setupIcons(
const AlkOnlineQuote::Errors &errors);
132 QString singleSymbol()
const;
133 QStringList doubleSymbol()
const;
134 QString expandedUrl()
const;
135 void updateButtonState();
136 void setDefaultSource(QLineEdit* editWidget,
const QString& sourceDefaultValue,
const QString& defaultValue);
139AlkOnlineQuotesWidget::Private::Private(
bool showProfiles,
bool showUpload, AlkOnlineQuotesWidget *parent)
141 , m_quoteInEditing(false)
143 , m_showProfiles(showProfiles)
144 , m_showUpload(showUpload)
145 , m_ghnsEditable(false)
146 , m_disableUpdate(false)
147#if QT_VERSION < QT_VERSION_CHECK(5, 0, 0)
148 , m_inWorkIcon(BarIcon(
"view-refresh"))
149 , m_okIcon(BarIcon(
"dialog-ok-apply"))
150 , m_failIcon(BarIcon(
"dialog-cancel"))
152 , m_inWorkIcon(
QIcon::fromTheme(
"view-refresh").pixmap(16))
153 , m_okIcon(
QIcon::fromTheme(
"dialog-ok-apply").pixmap(16))
154 , m_failIcon(
QIcon::fromTheme(
"dialog-cancel").pixmap(16))
156 , m_webPageDialog(nullptr)
158#if QT_VERSION >= QT_VERSION_CHECK(5, 0, 0)
159 , m_infoMessage(nullptr)
164#if QT_VERSION < QT_VERSION_CHECK(5, 0, 0)
165 static KComponentData alk(TRANSLATION_DOMAIN);
167 Ui::AlkOnlineQuoteDetailsWidget::setupUi(parent);
168 Ui::AlkOnlineQuotesDebugWidget::setupUi(parent);
169 Ui::AlkOnlineQuotesProfileDetailsWidget::setupUi(parent);
170 Ui::AlkOnlineQuotesProfilesWidget::setupUi(parent);
171 Ui::AlkOnlineQuotesListWidget::setupUi(parent);
173 if (!
QString(BUILD_KEY).isEmpty())
174 m_buildKey->setText(
QString(
"<small>alkimia version: %1</small>").arg(BUILD_KEY));
176 m_buildKey->setText(
QString());
178#ifdef BUILD_WITH_WEBENGINE
179 AlkWebView::setWebInspectorEnabled(
true);
184#ifdef BUILD_WITH_WEBKIT
185 m_webView->setWebInspectorEnabled(
true);
187 AlkOnlineQuotesProfileManager::instance().setWebView(m_webView);
188 AlkOnlineQuotesProfileManager::instance().setWebPage(m_webView->webPage());
190 profilesGroupBox->setVisible(showProfiles);
191 profileDetailsBox->setVisible(showProfiles);
192 m_showButton->setVisible(!showProfiles && AlkOnlineQuotesProfileManager::instance().webViewEnabled());
193 m_ghnsSource->setVisible(
false);
194 m_urlCheckLabel->setMinimumWidth(m_okIcon.
width());
198#if QT_VERSION >= QT_VERSION_CHECK(5, 0, 0)
200 groupBoxLayout->insertWidget(0, m_infoMessage);
201 m_infoMessage->
hide();
204 connect(m_newProfile, SIGNAL(clicked()),
this, SLOT(slotNewProfile()));
205 connect(m_deleteProfile, SIGNAL(clicked()),
this, SLOT(slotDeleteProfile()));
206 connect(m_profileList, SIGNAL(itemSelectionChanged()),
this, SLOT(slotLoadProfile()));
208 connect(m_cancelButton, SIGNAL(clicked()),
this, SLOT(slotLoadQuoteSource()));
209 connect(m_acceptButton, SIGNAL(clicked()),
this, SLOT(slotAcceptEntry()));
210 connect(m_copyButton, SIGNAL(clicked()),
this, SLOT(slotCopySettingsToClipboard()));
211 connect(m_addReferenceButton, SIGNAL(clicked()),
this, SLOT(slotAddReferenceButton()));
212 connect(m_newButton, SIGNAL(clicked()),
this, SLOT(slotNewEntry()));
213 connect(m_resetButton, SIGNAL(clicked()),
this, SLOT(slotResetQuotesList()));
214 connect(m_checkButton, SIGNAL(clicked()),
this, SLOT(slotCheckEntry()));
215 connect(m_deleteButton, SIGNAL(clicked()),
this, SLOT(slotDeleteEntry()));
216 connect(m_duplicateButton, SIGNAL(clicked()),
this, SLOT(slotDuplicateEntry()));
217 connect(m_installButton, SIGNAL(clicked()),
this, SLOT(slotInstallEntries()));
218 connect(m_uploadButton, SIGNAL(clicked()),
this, SLOT(slotUploadEntry()));
221 const int rowHeight = fm.height();
222#if QT_VERSION >= QT_VERSION_CHECK(5, 0, 0)
225 m_quoteSourceList->verticalHeader()->setDefaultSectionSize(rowHeight);
229 m_quoteSourceList->verticalHeader()->setDefaultSectionSize(rowHeight);
231 m_quoteSourceList->verticalHeader()->setVisible(
false);
232 m_quoteSourceList->setShowGrid(
false);
233 m_quoteSourceList->horizontalHeader()->setVisible(
true);
234 m_quoteSourceList->setSortingEnabled(
true);
240 connect(m_editURL, SIGNAL(textChanged(
QString)),
this, SLOT(slotEntryChanged()));
241 connect(m_editIdentifier, SIGNAL(textChanged(
QString)),
this, SLOT(slotEntryChanged()));
243 m_editIdSelector->addItem(
i18nc(
"@item:inlistbox Stock",
"Symbol"), AlkOnlineQuoteSource::IdSelector::Symbol);
244 m_editIdSelector->addItem(
i18nc(
"@item:inlistbox Stock",
"Identification number"), AlkOnlineQuoteSource::IdSelector::IdentificationNumber);
245 m_editIdSelector->addItem(
i18nc(
"@item:inlistbox Stock",
"Name"), AlkOnlineQuoteSource::IdSelector::Name);
246 connect(m_editIdSelector, SIGNAL(currentIndexChanged(
int)),
this, SLOT(slotEntryChanged()));
248 connect(m_editDate, SIGNAL(textChanged(
QString)),
this, SLOT(slotEntryChanged()));
249 connect(m_editDateFormat, SIGNAL(textChanged(
QString)),
this, SLOT(slotEntryChanged()));
250 connect(m_editDefaultId, SIGNAL(textChanged(
QString)),
this, SLOT(slotEntryChanged()));
257 m_editPriceDecimalSeparator->setItemData(0, AlkOnlineQuoteSource::DecimalSeparator::Period);
258 m_editPriceDecimalSeparator->setItemData(1, AlkOnlineQuoteSource::DecimalSeparator::Comma);
259 m_editPriceDecimalSeparator->setItemData(2, AlkOnlineQuoteSource::DecimalSeparator::Legacy);
265 connect(m_editPriceDecimalSeparator, SIGNAL(currentIndexChanged(
int)),
this, SLOT(slotEntryChanged()));
266 connect(m_editPrice, SIGNAL(textChanged(
QString)),
this, SLOT(slotEntryChanged()));
268 m_editDataFormat->addItem(toString(AlkOnlineQuoteSource::DataFormat::StrippedHTML), AlkOnlineQuoteSource::DataFormat::StrippedHTML);
269 m_editDataFormat->addItem(toString(AlkOnlineQuoteSource::DataFormat::HTML), AlkOnlineQuoteSource::DataFormat::HTML);
270 m_editDataFormat->addItem(toString(AlkOnlineQuoteSource::DataFormat::CSV), AlkOnlineQuoteSource::DataFormat::CSV);
271#ifdef BUILD_WITH_WEBKIT
272 m_editDataFormat->addItem(toString(AlkOnlineQuoteSource::DataFormat::CSS), AlkOnlineQuoteSource::DataFormat::CSS);
274 m_editDataFormat->addItem(toString(AlkOnlineQuoteSource::DataFormat::JSON), AlkOnlineQuoteSource::DataFormat::JSON);
275 connect(m_editDataFormat, SIGNAL(currentIndexChanged(
int)),
this, SLOT(slotEntryChanged()));
277 m_editDownloadType->addItem(
i18nc(
"@item:inlistbox Stock",
"Default"), AlkOnlineQuoteSource::DownloadType::Default);
278 m_editDownloadType->addItem(
i18nc(
"@item:inlistbox Stock",
"Javascript"), AlkOnlineQuoteSource::DownloadType::Javascript);
279 connect(m_editDownloadType, SIGNAL(currentIndexChanged(
int)),
this, SLOT(slotEntryChanged()));
281 connect(m_ghnsSource, SIGNAL(toggled(
bool)),
this, SLOT(slotEntryChanged()));
282 connect(m_showButton, SIGNAL(clicked()),
this, SLOT(slotShowButton()));
284 m_uploadButton->setVisible(
false);
285 m_acceptButton->setEnabled(
false);
286 m_resetButton->setVisible(m_showProfiles);
290AlkOnlineQuotesWidget::Private::~Private()
293 if (m_webPageDialog) {
294 m_webPageDialog->deleteLater();
296 delete m_webView->webPage();
301void AlkOnlineQuotesWidget::Private::loadProfiles()
303 AlkOnlineQuotesProfileList
list = AlkOnlineQuotesProfileManager::instance().profiles();
306 for (AlkOnlineQuotesProfile *profile : list) {
307 QListWidgetItem *item =
new QListWidgetItem(
dynamic_cast<QListWidget *
>(m_profileList));
308 item->
setText(profile->name());
311 m_profileList->setCurrentRow(0);
312 m_profile = AlkOnlineQuotesProfileManager::instance().profiles().
first();
313 loadQuotesList(
true);
316void AlkOnlineQuotesWidget::Private::loadQuotesList(
const bool updateResetList)
320 m_model =
new AlkOnlineQuotesModel(m_profile);
321 auto proxyModel =
new QSortFilterProxyModel(
this);
322 proxyModel->setSourceModel(m_model);
323 m_quoteSourceList->setModel(proxyModel);
325 m_model->setProfile(m_profile);
328 if (updateResetList) {
330 const QStringList groups = m_profile->quoteSources();
336 for (
const auto& quoteSourceName : groups) {
337 const auto quoteSource = AlkOnlineQuoteSource(quoteSourceName, m_profile);
338 if (!quoteSource.isGHNS()) {
339 m_resetList.
append(quoteSource);
345 const auto index = !indexes.isEmpty() ? indexes.at(0) : QModelIndex();
347 m_quoteSourceList->setCurrentIndex(index);
348 m_quoteSourceList->selectRow(index.row());
350 slotLoadQuoteSource(m_quoteSourceList->currentIndex());
354void AlkOnlineQuotesWidget::Private::slotNewProfile()
356 QTreeWidgetItem *item =
new QTreeWidgetItem(
dynamic_cast<QTreeWidget *
>(m_profileList));
357 item->
setText(0, QLatin1String(
"new profile"));
361void AlkOnlineQuotesWidget::Private::slotDeleteProfile()
363 delete m_profileList->currentItem();
366void AlkOnlineQuotesWidget::Private::slotSelectProfile()
371void AlkOnlineQuotesWidget::Private::slotLoadProfile()
373 m_uploadButton->setEnabled(
false);
374 const AlkOnlineQuotesProfileList
list = AlkOnlineQuotesProfileManager::instance().profiles();
375 if (!m_showProfiles) {
379 m_installButton->setVisible(m_profile->hasGHNSSupport());
380 m_uploadButton->setVisible(m_profile->hasGHNSSupport());
381 loadQuotesList(
true);
385 for (AlkOnlineQuotesProfile *profile : list) {
386 if (m_profileList->currentItem() && m_profileList->currentItem()->text() == profile->name()) {
388 loadQuotesList(
true);
389 m_installButton->setVisible(profile->hasGHNSSupport());
390 m_uploadButton->setVisible(profile->hasGHNSSupport());
395 bool visible = m_profile->type() != AlkOnlineQuotesProfile::Type::None;
396 m_configFilePath->setText(m_profile->kConfigFile());
397 m_configFilePath->setVisible(
visible);
398 m_configLabel->setEnabled(
visible);
400 visible = m_profile->hasGHNSSupport();
401 m_GHNSConfigFilePath->setText(m_profile->hotNewStuffConfigFile());
402 m_GHNSConfigFilePath->setVisible(
visible);
403 m_GHNSConfigLabel->setEnabled(
visible);
405 m_GHNSDataPath->setText(m_profile->hotNewStuffReadPath().
join(
" "));
406 m_GHNSDataPath->setVisible(
visible);
407 m_GHNSDataLabel->setEnabled(
visible);
410void AlkOnlineQuotesWidget::Private::slotLoadQuoteSource(
const QModelIndex &index)
414 m_quoteInEditing =
false;
416 m_disableUpdate =
true;
418 m_editIdentifier->clear();
419 m_editIdSelector->setCurrentIndex(AlkOnlineQuoteSource::IdSelector::Symbol);
420 m_editPriceDecimalSeparator->setCurrentIndex(AlkOnlineQuoteSource::DecimalSeparator::Legacy);
421 m_editPrice->clear();
423 m_editDateFormat->clear();
424 m_editDefaultId->clear();
427 if (m_quoteSourceList->currentIndex().isValid()) {
428 name = m_quoteSourceList->model()->
data(m_quoteSourceList->currentIndex(), AlkOnlineQuotesModel::NameRole).toString();
429 AlkOnlineQuoteSource source = AlkOnlineQuoteSource(name, m_profile);
430 m_currentItem = source;
433 m_editURL->setText(source.url());
434 m_editIdentifier->setText(source.idRegex());
435 m_editIdSelector->setData<AlkOnlineQuoteSource::IdSelector>(source.idSelector());
437 m_editPrice->setText(source.priceRegex());
439 m_editDate->setText(source.dateRegex());
440 m_editDateFormat->setText(source.dateFormat());
441 m_editDefaultId->setText(source.
defaultId());
442 m_editDownloadType->setData<AlkOnlineQuoteSource::DownloadType>(source.downloadType());
443 m_ghnsSource->setChecked(source.isGHNS());
448 m_profile->type() == AlkOnlineQuotesProfile::Type::Script;
450 if (isFinanceQuoteSource || (m_currentItem.isGHNS() && !m_ghnsEditable))
453 m_editURL->setEnabled(
enabled);
454 m_editIdentifier->setEnabled(
enabled);
455 m_editIdSelector->setEnabled(
enabled);
456 m_editPriceDecimalSeparator->setEnabled(
enabled);
457 m_editPrice->setEnabled(
enabled);
458 m_editDate->setEnabled(
enabled);
459 m_editDateFormat->setEnabled(
enabled);
460 m_editDefaultId->setEnabled(
enabled);
461 m_editDownloadType->setEnabled(
enabled);
462 m_ghnsSource->setVisible(m_profile && m_profile->hasGHNSSupport());
463 m_ghnsSource->setEnabled(m_showUpload && m_profile && m_profile->hasGHNSSupport() &&
enabled);
464 m_uploadButton->setEnabled(m_showUpload && m_profile && m_profile->hasGHNSSupport());
465 m_addReferenceButton->setEnabled(m_currentItem.isGHNS());
466 m_editDataFormat->setEnabled(
enabled);
484 m_disableUpdate =
false;
489void AlkOnlineQuotesWidget::Private::slotEntryChanged()
491 if (!m_disableUpdate)
495void AlkOnlineQuotesWidget::Private::updateButtonState()
499 (m_editURL->text() != m_currentItem.url()
500 || m_editIdentifier->text() != m_currentItem.idRegex()
501 || m_editIdSelector->currentIndex() != m_editIdSelector->findData(m_currentItem.idSelector())
502 || m_editDataFormat->currentIndex() != m_editDataFormat->findData(m_currentItem.
dataFormat())
503 || m_editDate->text() != m_currentItem.dateRegex()
504 || m_editDateFormat->text() != m_currentItem.dateFormat()
505 || m_editDefaultId->text() != m_currentItem.
defaultId()
506 || m_editPriceDecimalSeparator->currentIndex() != m_editPriceDecimalSeparator->findData(m_currentItem.priceDecimalSeparator())
507 || m_editDownloadType->currentIndex() != m_editDownloadType->findData(m_currentItem.downloadType())
508 || m_editPrice->text() != m_currentItem.priceRegex()
509 || m_ghnsSource->isChecked() != m_currentItem.isGHNS());
511 bool isFinanceQuote = m_currentItem.
isFinanceQuote() || m_profile->type() == AlkOnlineQuotesProfile::Type::Script;
512 bool hasWriteSupport = (m_profile->type() != AlkOnlineQuotesProfile::Type::None && !isFinanceQuote) || m_profile->hasGHNSSupport();
513 bool isRemoteUnpublished = m_currentItem.isGHNS() && m_currentItem.profile()->GHNSFilePath(m_currentItem.name()).
isEmpty();
514 bool isDefaultSource = m_profile->defaultQuoteSources().
contains(m_currentItem.name());
515 m_newButton->setEnabled(hasWriteSupport);
516 m_cancelButton->setEnabled(modified);
517 m_duplicateButton->setEnabled(hasWriteSupport);
518 m_deleteButton->setEnabled((!m_currentItem.isReadOnly() && !m_currentItem.isGHNS() && !isDefaultSource) || isRemoteUnpublished);
519 m_uploadButton->setEnabled(m_profile->hasGHNSSupport() && m_currentItem.isGHNS() && AlkOnlineQuoteUploadDialog::isSupported());
520 m_acceptButton->setEnabled(modified);
521 m_checkButton->setEnabled(isFinanceQuote || !modified);
522 m_editIdSelector->setVisible(m_profile->type() == AlkOnlineQuotesProfile::Type::KMyMoney5);
523 m_editIdSelectorLabel->setVisible(m_profile->type() == AlkOnlineQuotesProfile::Type::KMyMoney5);
526 AlkOnlineQuoteSource source(m_currentItem);
530 bool hasDateRange = source.
dataFormat() == AlkOnlineQuoteSource::CSV || source.
dataFormat() == AlkOnlineQuoteSource::JSON;
531 m_startDateLabel->setVisible(hasDateRange);
532 m_endDateLabel->setVisible(hasDateRange);
533 m_startDateEdit->setVisible(hasDateRange);
534 m_endDateEdit->setVisible(hasDateRange);
537 m_checkSymbol->setEnabled(
false);
538 m_checkSymbol->setText(QString());
539 m_checkSymbol2->setEnabled(
true);
540 setDefaultSource(m_checkSymbol2, source.
defaultId(),
"BTC GBP");
542 m_checkSymbol->setEnabled(
true);
543 setDefaultSource(m_checkSymbol, source.
defaultId(),
"ORCL");
544 m_checkSymbol2->setEnabled(
false);
545 m_checkSymbol2->setText(QString());
549void AlkOnlineQuotesWidget::Private::setDefaultSource(QLineEdit* editWidget,
const QString& sourceDefaultValue,
const QString& defaultValue)
551 QString currentValue = editWidget->
text();
553 editWidget->
setText(!sourceDefaultValue.
isEmpty() ? sourceDefaultValue : defaultValue);
556void AlkOnlineQuotesWidget::Private::slotDeleteEntry()
558 if (!m_quoteSourceList->currentIndex().isValid())
562 i18n(
"Are you sure to delete this online quote ?"),
563 i18n(
"Delete online quote"),
566 QString(
"DeletingOnlineQuote"));
572 m_quoteSourceList->model()->removeRow(m_quoteSourceList->currentIndex().row());
576void AlkOnlineQuotesWidget::Private::slotDuplicateEntry()
578 if (!m_quoteSourceList->currentIndex().isValid())
581 AlkOnlineQuoteSource
copy(m_currentItem);
585 m_currentItem =
copy;
589void AlkOnlineQuotesWidget::Private::slotAcceptEntry()
591 m_currentItem.setUrl(m_editURL->text());
592 m_currentItem.setIdRegex(m_editIdentifier->text());
593 m_currentItem.setIdSelector(m_editIdSelector->currentData().value<AlkOnlineQuoteSource::IdSelector>());
596 m_currentItem.setDateFormat(m_editDateFormat->text());
599 m_currentItem.setDownloadType(m_editDownloadType->currentData().value<AlkOnlineQuoteSource::DownloadType>());
600 m_currentItem.setPriceRegex(m_editPrice->text());
601 m_currentItem.setGHNS(m_ghnsSource->isChecked());
602 m_currentItem.write();
603 m_checkButton->setEnabled(
true);
608void AlkOnlineQuotesWidget::Private::slotCopySettingsToClipboard()
612 QStringList settings;
613 settings <<
i18nc(
"@title %1 is version info",
"Online quote settings generated with Alkimia %1").
arg(BUILD_KEY);
614 settings << QString();
616 settings <<
i18nc(
"@info online quote setting",
"URL: %1").
arg(m_editURL->text());
617 settings <<
i18nc(
"@info online quote setting",
"Download mode: %1").
arg(m_editDownloadType->currentText());
618 settings <<
i18nc(
"@info online quote setting",
"Data format: %1").
arg(m_editDataFormat->currentText());
619 settings <<
i18nc(
"@info online quote setting",
"Identifier: %1").
arg(m_editIdentifier->text());
620 settings <<
i18nc(
"@info online quote setting",
"Select by: %1").
arg(m_editIdSelector->currentText());
621 settings <<
i18nc(
"@info online quote setting",
"Price: %1").
arg(m_editPrice->text());
622 settings <<
i18nc(
"@info online quote setting",
"Price decimal separator: %1").
arg(m_editPriceDecimalSeparator->currentText());
623 settings <<
i18nc(
"@info online quote setting",
"Date: %1").
arg(m_editDate->text());
624 settings <<
i18nc(
"@info online quote setting",
"Date format: %1").
arg(m_editDateFormat->text());
625 settings <<
i18nc(
"@info online quote setting",
"Default identifier: %1").
arg(m_editDefaultId->text());
626 settings <<
i18nc(
"@info online quote setting",
"Remote source: %1")
627 .
arg(m_ghnsSource->isChecked() ?
i18nc(
"@item:intext checkbox setting",
"checked") :
i18nc(
"@item:intext checkbox setting",
"not checked"));
630 settings << QString();
632 clipboard->
setText(settings.
join(QLatin1String(
"\n")));
635void AlkOnlineQuotesWidget::Private::slotAddReferenceButton()
637 if (!m_quoteSourceList->currentIndex().isValid())
640 QString newNameBase = m_currentItem.name() +
i18nc(
"@item:valuesuffix to name for a quote source reference",
".reference");
642 QString newName = newNameBase;
643 while(m_profile->quoteSources().
contains(newName)) {
644 newName = QString(
"%1%2").
arg(newNameBase).
arg(index++);
646 AlkOnlineQuoteSource
copy(newName, m_profile);
648 copy.setReferenceName(m_currentItem.name());
650 m_currentItem =
copy;
654void AlkOnlineQuotesWidget::Private::slotNewEntry()
656 const bool newEntries = m_profile->quoteSources().
contains(
i18n(
"New Quote Source"));
658 AlkOnlineQuoteSource newSource(
i18n(
"New Quote Source"), m_profile);
660 m_currentItem = newSource;
664#if QT_VERSION >= QT_VERSION_CHECK(5, 0, 0)
668 i18nc(
"@info Detail that only one new entry can exist at any time",
"<b>New Quote Source</b> already exists."));
676void AlkOnlineQuotesWidget::Private::clearIcons()
678 m_urlCheckLabel->setPixmap(m_emptyIcon);
679 m_dateCheckLabel->setPixmap(m_emptyIcon);
680 m_priceCheckLabel->setPixmap(m_emptyIcon);
681 m_symbolCheckLabel->setPixmap(m_emptyIcon);
682 m_dateFormatCheckLabel->setPixmap(m_emptyIcon);
685void AlkOnlineQuotesWidget::Private::initIcons()
687 m_urlCheckLabel->setPixmap(m_inWorkIcon);
688 m_dateCheckLabel->setPixmap(m_inWorkIcon);
689 m_priceCheckLabel->setPixmap(m_inWorkIcon);
690 m_symbolCheckLabel->setPixmap(m_inWorkIcon);
691 m_dateFormatCheckLabel->setPixmap(m_inWorkIcon);
694void AlkOnlineQuotesWidget::Private::setupIcons(
const AlkOnlineQuote::Errors &errors)
697 if (errors & AlkOnlineQuote::Errors::URL) {
698 m_urlCheckLabel->setPixmap(m_failIcon);
700 m_urlCheckLabel->setPixmap(m_okIcon);
701 m_symbolCheckLabel->setPixmap((errors & AlkOnlineQuote::Errors::Symbol) ? m_failIcon : m_okIcon);
702 m_priceCheckLabel->setPixmap((errors & AlkOnlineQuote::Errors::Price) ? m_failIcon : m_okIcon);
703 if (errors & AlkOnlineQuote::Errors::Date) {
704 m_dateCheckLabel->setPixmap(m_failIcon);
706 if (m_currentItem.dateRegex().
isEmpty()) {
707 m_dateCheckLabel->setPixmap(m_emptyIcon);
708 m_dateFormatCheckLabel->setPixmap(m_emptyIcon);
710 m_dateCheckLabel->setPixmap(m_okIcon);
711 m_dateFormatCheckLabel->setPixmap(
712 (errors & AlkOnlineQuote::Errors::DateFormat) ? m_failIcon : m_okIcon);
718void AlkOnlineQuotesWidget::Private::slotCheckEntry()
720 AlkOnlineQuote quote(m_profile);
721 m_logWindow->setVisible(
true);
722 m_logWindow->clear();
724 quote.setAcceptLanguage(m_acceptLanguage);
726 connect("e, SIGNAL(
status(QString)),
this, SLOT(slotLogStatus(QString)));
727 connect("e, SIGNAL(
error(QString)),
this, SLOT(slotLogError(QString)));
728 connect("e, SIGNAL(failed(QString,QString)),
this, SLOT(slotLogFailed(QString,QString)));
729 connect("e, SIGNAL(quote(QString,QString,QDate,
double)),
this,
730 SLOT(slotLogQuote(QString,QString,QDate,
double)));
731 connect("e, SIGNAL(quotes(QString,QString,AlkDatePriceMap)),
this,
732 SLOT(slotLogQuotes(QString,QString,AlkDatePriceMap)));
735 AlkOnlineQuoteSource source(m_currentItem);
738 if (source.
dataFormat() == AlkOnlineQuoteSource::CSV || source.
dataFormat() == AlkOnlineQuoteSource::JSON) {
739 quote.setDateRange(m_startDateEdit->date(), m_endDateEdit->date());
741 quote.setDateRange(QDate(), QDate());
745 quote.launch(m_checkSymbol2->text(), m_checkSymbol2->text(), source.name());
747 quote.launch(m_checkSymbol->text(), m_checkSymbol->text(), source.name());
749 setupIcons(quote.errors());
752void AlkOnlineQuotesWidget::Private::slotLogStatus(
const QString &s)
754 m_logWindow->append(s);
757void AlkOnlineQuotesWidget::Private::slotLogError(
const QString &s)
759 slotLogStatus(QString(
"<font color=\"red\"><b>") + s + QString(
"</b></font>"));
762void AlkOnlineQuotesWidget::Private::slotLogFailed(
const QString &
id,
const QString &symbol)
764 slotLogStatus(QString(
"%1 %2").arg(
id, symbol));
767void AlkOnlineQuotesWidget::Private::slotLogQuote(
const QString &
id,
const QString &symbol,
768 const QDate &date,
double price)
770 slotLogStatus(QString(
"<font color=\"green\">%1 %2 %3 %4</font>").arg(
id, symbol,
775void AlkOnlineQuotesWidget::Private::slotLogQuotes(
const QString &
id,
const QString &symbol,
776 const AlkDatePriceMap &prices)
778 slotLogStatus(QString(
"<font color=\"green\">%1 %2</font>").arg(
id, symbol));
780 slotLogStatus(QString(
"<font color=\"green\">date price</font>"));
782 slotLogStatus(QString(
"<font color=\"green\">%1 %2</font>")
783 .arg(i.key().toString(
Qt::ISODate)).arg(i.value().toDouble()));
787void AlkOnlineQuotesWidget::Private::slotInstallEntries()
789 QString configFile = m_profile->hotNewStuffConfigFile();
791 AlkNewStuffWidget widget;
792 widget.init(configFile);
793 if (widget.showInstallDialog()) {
799void AlkOnlineQuotesWidget::Private::slotResetQuotesList()
804void AlkOnlineQuotesWidget::Private::slotUploadEntry()
806 QPointer<AlkOnlineQuoteUploadDialog> dialog =
new AlkOnlineQuoteUploadDialog(m_currentItem,
false,
this);
811void AlkOnlineQuotesWidget::Private::slotShowButton()
813 if (!m_webPageDialog) {
814 m_webPageDialog =
new QDialog;
816 QVBoxLayout *
layout =
new QVBoxLayout;
817 layout->addWidget(m_webView);
820 m_webPageDialog->
show();
823QString AlkOnlineQuotesWidget::Private::expandedUrl()
const
825 AlkOnlineQuoteSource source(m_currentItem);
829 return source.url().
arg(m_checkSymbol2->text());
831 return source.url().
arg(m_checkSymbol->text());
835AlkOnlineQuotesWidget::AlkOnlineQuotesWidget(
bool showProfiles,
bool showUpload,
QWidget *
parent)
837 , d(new Private(showProfiles, showUpload, this))
841AlkOnlineQuotesWidget::~AlkOnlineQuotesWidget()
846QWidget *AlkOnlineQuotesWidget::profilesWidget()
848 QFrame *frame =
new QFrame;
849 frame->
setLayout(d->profilesGroupBox->layout());
853QWidget *AlkOnlineQuotesWidget::profileDetailsWidget()
855 QFrame *frame =
new QFrame;
856 frame->
setLayout(d->profileDetailsBox->layout());
860QWidget *AlkOnlineQuotesWidget::onlineQuotesWidget()
862 QFrame *frame =
new QFrame;
863 frame->
setLayout(d->onlineQuotesGroupBox->layout());
867QWidget *AlkOnlineQuotesWidget::quoteDetailsWidget()
869 QFrame *frame =
new QFrame;
870 frame->
setLayout(d->detailsGroupBox->layout());
874QWidget *AlkOnlineQuotesWidget::debugWidget()
876 QFrame *frame =
new QFrame;
877 frame->
setLayout(d->debugGroupBox->layout());
881void AlkOnlineQuotesWidget::readConfig()
885void AlkOnlineQuotesWidget::writeConfig()
889void AlkOnlineQuotesWidget::resetConfig()
892 QStringList groups = d->m_profile->quoteSources();
896 AlkOnlineQuoteSource quoteSource(*it, d->m_profile);
903 if (!quoteSource.isGHNS()) {
904 quoteSource.remove();
909 QList<AlkOnlineQuoteSource>::iterator itr;
910 for (itr = d->m_resetList.begin(); itr != d->m_resetList.end(); ++itr) {
917QString AlkOnlineQuotesWidget::acceptLanguage()
const
919 return d->m_acceptLanguage;
922void AlkOnlineQuotesWidget::setAcceptLanguage(
const QString &text)
924 d->m_acceptLanguage = text;
927bool AlkOnlineQuotesWidget::GHNSSourceEditable()
929 return d->m_ghnsEditable;
933void AlkOnlineQuotesWidget::setGHNSSourceEditable(
bool state)
935 d->m_ghnsEditable = state;
938#include "alkonlinequoteswidget.moc"
Wrapper for debug output.
const QString & defaultId() const
Return the default identifier known to work.
void setDefaultId(const QString &defaultId)
Set the default identifier, which is known to work.
bool requiresTwoIdentifier() const
Return state if this source requires two identifier.
DataFormat
Supported formats of downloaded data.
bool isReference() const
Return state if this source is a reference.
DecimalSeparator
Type of decimal separator.
AlkOnlineQuoteSource asReference() const
Return referenced quote source.
DataFormat dataFormat() const
Return the format of the downloaded data.
bool isFinanceQuote() const
Checks whether the current source is of type "Finance::Quote".
void setDataFormat(DataFormat dataFormat)
Set the format of the downloaded data.
void setDateRegex(const QString &dateRegex)
Set regular expression for parsing dates.
LastPriceState
Supported values for returning prices in special cases.
The AlkWebPage class provides an object to load and view web documents to provide functionality like ...
The AlkWebView class provides a widget that is used to load and display web documents.
Q_SCRIPTABLE CaptureState status()
QString i18nc(const char *context, const char *text, const TYPE &arg...)
QString i18n(const char *text, const TYPE &arg...)
ButtonCode warningContinueCancel(QWidget *parent, const QString &text, const QString &title=QString(), const KGuiItem &buttonContinue=KStandardGuiItem::cont(), const KGuiItem &buttonCancel=KStandardGuiItem::cancel(), const QString &dontAskAgainName=QString(), Options options=Notify)
void error(QWidget *parent, const QString &text, const QString &title, const KGuiItem &buttonOk, Options options=Notify)
KIOCORE_EXPORT QStringList list(const QString &fileClass)
QString name(StandardAction id)
QAction * copy(const QObject *recvr, const char *slot, QObject *parent)
virtual QModelIndex index(int row, int column, const QModelIndex &parent) const const override
void setText(const QString &text, Mode mode)
QString toString(QStringView format, QCalendar cal) const const
void append(QList< T > &&value)
const_iterator constBegin() const const
const_iterator constEnd() const const
bool isEmpty() const const
void setText(const QString &text)
const_iterator constBegin() const const
const_iterator constEnd() const const
bool contains(const Key &key) const const
QMetaObject::Connection connect(const QObject *sender, PointerToMemberFunction signal, Functor functor)
QObject * parent() const const
QString arg(Args &&... args) const const
bool isEmpty() const const
bool contains(QLatin1StringView str, Qt::CaseSensitivity cs) const const
QString join(QChar separator) const const
QFuture< ArgsType< Signal > > connect(Sender *sender, Signal signal)
void setText(int column, const QString &text)