//---------------------------------------------------------- bool MButil::readInt16 (ZUFILE *f, int *val) { unsigned char a,b; if (zu_read (f, &a, 1) != 1) return false; if (zu_read (f, &b, 1) != 1) return false; *val = (a<<8) + b; return true; }
//---------------------------------------------------------- bool MButil::readInt32 (ZUFILE *f, int *val) { unsigned char a,b,c,d; if (zu_read (f, &a, 1) != 1) return false; if (zu_read (f, &b, 1) != 1) return false; if (zu_read (f, &c, 1) != 1) return false; if (zu_read (f, &d, 1) != 1) return false; *val = (a<<24) + (b<<16) + (c<<8) + d; return true; }
//================================================================== bool MButil::readInt8 (ZUFILE *f, int *val) { unsigned char a; if (zu_read (f, &a, 1) != 1) return false; *val = a; return true; }
//---------------------------------------------- // SECTION 1: THE PRODUCT DEFINITION SECTION (PDS) //---------------------------------------------- bool GribV1Record::readGribSection1_PDS(ZUFILE* file) { fileOffset1 = zu_tell(file); if (zu_read(file, data1, 28) != 28) { ok=false; eof = true; return false; } sectionSize1 = makeInt3(data1[0],data1[1],data1[2]); tableVersion = data1[3]; idCenter = data1[4]; idModel = data1[5]; idGrid = data1[6]; hasGDS = (data1[7]&128)!=0; hasBMS = (data1[7]&64)!=0; dataTypeV1 = data1[8]; // octet 9 = parameters and units /* convert data type */ dataType=GRBV1_TO_DATA[dataTypeV1]; levelTypeV1 = data1[9]; /* convert level type */ levelType=GRBV1_TO_DATA_LV[levelTypeV1]; levelValue = makeInt2(data1[10],data1[11]); refYear = (data1[24]-1)*100+data1[12]; refMonth = data1[13]; refDay = data1[14]; refHour = data1[15]; refMinute = data1[16]; refDate = makeDate(refYear,refMonth,refDay,refHour,refMinute,0); periodP1 = data1[18]; periodP2 = data1[19]; timeRange = data1[20]; periodsec = periodSeconds(data1[17],data1[18],data1[19],timeRange); if(periodP2 > periodP1) deltaPeriod=periodP2-periodP1; //qWarning() << "Periodsec:" << periodP2-periodP1 << " - comp= " << periodsec; curDate = makeDate(refYear,refMonth,refDay,refHour,refMinute,periodsec); //if (dataType == GRB_PRECIP_TOT) printf("P1=%d p2=%d\n", periodP1,periodP2); int decim; decim = (int)(((((zuint)data1[26]&0x7F)<<8)+(zuint)data1[27])&0x7FFF); if (data1[26]&0x80) decim *= -1; decimalFactorD = pow(10.0, decim); // Controls if (! hasGDS) { //erreur("Record: GDS not found"); ok = false; } if (decimalFactorD == 0) { //erreur("Record: decimalFactorD null"); ok = false; } return ok; }
//---------------------------------------------- zuint GribV1Record::readInt2(ZUFILE* file) { unsigned char t[2]; if (zu_read(file, t, 2) != 2) { ok = false; eof = true; return 0; } return ((zuint)t[0]<<8)+(zuint)t[1]; }
//---------------------------------------------- zuchar GribV1Record::readChar(ZUFILE* file) { zuchar t; if (zu_read(file, &t, 1) != 1) { ok = false; eof = true; return 0; } return t; }
//---------------------------------------------- int GribV1Record::readSignedInt2(ZUFILE* file) { unsigned char t[2]; if (zu_read(file, t, 2) != 2) { ok = false; eof = true; return 0; } int val = (((zuint)t[0]&0x7F)<<8)+(zuint)t[1]; if (t[0]&0x80) return -val; else return val; }
//---------------------------------------------- // SECTION 5: END SECTION (ES) //---------------------------------------------- bool GribV1Record::readGribSection5_ES(ZUFILE* file) { char str[4]; if (zu_read(file, str, 4) != 4) { ok = false; eof = true; return false; } if (strncmp(str, "7777", 4) != 0) { erreur("Final 7777 not read: %c%c%c%c",str[0],str[1],str[2],str[3]); ok = false; return false; } return ok; }
//============================================================== // Fonctions utiles //============================================================== double GribV1Record::readFloat4(ZUFILE* file) { unsigned char t[4]; if (zu_read(file, t, 4) != 4) { ok = false; eof = true; return 0; } double val; int A = (zuint)t[0]&0x7F; int B = ((zuint)t[1]<<16)+((zuint)t[2]<<8)+(zuint)t[3]; val = pow(2.0,-24)*B*pow(16.0,A-64); if (t[0]&0x80) return -val; else return val; }
//--------------------------------------------------- void MbzFile::read_header (ZUFILE *f) { char buf[128]; int pad; if (zu_read (f, buf, 8) != 8) {ok=false; return;} buf [8] = 0; if (strcmp(buf, "MBZYGRIB") != 0) {ok=false; return;} if (! MButil::readInt8 (f, &version)) {ok=false; return;} if (! MButil::readInt16 (f, &year)) {ok=false; return;} if (! MButil::readInt8 (f, &month)) {ok=false; return;} if (! MButil::readInt8 (f, &day)) {ok=false; return;} if (! MButil::readInt8 (f, &href)) {ok=false; return;} if (! MButil::readInt32 (f, &nbData)) {ok=false; return;} if (! MButil::readInt32 (f, &nbLines)) {ok=false; return;} if (! MButil::readFloat32 (f, &xmin)) {ok=false; return;} if (! MButil::readFloat32 (f, &xmax)) {ok=false; return;} if (! MButil::readFloat32 (f, &ymin)) {ok=false; return;} if (! MButil::readFloat32 (f, &ymax)) {ok=false; return;} if (! MButil::readInt16 (f, &pad)) {ok=false; return;} if (! MButil::readInt32 (f, &pad)) {ok=false; return;} if (! MButil::readInt32 (f, &pad)) {ok=false; return;} }
CelestialNavigationDialog::CelestialNavigationDialog(wxWindow *parent) : CelestialNavigationDialogBase(parent), m_FixDialog(this), m_ClockCorrectionDialog(this) { wxFileConfig *pConf = GetOCPNConfigObject(); pConf->SetPath( _T("/PlugIns/CelestialNavigation") ); //#ifdef __WXGTK__ // Move(0, 0); // workaround for gtk autocentre dialog behavior //#endif // Move(pConf->Read ( _T ( "DialogPosX" ), 20L ), pConf->Read ( _T ( "DialogPosY" ), 20L )); wxPoint p = GetPosition(); pConf->Read ( _T ( "DialogX" ), &p.x, p.x); pConf->Read ( _T ( "DialogY" ), &p.y, p.y); SetPosition(p); wxSize s = GetSize(); pConf->Read ( _T ( "DialogWidth" ), &s.x, s.x); pConf->Read ( _T ( "DialogHeight" ), &s.y, s.y); SetSize(s); // create a image list for the list with just the eye icon wxImageList *imglist = new wxImageList(20, 20, true, 1); imglist->Add(wxBitmap(eye)); m_lSights->AssignImageList(imglist, wxIMAGE_LIST_SMALL); m_lSights->InsertColumn(rmVISIBLE, wxT("")); m_lSights->SetColumnWidth(0, 28); m_lSights->InsertColumn(rmTYPE, _("Type")); m_lSights->InsertColumn(rmBODY, _("Body")); m_lSights->InsertColumn(rmTIME, _("Time (UT)")); m_lSights->InsertColumn(rmMEASUREMENT, _("Measurement")); m_lSights->InsertColumn(rmCOLOR, _("Color")); m_sights_path = celestial_navigation_pi::StandardPath() + _T("Sights.xml"); if(!OpenXML(m_sights_path, false)) { /* create directory for plugin files if it doesn't already exist */ wxFileName fn(m_sights_path); wxFileName fn2 = fn.GetPath(); if(!fn.DirExists()) { fn2.Mkdir(); fn.Mkdir(); } } wxString filename = DataDirectory() + "vsop87d.txt"; wxFileName fn(filename); if(!fn.Exists()) filename = UserDataDirectory() + "vsop87d.txt"; astrolabe::globals::vsop87d_text_path = (const char *)filename.mb_str(); #ifndef WIN32 // never hit because data is distribued easier to not compile compression support wxMessageDialog mdlg(this, _("Astrolab data unavailable.\n") + _("\nWould you like to download?"), _("Failure Alert"), wxYES | wxNO | wxICON_ERROR); if(mdlg.ShowModal() == wxID_YES) { wxString url = "https://cfhcable.dl.sourceforge.net/project/opencpnplugins/celestial_navigation_pi/"; wxString path = UserDataDirectory(); wxString fn = "vsop87d.txt.gz"; _OCPN_DLStatus status = OCPN_downloadFile( url+fn, path+fn, _("downloading celestial navigation data file"), "downloading...", *_img_celestial_navigation, this, OCPN_DLDS_CAN_ABORT|OCPN_DLDS_ELAPSED_TIME|OCPN_DLDS_ESTIMATED_TIME|OCPN_DLDS_REMAINING_TIME|OCPN_DLDS_SPEED|OCPN_DLDS_SIZE|OCPN_DLDS_URL|OCPN_DLDS_AUTO_CLOSE, 20); if(status == OCPN_DL_NO_ERROR) { // now decompress downloaded file ZUFILE *f = zu_open(path+fn.mb_str(), "rb", ZU_COMPRESS_AUTO); if(f) { FILE *out = fopen(path+"vsop87d.txt", "w"); if(out) { char buf[1024]; for(;;) { size_t size = zu_read(f, buf, sizeof buf); fwrite(buf, size, 1, out); if(size != sizeof buf) break; } fclose(out); } zu_close(f); } } } #endif #ifdef __OCPN__ANDROID__ GetHandle()->setStyleSheet( qtStyleSheet); Move(0, 0); #endif }
//---------------------------------------------- // SECTION 4: BINARY DATA SECTION (BDS) //---------------------------------------------- bool GribV1Record::readGribSection4_BDS(ZUFILE* file) { fileOffset4 = zu_tell(file); sectionSize4 = readInt3(file); // byte 1-2-3 zuchar flags = readChar(file); // byte 4 scaleFactorE = readSignedInt2(file); // byte 5-6 refValue = readFloat4(file); // byte 7-8-9-10 nbBitsInPack = readChar(file); // byte 11 scaleFactorEpow2 = pow(2.0,scaleFactorE); unusedBitsEndBDS = flags & 0x0F; isGridData = (flags&0x80) ==0; isSimplePacking = (flags&0x80) ==0; isFloatValues = (flags&0x80) ==0; //printf("BDS type=%3d - bits=%02d - level %3d - %d\n", dataType, nbBitsInPack, levelType,levelValue); if (! isGridData) { //erreur("Record: need grid data"); ok = false; } if (! isSimplePacking) { //erreur("Record: need simple packing"); ok = false; } if (! isFloatValues) { //erreur("Record: need double values"); ok = false; } if (!ok) { return ok; } // Allocate memory for the data data = new float[Ni*Nj]; if (!data) { //erreur("Record: out of memory"); ok = false; } zuint startbit = 0; int datasize = sectionSize4-11; zuchar *buf = new zuchar[datasize+4]; // +4 pour simplifier les decalages ds readPackedBits if (!buf) { //erreur("Record: out of memory"); ok = false; } if (zu_read(file, buf, datasize) != datasize) { //erreur("Record: data read error"); ok = false; eof = true; } if (!ok) { return ok; } // Initialize the las 4 bytes of buf since we didn't read them buf[datasize+0] = buf[datasize+1] = buf[datasize+2] = buf[datasize+3] = 0; // Read data in the order given by isAdjacentI zuint i, j, x; int ind; if (isAdjacentI) { for (j=0; j<Nj; j++) { for (i=0; i<Ni; i++) { if (!hasDiDj && !isScanJpositive) { ind = (Nj-1 -j)*Ni+i; } else { ind = j*Ni+i; } if (hasValue(i,j)) { x = readPackedBits(buf, startbit, nbBitsInPack); data[ind] = (refValue + x*scaleFactorEpow2)/decimalFactorD; startbit += nbBitsInPack; } else { data[ind] = (float) GRIB_NOTDEF; } } } } else { for (i=0; i<Ni; i++) { for (j=0; j<Nj; j++) { if (!hasDiDj && !isScanJpositive) { ind = (Nj-1 -j)*Ni+i; } else { ind = j*Ni+i; } if (hasValue(i,j)) { x = readPackedBits(buf, startbit, nbBitsInPack); startbit += nbBitsInPack; data[ind] = (refValue + x*scaleFactorEpow2)/decimalFactorD; } else { data[ind] = (float)GRIB_NOTDEF; } } } } if (buf) { delete [] buf; buf = NULL; } return ok; }
//============================================================== // Lecture des donnees //============================================================== //---------------------------------------------- // SECTION 0: THE INDICATOR SECTION (IS) //---------------------------------------------- bool GribV1Record::readGribSection0_IS(ZUFILE* file) { char strgrib[4]; memset (strgrib, 0, sizeof (strgrib)); zuint initFoffset; fileOffset0 = zu_tell(file); initFoffset=fileOffset0; #if 1 char buf[1]; memset (buf, 0, sizeof (buf)); while(true) { if(zu_read(file,buf,1)!=1) break; ++fileOffset0; if(buf[0]!='G') continue; if(zu_read(file,buf,1)!=1) break; ++fileOffset0; if(buf[0]!='R') { if(buf[0]=='G') zu_seek(file,--fileOffset0,SEEK_SET); continue; } if(zu_read(file,buf,1)!=1) break; ++fileOffset0; if(buf[0]!='I') { if(buf[0]=='G') zu_seek(file,--fileOffset0,SEEK_SET); continue; } if(zu_read(file,buf,1)!=1) break; ++fileOffset0; if(buf[0]!='B') { if(buf[0]=='G') zu_seek(file,--fileOffset0,SEEK_SET); continue; } strgrib[0]='G'; strgrib[1]='R'; strgrib[2]='I'; strgrib[3]='B'; break; } #else while((zu_read(file, strgrib, 4) == 4) && (strgrib[0] != 'G' || strgrib[1] != 'R' || strgrib[2] != 'I' || strgrib[3] != 'B')) { zu_seek(file,++fileOffset0,SEEK_SET); } #endif if(strgrib[0] != 'G' || strgrib[1] != 'R' || strgrib[2] != 'I' || strgrib[3] != 'B') { if((fileOffset0-10)>initFoffset) // displaying error msg only if we are really far from initial offset qWarning() << "Can't find next record / EOF - offset=" << fileOffset0 << ", initOffset=" << initFoffset ; ok = false; eof = true; return false; } seekStart=zu_tell(file)-4; totalSize = readInt3(file); //qWarning() << "Start = " << seekStart << ", size = " << totalSize; editionNumber = readChar(file); if (editionNumber != 1) { ok = false; eof = true; return false; } return true; }
//---------------------------------------------------------- bool MButil::readFloat32 (ZUFILE *f, float *val) { if (zu_read (f, val, 4) != 4) return false; return true; }