diff --git a/RUNNING.md b/RUNNING.md index 93263b84..f3879a0e 100644 --- a/RUNNING.md +++ b/RUNNING.md @@ -6,13 +6,21 @@ All you will need is an ssh client to connect to the FreeBSD server (currently n ### Obtaining an account and logging in -Request an account by email to travmap@teresco.org. We will select a username and you can set a password when you first log in. To connect with PuTTY from Windows, run the "PuTTY" program (not pscp or WinSCP). You will create a new connection and enter `noreaster.teresco.org` in the host name, and the port number that you will be given with your account information (we run `sshd` on a nonstandard port to enhance security, so please don't publicize it). You will be prompted for your username and password. From a Mac Terminal or other Unix-like command-line environment, you will connect with +Request an account by email to travmap@teresco.org. We will select a username and you can set a password when you first log in. You will also be given a port number to specify with your Secure Shell (ssh) connection. We run `sshd` on a nonstandard port to enhance security, so please don't publicize it. + +#### For Windows users + +To connect with PuTTY from Windows, run the "PuTTY" program (not pscp or WinSCP). You will create a new connection and enter `noreaster.teresco.org` in the host name, and the port number that you will be given with your account information. You will be prompted for your username and password. + +#### For Mac, Linux, and other Unix-like system users + +From a Mac Terminal (which you can launch by searching for it by name with Spotlight) or other Unix-like command-line environment, you will connect with ``` ssh -l username -p portnum noreaster.teresco.org ``` -Where you would replace "username" with your assigned username, and "portnum" with the number you are given with your account information. +Where you would replace "username" with your assigned username, and "portnum" with the number you will be given with your account information. ### First time setup @@ -38,7 +46,9 @@ If all were successful, you should now have copies of each of the repositories i ### Running the site update code in "highway data check mode" -At this time, will run the site update program in "highway data check mode". Since for checking highway data updates, it is not necessary to complete a few parts of the process nor is it necessary to generate the large SQL file that would populate the database, the program should be run with the `-e` flag. A script called `datacheck.sh` has been provided that will run this program with appropriate parameters, and it will make sure your `HighwayData` and `UserData` repositories are up to date as well. +The above is only needed on the initial setup. Everything from here on is what you'll do every time you want to perform a data check before issuing a pull request to bring your changes into the master. + +At this time, run the site update program in "highway data check mode". Since for checking highway data updates, it is not necessary to complete a few parts of the process nor is it necessary to generate the large SQL file that would populate the database, the program should be run with the `-e` flag. A script called `datacheck.sh` has been provided that will run this program with appropriate parameters, and it will make sure your `HighwayData` and `UserData` repositories are up to date as well. To run it, you will enter the following at your $ prompt: diff --git a/siteupdate/python-teresco/siteupdate.py b/siteupdate/python-teresco/siteupdate.py index cf2ee65b..3947cfe6 100755 --- a/siteupdate/python-teresco/siteupdate.py +++ b/siteupdate/python-teresco/siteupdate.py @@ -2153,8 +2153,8 @@ def run(self): nmpfpfile = open(args.highwaydatapath+'/nmpfps.log','r') nmpfilelines = nmpfpfile.readlines() for line in nmpfilelines: - if len(line.rstrip('\n')) > 0: - nmpfplist.append(line.rstrip('\n')) + if len(line.rstrip('\n ')) > 0: + nmpfplist.append(line.rstrip('\n ')) nmpfpfile.close() nmpfile = open(args.logfilepath+'/nearmisspoints.log','w') @@ -2163,7 +2163,12 @@ def run(self): if w.near_miss_points is not None: nmpline = str(w) + " NMP " nmplooksintentional = False - for other_w in w.near_miss_points: + nmpnmplines = [] + # sort the near miss points for consistent ordering to facilitate + # NMP FP marking + for other_w in sorted(w.near_miss_points, + key=lambda waypoint: + waypoint.route.root + "@" + waypoint.label): if (abs(w.lat - other_w.lat) < 0.0000015) and \ (abs(w.lng - other_w.lng) < 0.0000015): nmplooksintentional = True @@ -2173,21 +2178,39 @@ def run(self): # make sure we only plot once, since the NMP should be listed # both ways (other_w in w's list, w in other_w's list) if w_label < other_label: - nmpnmp.write(w_label + " " + str(w.lat) + " " + str(w.lng) + "\n") - nmpnmp.write(other_label + " " + str(other_w.lat) + " " + str(other_w.lng) + "\n") + nmpnmplines.append(w_label + " " + str(w.lat) + " " + str(w.lng)) + nmpnmplines.append(other_label + " " + str(other_w.lat) + " " + str(other_w.lng)) # indicate if this was in the FP list or if it's off by exact amt # so looks like it's intentional, and detach near_miss_points list # so it doesn't get a rewrite - if nmpline in nmpfplist: + # also set the extra field to mark FP/LI items in the .nmp file + extra_field = "" + if nmpline.rstrip() in nmpfplist: + nmpfplist.remove(nmpline.rstrip()) nmpline += "[MARKED FP]" w.near_miss_points = None + extra_field += "FP" if nmplooksintentional: nmpline += "[LOOKS INTENTIONAL]" w.near_miss_points = None - nmpfile.write(nmpline + '\n') + extra_field += "LI" + if extra_field != "": + extra_field = " " + extra_field + nmpfile.write(nmpline.rstrip() + '\n') + + # write actual lines to nmp file, indicating FP and/or LI + # for marked FPs or looks intentional items + for nmpnmpline in nmpnmplines: + nmpnmp.write(nmpnmpline + extra_field + "\n") nmpfile.close() nmpnmp.close() +# report any unmatched nmpfps.log entries +nmpfpsunmatchedfile = open(args.logfilepath+'/nmpfpsunmatched.log','w') +for line in nmpfplist: + nmpfpsunmatchedfile.write(line + '\n') +nmpfpsunmatchedfile.close() + # if requested, rewrite data with near-miss points merged in if args.nmpmergepath != "" and not args.errorcheck: print(et.et() + "Writing near-miss point merged wpt files.", flush=True) diff --git a/tmg2html/README.md b/tmg2html/README.md new file mode 100644 index 00000000..98859e6a --- /dev/null +++ b/tmg2html/README.md @@ -0,0 +1,27 @@ +# tmg2html +From yakra/tmtools/tmg2html.
+The "official" version can be found at [this link](https://github.com/yakra/tmtools/tree/master/tmg2html). +
+ +**Purpose:**
+Converts a .tmg [graph](http://travelmapping.net/graphs/) file into a web page with a Javascript "HDX-Lite" implementation using the HTML5 \ tag.
+This can be used to check concurrencies and NMPs, without having to deal with the slowdown Leaflet experiences with larger datasets in the full [HDX](http://courses.teresco.org/metal/hdx/) implementation. + +**Compiling:**
+C++11 support is required.
+With GCC, I use the commandline `g++ tmg2html.cpp -o tmg2html -std=c++11`
+tmg2html.cpp is all you need; no other files from the `tmtools` repository are required. + +**Commandline:**
+`tmg2html ` + +**Web page interface:** +* Pan by using the arrow keys, or double-clicking or dragging the map. +* Zoom by using the mouse wheel, or the `+` or `-` keys or buttons. +* Clicking a vertex or edge on the map will highlight it and display its info. +* Clicking a vertex or edge in the table will highlight & pan to it, and display its info. + +**Compatibility:**
+* **Firefox** is recommended. +* **Chrome & Chromium:** Rendering & redrawing the map, or getting results after clicking a vertex or edge are considerably slower, especially with larger data sets or more data on screen. +* **Other browsers** have not been tested. diff --git a/tmg2html/tmg2html.cpp b/tmg2html/tmg2html.cpp new file mode 100644 index 00000000..94381bce --- /dev/null +++ b/tmg2html/tmg2html.cpp @@ -0,0 +1,611 @@ +#include +#include +#include +#include +#include +using namespace std; + +class vertex +{ public: + string label; + double lat, lon; + + vertex(string &ConstLine) + { char *line = new char[ConstLine.size()+1]; + strcpy(line, ConstLine.data()); + label = strtok(line, " "); + lat = stod(strtok(0, " ")); + lon = stod(strtok(0, " ")); + } +}; + +class edge +{ public: + unsigned int BegI, EndI, qty; + vertex *BegP, *EndP; + char *label; + vector shape; + + edge(string &ConstLine, vertex **vertices) + { char *line = new char[ConstLine.size()+1]; + strcpy(line, ConstLine.data()); + BegI = stoi(strtok(line, " ")); BegP = vertices[BegI]; + EndI = stoi(strtok(0, " ")); EndP = vertices[EndI]; + label = strtok(0, " "); + for (char *val = strtok(0, " "); val; val = strtok(0, " ")) + { shape.push_back(stod(val)); + } + qty = 1; + for (char *comma = strchr(label, ','); comma; qty++) comma = strchr(comma+1, ','); + } +}; + +int main(int argc, char *argv[]) +{ ifstream tmg(argv[1]); + if (argc < 3) { cout << "usage: ./tmg2html \n"; return 0; } + if (!tmg) { cout << argv[1] << " not found.\n"; return 0; } + + const char *filename = &argv[1][string(argv[1]).find_last_of("/\\")+1]; + + unsigned int NumVertices, NumEdges; + string tmgline; + getline(tmg, tmgline); + if (tmgline.substr(0, 7) != "TMG 1.0") { cout << '\"' << tmgline << "\" unsupported.\n"; return 0; } + tmg >> NumVertices; + tmg >> NumEdges; + vertex **vertices = new vertex*[NumVertices]; + edge **edges = new edge*[NumEdges]; + getline(tmg, tmgline); // seek to end of NumVertices, NumEdges line + + // read vertices + for (unsigned int i = 0; i < NumVertices; i++) + { getline(tmg, tmgline); + vertices[i] = new vertex(tmgline); + //cout << vertices[i]->label << ' ' << to_string(vertices[i]->lat) << ' ' << to_string(vertices[i]->lon) << '\n'; + } + + // read edges + for (unsigned int i = 0; i < NumEdges; i++) + { getline(tmg, tmgline); + edges[i] = new edge(tmgline, vertices); + /*cout << edges[i]->BegI << ' ' << edges[i]->EndI << ' ' << edges[i]->label; + for (unsigned int j = 0; j < edges[i]->shape.size(); j++) cout << ' ' << edges[i]->shape[j]; + cout << '\n';//*/ + } + + // HTML output + ofstream html(argv[2]); + + // html elements + html << "\n"; + html << "\n"; + html << "\n"; + html << " \n"; + html << " yakra's HDX-Lite: " << filename << "\n"; + html << " \n"; + html << "\n"; + html << "\n"; + html << "\n"; + html << "\n"; + html << "\n"; + html << "(To see Map, upgrade browser.)\n"; + html << "\n"; + html << "\n"; + html << "


\n"; + html << "
\n"; + html << "+\n"; + html << "-\n"; + html << "\n"; + html << "Reset\n"; + html << "\n"; + html << "
\n"; + html << "\n"; + html << "
\n"; + html << "\n"; + html << "\n"; + html << "\n"; + html << "
Info\n"; + html << " X
\n"; + html << "
\n"; + html << "\n"; + html << "\n"; + html << "\n"; + html << "\n"; +}