WME PlaceNames

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

Устаревшая версия за 12.11.2014. Перейдите к последней версии.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey, Greasemonkey или Violentmonkey.

Для установки этого скрипта вам необходимо установить расширение, такое как Tampermonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Violentmonkey.

Чтобы установить этот скрипт, вы сначала должны установить расширение браузера, например Tampermonkey или Userscripts.

Чтобы установить этот скрипт, сначала вы должны установить расширение браузера, например Tampermonkey.

Чтобы установить этот скрипт, вы должны установить расширение — менеджер скриптов.

(у меня уже есть менеджер скриптов, дайте мне установить скрипт!)

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение браузера, например Stylus.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

Чтобы установить этот стиль, сначала вы должны установить расширение — менеджер стилей.

(у меня уже есть менеджер стилей, дайте мне установить скрипт!)

// ==UserScript==
// @name       WME PlaceNames
// @version    0.3
// @description  Show area place names in WME, color and highlight places by type and properties
// @include             https://www.waze.com/editor/*
// @include             https://www.waze.com/*/editor/*
// @include             https://editor-beta.waze.com/editor/*
// @include             https://editor-beta.waze.com/*/editor/*
// @copyright  2014, ragacs
// @namespace https://greasyfork.org/users/6330
// ==/UserScript==

var wmepn_version = "0.3"

// Using parts from highlight and route speed scripts by various authors

/* bootstrap, will call initialiseLandmarkNames() */
function bootstrapLandmarkNames()
{
  var bGreasemonkeyServiceDefined = false;

  try {
    bGreasemonkeyServiceDefined = (typeof Components.interfaces.gmIGreasemonkeyService === "object");
  }
  catch (err) { /* Ignore */ }

  if (typeof unsafeWindow === "undefined" || ! bGreasemonkeyServiceDefined) {
    unsafeWindow    = ( function () {
      var dummyElem = document.createElement('p');
      dummyElem.setAttribute('onclick', 'return window;');
      return dummyElem.onclick();
    }) ();
  }

  /* begin running the code! */
  setTimeout(initialiseLandmarkNames, 999);
}

function testWhite(x) {
    var white = new RegExp(/^\s$/);
    return white.test(x.charAt(0));
};

function wordWrap(str, maxWidth) {
    var newLineStr = "\n"; done = false; res = '';
    do {                    
        found = false;
        // Inserts new line at first whitespace of the line
        for (i = maxWidth - 1; i >= 0; i--) {
            if (testWhite(str.charAt(i))) {
                res = res + [str.slice(0, i), newLineStr].join('');
                str = str.slice(i + 1);
                found = true;
                break;
            }
        }
        // Inserts new line at maxWidth position, the word is too long to wrap
        if (!found) {
            res += [str.slice(0, maxWidth), newLineStr].join('');
            str = str.slice(maxWidth);
        }

        if (str.length < maxWidth)
        {
            res = res + str;
            done = true;
        }
    } while (!done);

    return res;
}

function resetLandmarks()
{
    for (var mark in Waze.model.venues.objects) {
        var venue = Waze.model.venues.get(mark);
        var poly = getId(venue.geometry.id);
        if (poly !== null) {
            if (poly.getAttribute("stroke-opacity") != 1) {
                poly.setAttribute("fill","#d191d6");
                poly.setAttribute("stroke","#d191d6");
                poly.setAttribute("fill-opacity",0.3);
                poly.setAttribute("stroke-opacity",1);
            }
        }
    }
    showLandmarkNames();
}

