📄 gpsdata.cpp
字号:
tIter->writeXML(stream); stream<<"</gpx>\n"; stream<<flush;}GPSData* GPSData::getData(const QString& filename) { // if the data isn't there already, try to load it if (dataObjects.find(filename) == dataObjects.end()) { QFile file(filename); if (!file.open(QIODevice::ReadOnly)) { QgsLogger::warning(QObject::tr("Couldn't open the data source: ") + filename); return 0; } GPSData* data = new GPSData; QgsLogger::debug("Loading file " + filename); GPXHandler handler(*data); bool failed = false; // SAX parsing XML_Parser p = XML_ParserCreate(NULL); XML_SetUserData(p, &handler); XML_SetElementHandler(p, GPXHandler::start, GPXHandler::end); XML_SetCharacterDataHandler(p, GPXHandler::chars); long int bufsize = 10*1024*1024; char* buffer = new char[bufsize]; int atEnd = 0; while (!file.atEnd()) { long int readBytes = file.readBlock(buffer, bufsize); if (file.atEnd()) atEnd = 1; if (!XML_Parse(p, buffer, readBytes, atEnd)) { QgsLogger::warning(QObject::tr("Parse error at line ") + QString("%1").arg(XML_GetCurrentLineNumber(p)) + " : " + QString(XML_ErrorString(XML_GetErrorCode(p)))); failed = true; break; } } delete [] buffer; XML_ParserFree(p); if (failed) return 0; data->setNoDataExtent(); dataObjects[filename] = std::pair<GPSData*, unsigned>(data, 0); } else QgsLogger::debug(filename + " is already loaded"); // return a pointer and increase the reference count for that filename DataMap::iterator iter = dataObjects.find(filename); ++(iter->second.second); return (GPSData*)(iter->second.first);}void GPSData::releaseData(const QString& filename) { /* decrease the reference count for the filename (if it is used), and erase it if the reference count becomes 0 */ DataMap::iterator iter = dataObjects.find(filename); if (iter != dataObjects.end()) { QgsLogger::debug("unrefing " + filename); if (--(iter->second.second) == 0) { QgsLogger::debug("No one's using " + filename + ", I'll erase it"); delete iter->second.first; dataObjects.erase(iter); } }}// we have to initialize the static memberGPSData::DataMap GPSData::dataObjects;bool GPXHandler::startElement(const XML_Char* qName, const XML_Char** attr) { if (!std::strcmp(qName, "gpx")) { parseModes.push(ParsingDocument); mData = GPSData(); } // top level objects else if (!std::strcmp(qName, "wpt")) { parseModes.push(ParsingWaypoint); mWpt = Waypoint(); for (int i = 0; attr[2*i] != NULL; ++i) { if (!std::strcmp(attr[2*i], "lat")) mWpt.lat = QString(attr[2*i+1]).toDouble(); else if (!std::strcmp(attr[2*i], "lon")) mWpt.lon = QString(attr[2*i+1]).toDouble(); } mObj = &mWpt; } else if (!std::strcmp(qName, "rte")) { parseModes.push(ParsingRoute); mRte = Route(); mObj = &mRte; } else if (!std::strcmp(qName, "trk")) { parseModes.push(ParsingTrack); mTrk = Track(); mObj = &mTrk; } // common properties else if (!std::strcmp(qName, "name")) { if (parseModes.top() == ParsingWaypoint || parseModes.top() == ParsingRoute || parseModes.top() == ParsingTrack) { mString = &mObj->name; mCharBuffer = ""; parseModes.push(ParsingString); } else parseModes.push(ParsingUnknown); } else if (!std::strcmp(qName, "cmt")) { if (parseModes.top() == ParsingWaypoint || parseModes.top() == ParsingRoute || parseModes.top() == ParsingTrack) { mString = &mObj->cmt; mCharBuffer = ""; parseModes.push(ParsingString); } else parseModes.push(ParsingUnknown); } else if (!std::strcmp(qName, "desc")) { if (parseModes.top() == ParsingWaypoint || parseModes.top() == ParsingRoute || parseModes.top() == ParsingTrack) { mString = &mObj->desc; mCharBuffer = ""; parseModes.push(ParsingString); } else parseModes.push(ParsingUnknown); } else if (!std::strcmp(qName, "src")) { if (parseModes.top() == ParsingWaypoint || parseModes.top() == ParsingRoute || parseModes.top() == ParsingTrack) { mString = &mObj->src; mCharBuffer = ""; parseModes.push(ParsingString); } else parseModes.push(ParsingUnknown); } else if (!std::strcmp(qName, "url")) { if (parseModes.top() == ParsingWaypoint || parseModes.top() == ParsingRoute || parseModes.top() == ParsingTrack) { mString = &mObj->url; mCharBuffer = ""; parseModes.push(ParsingString); } else parseModes.push(ParsingUnknown); } else if (!std::strcmp(qName, "urlname")) { if (parseModes.top() == ParsingWaypoint || parseModes.top() == ParsingRoute || parseModes.top() == ParsingTrack) { mString = &mObj->urlname; mCharBuffer = ""; parseModes.push(ParsingString); } else parseModes.push(ParsingUnknown); } // waypoint-specific attributes else if (!std::strcmp(qName, "ele")) { if (parseModes.top() == ParsingWaypoint) { mDouble = &mWpt.ele; mCharBuffer = ""; parseModes.push(ParsingDouble); } else parseModes.push(ParsingUnknown); } else if (!std::strcmp(qName, "sym")) { if (parseModes.top() == ParsingWaypoint) { mString = &mWpt.sym; mCharBuffer = ""; parseModes.push(ParsingString); } else parseModes.push(ParsingUnknown); } // route/track-specific attributes else if (!std::strcmp(qName, "number")) { if (parseModes.top() == ParsingRoute) { mInt = &mRte.number; mCharBuffer = ""; parseModes.push(ParsingInt); } else if (parseModes.top() == ParsingTrack) { mInt = &mTrk.number; parseModes.push(ParsingInt); } else parseModes.push(ParsingUnknown); } // route points else if (!std::strcmp(qName, "rtept")) { if (parseModes.top() == ParsingRoute) { mRtept = Routepoint(); for (int i = 0; attr[2*i] != NULL; ++i) { if (!std::strcmp(attr[2*i], "lat")) mRtept.lat = QString(attr[2*i+1]).toDouble(); else if (!std::strcmp(attr[2*i], "lon")) mRtept.lon = QString(attr[2*i+1]).toDouble(); } parseModes.push(ParsingRoutepoint); } else parseModes.push(ParsingUnknown); } // track segments and points else if (!std::strcmp(qName, "trkseg")) { if (parseModes.top() == ParsingTrack) { mTrkseg = TrackSegment(); parseModes.push(ParsingTrackSegment); } else parseModes.push(ParsingUnknown); } else if (!std::strcmp(qName, "trkpt")) { if (parseModes.top() == ParsingTrackSegment) { mTrkpt = Trackpoint(); for (int i = 0; attr[2*i] != NULL; ++i) { if (!std::strcmp(attr[2*i], "lat")) mTrkpt.lat = QString(attr[2*i+1]).toDouble(); else if (!std::strcmp(attr[2*i], "lon")) mTrkpt.lon = QString(attr[2*i+1]).toDouble(); } parseModes.push(ParsingTrackpoint); } else parseModes.push(ParsingUnknown); } // unknown else parseModes.push(ParsingUnknown); return true;}void GPXHandler::characters(const XML_Char* chars, int len) { // This is horrible.#ifdef XML_UNICODE for (int i = 0; i < len; ++i) mCharBuffer += QChar(chars[i]);#else mCharBuffer += QString::fromUtf8(chars, len);#endif}bool GPXHandler::endElement(const std::string& qName) { if (parseModes.top() == ParsingWaypoint) { mData.addWaypoint(mWpt); } else if (parseModes.top() == ParsingRoute) { mData.addRoute(mRte); } else if (parseModes.top() == ParsingTrack) { mData.addTrack(mTrk); } else if (parseModes.top() == ParsingRoutepoint) { mRte.points.push_back(mRtept); mRte.xMin = (mRte.xMin < mRtept.lon ? mRte.xMin : mRtept.lon); mRte.xMax = (mRte.xMax > mRtept.lon ? mRte.xMax : mRtept.lon); mRte.yMin = (mRte.yMin < mRtept.lat ? mRte.yMin : mRtept.lat); mRte.yMax = (mRte.yMax > mRtept.lat ? mRte.yMax : mRtept.lat); } else if (parseModes.top() == ParsingTrackSegment) { mTrk.segments.push_back(mTrkseg); } else if (parseModes.top() == ParsingTrackpoint) { mTrkseg.points.push_back(mTrkpt); mTrk.xMin = (mTrk.xMin < mTrkpt.lon ? mTrk.xMin : mTrkpt.lon); mTrk.xMax = (mTrk.xMax > mTrkpt.lon ? mTrk.xMax : mTrkpt.lon); mTrk.yMin = (mTrk.yMin < mTrkpt.lat ? mTrk.yMin : mTrkpt.lat); mTrk.yMax = (mTrk.yMax > mTrkpt.lat ? mTrk.yMax : mTrkpt.lat); } else if (parseModes.top() == ParsingDouble) { *mDouble = QString(mCharBuffer).toDouble(); mCharBuffer = ""; } else if (parseModes.top() == ParsingInt) { *mInt = QString(mCharBuffer).toInt(); mCharBuffer = ""; } else if (parseModes.top() == ParsingString) { *mString = mCharBuffer; mCharBuffer = ""; } parseModes.pop(); return true;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -