1 /***************************************************************************
2     qgsdatetimesearchwidgetwrapper.cpp
3      ---------------------------------
4     Date                 : 2016-05-23
5     Copyright            : (C) 2016 Nyall Dawson
6     Email                : nyall dot dawson at gmail dot com
7  ***************************************************************************
8  *                                                                         *
9  *   This program is free software; you can redistribute it and/or modify  *
10  *   it under the terms of the GNU General Public License as published by  *
11  *   the Free Software Foundation; either version 2 of the License, or     *
12  *   (at your option) any later version.                                   *
13  *                                                                         *
14  ***************************************************************************/
15 
16 #include "qgsdatetimesearchwidgetwrapper.h"
17 
18 #include "qgsfields.h"
19 #include "qgsdatetimeeditfactory.h"
20 #include "qgsvectorlayer.h"
21 #include "qgsdatetimeedit.h"
22 #include "qcalendarwidget.h"
23 #include "qgsdatetimeeditconfig.h"
24 #include "qgsdatetimefieldformatter.h"
25 
26 #include <QSettings>
27 
QgsDateTimeSearchWidgetWrapper(QgsVectorLayer * vl,int fieldIdx,QWidget * parent)28 QgsDateTimeSearchWidgetWrapper::QgsDateTimeSearchWidgetWrapper( QgsVectorLayer *vl, int fieldIdx, QWidget *parent )
29   : QgsSearchWidgetWrapper( vl, fieldIdx, parent )
30 
31 {
32 }
33 
applyDirectly()34 bool QgsDateTimeSearchWidgetWrapper::applyDirectly()
35 {
36   return true;
37 }
38 
expression() const39 QString QgsDateTimeSearchWidgetWrapper::expression() const
40 {
41   return mExpression;
42 }
43 
value() const44 QVariant QgsDateTimeSearchWidgetWrapper::value() const
45 {
46   if ( ! mDateTimeEdit )
47     return QDateTime();
48 
49   const bool fieldIsoFormat = config( QStringLiteral( "field_iso_format" ), false ).toBool();
50   const QString fieldFormat = config( QStringLiteral( "field_format" ), QgsDateTimeFieldFormatter::defaultFormat( layer()->fields().at( mFieldIdx ).type() ) ).toString();
51   if ( fieldIsoFormat )
52   {
53     return mDateTimeEdit->dateTime().toString( Qt::ISODate );
54   }
55   else
56   {
57     return mDateTimeEdit->dateTime().toString( fieldFormat );
58   }
59 }
60 
supportedFlags() const61 QgsSearchWidgetWrapper::FilterFlags QgsDateTimeSearchWidgetWrapper::supportedFlags() const
62 {
63   return EqualTo | NotEqualTo | GreaterThan | LessThan | GreaterThanOrEqualTo | LessThanOrEqualTo | IsNull | Between | IsNotNull | IsNotBetween;
64 }
65 
defaultFlags() const66 QgsSearchWidgetWrapper::FilterFlags QgsDateTimeSearchWidgetWrapper::defaultFlags() const
67 {
68   return EqualTo;
69 }
70 
createExpression(QgsSearchWidgetWrapper::FilterFlags flags) const71 QString QgsDateTimeSearchWidgetWrapper::createExpression( QgsSearchWidgetWrapper::FilterFlags flags ) const
72 {
73   QString fieldName = createFieldIdentifier();
74 
75   //clear any unsupported flags
76   flags &= supportedFlags();
77   if ( flags & IsNull )
78     return fieldName + " IS NULL";
79   if ( flags & IsNotNull )
80     return fieldName + " IS NOT NULL";
81 
82   QVariant v = value();
83   if ( !v.isValid() )
84     return QString();
85 
86   if ( flags & EqualTo )
87     return fieldName + "='" + v.toString() + '\'';
88   else if ( flags & NotEqualTo )
89     return fieldName + "<>'" + v.toString() + '\'';
90   else if ( flags & GreaterThan )
91     return fieldName + ">'" + v.toString() + '\'';
92   else if ( flags & LessThan )
93     return fieldName + "<'" + v.toString() + '\'';
94   else if ( flags & GreaterThanOrEqualTo )
95     return fieldName + ">='" + v.toString() + '\'';
96   else if ( flags & LessThanOrEqualTo )
97     return fieldName + "<='" + v.toString() + '\'';
98 
99   return QString();
100 }
101 
clearWidget()102 void QgsDateTimeSearchWidgetWrapper::clearWidget()
103 {
104   if ( mDateTimeEdit )
105   {
106     mDateTimeEdit->setEmpty();
107   }
108 }
109 
setEnabled(bool enabled)110 void QgsDateTimeSearchWidgetWrapper::setEnabled( bool enabled )
111 {
112   if ( mDateTimeEdit )
113   {
114     mDateTimeEdit->setEnabled( enabled );
115   }
116 }
117 
valid() const118 bool QgsDateTimeSearchWidgetWrapper::valid() const
119 {
120   return true;
121 }
122 
setExpression(const QString & expression)123 void QgsDateTimeSearchWidgetWrapper::setExpression( const QString &expression )
124 {
125   QString exp = expression;
126   QString fieldName = layer()->fields().at( mFieldIdx ).name();
127 
128   QString str = QStringLiteral( "%1 = '%3'" )
129                 .arg( QgsExpression::quotedColumnRef( fieldName ),
130                       exp.replace( '\'', QLatin1String( "''" ) )
131                     );
132   mExpression = str;
133 }
134 
dateTimeChanged(const QDateTime & dt)135 void QgsDateTimeSearchWidgetWrapper::dateTimeChanged( const QDateTime &dt )
136 {
137   if ( mDateTimeEdit )
138   {
139     QString exp = value().toString();
140     setExpression( exp );
141     if ( dt.isValid() && !dt.isNull() )
142       emit valueChanged();
143     else
144       emit valueCleared();
145     emit expressionChanged( mExpression );
146   }
147 }
148 
createWidget(QWidget * parent)149 QWidget *QgsDateTimeSearchWidgetWrapper::createWidget( QWidget *parent )
150 {
151   QgsDateTimeEdit *widget = new QgsDateTimeEdit( parent );
152   widget->setEmpty();
153   return widget;
154 }
155 
initWidget(QWidget * editor)156 void QgsDateTimeSearchWidgetWrapper::initWidget( QWidget *editor )
157 {
158   mDateTimeEdit = qobject_cast<QgsDateTimeEdit *>( editor );
159 
160   if ( mDateTimeEdit )
161   {
162     mDateTimeEdit->setAllowNull( false );
163 
164     const QString displayFormat = config( QStringLiteral( "display_format" ), QgsDateTimeFieldFormatter::defaultFormat( layer()->fields().at( mFieldIdx ).type() ) ).toString();
165     mDateTimeEdit->setDisplayFormat( displayFormat );
166 
167     const bool calendar = config( QStringLiteral( "calendar_popup" ), false ).toBool();
168     mDateTimeEdit->setCalendarPopup( calendar );
169     if ( calendar && mDateTimeEdit->calendarWidget() )
170     {
171       // highlight today's date
172       QTextCharFormat todayFormat;
173       todayFormat.setBackground( QColor( 160, 180, 200 ) );
174       mDateTimeEdit->calendarWidget()->setDateTextFormat( QDate::currentDate(), todayFormat );
175     }
176 
177     mDateTimeEdit->setEmpty();
178 
179     connect( mDateTimeEdit, &QDateTimeEdit::dateTimeChanged, this, &QgsDateTimeSearchWidgetWrapper::dateTimeChanged );
180   }
181 }
182 
183 
184