function showLandmarkNames() {
	var routeLayer = undefined;
    var rlayers = unsafeWindow.Waze.map.getLayersBy("uniqueName","__DrawPlaceNames");
    if(rlayers.length == 0) {
        var lname = "Place Names";
        var drc_style1 = new unsafeWindow.OpenLayers.Style({
            strokeDashstyle: 'solid',
            strokeColor : "${strokeColor}",
            strokeOpacity: 1.0,
            strokeWidth: "${strokeWidth}",
            fillColor: '#0040FF',
            fillOpacity: 1.0,
            pointRadius: "${pointRadius}",
            label : "${labelText}",
            fontFamily: "Tahoma, Courier New",
            labelOutlineColor: '#FFEEEE',
            labelOutlineWidth: 2,
            labelAlign: 'cm',
            fontColor: "#301130",
            fontOpacity: 1.0,
            fontSize: "11px",
            display: 'block'
        });
        var drc_mapLayer1 = new unsafeWindow.OpenLayers.Layer.Vector(lname, {
            displayInLayerSwitcher: true,
            uniqueName: "__DrawPlaceNames",
            shortcutKey: "S+n",
			accelerator: "toggle" + lname.replace(/\s+/g,''),
            styleMap: new unsafeWindow.OpenLayers.StyleMap(drc_style1)
        });
        drc_mapLayer1.setVisibility(true);
        //drc_mapLayer1.moveLayerToTop();
        unsafeWindow.Waze.map.addLayer(drc_mapLayer1);
        //var zLandmarks = Waze.map.getLayersBy("uniqueName", "landmarks")[0].getZIndex();
        //var zPlaceNames = drc_mapLayer1.getZIndex();   
        //Waze.map.getLayersBy("uniqueName", "landmarks")[0].setZIndex(zPlaceNames);
        //drc_mapLayer1.setZIndex(zLandmarks);
        routeLayer = drc_mapLayer1;
    }
    else routeLayer = rlayers[0];
    routeLayer.removeAllFeatures();
    
  if (typeof Waze.model.venues == "undefined") {
    return;
  }

  var showNames = routeLayer.getVisibility() && Waze.map.getLayersBy("uniqueName", "landmarks")[0].getVisibility();
  // if checkbox unticked, reset places to original style
  if (!showNames
     && !getId('_cbLandmarkColors').checked
     && !getId('_cbLandmarkHiliteNoName').checked) {
    for (var mark in Waze.model.venues.objects) {
      var venue = Waze.model.venues.get(mark);
      var poly = getId(venue.geometry.id);
      if (poly !== null) {
        if (poly.getAttribute("stroke-opacity") != 1) {
          poly.setAttribute("fill","#d191d6");
          poly.setAttribute("stroke","#d191d6");
          poly.setAttribute("fill-opacity",0.3);
          poly.setAttribute("stroke-opacity",1);
        }
      }
    }
    return;
  }

  var specificCity = getId('_cbLandmarkHiliteNoName').checked;    
  var colorLandmarks = getId('_cbLandmarkColors').checked;
  var showPoints = (getId('_seLandmarkPoints').value == "all" || getId('_seLandmarkPoints').value == "point");
  var showAreas = (getId('_seLandmarkPoints').value == "all" || getId('_seLandmarkPoints').value == "area");
    //var routeLayer = unsafeWindow.Waze.map.getLayersBy("uniqueName","landmarks")[0];    
    //routeLayer.styleMap.styles.default = drc_style1;

  for (var mark in Waze.model.venues.objects) {
    var venue = Waze.model.venues.get(mark);
    var poly = getId(venue.geometry.id);
    if (poly !== null && venue.geometry.toString().match(/^POLYGON/)) {
      venueStreet = Waze.model.streets.get(venue.attributes.streetID);
      selectedCityMatch = (venue.attributes.name.length == 0);

        if(showNames && venue.attributes.name.length > 0 && showAreas)
        {            
            // Add label texts
            var labelFeatures = [];        
            var pt = new OpenLayers.Geometry.Point((venue.geometry.bounds.left + venue.geometry.bounds.right)/2, (venue.geometry.bounds.top + venue.geometry.bounds.bottom)/2);
            var closest =_.min(routeLayer.features, function(feature) {
                return feature.geometry.distanceTo(pt);
            });
            //console.log(closest);
            var wrappedText = wordWrap(venue.attributes.name, 30);
            var textFeature = new OpenLayers.Feature.Vector( pt, {labelText: wrappedText, fontColor: '#F0F0F0', pointRadius: 0 } );
            labelFeatures.push(textFeature);
            routeLayer.addFeatures(labelFeatures);        
            //if(closest != Infinity && closest.geometry.bounds.intersectsBounds(textFeature.geometry.bounds))
            //{
            //    routeLayer.removeFeatures(labelFeatures);
            //}
        }
        
        // Production polygons: #d191d6, Beta editor polygons: #c290c6
      if ((poly.getAttribute("fill") == "#d191d6" || poly.getAttribute("fill") == "#c290c6") && poly.getAttribute("stroke-opacity") == 1) {
        var categories   = venue.attributes.categories;

          if(colorLandmarks)
          {
              // gas station = orange
              if (categories.indexOf("GAS_STATION") > -1) {
                  poly.setAttribute("fill","#f90");
                  poly.setAttribute("stroke","#f90");
              }
              
              // parking lot = cyan
              else if (categories.indexOf("PARKING_LOT") > -1) {
                  poly.setAttribute("fill","#099");
                  poly.setAttribute("stroke","#0cc");
              }
                  
                  // water = blue
                  else if (categories.indexOf("RIVER_STREAM") > -1 ||
                           categories.indexOf("SEA_LAKE_POOL") > -1) {
                      poly.setAttribute("fill","#09f");
                      poly.setAttribute("stroke","#06c");
                  }
                  
                  // park/grass/trees = green
                  else if (categories.indexOf("PARK") > -1 ||
                           categories.indexOf("FARM") > -1 ||
                           categories.indexOf("FOREST_GROVE") > -1 ||
                           categories.indexOf("GOLF_COURSE") > -1) {
                      poly.setAttribute("fill","#4f4");
                      poly.setAttribute("stroke","#6a6");
                  }
        }

        poly.setAttribute("stroke-opacity",0.97);
          
          // highlight places which have no name
          if (poly.getAttribute("fill") == "#d191d6" || poly.getAttribute("fill") == "#c290c6") {
              if (specificCity && selectedCityMatch) {
                  poly.setAttribute("fill","#ff8");
                  poly.setAttribute("stroke","#cc0");
              }
          }
          // if was yellow and now not yellow, reset
          else if (poly.getAttribute("fill") == "#ff8" && (!specificCity || !selectedCityMatch)) {
              poly.setAttribute("fill","#d191d6");
              poly.setAttribute("stroke","#d191d6");
              poly.setAttribute("stroke-opacity",1);
          }        
      }
    }
    if(poly !== null && venue.geometry.toString().match(/^POINT/) && showPoints == true && showNames == true && venue.attributes.name.length > 0)
    {
        // Add label texts
        var labelFeatures = [];        
        var pt = new OpenLayers.Geometry.Point(venue.geometry.x, venue.geometry.y);
        var wrappedText = wordWrap(venue.attributes.name, 30);
        var textFeature = new OpenLayers.Feature.Vector( pt, {labelText: wrappedText, fontColor: '#F0F0F0', pointRadius: 0 } );
        labelFeatures.push(textFeature);
        routeLayer.addFeatures(labelFeatures);        
    }
  }
}

