Python activity, series and seriesPresent optional datetime parameter

It can be used to get data from other than current selected activiy,
identified by datetime, s.t. the items returned by activities(filter)
This commit is contained in:
Alejandro Martinez
2017-12-18 20:50:53 -03:00
parent fe1313bac1
commit 5d94ce2167
7 changed files with 102 additions and 60 deletions

View File

@@ -93,7 +93,7 @@ Bindings::activities(QString filter) const
// add datetime to the list
QDate d = item->dateTime.date();
QTime t = item->dateTime.time();
PyList_SET_ITEM(dates, idx++, PyDateTime_FromDateAndTime(d.year(), d.month(), d.day(), t.hour(), t.minute(), t.second(), t.msec()));
PyList_SET_ITEM(dates, idx++, PyDateTime_FromDateAndTime(d.year(), d.month(), d.day(), t.hour(), t.minute(), t.second(), t.msec()*10));
}
return dates;
@@ -102,14 +102,41 @@ Bindings::activities(QString filter) const
return NULL;
}
// get the data series for the currently selected ride
PythonDataSeries*
Bindings::series(int type) const
RideItem*
Bindings::fromDateTime(PyObject* activity) const
{
Context *context = python->contexts.value(threadid());
if (context == NULL || context->currentRideItem()==NULL) return NULL;
RideFile* f = const_cast<RideItem*>(context->currentRideItem())->ride();
// import datetime if necessary
if (PyDateTimeAPI == NULL) PyDateTime_IMPORT;
if (context !=NULL && activity != NULL && PyDate_Check(activity)) {
// convert PyDateTime to QDateTime
QDateTime dateTime(QDate(PyDateTime_GET_YEAR(activity), PyDateTime_GET_MONTH(activity), PyDateTime_GET_DAY(activity)),
QTime(PyDateTime_DATE_GET_HOUR(activity), PyDateTime_DATE_GET_MINUTE(activity), PyDateTime_DATE_GET_SECOND(activity), PyDateTime_DATE_GET_MICROSECOND(activity)/10));
// search the RideCache
foreach(RideItem*item, context->athlete->rideCache->rides())
if (item->dateTime.toUTC() == dateTime.toUTC())
return const_cast<RideItem*>(item);
}
return NULL;
}
// get the data series for the currently selected ride
PythonDataSeries*
Bindings::series(int type, PyObject* activity) const
{
Context *context = python->contexts.value(threadid());
if (context == NULL) return NULL;
RideItem* item = fromDateTime(activity);
if (item == NULL) item = const_cast<RideItem*>(context->currentRideItem());
if (item == NULL) return NULL;
RideFile* f = item->ride();
PythonDataSeries* ds = new PythonDataSeries(seriesName(type), f->dataPoints().count());
for(int i=0; i<ds->count; i++) ds->data[i] = f->dataPoints()[i]->value(static_cast<RideFile::SeriesType>(type));
@@ -129,12 +156,17 @@ Bindings::seriesName(int type) const
}
bool
Bindings::seriesPresent(int type) const
Bindings::seriesPresent(int type, PyObject* activity) const
{
Context *context = python->contexts.value(threadid());
if (context == NULL || context->currentRideItem()==NULL) return false;
return const_cast<RideItem*>(context->currentRideItem())->ride()->isDataPresent(static_cast<RideFile::SeriesType>(type));
if (context == NULL) return false;
RideItem* item = fromDateTime(activity);
if (item == NULL) item = const_cast<RideItem*>(context->currentRideItem());
if (item == NULL) return NULL;
return item->ride()->isDataPresent(static_cast<RideFile::SeriesType>(type));
}
PythonDataSeries::PythonDataSeries(QString name, Py_ssize_t count) : name(name), count(count), data(NULL)
@@ -223,7 +255,7 @@ Bindings::activityMetrics(RideItem* item) const
QDate d = item->dateTime.date();
PyDict_SetItemString(dict, "date", PyDate_FromDate(d.year(), d.month(), d.day()));
QTime t = item->dateTime.time();
PyDict_SetItemString(dict, "time", PyTime_FromTime(t.hour(), t.minute(), t.second(), t.msec()));
PyDict_SetItemString(dict, "time", PyTime_FromTime(t.hour(), t.minute(), t.second(), t.msec()*10));
//
// METRICS
@@ -389,7 +421,7 @@ Bindings::seasonMetrics(bool all, DateRange range, QString filter) const
PyList_SET_ITEM(datelist, idx, PyDate_FromDate(d.year(), d.month(), d.day()));
QTime t = ride->dateTime.time();
PyList_SET_ITEM(timelist, idx, PyTime_FromTime(t.hour(), t.minute(), t.second(), t.msec()));
PyList_SET_ITEM(timelist, idx, PyTime_FromTime(t.hour(), t.minute(), t.second(), t.msec()*10));
// apply item color, remembering that 1,1,1 means use default (reverse in this case)
QString color;

