mirror of
https://gitlab.com/pholy/OSCAR-code.git
synced 2025-04-08 20:20:44 +00:00
Split parsing from importing for F0 events.
This commit is contained in:
parent
abac19bbf1
commit
0d8e37c94c
@ -965,17 +965,21 @@ enum PRS1ParsedEventType
|
|||||||
EV_PRS1_PB,
|
EV_PRS1_PB,
|
||||||
EV_PRS1_LL,
|
EV_PRS1_LL,
|
||||||
EV_PRS1_HY,
|
EV_PRS1_HY,
|
||||||
EV_PRS1_IPAP,
|
|
||||||
EV_PRS1_TOTLEAK,
|
EV_PRS1_TOTLEAK,
|
||||||
EV_PRS1_LEAK, // F5V2: Is this real or actually TOTLEAK?
|
EV_PRS1_LEAK, // F5V2: Is this real or actually TOTLEAK?
|
||||||
|
EV_PRS1_PRESSURE, // TODO: maybe fold PRESSURE and IPAP into one
|
||||||
|
EV_PRS1_IPAP,
|
||||||
EV_PRS1_IPAPLOW,
|
EV_PRS1_IPAPLOW,
|
||||||
EV_PRS1_IPAPHIGH,
|
EV_PRS1_IPAPHIGH,
|
||||||
|
EV_PRS1_EPAP,
|
||||||
|
EV_PRS1_FLEX,
|
||||||
EV_PRS1_RR,
|
EV_PRS1_RR,
|
||||||
EV_PRS1_PTB,
|
EV_PRS1_PTB,
|
||||||
EV_PRS1_MV,
|
EV_PRS1_MV,
|
||||||
EV_PRS1_TV,
|
EV_PRS1_TV,
|
||||||
EV_PRS1_SNORE,
|
EV_PRS1_SNORE,
|
||||||
EV_PRS1_EPAP,
|
EV_PRS1_VS, // F0: Is this different from SNORE?
|
||||||
|
EV_PRS1_PP,
|
||||||
EV_PRS1_RERA,
|
EV_PRS1_RERA,
|
||||||
EV_PRS1_NRI,
|
EV_PRS1_NRI,
|
||||||
EV_PRS1_FLOWRATE,
|
EV_PRS1_FLOWRATE,
|
||||||
@ -1137,12 +1141,6 @@ public:
|
|||||||
PRS1HypopneaEvent(int start, int duration) : PRS1ParsedDurationEvent(EV_PRS1_HY, start, duration) {}
|
PRS1HypopneaEvent(int start, int duration) : PRS1ParsedDurationEvent(EV_PRS1_HY, start, duration) {}
|
||||||
};
|
};
|
||||||
|
|
||||||
class PRS1IPAPEvent : public PRS1PressureEvent
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
PRS1IPAPEvent(int start, int value) : PRS1PressureEvent(EV_PRS1_IPAP, start, value) {}
|
|
||||||
};
|
|
||||||
|
|
||||||
class PRS1TotalLeakEvent : public PRS1ParsedValueEvent
|
class PRS1TotalLeakEvent : public PRS1ParsedValueEvent
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
@ -1155,6 +1153,18 @@ public:
|
|||||||
PRS1LeakEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_LEAK, start, value) {}
|
PRS1LeakEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_LEAK, start, value) {}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class PRS1CPAPEvent : public PRS1PressureEvent
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
PRS1CPAPEvent(int start, int value) : PRS1PressureEvent(EV_PRS1_PRESSURE, start, value) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
class PRS1IPAPEvent : public PRS1PressureEvent
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
PRS1IPAPEvent(int start, int value) : PRS1PressureEvent(EV_PRS1_IPAP, start, value) {}
|
||||||
|
};
|
||||||
|
|
||||||
class PRS1IPAPHighEvent : public PRS1PressureEvent
|
class PRS1IPAPHighEvent : public PRS1PressureEvent
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
@ -1167,6 +1177,18 @@ public:
|
|||||||
PRS1IPAPLowEvent(int start, int value) : PRS1PressureEvent(EV_PRS1_IPAPLOW, start, value) {}
|
PRS1IPAPLowEvent(int start, int value) : PRS1PressureEvent(EV_PRS1_IPAPLOW, start, value) {}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class PRS1EPAPEvent : public PRS1PressureEvent
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
PRS1EPAPEvent(int start, int value) : PRS1PressureEvent(EV_PRS1_EPAP, start, value) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
class PRS1PressureReliefEvent : public PRS1PressureEvent // value is pressure applied during pressure relief, similar to EPAP
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
PRS1PressureReliefEvent(int start, int value) : PRS1PressureEvent(EV_PRS1_FLEX, start, value) {}
|
||||||
|
};
|
||||||
|
|
||||||
class PRS1RespiratoryRateEvent : public PRS1ParsedValueEvent
|
class PRS1RespiratoryRateEvent : public PRS1ParsedValueEvent
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
@ -1202,13 +1224,19 @@ public:
|
|||||||
PRS1SnoreEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_SNORE, start, value) {}
|
PRS1SnoreEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_SNORE, start, value) {}
|
||||||
};
|
};
|
||||||
|
|
||||||
class PRS1EPAPEvent : public PRS1PressureEvent
|
class PRS1VibratorySnoreEvent : public PRS1ParsedValueEvent
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
PRS1EPAPEvent(int start, int value) : PRS1PressureEvent(EV_PRS1_EPAP, start, value) {}
|
PRS1VibratorySnoreEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_VS, start, value) {}
|
||||||
};
|
};
|
||||||
|
|
||||||
class PRS1RERAEvent : public PRS1ParsedValueEvent
|
class PRS1PressurePulseEvent : public PRS1ParsedValueEvent
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
PRS1PressurePulseEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_PP, start, value) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
class PRS1RERAEvent : public PRS1ParsedValueEvent // TODO: should this really be a duration event?
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
PRS1RERAEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_RERA, start, value) {}
|
PRS1RERAEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_RERA, start, value) {}
|
||||||
@ -1226,7 +1254,7 @@ public:
|
|||||||
PRS1FlowRateEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_FLOWRATE, start, value) {}
|
PRS1FlowRateEvent(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_FLOWRATE, start, value) {}
|
||||||
};
|
};
|
||||||
|
|
||||||
class PRS1Test1Event : public PRS1ParsedValueEvent
|
class PRS1Test1Event : public PRS1ParsedValueEvent // TODO: replace test1/2 event with unknownvalue events and appropriate mapping
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
PRS1Test1Event(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_TEST1, start, value) {}
|
PRS1Test1Event(int start, int value) : PRS1ParsedValueEvent(EV_PRS1_TEST1, start, value) {}
|
||||||
@ -2415,17 +2443,20 @@ void SmoothEventList(Session * session, EventList * ev, ChannelID code)
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// 750P is F0V2; 550P is F0V2/F0V3; 450P is F0V3; 460P, 560P[BT], 660P, 760P are F0V4
|
||||||
|
// 200X, 400X, 400G, 500X, 502G, 600X, 700X are F0V6
|
||||||
bool PRS1Import::ParseF0Events()
|
bool PRS1Import::ParseF0Events()
|
||||||
{
|
{
|
||||||
unsigned char code=0;
|
ChannelID Codes[] = {
|
||||||
|
PRS1_00, PRS1_01, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
PRS1_0B, 0, 0, PRS1_0E
|
||||||
|
};
|
||||||
|
|
||||||
|
int ncodes = sizeof(Codes) / sizeof(ChannelID);
|
||||||
EventList *Code[0x20] = {0};
|
EventList *Code[0x20] = {0};
|
||||||
|
|
||||||
EventDataType data0, data1, data2;
|
qint64 t = qint64(event->timestamp) * 1000L;
|
||||||
Q_UNUSED(data2)
|
|
||||||
int cnt = 0;
|
|
||||||
short delta;
|
|
||||||
int pos;
|
|
||||||
qint64 t = qint64(event->timestamp) * 1000L, tt;
|
|
||||||
|
|
||||||
session->updateFirst(t);
|
session->updateFirst(t);
|
||||||
|
|
||||||
@ -2444,7 +2475,7 @@ bool PRS1Import::ParseF0Events()
|
|||||||
EventList *VS2 = session->AddEventList(CPAP_VSnore2, EVL_Event);
|
EventList *VS2 = session->AddEventList(CPAP_VSnore2, EVL_Event);
|
||||||
//EventList *T1 = session->AddEventList(CPAP_Test1, EVL_Event, 0.1);
|
//EventList *T1 = session->AddEventList(CPAP_Test1, EVL_Event, 0.1);
|
||||||
|
|
||||||
Code[17] = session->AddEventList(PRS1_0E, EVL_Event);
|
Code[0x0e] = session->AddEventList(PRS1_0E, EVL_Event);
|
||||||
EventList * LL = session->AddEventList(CPAP_LargeLeak, EVL_Event);
|
EventList * LL = session->AddEventList(CPAP_LargeLeak, EVL_Event);
|
||||||
|
|
||||||
EventList *PRESSURE = nullptr;
|
EventList *PRESSURE = nullptr;
|
||||||
@ -2452,14 +2483,6 @@ bool PRS1Import::ParseF0Events()
|
|||||||
EventList *IPAP = nullptr;
|
EventList *IPAP = nullptr;
|
||||||
EventList *PS = nullptr;
|
EventList *PS = nullptr;
|
||||||
|
|
||||||
unsigned char lastcode3 = 0, lastcode2 = 0, lastcode = 0;
|
|
||||||
int lastpos = 0, startpos = 0, lastpos2 = 0, lastpos3 = 0;
|
|
||||||
|
|
||||||
int size = event->m_data.size();
|
|
||||||
|
|
||||||
bool FV3 = (event->fileVersion == 3);
|
|
||||||
unsigned char * buffer = (unsigned char *)event->m_data.data();
|
|
||||||
|
|
||||||
EventDataType currentPressure=0, leak; //, p;
|
EventDataType currentPressure=0, leak; //, p;
|
||||||
|
|
||||||
bool calcLeaks = p_profile->cpap->calculateUnintentionalLeaks();
|
bool calcLeaks = p_profile->cpap->calculateUnintentionalLeaks();
|
||||||
@ -2471,6 +2494,145 @@ bool PRS1Import::ParseF0Events()
|
|||||||
|
|
||||||
CPAPMode mode = (CPAPMode) session->settings[CPAP_Mode].toInt();
|
CPAPMode mode = (CPAPMode) session->settings[CPAP_Mode].toInt();
|
||||||
|
|
||||||
|
bool ok;
|
||||||
|
ok = event->ParseEventsF0(mode);
|
||||||
|
|
||||||
|
for (int i=0; i < event->m_parsedData.count(); i++) {
|
||||||
|
PRS1ParsedEvent* e = event->m_parsedData.at(i);
|
||||||
|
t = qint64(event->timestamp + e->m_start) * 1000L;
|
||||||
|
|
||||||
|
switch (e->m_type) {
|
||||||
|
case EV_PRS1_PRESSURE:
|
||||||
|
if (!PRESSURE) {
|
||||||
|
if (!(PRESSURE = session->AddEventList(CPAP_Pressure, EVL_Event, e->m_gain))) { return false; }
|
||||||
|
}
|
||||||
|
PRESSURE->AddEvent(t, e->m_value);
|
||||||
|
currentPressure = e->m_value;
|
||||||
|
break;
|
||||||
|
case EV_PRS1_IPAP:
|
||||||
|
if(!IPAP) {
|
||||||
|
if (!(IPAP = session->AddEventList(CPAP_IPAP, EVL_Event, e->m_gain))) { return false; }
|
||||||
|
}
|
||||||
|
IPAP->AddEvent(t, e->m_value);
|
||||||
|
currentPressure = e->m_value;
|
||||||
|
break;
|
||||||
|
case EV_PRS1_EPAP:
|
||||||
|
if (!EPAP) {
|
||||||
|
if (!(EPAP = session->AddEventList(CPAP_EPAP, EVL_Event, e->m_gain))) { return false; }
|
||||||
|
}
|
||||||
|
if(!PS) {
|
||||||
|
if (!(PS = session->AddEventList(CPAP_PS, EVL_Event, e->m_gain))) { return false; }
|
||||||
|
}
|
||||||
|
EPAP->AddEvent(t, e->m_value);
|
||||||
|
PS->AddEvent(t, currentPressure - e->m_value);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_FLEX:
|
||||||
|
if (!EPAP) {
|
||||||
|
if (!(EPAP = session->AddEventList(CPAP_EPAP, EVL_Event, e->m_gain))) { return false; }
|
||||||
|
}
|
||||||
|
EPAP->AddEvent(t, e->m_value);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_OA:
|
||||||
|
OA->AddEvent(t, e->m_duration);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_CA:
|
||||||
|
CA->AddEvent(t, e->m_duration);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_FL:
|
||||||
|
FL->AddEvent(t, e->m_duration);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_PB:
|
||||||
|
PB->AddEvent(t, e->m_duration);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_LL:
|
||||||
|
LL->AddEvent(t, e->m_duration);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_HY:
|
||||||
|
HY->AddEvent(t, e->m_duration);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_TOTLEAK:
|
||||||
|
TOTLEAK->AddEvent(t, e->m_value);
|
||||||
|
leak = e->m_value;
|
||||||
|
if (calcLeaks) { // Much Quicker doing this here than the recalc method.
|
||||||
|
leak -= (((currentPressure/10.0f) - 4.0) * ppm + lpm4);
|
||||||
|
if (leak < 0) leak = 0;
|
||||||
|
LEAK->AddEvent(t, leak);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case EV_PRS1_SNORE:
|
||||||
|
SNORE->AddEvent(t, e->m_value);
|
||||||
|
if (e->m_value > 0) {
|
||||||
|
VS2->AddEvent(t, e->m_value);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case EV_PRS1_VS: // F0: Is this really distinct from SNORE and VS2?
|
||||||
|
VS->AddEvent(t, 0);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_RERA:
|
||||||
|
RE->AddEvent(t, e->m_value);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_PP:
|
||||||
|
PP->AddEvent(t, e->m_value);
|
||||||
|
break;
|
||||||
|
case EV_PRS1_UNKNOWN:
|
||||||
|
{
|
||||||
|
int code = ((PRS1UnknownValueEvent*) e)->m_code;
|
||||||
|
Q_ASSERT(code < ncodes);
|
||||||
|
if (!Code[code]) {
|
||||||
|
ChannelID cpapcode = Codes[(int)code];
|
||||||
|
Q_ASSERT(cpapcode); // any unknown codes returned by chunk parser should be given a channel above
|
||||||
|
if (!(Code[code] = session->AddEventList(cpapcode, EVL_Event, e->m_gain))) { return false; }
|
||||||
|
}
|
||||||
|
Code[code]->AddEvent(t, e->m_value);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
qWarning() << "Unknown PRS1 event type" << (int) e->m_type;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!ok) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
t = qint64(event->timestamp + event->duration) * 1000L;
|
||||||
|
|
||||||
|
// SmoothEventList(session, PRESSURE, CPAP_Pressure);
|
||||||
|
// SmoothEventList(session, IPAP, CPAP_IPAP);
|
||||||
|
// SmoothEventList(session, EPAP, CPAP_EPAP);
|
||||||
|
|
||||||
|
session->updateLast(t);
|
||||||
|
session->m_cnt.clear();
|
||||||
|
session->m_cph.clear();
|
||||||
|
session->m_lastchan.clear();
|
||||||
|
session->m_firstchan.clear();
|
||||||
|
session->m_valuesummary[CPAP_Pressure].clear();
|
||||||
|
session->m_valuesummary.erase(session->m_valuesummary.find(CPAP_Pressure));
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool PRS1DataChunk::ParseEventsF0(CPAPMode mode)
|
||||||
|
{
|
||||||
|
unsigned char code=0;
|
||||||
|
|
||||||
|
EventDataType data0, data1, data2;
|
||||||
|
Q_UNUSED(data2)
|
||||||
|
int cnt = 0;
|
||||||
|
short delta;
|
||||||
|
int pos;
|
||||||
|
int t = 0;
|
||||||
|
|
||||||
|
unsigned char lastcode3 = 0, lastcode2 = 0, lastcode = 0;
|
||||||
|
int lastpos = 0, startpos = 0, lastpos2 = 0, lastpos3 = 0;
|
||||||
|
|
||||||
|
int size = this->m_data.size();
|
||||||
|
|
||||||
|
bool FV3 = (this->fileVersion == 3);
|
||||||
|
unsigned char * buffer = (unsigned char *)this->m_data.data();
|
||||||
|
|
||||||
for (pos = 0; pos < size;) {
|
for (pos = 0; pos < size;) {
|
||||||
lastcode3 = lastcode2;
|
lastcode3 = lastcode2;
|
||||||
lastcode2 = lastcode;
|
lastcode2 = lastcode;
|
||||||
@ -2482,7 +2644,7 @@ bool PRS1Import::ParseF0Events()
|
|||||||
code = buffer[pos++];
|
code = buffer[pos++];
|
||||||
|
|
||||||
if (code > 0x15) {
|
if (code > 0x15) {
|
||||||
qDebug() << "Illegal PRS1 code " << hex << int(code) << " appeared at " << hex << startpos << "in" << event->sessionid;
|
qDebug() << "Illegal PRS1 code " << hex << int(code) << " appeared at " << hex << startpos << "in" << this->sessionid;
|
||||||
qDebug() << "1: (" << hex << int(lastcode) << hex << lastpos << ")";
|
qDebug() << "1: (" << hex << int(lastcode) << hex << lastpos << ")";
|
||||||
qDebug() << "2: (" << hex << int(lastcode2) << hex << lastpos2 << ")";
|
qDebug() << "2: (" << hex << int(lastcode2) << hex << lastpos2 << ")";
|
||||||
qDebug() << "3: (" << hex << int(lastcode3) << hex << lastpos3 << ")";
|
qDebug() << "3: (" << hex << int(lastcode3) << hex << lastpos3 << ")";
|
||||||
@ -2493,8 +2655,7 @@ bool PRS1Import::ParseF0Events()
|
|||||||
delta = buffer[pos + 1] << 8 | buffer[pos];
|
delta = buffer[pos + 1] << 8 | buffer[pos];
|
||||||
pos += 2;
|
pos += 2;
|
||||||
|
|
||||||
t += qint64(delta) * 1000L;
|
t += delta;
|
||||||
tt = t;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
cnt++;
|
cnt++;
|
||||||
@ -2502,128 +2663,70 @@ bool PRS1Import::ParseF0Events()
|
|||||||
switch (code) {
|
switch (code) {
|
||||||
|
|
||||||
case 0x00: // Unknown 00
|
case 0x00: // Unknown 00
|
||||||
|
this->AddEvent(new PRS1UnknownValueEvent(code, t, buffer[pos++]));
|
||||||
if (!Code[0]) {
|
if (((this->family == 0) && (this->familyVersion >= 4)) || (this->fileVersion == 3)){
|
||||||
if (!(Code[0] = session->AddEventList(PRS1_00, EVL_Event))) { return false; }
|
|
||||||
}
|
|
||||||
|
|
||||||
Code[0]->AddEvent(t, buffer[pos++]);
|
|
||||||
|
|
||||||
if (((event->family == 0) && (event->familyVersion >= 4)) || (event->fileVersion == 3)){
|
|
||||||
pos++;
|
pos++;
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x01: // Unknown
|
case 0x01: // Unknown
|
||||||
if ((event->family == 0) && (event->familyVersion >= 4)) {
|
if ((this->family == 0) && (this->familyVersion >= 4)) {
|
||||||
if (!PRESSURE) {
|
this->AddEvent(new PRS1CPAPEvent(t, buffer[pos++]));
|
||||||
PRESSURE = session->AddEventList(CPAP_Pressure, EVL_Event, 0.1F);
|
|
||||||
|
|
||||||
if (!PRESSURE) { return false; }
|
|
||||||
}
|
|
||||||
|
|
||||||
PRESSURE->AddEvent(t, currentPressure = buffer[pos++]);
|
|
||||||
} else {
|
} else {
|
||||||
if (!Code[1]) {
|
this->AddEvent(new PRS1UnknownValueEvent(code, t, 0));
|
||||||
if (!(Code[1] = session->AddEventList(PRS1_01, EVL_Event))) { return false; }
|
|
||||||
}
|
|
||||||
|
|
||||||
Code[1]->AddEvent(t, 0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x02: // Pressure
|
case 0x02: // Pressure
|
||||||
if ((event->family == 0) && (event->familyVersion >= 4)) { // BiPAP Pressure
|
if ((this->family == 0) && (this->familyVersion >= 4)) { // BiPAP Pressure
|
||||||
if (!EPAP) {
|
data0 = buffer[pos++];
|
||||||
if (!(EPAP = session->AddEventList(CPAP_EPAP, EVL_Event, 0.1F))) { return false; }
|
data1 = buffer[pos++];
|
||||||
}
|
this->AddEvent(new PRS1IPAPEvent(t, data1));
|
||||||
if(!IPAP) {
|
this->AddEvent(new PRS1EPAPEvent(t, data0)); // EPAP needs to be added second to calculate PS
|
||||||
if (!(IPAP = session->AddEventList(CPAP_IPAP, EVL_Event, 0.1F))) { return false; }
|
|
||||||
}
|
|
||||||
if(!PS) {
|
|
||||||
if (!(PS = session->AddEventList(CPAP_PS, EVL_Event, 0.1F))) { return false; }
|
|
||||||
}
|
|
||||||
|
|
||||||
EPAP->AddEvent(t, data0 = buffer[pos++]);
|
|
||||||
IPAP->AddEvent(t, data1 = currentPressure = buffer[pos++]);
|
|
||||||
PS->AddEvent(t, data1 - data0);
|
|
||||||
} else {
|
} else {
|
||||||
if (!PRESSURE) {
|
this->AddEvent(new PRS1CPAPEvent(t, buffer[pos++]));
|
||||||
PRESSURE = session->AddEventList(CPAP_Pressure, EVL_Event, 0.1F);
|
|
||||||
|
|
||||||
if (!PRESSURE) { return false; }
|
|
||||||
}
|
|
||||||
|
|
||||||
PRESSURE->AddEvent(t, currentPressure = buffer[pos++]);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x03: // BIPAP Pressure
|
case 0x03: // BIPAP Pressure
|
||||||
if (FV3) {
|
if (FV3) {
|
||||||
if (!PRESSURE) {
|
this->AddEvent(new PRS1CPAPEvent(t, buffer[pos++]));
|
||||||
PRESSURE = session->AddEventList(CPAP_Pressure, EVL_Event, 0.1F);
|
|
||||||
|
|
||||||
if (!PRESSURE) { return false; }
|
|
||||||
}
|
|
||||||
PRESSURE->AddEvent(t, currentPressure = buffer[pos++]);
|
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
if (!EPAP) {
|
data0 = buffer[pos++];
|
||||||
if (!(EPAP = session->AddEventList(CPAP_EPAP, EVL_Event, 0.1F))) { return false; }
|
data1 = buffer[pos++];
|
||||||
}
|
this->AddEvent(new PRS1IPAPEvent(t, data1));
|
||||||
if(!IPAP) {
|
this->AddEvent(new PRS1EPAPEvent(t, data0)); // EPAP needs to be added second to calculate PS
|
||||||
if (!(IPAP = session->AddEventList(CPAP_IPAP, EVL_Event, 0.1F))) { return false; }
|
|
||||||
}
|
|
||||||
if(!PS) {
|
|
||||||
if (!(PS = session->AddEventList(CPAP_PS, EVL_Event, 0.1F))) { return false; }
|
|
||||||
}
|
|
||||||
|
|
||||||
EPAP->AddEvent(t, data0 = buffer[pos++]);
|
|
||||||
IPAP->AddEvent(t, data1 = currentPressure = buffer[pos++]);
|
|
||||||
PS->AddEvent(t, data1 - data0);
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x04: // Pressure Pulse
|
case 0x04: // Pressure Pulse
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
|
this->AddEvent(new PRS1PressurePulseEvent(t, data0));
|
||||||
PP->AddEvent(t, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x05: // RERA
|
case 0x05: // RERA
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
tt = t - (qint64(data0) * 1000L);
|
this->AddEvent(new PRS1RERAEvent(t - data0, data0));
|
||||||
|
|
||||||
RE->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x06: // Obstructive Apoanea
|
case 0x06: // Obstructive Apoanea
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
tt = t - (qint64(data0) * 1000L);
|
this->AddEvent(new PRS1ObstructiveApneaEvent(t - data0, data0));
|
||||||
OA->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x07: // Clear Airway
|
case 0x07: // Clear Airway
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
tt = t - (qint64(data0) * 1000L);
|
this->AddEvent(new PRS1ClearAirwayEvent(t - data0, data0));
|
||||||
|
|
||||||
CA->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x0a: // Hypopnea
|
case 0x0a: // Hypopnea
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
tt = t - (qint64(data0) * 1000L);
|
this->AddEvent(new PRS1HypopneaEvent(t - data0, data0));
|
||||||
HY->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x0c: // Flow Limitation
|
case 0x0c: // Flow Limitation
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
tt = t - (qint64(data0) * 1000L);
|
this->AddEvent(new PRS1FlowLimitationEvent(t - data0, data0));
|
||||||
|
|
||||||
FL->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x0b: // Breathing not Detected flag???? but it doesn't line up
|
case 0x0b: // Breathing not Detected flag???? but it doesn't line up
|
||||||
@ -2631,7 +2734,7 @@ bool PRS1Import::ParseF0Events()
|
|||||||
data1 = buffer[pos+1];
|
data1 = buffer[pos+1];
|
||||||
pos += 2;
|
pos += 2;
|
||||||
|
|
||||||
if (event->familyVersion >= 4) {
|
if (this->familyVersion >= 4) {
|
||||||
// might not doublerize on older machines?
|
// might not doublerize on older machines?
|
||||||
// data0 *= 2;
|
// data0 *= 2;
|
||||||
}
|
}
|
||||||
@ -2639,90 +2742,63 @@ bool PRS1Import::ParseF0Events()
|
|||||||
|
|
||||||
//tt = t - qint64((data0+data1)*2) * 1000L;
|
//tt = t - qint64((data0+data1)*2) * 1000L;
|
||||||
|
|
||||||
if (!Code[12]) {
|
this->AddEvent(new PRS1UnknownValueEvent(code, t, data0)); // FIXME
|
||||||
Code[12] = session->AddEventList(PRS1_0B, EVL_Event);
|
|
||||||
}
|
|
||||||
|
|
||||||
// FIXME
|
|
||||||
Code[12]->AddEvent(t, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x0d: // Vibratory Snore
|
case 0x0d: // Vibratory Snore
|
||||||
VS->AddEvent(t, 0);
|
this->AddEvent(new PRS1VibratorySnoreEvent(t, 0));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x0e: // Unknown
|
case 0x0e: // Unknown
|
||||||
data0 = buffer[pos + 1] << 8 | buffer[pos];
|
data0 = buffer[pos + 1] << 8 | buffer[pos];
|
||||||
if (event->familyVersion >= 4) {
|
if (this->familyVersion >= 4) {
|
||||||
// might not doublerize on older machines?
|
// might not doublerize on older machines?
|
||||||
data0 *= 2;
|
data0 *= 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
pos += 2;
|
pos += 2;
|
||||||
data1 = buffer[pos++];
|
data1 = buffer[pos++];
|
||||||
|
this->AddEvent(new PRS1UnknownValueEvent(code, t - data1, data0));
|
||||||
tt = t - qint64(data1) * 1000L;
|
|
||||||
Code[17]->AddEvent(tt, data0);
|
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x0f: // Cheyne Stokes Respiration
|
case 0x0f: // Cheyne Stokes Respiration
|
||||||
data0 = (buffer[pos + 1] << 8 | buffer[pos]);
|
data0 = (buffer[pos + 1] << 8 | buffer[pos]);
|
||||||
if (event->familyVersion >= 4) {
|
if (this->familyVersion >= 4) {
|
||||||
// might not doublerize on older machines
|
// might not doublerize on older machines
|
||||||
data0 *= 2;
|
data0 *= 2;
|
||||||
}
|
}
|
||||||
pos += 2;
|
pos += 2;
|
||||||
data1 = buffer[pos++];
|
data1 = buffer[pos++];
|
||||||
tt = t - qint64(data1) * 1000L;
|
this->AddEvent(new PRS1PeriodicBreathingEvent(t - data1, data0));
|
||||||
PB->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x10: // Large Leak
|
case 0x10: // Large Leak
|
||||||
data0 = buffer[pos + 1] << 8 | buffer[pos];
|
data0 = buffer[pos + 1] << 8 | buffer[pos];
|
||||||
if (event->familyVersion >= 4) {
|
if (this->familyVersion >= 4) {
|
||||||
// might not doublerize on older machines
|
// might not doublerize on older machines
|
||||||
data0 *= 2;
|
data0 *= 2;
|
||||||
}
|
}
|
||||||
pos += 2;
|
pos += 2;
|
||||||
data1 = buffer[pos++];
|
data1 = buffer[pos++];
|
||||||
|
this->AddEvent(new PRS1LargeLeakEvent(t - data1, data0));
|
||||||
tt = t - qint64(data1) * 1000L;
|
|
||||||
LL->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x11: // Leak Rate & Snore Graphs
|
case 0x11: // Leak Rate & Snore Graphs
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
data1 = buffer[pos++];
|
data1 = buffer[pos++];
|
||||||
|
this->AddEvent(new PRS1TotalLeakEvent(t, data0));
|
||||||
|
this->AddEvent(new PRS1SnoreEvent(t, data1));
|
||||||
|
|
||||||
TOTLEAK->AddEvent(t, data0);
|
if ((this->family == 0) && (this->familyVersion >= 4)) {
|
||||||
SNORE->AddEvent(t, data1);
|
|
||||||
|
|
||||||
if (calcLeaks) { // Much Quicker doing this here than the recalc method.
|
|
||||||
leak = data0-(((currentPressure/10.0f) - 4.0) * ppm + lpm4);
|
|
||||||
if (leak < 0) leak = 0;
|
|
||||||
|
|
||||||
LEAK->AddEvent(t, leak);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (data1 > 0) {
|
|
||||||
VS2->AddEvent(t, data1);
|
|
||||||
}
|
|
||||||
|
|
||||||
if ((event->family == 0) && (event->familyVersion >= 4)) {
|
|
||||||
// EPAP / Flex Pressure
|
// EPAP / Flex Pressure
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
|
|
||||||
// Perhaps this check is not necessary, as it will theoretically add extra resolution to pressure chart
|
// Perhaps this check is not necessary, as it will theoretically add extra resolution to pressure chart
|
||||||
// for bipap models and above???
|
// for bipap models and above???
|
||||||
if (mode <= MODE_BILEVEL_FIXED) {
|
if (mode <= MODE_BILEVEL_FIXED) {
|
||||||
if (!EPAP) {
|
this->AddEvent(new PRS1PressureReliefEvent(t, data0));
|
||||||
if (!(EPAP = session->AddEventList(CPAP_EPAP, EVL_Event, 0.1F))) { return false; }
|
|
||||||
}
|
|
||||||
EPAP->AddEvent(t, data0);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x12: // Summary
|
case 0x12: // Summary
|
||||||
@ -2737,36 +2813,22 @@ bool PRS1Import::ParseF0Events()
|
|||||||
|
|
||||||
case 0x14: // DreamStation Hypopnea
|
case 0x14: // DreamStation Hypopnea
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
tt = t - (qint64(data0) * 1000L);
|
this->AddEvent(new PRS1HypopneaEvent(t - data0, data0));
|
||||||
HY->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x15: // DreamStation Hypopnea
|
case 0x15: // DreamStation Hypopnea
|
||||||
data0 = buffer[pos++];
|
data0 = buffer[pos++];
|
||||||
tt = t - (qint64(data0) * 1000L);
|
this->AddEvent(new PRS1HypopneaEvent(t - data0, data0));
|
||||||
HY->AddEvent(tt, data0);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
// ERROR!!!
|
// ERROR!!!
|
||||||
qWarning() << "Some new fandangled PRS1 code detected in" << event->sessionid << hex
|
qWarning() << "Some new fandangled PRS1 code detected in" << this->sessionid << hex
|
||||||
<< int(code) << " at " << pos - 1;
|
<< int(code) << " at " << pos - 1;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
this->duration = t;
|
||||||
// SmoothEventList(session, PRESSURE, CPAP_Pressure);
|
|
||||||
// SmoothEventList(session, IPAP, CPAP_IPAP);
|
|
||||||
// SmoothEventList(session, EPAP, CPAP_EPAP);
|
|
||||||
|
|
||||||
|
|
||||||
session->updateLast(t);
|
|
||||||
session->m_cnt.clear();
|
|
||||||
session->m_cph.clear();
|
|
||||||
session->m_lastchan.clear();
|
|
||||||
session->m_firstchan.clear();
|
|
||||||
session->m_valuesummary[CPAP_Pressure].clear();
|
|
||||||
session->m_valuesummary.erase(session->m_valuesummary.find(CPAP_Pressure));
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -130,6 +130,9 @@ public:
|
|||||||
//! \brief Parse a single data chunk from a .001 file containing summary data for a family 5 ASV family version 3 machine
|
//! \brief Parse a single data chunk from a .001 file containing summary data for a family 5 ASV family version 3 machine
|
||||||
bool ParseSummaryF5V3(void);
|
bool ParseSummaryF5V3(void);
|
||||||
|
|
||||||
|
//! \brief Parse a single data chunk from a .002 file containing event data for a family 0 CPAP/APAP machine
|
||||||
|
bool ParseEventsF0(CPAPMode mode);
|
||||||
|
|
||||||
//! \brief Parse a single data chunk from a .002 file containing event data for a family 3 ventilator family version 3 machine
|
//! \brief Parse a single data chunk from a .002 file containing event data for a family 3 ventilator family version 3 machine
|
||||||
bool ParseEventsF3V3(void);
|
bool ParseEventsF3V3(void);
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user