Sample code for the TrainInfoLib
Dependencies: NJE10XCtrlLib NTPClient_NetServices mbed IniFileLib NextTrainFileLib TrainInfoLib lwip
Diff: TrainInfoSample.cpp
- Revision:
- 0:1a9fa43d77af
- Child:
- 1:93b052511e2c
diff -r 000000000000 -r 1a9fa43d77af TrainInfoSample.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/TrainInfoSample.cpp Fri Nov 19 20:40:48 2010 +0000 @@ -0,0 +1,353 @@ +/////////////////////////////////////////////////////////////////////////////// +// TrainInfo: sample code for the TrainInfo library by rinos 2010 +/////////////////////////////////////////////////////////////////////////////// + +#include "TrainInfo.h" +#include "NJE10XCtrl.h" +#include <time.h> + +/////////////////////////////////////////////////////////////////////////////// + +LocalFileSystem local("local"); +NJE10XCtrl gNJE(p9); + +// critical section +#define TickerLock() (NVIC_DisableIRQ(TIMER3_IRQn)) +#define TickerUnlock() (NVIC_EnableIRQ (TIMER3_IRQn)) + +// Config file +#ifndef ROOTPATH +#define ROOTPATH "/local/" +#endif +const char INI_FILE[] = ROOTPATH "TInfo.ini"; +const int DEFAULT_GIVEUP_SEC = 30; // Giveup-seconds to take the next train +int gGiveupSec = DEFAULT_GIVEUP_SEC; +char gDelayMessage[TrainInfo::MAX_DELAY_MESSAGE]; +int gDispMode = 0; +int gTimeZone = 540; // +9h00m + +// Latest search cache +time_t gSerchTime; +NextTrainFile::NextInfo gNext[2]; +int gDelayStatus = 0; +const int S_INFO_OK = 0x01; +const int S_DELAY = 0x10; + + +//////////////////////////////////////////////////////////////////////////////// +// RTC Configuration + +//#define USE_NTPCLIENT 1 + +#ifdef USE_NTPCLIENT +#include "EthernetNetIf.h" +#include "NTPClient.h" + +int UpdateRTC(const char* ntp_server, int ntp_port, int timezone) { + printf("UpdateRTC by NTPClient...\n"); + + EthernetNetIf eth; + EthernetErr ethErr = eth.setup(); // default timeout: 15sec + if (ethErr) { + printf("eth.setup failed %d.\n", ethErr); + return 1; + } +/* + time_t now = time(0); + if(now){ + printf("Use current RTC: %d\n", now); + return 0; + } +*/ + printf("Connect to the NTP server %s...\n", ntp_server); + + NTPResult ntpErr = NTPClient().setTime(Host(IpAddr(), ntp_port, ntp_server)); + if(ntpErr){ + printf("NTPClient::setTime failed %d.\n", ntpErr); + return 2; + } + +#else +// I can't use NTPClient with LWIP HTTPClient... +// So, I get the RTC via http-NTP server. + +#include "HTTPClient.h" +#define NTP2POSIX 2208988800UL + +int UpdateRTC(const char* ntp_server, int ntp_port, int timezone) { + printf("UpdateRTC by HTTP-NTP...\n"); + + char rbuf[80]; + printf("Connect to the NTP server %s...\n", ntp_server); + HTTPClient http; + http.timeout(10); + int len = http.get(ntp_server, rbuf, sizeof(rbuf) - 1); + if(len){ + rbuf[len] = '\0'; + char* p = strstr(rbuf, "<BODY>"); + if(p){ + p += 7; + time_t val = strtoul(p, 0, 10) - NTP2POSIX; + set_time(val); + printf("NTP set %d\n", val); + } + printf("HTTPClient download [%s]\n", rbuf); + } + +#endif + // Puts RTC (JST) + time_t now = time(0) + timezone; + printf("RTC(JST): %s\n", ctime(&now)); + return 0; +} + +//////////////////////////////////////////////////////////////////////////////// +// Display control + +#include "NJE10XCtrl.h" + +char gMsgNoTrain[100] = "NoTrain"; +char gMsgLeft [ 20] = "Left"; +char gMsgDir [ 20] = "To"; +char gMsgSec [ 20] = "Sec"; +int gMsgWarn = 60 * 3; // 3min + +void dispTime(){ + char buf[100]; + time_t t = time(0) + gTimeZone; + struct tm* st = localtime(&t); + t -= gSerchTime; + + gNJE.clear(); + NextTrainFile::NextInfo* p = &gNext[0]; + if(p->m_diff < 0){ + printf("Now:%02d:%02d:%02d, %s\n", st->tm_hour, st->tm_min, st->tm_sec, gMsgNoTrain); // or error + sprintf(buf, "%02d:%02d:%02d ", st->tm_hour, st->tm_min, st->tm_sec); + gNJE.add(buf); + gNJE.addAttr(NJE10XCtrl::ATTR_RED); + gNJE.add(gMsgNoTrain); + gNJE.setMessage(1); + return; + } + + // Check the difference (was gone?) + int diff = p->m_diff - t; + if(diff < gGiveupSec){ + p = &gNext[1]; + diff = p->m_diff - t; + } + + // Show message to the NJE-105 + NJE10XCtrl::Attr1 a1 = NJE10XCtrl::ATTR_GREEN; + NJE10XCtrl::Attr2 a2 = NJE10XCtrl::ATTR_SCROLL_R; + NJE10XCtrl::Attr3 a3 = NJE10XCtrl::ATTR_NORMAL; + + if(diff < 0){ + printf("%02d:%02d Gone%2dsec ", p->m_hour, p->m_min, -diff); + + sprintf(buf, "%02d:%02d", p->m_hour, p->m_min); + gNJE.add(buf); + //gNJE.addAttr(NJE10XCtrl::ATTR_YELLOW, NJE10XCtrl::ATTR_SCROLL); + gNJE.add(p->m_option); + gNJE.add(gMsgDir); + sprintf(buf, " Gone%ds", -diff); + gNJE.add(buf); + } else if(diff < 60) { + // 123456789012345678901234 (NJE-105) + // MM:HH Ê úgs c59b + printf("%02d:%02d Left%2dsec %s\n", p->m_hour, p->m_min, diff, p->m_option); + + sprintf(buf, "%02d:%02d", p->m_hour, p->m_min); + gNJE.add(buf); + gNJE.addAttr(NJE10XCtrl::ATTR_YELLOW, NJE10XCtrl::ATTR_SCROLL_R); + gNJE.add(p->m_option); + gNJE.add(gMsgDir); + gNJE.addAttr((diff<gMsgWarn)? NJE10XCtrl::ATTR_RED : NJE10XCtrl::ATTR_GREEN, NJE10XCtrl::ATTR_SCROLL_R); + gNJE.add(' '); + gNJE.add(gMsgLeft); + sprintf(buf, "%2d%s", diff, gMsgSec); + gNJE.add(buf); + } else { + // 123456789012345678901234 (NJE-105) + // MM:HHÊ úgs c01:23 + int diff_min = diff / 60; + int diff_sec = diff % 60; + printf("%02d:%02d Left%2d:%02d(%s)\n", p->m_hour, p->m_min, diff_min, diff_sec, p->m_option); + + sprintf(buf, "%02d:%02d", p->m_hour, p->m_min); + gNJE.add(buf); + gNJE.addAttr(NJE10XCtrl::ATTR_YELLOW, NJE10XCtrl::ATTR_SCROLL_R); + gNJE.add(p->m_option); + gNJE.add(gMsgDir); + gNJE.addAttr((diff<gMsgWarn)? NJE10XCtrl::ATTR_RED : NJE10XCtrl::ATTR_GREEN, NJE10XCtrl::ATTR_SCROLL_R); + gNJE.add(gMsgLeft); + sprintf(buf, "%2d:%02d", diff_min, diff_sec); + gNJE.add(buf); + } + + // delay + a1 = NJE10XCtrl::ATTR_GREEN; + int delay = 0; + if(gDelayStatus & S_DELAY){ + delay = 1; + a1 = NJE10XCtrl::ATTR_RED; + } else if(*gDelayMessage){ + if(diff % 60 < 3) delay = 1; + } + + if(delay) gNJE.setMessage(2, gDelayMessage, a1); + else gNJE.delMessage(2); + gNJE.setMessage(1, 0, a1, a2, a3); + +// if(delay) gNJE.setMessage(1, gDelayMessage); +// else gNJE.setMessage(1, 0, a1, a2, a3); +} + +void dispDelay(){ + if(++gDispMode > 10) gDispMode = 0; + if(gDispMode != 1){ + gNJE.delMessage(2); + return; + } + printf("%s\n", gDelayMessage); + gNJE.setMessage(2, gDelayMessage); +} + +void dispWait(){ + if(++gDispMode > 10) gDispMode = 0; + if(gDispMode != 1){ + return; + } + printf("Please wait...\n"); + gNJE.setMessage(1, "Please wait..."); +} + +void dispCB(){ +// if(gDelayStatus & S_DELAY){ +// dispDelay(); +// } else { + if(gDelayStatus & S_INFO_OK){ + dispTime(); + gDispMode = 0; + } else { + dispWait(); + } +// } +} + +//////////////////////////////////////////////////////////////////////////////// +// NextTrain & Delay information control +int updateNext(TrainInfo& train){ + printf("UpdateTrain\n"); + + // Next (and 2nd Next) train check + TickerLock(); + time_t now = time(0) + gTimeZone; + gSerchTime = now; + struct tm* st = localtime(&now); + for(int index = 0, offset = 0 ; index < 2; ++offset){ + NextTrainFile::Status ret = train.search(now, offset); + switch(ret){ + case NextTrainFile::S_SUCCESS: + if(train.next()->m_diff > gGiveupSec){ + gNext[index++] = *train.next(); + } + break; + + case NextTrainFile::S_NO_TRAIN: + gNext[index++].m_diff = -1; + break; + + default: + gNext[index++].m_diff = -2; + break; + } + } + gDelayStatus |= S_INFO_OK; + TickerUnlock(); + return 0; +} + +int updateDelay(TrainInfo& train){ + // Delay check + TrainInfo::Status ret = train.checkDelay(); + if(ret == TrainInfo::S_DELAY_DETECTED){ + TickerLock(); + train.getDelayMessage(gDelayMessage, sizeof(gDelayMessage)); + gDelayStatus |= S_DELAY; + TickerUnlock(); + } else { + TickerLock(); + train.getDelayMessage(gDelayMessage, sizeof(gDelayMessage)); // copy for testing... + gDelayStatus &= ~S_DELAY; + TickerUnlock(); + } + return 0; +} + +int updateAll(){ + TrainInfo train; + + if(train.open(INI_FILE)){ + printf("Can't open INI file '%s'\n", INI_FILE); + return 1; + } + updateNext (train); + updateDelay(train); + return 0; +} + +//////////////////////////////////////////////////////////////////////////////// +// Configuration and Startup +int setupParams(const char* inifile){ + char ntpserver[100] = "ntp.jst.mfeed.ad.jp"; + int ntpport = 123; + + const IniFile::IniList INI_PARAM_LIST[] = { + INIFILE_INT("GiveupSec", gGiveupSec), + INIFILE_STR("NTPServer", ntpserver, sizeof(ntpserver)), + INIFILE_INT("NTPPort", ntpport), + INIFILE_INT("TimeZone", gTimeZone), + + INIFILE_STR("MsgNoTrain", gMsgNoTrain, sizeof(gMsgNoTrain)), + INIFILE_STR("MsgLeft", gMsgLeft, sizeof(gMsgLeft)), + INIFILE_STR("MsgDir", gMsgDir, sizeof(gMsgDir)), + INIFILE_STR("MsgSec", gMsgSec, sizeof(gMsgSec)), + + INIFILE_INT("MsgWarn", gMsgWarn), + + INIFILE_END, + }; + + IniFile::getval(inifile, INI_PARAM_LIST); + gTimeZone *= 60; + + // Init NJE + gNJE.setScrollSpeed(NJE10XCtrl::ScrollSpeed(NJE10XCtrl::SCROLL_FAST)); + //gNJE.setBlinkSpeed(NJE10XCtrl::BlinkSpeed(NJE10XCtrl::BLINK_FAST)); + gNJE.setStopTime(1); + gNJE.setMessage(1, "Please wait..."); + + + // Init RTC + UpdateRTC(ntpserver, ntpport, gTimeZone); + return 0; +} + +int main(){ + setupParams(INI_FILE); + Ticker dispTicker; + dispTicker.attach(dispCB, 1); // 1 update per sec + + for(;;){ + printf("Update information\n"); + if(updateAll()) break; + + // Free LocalFileSystem before waiting. + // (For access file via USB) + wait(60); + } + dispTicker.detach(); + printf("Program end\n"); + return 0; +}