View File

@@ -31,10 +31,10 @@ class Bindings {
PyObject* activities(QString filter=QString()) const;
// working with data series
bool seriesPresent(int type) const;
bool seriesPresent(int type, PyObject* activity=NULL) const;
int seriesLast() const;
QString seriesName(int type) const;
PythonDataSeries *series(int type) const;
PythonDataSeries *series(int type, PyObject* activity=NULL) const;
// working with metrics
PyObject* activityMetrics(bool compare=false) const;
@@ -51,6 +51,9 @@ class Bindings {
int webpage(QString url) const;
private:
// find a RideItem by DateTime
RideItem* fromDateTime(PyObject* activity=NULL) const;
// get a dict populated with metrics and metadata
PyObject* activityMetrics(RideItem* item) const;
PyObject* seasonMetrics(bool all, DateRange range, QString filter) const;

View File

@@ -120,10 +120,10 @@ public:
PyObject* activities(QString filter=QString()) /TransferBack/;
// working with series
bool seriesPresent(int type=10) const;
bool seriesPresent(int type=10, PyObject* activity=NULL) const;
QString seriesName(int type=10) const;
int seriesLast() const;
PythonDataSeries series(int type=10) /TransferBack/;
PythonDataSeries series(int type=10, PyObject* activity=NULL) /TransferBack/;
// working with metrics
PyObject* activityMetrics(bool compare=false) /TransferBack/;

View File

@@ -37,44 +37,46 @@
#define sipName_activities &sipStrings_goldencheetah[139]
#define sipNameNr_measures 150
#define sipName_measures &sipStrings_goldencheetah[150]
#define sipNameNr_threadid 159
#define sipName_threadid &sipStrings_goldencheetah[159]
#define sipNameNr_Bindings 168
#define sipName_Bindings &sipStrings_goldencheetah[168]
#define sipNameNr_webpage 177
#define sipName_webpage &sipStrings_goldencheetah[177]
#define sipNameNr_metrics 185
#define sipName_metrics &sipStrings_goldencheetah[185]
#define sipNameNr_compare 193
#define sipName_compare &sipStrings_goldencheetah[193]
#define sipNameNr_version 201
#define sipName_version &sipStrings_goldencheetah[201]
#define sipNameNr_athlete 209
#define sipName_athlete &sipStrings_goldencheetah[209]
#define sipNameNr___len__ 217
#define sipName___len__ &sipStrings_goldencheetah[217]
#define sipNameNr___str__ 225
#define sipName___str__ &sipStrings_goldencheetah[225]
#define sipNameNr_QString 233
#define sipName_QString &sipStrings_goldencheetah[233]
#define sipNameNr_metric 241
#define sipName_metric &sipStrings_goldencheetah[241]
#define sipNameNr_series 248
#define sipName_series &sipStrings_goldencheetah[248]
#define sipNameNr_filter 255
#define sipName_filter &sipStrings_goldencheetah[255]
#define sipNameNr_group 262
#define sipName_group &sipStrings_goldencheetah[262]
#define sipNameNr_build 268
#define sipName_build &sipStrings_goldencheetah[268]
#define sipNameNr_type 274
#define sipName_type &sipStrings_goldencheetah[274]
#define sipNameNr_url 279
#define sipName_url &sipStrings_goldencheetah[279]
#define sipNameNr_pmc 283
#define sipName_pmc &sipStrings_goldencheetah[283]
#define sipNameNr_all 287
#define sipName_all &sipStrings_goldencheetah[287]
#define sipNameNr_activity 159
#define sipName_activity &sipStrings_goldencheetah[159]
#define sipNameNr_threadid 168
#define sipName_threadid &sipStrings_goldencheetah[168]
#define sipNameNr_Bindings 177
#define sipName_Bindings &sipStrings_goldencheetah[177]
#define sipNameNr_webpage 186
#define sipName_webpage &sipStrings_goldencheetah[186]
#define sipNameNr_metrics 194
#define sipName_metrics &sipStrings_goldencheetah[194]
#define sipNameNr_compare 202
#define sipName_compare &sipStrings_goldencheetah[202]
#define sipNameNr_version 210
#define sipName_version &sipStrings_goldencheetah[210]
#define sipNameNr_athlete 218
#define sipName_athlete &sipStrings_goldencheetah[218]
#define sipNameNr___len__ 226
#define sipName___len__ &sipStrings_goldencheetah[226]
#define sipNameNr___str__ 234
#define sipName___str__ &sipStrings_goldencheetah[234]
#define sipNameNr_QString 242
#define sipName_QString &sipStrings_goldencheetah[242]
#define sipNameNr_metric 250
#define sipName_metric &sipStrings_goldencheetah[250]
#define sipNameNr_series 257
#define sipName_series &sipStrings_goldencheetah[257]
#define sipNameNr_filter 264
#define sipName_filter &sipStrings_goldencheetah[264]
#define sipNameNr_group 271
#define sipName_group &sipStrings_goldencheetah[271]
#define sipNameNr_build 277
#define sipName_build &sipStrings_goldencheetah[277]
#define sipNameNr_type 283
#define sipName_type &sipStrings_goldencheetah[283]
#define sipNameNr_url 288
#define sipName_url &sipStrings_goldencheetah[288]
#define sipNameNr_pmc 292
#define sipName_pmc &sipStrings_goldencheetah[292]
#define sipNameNr_all 296
#define sipName_all &sipStrings_goldencheetah[296]
#define sipMalloc sipAPI_goldencheetah->api_malloc
#define sipFree sipAPI_goldencheetah->api_free

View File

@@ -158,17 +158,19 @@ static PyObject *meth_Bindings_seriesPresent(PyObject *sipSelf, PyObject *sipArg
{
int a0 = 10;
PyObject * a1 = 0;
const ::Bindings *sipCpp;
static const char *sipKwdList[] = {
sipName_type,
sipName_activity,
};
if (sipParseKwdArgs(&sipParseErr, sipArgs, sipKwds, sipKwdList, NULL, "B|i", &sipSelf, sipType_Bindings, &sipCpp, &a0))
if (sipParseKwdArgs(&sipParseErr, sipArgs, sipKwds, sipKwdList, NULL, "B|iP0", &sipSelf, sipType_Bindings, &sipCpp, &a0, &a1))
{
bool sipRes;
sipRes = sipCpp->seriesPresent(a0);
sipRes = sipCpp->seriesPresent(a0,a1);
return PyBool_FromLong(sipRes);
}
@@ -243,17 +245,19 @@ static PyObject *meth_Bindings_series(PyObject *sipSelf, PyObject *sipArgs, PyOb
{
int a0 = 10;
PyObject * a1 = 0;
::Bindings *sipCpp;
static const char *sipKwdList[] = {
sipName_type,
sipName_activity,
};
if (sipParseKwdArgs(&sipParseErr, sipArgs, sipKwds, sipKwdList, NULL, "B|i", &sipSelf, sipType_Bindings, &sipCpp, &a0))
if (sipParseKwdArgs(&sipParseErr, sipArgs, sipKwds, sipKwdList, NULL, "B|iP0", &sipSelf, sipType_Bindings, &sipCpp, &a0, &a1))
{
::PythonDataSeries*sipRes;
sipRes = new ::PythonDataSeries(sipCpp->series(a0));
sipRes = new ::PythonDataSeries(sipCpp->series(a0,a1));
return sipConvertFromNewType(sipRes,sipType_PythonDataSeries,Py_None);
}

View File

@@ -27,6 +27,7 @@ const char sipStrings_goldencheetah[] = {
's', 'e', 'r', 'i', 'e', 's', 'N', 'a', 'm', 'e', 0,
'a', 'c', 't', 'i', 'v', 'i', 't', 'i', 'e', 's', 0,
'm', 'e', 'a', 's', 'u', 'r', 'e', 's', 0,
'a', 'c', 't', 'i', 'v', 'i', 't', 'y', 0,
't', 'h', 'r', 'e', 'a', 'd', 'i', 'd', 0,
'B', 'i', 'n', 'd', 'i', 'n', 'g', 's', 0,
'w', 'e', 'b', 'p', 'a', 'g', 'e', 0,

View File

@@ -7,11 +7,11 @@
#--------------------------------------------------
# basic activity data
def __GCactivity():
def __GCactivity(activity=None):
rd={}
for x in range(0,GC.seriesLast()):
if (GC.seriesPresent(x)):
rd[GC.seriesName(x)] = GC.series(x)
if (GC.seriesPresent(x, activity)):
rd[GC.seriesName(x)] = GC.series(x, activity)
return rd
# add to main GC entrypoint