1 /***************************************************************************
2  *                                                                         *
3  *   copyright : (C) 2007 The University of Toronto                        *
4  *                   netterfield@astro.utoronto.ca                         *
5  *   copyright : (C) 2005  University of British Columbia                  *
6  *                   dscott@phas.ubc.ca                                    *
7  *                                                                         *
8  *   This program is free software; you can redistribute it and/or modify  *
9  *   it under the terms of the GNU General Public License as published by  *
10  *   the Free Software Foundation; either version 2 of the License, or     *
11  *   (at your option) any later version.                                   *
12  *                                                                         *
13  ***************************************************************************/
14 
15 /* FIXME: figure out what this plugin is supposed to do, and comment
16    accordingly. */
17 
18 #include "phase.h"
19 #include "objectstore.h"
20 #include "ui_phaseconfig.h"
21 
22 static const QString& VECTOR_IN_TIME = "Vector In Time";
23 static const QString& VECTOR_IN_DATA = "Vector In Data";
24 static const QString& SCALAR_IN_PERIOD = "Period";
25 static const QString& SCALAR_IN_ZEROPHASE = "Zero Phase";
26 
27 static const QString& VECTOR_OUT_PHASE = "Phase";
28 static const QString& VECTOR_OUT_DATA = "Data Out";
29 
30 class ConfigPhasePlugin : public Kst::DataObjectConfigWidget, public Ui_PhaseConfig {
31   public:
ConfigPhasePlugin(QSettings * cfg)32     ConfigPhasePlugin(QSettings* cfg) : DataObjectConfigWidget(cfg), Ui_PhaseConfig() {
33       _store = 0;
34       setupUi(this);
35     }
36 
~ConfigPhasePlugin()37     ~ConfigPhasePlugin() {}
38 
setObjectStore(Kst::ObjectStore * store)39     void setObjectStore(Kst::ObjectStore* store) {
40       _store = store;
41       _vectorTime->setObjectStore(store);
42       _vectorData->setObjectStore(store);
43       _scalarPeriod->setObjectStore(store);
44       _scalarZeroPhase->setObjectStore(store);
45       _scalarPeriod->setDefaultValue(0);
46       _scalarZeroPhase->setDefaultValue(0);
47     }
48 
setupSlots(QWidget * dialog)49     void setupSlots(QWidget* dialog) {
50       if (dialog) {
51         connect(_vectorTime, SIGNAL(selectionChanged(QString)), dialog, SIGNAL(modified()));
52         connect(_vectorData, SIGNAL(selectionChanged(QString)), dialog, SIGNAL(modified()));
53         connect(_scalarPeriod, SIGNAL(selectionChanged(QString)), dialog, SIGNAL(modified()));
54         connect(_scalarZeroPhase, SIGNAL(selectionChanged(QString)), dialog, SIGNAL(modified()));
55       }
56     }
57 
selectedVectorTime()58     Kst::VectorPtr selectedVectorTime() { return _vectorTime->selectedVector(); };
setSelectedVectorTime(Kst::VectorPtr vector)59     void setSelectedVectorTime(Kst::VectorPtr vector) { return _vectorTime->setSelectedVector(vector); };
60 
selectedVectorData()61     Kst::VectorPtr selectedVectorData() { return _vectorData->selectedVector(); };
setSelectedVectorData(Kst::VectorPtr vector)62     void setSelectedVectorData(Kst::VectorPtr vector) { return _vectorData->setSelectedVector(vector); };
63 
selectedScalarPeriod()64     Kst::ScalarPtr selectedScalarPeriod() { return _scalarPeriod->selectedScalar(); };
setSelectedScalarPeriod(Kst::ScalarPtr scalar)65     void setSelectedScalarPeriod(Kst::ScalarPtr scalar) { return _scalarPeriod->setSelectedScalar(scalar); };
66 
selectedScalarZeroPhase()67     Kst::ScalarPtr selectedScalarZeroPhase() { return _scalarZeroPhase->selectedScalar(); };
setSelectedScalarZeroPhase(Kst::ScalarPtr scalar)68     void setSelectedScalarZeroPhase(Kst::ScalarPtr scalar) { return _scalarZeroPhase->setSelectedScalar(scalar); };
69 
setupFromObject(Kst::Object * dataObject)70     virtual void setupFromObject(Kst::Object* dataObject) {
71       if (PhaseSource* source = static_cast<PhaseSource*>(dataObject)) {
72         setSelectedVectorTime(source->vectorTime());
73         setSelectedVectorData(source->vectorData());
74         setSelectedScalarPeriod(source->scalarPeriod());
75         setSelectedScalarZeroPhase(source->scalarZeroPhase());
76       }
77     }
78 
configurePropertiesFromXml(Kst::ObjectStore * store,QXmlStreamAttributes & attrs)79     virtual bool configurePropertiesFromXml(Kst::ObjectStore *store, QXmlStreamAttributes& attrs) {
80       Q_UNUSED(store);
81       Q_UNUSED(attrs);
82 
83       bool validTag = true;
84 
85 //       QStringRef av;
86 //       av = attrs.value("value");
87 //       if (!av.isNull()) {
88 //         _configValue = QVariant(av.toString()).toBool();
89 //       }
90 
91       return validTag;
92     }
93 
94   public slots:
save()95     virtual void save() {
96       if (_cfg) {
97         _cfg->beginGroup("Phase DataObject Plugin");
98         _cfg->setValue("Input Vector Time", _vectorTime->selectedVector()->Name());
99         _cfg->setValue("Input Vector Data", _vectorData->selectedVector()->Name());
100         _cfg->setValue("Input Scalar Period", _scalarPeriod->selectedScalar()->Name());
101         _cfg->setValue("Input Scalar Zero Phase", _scalarZeroPhase->selectedScalar()->Name());
102         _cfg->endGroup();
103       }
104     }
105 
load()106     virtual void load() {
107       if (_cfg && _store) {
108         _cfg->beginGroup("Phase DataObject Plugin");
109         QString vectorName = _cfg->value("Input Vector Time").toString();
110         Kst::Object* object = _store->retrieveObject(vectorName);
111         Kst::Vector* vectorTime = static_cast<Kst::Vector*>(object);
112         if (vectorTime) {
113           setSelectedVectorTime(vectorTime);
114         }
115         vectorName = _cfg->value("Input Vector Data").toString();
116         object = _store->retrieveObject(vectorName);
117         Kst::Vector* vectorData = static_cast<Kst::Vector*>(object);
118         if (vectorData) {
119           setSelectedVectorData(vectorData);
120         }
121         QString scalarName = _cfg->value("Input Scalar Period").toString();
122         object = _store->retrieveObject(scalarName);
123         Kst::Scalar* scalarPeriod = static_cast<Kst::Scalar*>(object);
124         if (scalarPeriod) {
125           setSelectedScalarPeriod(scalarPeriod);
126         }
127         scalarName = _cfg->value("Input Scalar Zero Phase").toString();
128         object = _store->retrieveObject(scalarName);
129         Kst::Scalar* scalarZeroPhase = static_cast<Kst::Scalar*>(object);
130         if (scalarZeroPhase) {
131           setSelectedScalarZeroPhase(scalarZeroPhase);
132         }
133         _cfg->endGroup();
134       }
135     }
136 
137   private:
138     Kst::ObjectStore *_store;
139 
140 };
141 
142 
PhaseSource(Kst::ObjectStore * store)143 PhaseSource::PhaseSource(Kst::ObjectStore *store)
144 : Kst::BasicPlugin(store) {
145 }
146 
147 
~PhaseSource()148 PhaseSource::~PhaseSource() {
149 }
150 
151 
_automaticDescriptiveName() const152 QString PhaseSource::_automaticDescriptiveName() const {
153   return tr("Phase Plugin Object");
154 }
155 
156 
change(Kst::DataObjectConfigWidget * configWidget)157 void PhaseSource::change(Kst::DataObjectConfigWidget *configWidget) {
158   if (ConfigPhasePlugin* config = static_cast<ConfigPhasePlugin*>(configWidget)) {
159     setInputVector(VECTOR_IN_TIME, config->selectedVectorTime());
160     setInputVector(VECTOR_IN_DATA, config->selectedVectorData());
161     setInputScalar(SCALAR_IN_PERIOD, config->selectedScalarPeriod());
162     setInputScalar(SCALAR_IN_ZEROPHASE, config->selectedScalarZeroPhase());
163   }
164 }
165 
166 
setupOutputs()167 void PhaseSource::setupOutputs() {
168   setOutputVector(VECTOR_OUT_PHASE, "");
169   setOutputVector(VECTOR_OUT_DATA, "");
170 }
171 
172 
algorithm()173 bool PhaseSource::algorithm() {
174   Kst::VectorPtr inputVectorTime = _inputVectors[VECTOR_IN_TIME];
175   Kst::VectorPtr inputVectorData = _inputVectors[VECTOR_IN_DATA];
176   Kst::ScalarPtr inputScalarPeriod = _inputScalars[SCALAR_IN_PERIOD];
177   Kst::ScalarPtr inputScalarZeroPhase = _inputScalars[SCALAR_IN_ZEROPHASE];
178 
179   Kst::VectorPtr outputVectorPhase = _outputVectors[VECTOR_OUT_PHASE];
180   Kst::VectorPtr outputVectorDataOut = _outputVectors[VECTOR_OUT_DATA];
181 
182   double* pResult[2];
183   double  dPhasePeriod = inputScalarPeriod->value();
184   double dPhaseZero = inputScalarZeroPhase->value();
185   int iLength;
186 
187   bool bReturn = false;
188 
189   if (dPhasePeriod <= 0.0) {
190     _errorString = tr("Error:  Input Scalar Phase must be greater than zero.");
191     return false;
192   }
193 
194   if (inputVectorTime->length() != inputVectorData->length()) {
195     _errorString = tr("Error:  Input Vector lengths do not match.");
196     return false;
197   }
198 
199   iLength = inputVectorTime->length();
200 
201   outputVectorPhase->resize(iLength, true);
202   pResult[0] = outputVectorPhase->raw_V_ptr();
203 
204   outputVectorDataOut->resize(iLength, true);
205   pResult[1] = outputVectorDataOut->raw_V_ptr();
206 
207   if (pResult[0] != NULL && pResult[1] != NULL) {
208     for (int i = 0; i < outputVectorPhase->length(); ++i) {
209       outputVectorPhase->raw_V_ptr()[i] = pResult[0][i];
210     }
211     for (int i = 0; i < outputVectorDataOut->length(); ++i) {
212       outputVectorDataOut->raw_V_ptr()[i] = pResult[1][i];
213     }
214 
215     /*
216     determine the outputVectorPhase...
217     */
218     for (int i=0; i<iLength; i++) {
219       outputVectorPhase->raw_V_ptr()[i] = fmod( ( inputVectorTime->raw_V_ptr()[i] - dPhaseZero ) / dPhasePeriod, 1.0 );
220     }
221 
222     /*
223     sort by outputVectorPhase...
224     */
225     memcpy( outputVectorDataOut->raw_V_ptr(), inputVectorData->value(), iLength * sizeof( double ) );
226     double* sort[2];
227     sort[0] = outputVectorPhase->raw_V_ptr();
228     sort[1] = outputVectorDataOut->raw_V_ptr();
229     quicksort( sort, 0, iLength-1 );
230 
231     bReturn = true;
232   }
233 
234   return bReturn;
235 }
236 
237 
swap(double * pData[],int iOne,int iTwo)238 void PhaseSource::swap(double* pData[], int iOne, int iTwo) {
239   double dTemp;
240 
241   for (int i=0; i<2; i++) {
242     dTemp = pData[i][iOne];
243     pData[i][iOne] = pData[i][iTwo];
244     pData[i][iTwo] = dTemp;
245   }
246 }
247 
248 
quicksort(double * pData[],int iLeft,int iRight)249 void PhaseSource::quicksort( double* pData[], int iLeft, int iRight) {
250   double dVal = pData[0][iRight];
251   int i = iLeft - 1;
252   int j = iRight;
253 
254   if (iRight <= iLeft) {
255     return;
256   }
257 
258   while (1) {
259     while (pData[0][++i] < dVal) {}
260 
261     while (dVal < pData[0][--j]) {
262       if (j == iLeft) {
263         break;
264       }
265     }
266     if (i >= j) {
267       break;
268     }
269     swap( pData, i, j );
270   }
271   swap( pData, i, iRight );
272   quicksort( pData, iLeft, i-1 );
273   quicksort( pData, i+1, iRight );
274 }
275 
276 
vectorTime() const277 Kst::VectorPtr PhaseSource::vectorTime() const {
278   return _inputVectors[VECTOR_IN_TIME];
279 }
280 
281 
vectorData() const282 Kst::VectorPtr PhaseSource::vectorData() const {
283   return _inputVectors[VECTOR_IN_DATA];
284 }
285 
286 
scalarPeriod() const287 Kst::ScalarPtr PhaseSource::scalarPeriod() const {
288   return _inputScalars[SCALAR_IN_PERIOD];
289 }
290 
291 
scalarZeroPhase() const292 Kst::ScalarPtr PhaseSource::scalarZeroPhase() const {
293   return _inputScalars[SCALAR_IN_ZEROPHASE];
294 }
295 
296 
inputVectorList() const297 QStringList PhaseSource::inputVectorList() const {
298   QStringList vectors(VECTOR_IN_TIME);
299   vectors += VECTOR_IN_DATA;
300   return vectors;
301 }
302 
303 
inputScalarList() const304 QStringList PhaseSource::inputScalarList() const {
305   QStringList scalars(SCALAR_IN_PERIOD);
306   scalars += SCALAR_IN_ZEROPHASE;
307   return scalars;
308 }
309 
310 
inputStringList() const311 QStringList PhaseSource::inputStringList() const {
312   return QStringList( /*STRING_IN*/ );
313 }
314 
315 
outputVectorList() const316 QStringList PhaseSource::outputVectorList() const {
317   QStringList vectors(VECTOR_OUT_PHASE);
318   vectors += VECTOR_OUT_DATA;
319   return vectors;
320 }
321 
322 
outputScalarList() const323 QStringList PhaseSource::outputScalarList() const {
324   return QStringList( /*SCALAR_OUT*/ );
325 }
326 
327 
outputStringList() const328 QStringList PhaseSource::outputStringList() const {
329   return QStringList( /*STRING_OUT*/ );
330 }
331 
332 
saveProperties(QXmlStreamWriter & s)333 void PhaseSource::saveProperties(QXmlStreamWriter &s) {
334   Q_UNUSED(s);
335 //   s.writeAttribute("value", _configValue);
336 }
337 
338 
pluginName() const339 QString PhasePlugin::pluginName() const { return tr("Phase"); }
pluginDescription() const340 QString PhasePlugin::pluginDescription() const { return tr("Phases a given data set to the specified period and zero outputVectorPhase."); }
341 
342 
create(Kst::ObjectStore * store,Kst::DataObjectConfigWidget * configWidget,bool setupInputsOutputs) const343 Kst::DataObject *PhasePlugin::create(Kst::ObjectStore *store, Kst::DataObjectConfigWidget *configWidget, bool setupInputsOutputs) const {
344 
345   if (ConfigPhasePlugin* config = static_cast<ConfigPhasePlugin*>(configWidget)) {
346 
347     PhaseSource* object = store->createObject<PhaseSource>();
348 
349     if (setupInputsOutputs) {
350       object->setInputScalar(SCALAR_IN_PERIOD, config->selectedScalarPeriod());
351       object->setInputScalar(SCALAR_IN_ZEROPHASE, config->selectedScalarZeroPhase());
352       object->setupOutputs();
353       object->setInputVector(VECTOR_IN_TIME, config->selectedVectorTime());
354       object->setInputVector(VECTOR_IN_DATA, config->selectedVectorData());
355     }
356 
357     object->setPluginName(pluginName());
358 
359     object->writeLock();
360     object->registerChange();
361     object->unlock();
362 
363     return object;
364   }
365   return 0;
366 }
367 
368 
configWidget(QSettings * settingsObject) const369 Kst::DataObjectConfigWidget *PhasePlugin::configWidget(QSettings *settingsObject) const {
370   ConfigPhasePlugin *widget = new ConfigPhasePlugin(settingsObject);
371   return widget;
372 }
373 
374 #ifndef QT5
375 Q_EXPORT_PLUGIN2(kstplugin_BinPlugin, PhasePlugin)
376 #endif
377 
378 // vim: ts=2 sw=2 et
379