function toggleOptions () {
  return false;
}

/* helper function */
function getElementsByClassName(classname, node) {
  if(!node) node = document.getElementsByTagName("body")[0];
  var a = [];
  var re = new RegExp('\\b' + classname + '\\b');
  var els = node.getElementsByTagName("*");
  for (var i=0,j=els.length; i<j; i++)
    if (re.test(els[i].className)) a.push(els[i]);
  return a;
}

function getId(node) {
  return document.getElementById(node);
}

/* =========================================================================== */

function initialiseLandmarkNames()
{
  // global variables
  advancedMode = false;
  betaMode = location.hostname.match(/editor-beta.waze.com/);
  lastSelected = null;
  lastModified = false;
  selectedLines = [];

  // add new box to left of the map
  var addon = document.createElement('section');
  addon.id = "landmarkname-addon";

  if (navigator.userAgent.match(/Chrome/)) {
    addon.innerHTML  = '<b>'
                     + '<a href="https://www.waze.com/forum/viewtopic.php?f=819&t=116843" target="_blank">WME PlaceNames</a></b> &nbsp; v' + wmepn_version;
  } else {
    addon.innerHTML  = '<b>'
                     + '<a href="https://www.waze.com/forum/viewtopic.php?f=819&t=116843" target="_blank">WME PlaceNames</a></b> &nbsp; v' + wmepn_version;
  }

  // highlight landmarks
  section = document.createElement('p');
  section.style.padding = "8px 16px";
  //section.style.textIndent = "-16px";
  section.id = "nameLandmarks";
  section.innerHTML  = '<input type="checkbox" id="_cbLandmarkColors" /> <b>Color places</b><br>'
  					+  '<input type="checkbox" id="_cbLandmarkHiliteNoName" /> <b>Highlight places without name</b><br>'
  					+  '<b>Show</b> <select id="_seLandmarkPoints"> <option value="area">Area only</option><option value="all">Area and Point</option><option value="point">Point only</option><br>';
  addon.appendChild(section);

  var userTabs = getId('user-info');
  var navTabs = getElementsByClassName('nav-tabs', userTabs)[0];
  var tabContent = getElementsByClassName('tab-content', userTabs)[0];

  newtab = document.createElement('li');
  newtab.innerHTML = '<a href="#sidepanel-landmarknames" data-toggle="tab">PlaceNames</a>';
  navTabs.appendChild(newtab);

  addon.id = "sidepanel-landmarknames";
  addon.className = "tab-pane";
  tabContent.appendChild(addon);

  // setup onclick handlers for instant update:
    getId('_cbLandmarkColors').onclick = resetLandmarks;
    getId('_cbLandmarkHiliteNoName').onclick = resetLandmarks;
    getId('_seLandmarkPoints').onchange = resetLandmarks;

  // restore saved settings
  if (localStorage.WMELandmarkNamesScript) {
    console.log("WME LandmarkNames: loading options");
    options = JSON.parse(localStorage.WMELandmarkNamesScript);

    getId('_cbLandmarkColors').checked   	    = options[1];
    getId('_cbLandmarkHiliteNoName').checked    = options[2];
    getId('_seLandmarkPoints').value    		= options[3];
  } else {
    getId('_cbLandmarkColors').checked = true;
    getId('_cbLandmarkHiliteNoName').checked = true;
    getId('_seLandmarkPoints').value = "area";
  }

  if (typeof Waze.model.venues == "undefined") {
    getId('_cbLandmarkColors').checked = false;
    getId('_cbLandmarkHiliteNoName').checked = false;
    getId('_cbLandmarkColors').disabled = true;
    getId('_cbLandmarkHiliteNoName').disabled = true;
    getId('_seLandmarkPoints').disabled = true;      
  }

  // overload the WME exit function
  saveLandmarkNamesOptions = function() {
    if (localStorage) {
      console.log("WME LandmarkNames: saving options");
      var options = [];

      // preserve previous options which may get lost after logout
      if (localStorage.WMELandmarkNamesScript)
          options = JSON.parse(localStorage.WMELandmarkNamesScript);
        
        options[1] = getId('_cbLandmarkColors').checked;
        options[2] = getId('_cbLandmarkHiliteNoName').checked;
        options[3] = getId('_seLandmarkPoints').value;
        
      localStorage.WMELandmarkNamesScript = JSON.stringify(options);
    }
  }
  window.addEventListener("beforeunload", saveLandmarkNamesOptions, false);

  // begin periodic updates
  window.setInterval(showLandmarkNames,500);

  // trigger code when page is fully loaded, to catch any missing bits
  window.addEventListener("load", function(e) {
    var mapProblems = getId('map-problems-explanation')
    if (mapProblems !== null) mapProblems.style.display = "none";
  });

  // register some events...
  Waze.map.events.register("zoomend", null, showLandmarkNames);
  Waze.map.events.register("changelayer", null, showLandmarkNames);
}

/* engage! =================================================================== */
bootstrapLandmarkNames();

/* end ======================================================================= */