WME PlaceNames

Show area place names in WME, color and highlight places by type and properties

目前為 2014-10-28 提交的版本,檢視 最新版本

  1. // ==UserScript==
  2. // @name WME PlaceNames
  3. // @version 0.1
  4. // @description Show area place names in WME, color and highlight places by type and properties
  5. // @include https://www.waze.com/editor/*
  6. // @include https://www.waze.com/*/editor/*
  7. // @include https://editor-beta.waze.com/editor/*
  8. // @include https://editor-beta.waze.com/*/editor/*
  9. // @copyright 2014, ragacs
  10. // @namespace https://gf.qytechs.cn/users/6330
  11. // ==/UserScript==
  12.  
  13. var wmepn_version = "0.1"
  14.  
  15. // Using parts from highlight and route speed scripts by various authors
  16.  
  17. /* bootstrap, will call initialiseLandmarkNames() */
  18. function bootstrapLandmarkNames()
  19. {
  20. var bGreasemonkeyServiceDefined = false;
  21.  
  22. try {
  23. bGreasemonkeyServiceDefined = (typeof Components.interfaces.gmIGreasemonkeyService === "object");
  24. }
  25. catch (err) { /* Ignore */ }
  26.  
  27. if (typeof unsafeWindow === "undefined" || ! bGreasemonkeyServiceDefined) {
  28. unsafeWindow = ( function () {
  29. var dummyElem = document.createElement('p');
  30. dummyElem.setAttribute('onclick', 'return window;');
  31. return dummyElem.onclick();
  32. }) ();
  33. }
  34.  
  35. /* begin running the code! */
  36. setTimeout(initialiseLandmarkNames, 999);
  37. }
  38.  
  39. function testWhite(x) {
  40. var white = new RegExp(/^\s$/);
  41. return white.test(x.charAt(0));
  42. };
  43.  
  44. function wordWrap(str, maxWidth) {
  45. var newLineStr = "\n"; done = false; res = '';
  46. do {
  47. found = false;
  48. // Inserts new line at first whitespace of the line
  49. for (i = maxWidth - 1; i >= 0; i--) {
  50. if (testWhite(str.charAt(i))) {
  51. res = res + [str.slice(0, i), newLineStr].join('');
  52. str = str.slice(i + 1);
  53. found = true;
  54. break;
  55. }
  56. }
  57. // Inserts new line at maxWidth position, the word is too long to wrap
  58. if (!found) {
  59. res += [str.slice(0, maxWidth), newLineStr].join('');
  60. str = str.slice(maxWidth);
  61. }
  62.  
  63. if (str.length < maxWidth)
  64. {
  65. res = res + str;
  66. done = true;
  67. }
  68. } while (!done);
  69.  
  70. return res;
  71. }
  72.  
  73. function resetLandmarks()
  74. {
  75. for (var mark in Waze.model.venues.objects) {
  76. var venue = Waze.model.venues.get(mark);
  77. var poly = getId(venue.geometry.id);
  78. if (poly !== null) {
  79. if (poly.getAttribute("stroke-opacity") != 1) {
  80. poly.setAttribute("fill","#d191d6");
  81. poly.setAttribute("stroke","#d191d6");
  82. poly.setAttribute("fill-opacity",0.3);
  83. poly.setAttribute("stroke-opacity",1);
  84. }
  85. }
  86. }
  87. showLandmarkNames();
  88. }
  89.  
  90. function showLandmarkNames() {
  91. var routeLayer = undefined;
  92. var rlayers = unsafeWindow.Waze.map.getLayersBy("uniqueName","__DrawPlaceNames");
  93. if(rlayers.length == 0) {
  94. var drc_style1 = new unsafeWindow.OpenLayers.Style({
  95. strokeDashstyle: 'solid',
  96. strokeColor : "${strokeColor}",
  97. strokeOpacity: 1.0,
  98. strokeWidth: "${strokeWidth}",
  99. fillColor: '#0040FF',
  100. fillOpacity: 1.0,
  101. pointRadius: "${pointRadius}",
  102. label : "${labelText}",
  103. fontFamily: "Tahoma, Courier New",
  104. labelOutlineColor: '#FFEEEE',
  105. labelOutlineWidth: 2,
  106. labelAlign: 'cm',
  107. fontColor: "#301130",
  108. fontOpacity: 1.0,
  109. fontSize: "11px",
  110. display: 'block'
  111. });
  112. var drc_mapLayer1 = new unsafeWindow.OpenLayers.Layer.Vector("Place Names", {
  113. displayInLayerSwitcher: true,
  114. uniqueName: "__DrawPlaceNames",
  115. styleMap: new unsafeWindow.OpenLayers.StyleMap(drc_style1)
  116. });
  117. drc_mapLayer1.setVisibility(true);
  118. //drc_mapLayer1.moveLayerToTop();
  119. unsafeWindow.Waze.map.addLayer(drc_mapLayer1);
  120. //var zLandmarks = Waze.map.getLayersBy("uniqueName", "landmarks")[0].getZIndex();
  121. //var zPlaceNames = drc_mapLayer1.getZIndex();
  122. //Waze.map.getLayersBy("uniqueName", "landmarks")[0].setZIndex(zPlaceNames);
  123. //drc_mapLayer1.setZIndex(zLandmarks);
  124. routeLayer = drc_mapLayer1;
  125. }
  126. else routeLayer = rlayers[0];
  127. routeLayer.removeAllFeatures();
  128. if (typeof Waze.model.venues == "undefined") {
  129. return;
  130. }
  131.  
  132. var showNames = routeLayer.getVisibility() && Waze.map.getLayersBy("uniqueName", "landmarks")[0].getVisibility();
  133. // if checkbox unticked, reset places to original style
  134. if (!showNames
  135. && !getId('_cbLandmarkColors').checked
  136. && !getId('_cbLandmarkHiliteNoName').checked) {
  137. for (var mark in Waze.model.venues.objects) {
  138. var venue = Waze.model.venues.get(mark);
  139. var poly = getId(venue.geometry.id);
  140. if (poly !== null) {
  141. if (poly.getAttribute("stroke-opacity") != 1) {
  142. poly.setAttribute("fill","#d191d6");
  143. poly.setAttribute("stroke","#d191d6");
  144. poly.setAttribute("fill-opacity",0.3);
  145. poly.setAttribute("stroke-opacity",1);
  146. }
  147. }
  148. }
  149. return;
  150. }
  151.  
  152. var specificCity = getId('_cbLandmarkHiliteNoName').checked;
  153. var colorLandmarks = getId('_cbLandmarkColors').checked;
  154. //var routeLayer = unsafeWindow.Waze.map.getLayersBy("uniqueName","landmarks")[0];
  155. //routeLayer.styleMap.styles.default = drc_style1;
  156.  
  157. for (var mark in Waze.model.venues.objects) {
  158. var venue = Waze.model.venues.get(mark);
  159. var poly = getId(venue.geometry.id);
  160. if (poly !== null && venue.geometry.toString().match(/^POLYGON/)) {
  161. venueStreet = Waze.model.streets.get(venue.attributes.streetID);
  162. selectedCityMatch = (venue.attributes.name.length == 0);
  163.  
  164. if(showNames && venue.attributes.name.length > 0)
  165. {
  166. // Add label texts
  167. var labelFeatures = [];
  168. var pt = new OpenLayers.Geometry.Point((venue.geometry.bounds.left + venue.geometry.bounds.right)/2, (venue.geometry.bounds.top + venue.geometry.bounds.bottom)/2);
  169. var closest =_.min(routeLayer.features, function(feature) {
  170. return feature.geometry.distanceTo(pt);
  171. });
  172. //console.log(closest);
  173. var wrappedText = wordWrap(venue.attributes.name, 30);
  174. var textFeature = new OpenLayers.Feature.Vector( pt, {labelText: wrappedText, fontColor: '#F0F0F0', pointRadius: 0 } );
  175. labelFeatures.push(textFeature);
  176. routeLayer.addFeatures(labelFeatures);
  177. //if(closest != Infinity && closest.geometry.bounds.intersectsBounds(textFeature.geometry.bounds))
  178. //{
  179. // routeLayer.removeFeatures(labelFeatures);
  180. //}
  181. }
  182. // Production polygons: #d191d6, Beta editor polygons: #c290c6
  183. if ((poly.getAttribute("fill") == "#d191d6" || poly.getAttribute("fill") == "#c290c6") && poly.getAttribute("stroke-opacity") == 1) {
  184. var categories = venue.attributes.categories;
  185.  
  186. if(colorLandmarks)
  187. {
  188. // gas station = orange
  189. if (categories.indexOf("GAS_STATION") > -1) {
  190. poly.setAttribute("fill","#f90");
  191. poly.setAttribute("stroke","#f90");
  192. }
  193. // parking lot = cyan
  194. else if (categories.indexOf("PARKING_LOT") > -1) {
  195. poly.setAttribute("fill","#099");
  196. poly.setAttribute("stroke","#0cc");
  197. }
  198. // water = blue
  199. else if (categories.indexOf("RIVER_STREAM") > -1 ||
  200. categories.indexOf("SEA_LAKE_POOL") > -1) {
  201. poly.setAttribute("fill","#09f");
  202. poly.setAttribute("stroke","#06c");
  203. }
  204. // park/grass/trees = green
  205. else if (categories.indexOf("PARK") > -1 ||
  206. categories.indexOf("FARM") > -1 ||
  207. categories.indexOf("FOREST_GROVE") > -1 ||
  208. categories.indexOf("GOLF_COURSE") > -1) {
  209. poly.setAttribute("fill","#4f4");
  210. poly.setAttribute("stroke","#6a6");
  211. }
  212. }
  213.  
  214. poly.setAttribute("stroke-opacity",0.97);
  215. // highlight places which have no name
  216. if (poly.getAttribute("fill") == "#d191d6" || poly.getAttribute("fill") == "#c290c6") {
  217. if (specificCity && selectedCityMatch) {
  218. poly.setAttribute("fill","#ff8");
  219. poly.setAttribute("stroke","#cc0");
  220. }
  221. }
  222. // if was yellow and now not yellow, reset
  223. else if (poly.getAttribute("fill") == "#ff8" && (!specificCity || !selectedCityMatch)) {
  224. poly.setAttribute("fill","#d191d6");
  225. poly.setAttribute("stroke","#d191d6");
  226. poly.setAttribute("stroke-opacity",1);
  227. }
  228. }
  229. }
  230. }
  231. }
  232.  
  233. function toggleOptions () {
  234. return false;
  235. }
  236.  
  237. /* helper function */
  238. function getElementsByClassName(classname, node) {
  239. if(!node) node = document.getElementsByTagName("body")[0];
  240. var a = [];
  241. var re = new RegExp('\\b' + classname + '\\b');
  242. var els = node.getElementsByTagName("*");
  243. for (var i=0,j=els.length; i<j; i++)
  244. if (re.test(els[i].className)) a.push(els[i]);
  245. return a;
  246. }
  247.  
  248. function getId(node) {
  249. return document.getElementById(node);
  250. }
  251.  
  252. /* =========================================================================== */
  253.  
  254. function initialiseLandmarkNames()
  255. {
  256. // global variables
  257. advancedMode = false;
  258. betaMode = location.hostname.match(/editor-beta.waze.com/);
  259. lastSelected = null;
  260. lastModified = false;
  261. selectedLines = [];
  262.  
  263. // add new box to left of the map
  264. var addon = document.createElement('section');
  265. addon.id = "landmarkname-addon";
  266.  
  267. if (navigator.userAgent.match(/Chrome/)) {
  268. addon.innerHTML = '<b>'
  269. + 'WME PlaceNames</b> &nbsp; v' + wmepn_version;
  270. } else {
  271. addon.innerHTML = '<b>'
  272. + 'WME PlaceNames</b> &nbsp; v' + wmepn_version;
  273. }
  274.  
  275. // highlight landmarks
  276. section = document.createElement('p');
  277. section.style.padding = "8px 16px";
  278. //section.style.textIndent = "-16px";
  279. section.id = "nameLandmarks";
  280. section.innerHTML = '<input type="checkbox" id="_cbLandmarkColors" /> <b>Color places</b><br>'
  281. + '<input type="checkbox" id="_cbLandmarkHiliteNoName" /> <b>Highlight places without name</b><br>';
  282. addon.appendChild(section);
  283.  
  284. var userTabs = getId('user-info');
  285. var navTabs = getElementsByClassName('nav-tabs', userTabs)[0];
  286. var tabContent = getElementsByClassName('tab-content', userTabs)[0];
  287.  
  288. newtab = document.createElement('li');
  289. newtab.innerHTML = '<a href="#sidepanel-landmarknames" data-toggle="tab">PlaceNames</a>';
  290. navTabs.appendChild(newtab);
  291.  
  292. addon.id = "sidepanel-landmarknames";
  293. addon.className = "tab-pane";
  294. tabContent.appendChild(addon);
  295.  
  296. // setup onclick handlers for instant update:
  297. getId('_cbLandmarkColors').onclick = resetLandmarks;
  298. getId('_cbLandmarkHiliteNoName').onclick = resetLandmarks;
  299.  
  300. // restore saved settings
  301. if (localStorage.WMELandmarkNamesScript) {
  302. console.log("WME LandmarkNames: loading options");
  303. options = JSON.parse(localStorage.WMELandmarkNamesScript);
  304.  
  305. getId('_cbLandmarkColors').checked = options[1];
  306. getId('_cbLandmarkHiliteNoName').checked = options[2];
  307. } else {
  308. getId('_cbLandmarkColors').checked = true;
  309. getId('_cbLandmarkHiliteNoName').checked = true;
  310. }
  311.  
  312. if (typeof Waze.model.venues == "undefined") {
  313. getId('_cbLandmarkColors').checked = false;
  314. getId('_cbLandmarkHiliteNoName').checked = false;
  315. getId('_cbLandmarkColors').disabled = true;
  316. getId('_cbLandmarkHiliteNoName').disabled = true;
  317. }
  318.  
  319. // overload the WME exit function
  320. saveLandmarkNamesOptions = function() {
  321. if (localStorage) {
  322. console.log("WME LandmarkNames: saving options");
  323. var options = [];
  324.  
  325. // preserve previous options which may get lost after logout
  326. if (localStorage.WMELandmarkNamesScript)
  327. options = JSON.parse(localStorage.WMELandmarkNamesScript);
  328. options[1] = getId('_cbLandmarkColors').checked;
  329. options[2] = getId('_cbLandmarkHiliteNoName').checked;
  330. localStorage.WMELandmarkNamesScript = JSON.stringify(options);
  331. }
  332. }
  333. window.addEventListener("beforeunload", saveLandmarkNamesOptions, false);
  334.  
  335. // begin periodic updates
  336. window.setInterval(showLandmarkNames,500);
  337.  
  338. // trigger code when page is fully loaded, to catch any missing bits
  339. window.addEventListener("load", function(e) {
  340. var mapProblems = getId('map-problems-explanation')
  341. if (mapProblems !== null) mapProblems.style.display = "none";
  342. });
  343.  
  344. // register some events...
  345. Waze.map.events.register("zoomend", null, showLandmarkNames);
  346. Waze.map.events.register("changelayer", null, showLandmarkNames);
  347. }
  348.  
  349. /* engage! =================================================================== */
  350. bootstrapLandmarkNames();
  351.  
  352. /* end ======================================================================= */

QingJ © 2025

镜像随时可能失效,请加Q群300939539或关注我们的公众号极客氢云获取最新地址