GeometryFeature.js 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404
  1. define("dojox/geo/openlayers/GeometryFeature", ["dojo/_base/kernel",
  2. "dojo/_base/declare",
  3. "dojo/_base/array",
  4. "dojo/_base/lang",
  5. "dojox/gfx/matrix",
  6. "dojox/geo/openlayers/Point",
  7. "dojox/geo/openlayers/LineString",
  8. "dojox/geo/openlayers/Collection",
  9. "dojox/geo/openlayers/Feature"], function(dojo, declare, array, lang, matrix, Point, LineString,
  10. Collection, Feature){
  11. /*=====
  12. var Feature = dojox.geo.openlayers.Feature;
  13. =====*/
  14. return declare("dojox.geo.openlayers.GeometryFeature", Feature, {
  15. // summary:
  16. // A Feature encapsulating a geometry.
  17. // description:
  18. // This Feature renders a geometry such as a Point or LineString geometry. This Feature
  19. // is responsible for reprojecting the geometry before creating a gfx shape to display it.
  20. // By default the shape created is a circle for a Point geometry and a polyline for a
  21. // LineString geometry. User can change these behavior by overriding the createShape
  22. // method to create the desired shape.
  23. // example:
  24. // | var geom = new dojox.geo.openlayers.Point({x:0, y:0});
  25. // | var gf = new dojox.geo.openlayers.GeometryFeature(geom);
  26. constructor : function(/* dojox.geo.openlayers.Geometry */geometry){
  27. // summary:
  28. // Constructs a GeometryFeature for the specified geometry.
  29. // geometry: OpenLayer.Geometry
  30. // The geometry to render.
  31. this._geometry = geometry;
  32. this._shapeProperties = {};
  33. this._fill = null;
  34. this._stroke = null;
  35. },
  36. _createCollection : function(/* dojox.geo.openlayers.Geometry */g){
  37. // summary:
  38. // Create collection shape and add it to the viewport.
  39. // tags:
  40. // private
  41. var layer = this.getLayer();
  42. var s = layer.getSurface();
  43. var c = this.createShape(s, g);
  44. var vp = layer.getViewport();
  45. vp.add(c);
  46. return c;
  47. },
  48. _getCollectionShape : function(/* dojox.geo.openlayers.Geometry */g){
  49. // summary:
  50. // Get the collection shape, create it if necessary
  51. // tags:
  52. // private
  53. var s = g.shape;
  54. if (s == null) {
  55. s = this._createCollection(g);
  56. g.shape = s;
  57. }
  58. return s;
  59. },
  60. renderCollection : function(/* undefined | dojox.geo.openlayers.Geometry */g){
  61. // summary:
  62. // Renders a geometry collection.
  63. // g: undefined | dojox.geo.openlayers.Geometry
  64. // The geometry to render.
  65. if (g == undefined)
  66. g = this._geometry;
  67. s = this._getCollectionShape(g);
  68. var prop = this.getShapeProperties();
  69. s.setShape(prop);
  70. array.forEach(g.coordinates, function(item){
  71. if (item instanceof Point)
  72. this.renderPoint(item);
  73. else if (item instanceof LineString)
  74. this.renderLineString(item);
  75. else if (item instanceof Collection)
  76. this.renderCollection(item);
  77. else
  78. throw new Error();
  79. }, this);
  80. this._applyStyle(g);
  81. },
  82. render : function(/* undefined || dojox.geo.openlayer.Geometry */g){
  83. // summary:
  84. // Render a geometry.
  85. // Called by the Layer on which the feature is added.
  86. // g: undefined || dojox.geo.openlayer.Geometry
  87. // The geometry to draw
  88. if (g == undefined)
  89. g = this._geometry;
  90. if (g instanceof Point)
  91. this.renderPoint(g);
  92. else if (g instanceof LineString)
  93. this.renderLineString(g);
  94. else if (g instanceof Collection)
  95. this.renderCollection(g);
  96. else
  97. throw new Error();
  98. },
  99. getShapeProperties : function(){
  100. // summary:
  101. // Returns the shape properties.
  102. // returns: Object
  103. // The shape properties.
  104. return this._shapeProperties;
  105. },
  106. setShapeProperties : function(/* Object */s){
  107. // summary:
  108. // Sets the shape properties.
  109. // s: Object
  110. // The shape properties to set.
  111. this._shapeProperties = s;
  112. return this;
  113. },
  114. createShape : function(/* Surface */s, /* dojox.geo.openlayers.Geometry */g){
  115. // summary:
  116. // Called when the shape rendering the geometry has to be created.
  117. // This default implementation creates a circle for a point geometry, a polyline for
  118. // a LineString geometry and is recursively called when creating a collection.
  119. // User may replace this method to produce a custom shape.
  120. // s: dojox.gfx.Surface
  121. // The surface on which the method create the shapes.
  122. // g: dojox.geo.openlayers.Geometry
  123. // The reference geometry
  124. // returns: dojox.gfx.Shape
  125. // The resulting shape.
  126. if (!g)
  127. g = this._geometry;
  128. var shape = null;
  129. if (g instanceof Point) {
  130. shape = s.createCircle();
  131. } else if (g instanceof LineString) {
  132. shape = s.createPolyline();
  133. } else if (g instanceof Collection) {
  134. var grp = s.createGroup();
  135. array.forEach(g.coordinates, function(item){
  136. var shp = this.createShape(s, item);
  137. grp.add(shp);
  138. }, this);
  139. shape = grp;
  140. } else
  141. throw new Error();
  142. return shape;
  143. },
  144. getShape : function(){
  145. // summary:
  146. // Retrieves the shape rendering the geometry
  147. // returns: Shape
  148. // The shape used to render the geometry.
  149. var g = this._geometry;
  150. if (!g)
  151. return null;
  152. if (g.shape)
  153. return g.shape;
  154. this.render();
  155. return g.shape;
  156. },
  157. _createPoint : function(/* dojox.geo.openlayer.Geometry */g){
  158. // summary:
  159. // Create a point shape
  160. // tags:
  161. // private
  162. var layer = this.getLayer();
  163. var s = layer.getSurface();
  164. var c = this.createShape(s, g);
  165. var vp = layer.getViewport();
  166. vp.add(c);
  167. return c;
  168. },
  169. _getPointShape : function(/* dojox.geo.openlayers.Geometry */g){
  170. // summary:
  171. // get the point geometry shape, create it if necessary
  172. // tags:
  173. // private
  174. var s = g.shape;
  175. if (s == null) {
  176. s = this._createPoint(g);
  177. g.shape = s;
  178. }
  179. return s;
  180. },
  181. renderPoint : function(/* undefined | dojox.geo.openlayers.Point */g){
  182. // summary:
  183. // Renders a point geometry.
  184. // g: undefined | dojox.geo.openlayers.Point
  185. // The geometry to render.
  186. if (g == undefined)
  187. g = this._geometry;
  188. var layer = this.getLayer();
  189. var map = layer.getDojoMap();
  190. s = this._getPointShape(g);
  191. var prop = lang.mixin({}, this._defaults.pointShape);
  192. prop = lang.mixin(prop, this.getShapeProperties());
  193. s.setShape(prop);
  194. var from = this.getCoordinateSystem();
  195. var p = map.transform(g.coordinates, from);
  196. var a = this._getLocalXY(p);
  197. var cx = a[0];
  198. var cy = a[1];
  199. var tr = layer.getViewport().getTransform();
  200. if (tr)
  201. s.setTransform(matrix.translate(cx - tr.dx, cy - tr.dy));
  202. this._applyStyle(g);
  203. },
  204. _createLineString : function(/* dojox.geo.openlayers.Geometry */g){
  205. // summary:
  206. // Create polyline shape and add it to the viewport.
  207. // tags:
  208. // private
  209. var layer = this.getLayer();
  210. var s = layer._surface;
  211. var shape = this.createShape(s, g);
  212. var vp = layer.getViewport();
  213. vp.add(shape);
  214. g.shape = shape;
  215. return shape;
  216. },
  217. _getLineStringShape : function(/* dojox.geo.openlayers.Geometry */g){
  218. // summary:
  219. // Get the line string geometry shape, create it if necessary
  220. // tags:
  221. // private
  222. var s = g.shape;
  223. if (s == null) {
  224. s = this._createLineString(g);
  225. g.shape = s;
  226. }
  227. return s;
  228. },
  229. renderLineString : function(/* undefined | dojox.geo.openlayers.geometry */g){
  230. // summary:
  231. // Renders a line string geometry.
  232. // g: undefined | dojox.geo.openlayers.Geometry
  233. // The geometry to render.
  234. if (g == undefined)
  235. g = this._geometry;
  236. var layer = this.getLayer();
  237. var map = layer.getDojoMap();
  238. var lss = this._getLineStringShape(g);
  239. var from = this.getCoordinateSystem();
  240. var points = new Array(g.coordinates.length); // ss.getShape().points;
  241. var tr = layer.getViewport().getTransform();
  242. array.forEach(g.coordinates, function(c, i, array){
  243. var p = map.transform(c, from);
  244. var a = this._getLocalXY(p);
  245. if (tr) {
  246. a[0] -= tr.dx;
  247. a[1] -= tr.dy;
  248. }
  249. points[i] = {
  250. x : a[0],
  251. y : a[1]
  252. };
  253. }, this);
  254. var prop = lang.mixin({}, this._defaults.lineStringShape);
  255. prop = lang.mixin(prop, this.getShapeProperties());
  256. prop = lang.mixin(prop, {
  257. points : points
  258. });
  259. lss.setShape(prop);
  260. this._applyStyle(g);
  261. },
  262. _applyStyle : function(/* Geometry */g){
  263. // summary:
  264. // Apply the style on the geometry's shape.
  265. // g: dojox.geo.openlayers.Geometry
  266. // The geometry.
  267. // tags:
  268. // private
  269. if (!g || !g.shape)
  270. return;
  271. var f = this.getFill();
  272. var fill;
  273. if (!f || lang.isString(f) || lang.isArray(f))
  274. fill = f;
  275. else {
  276. fill = lang.mixin({}, this._defaults.fill);
  277. fill = lang.mixin(fill, f);
  278. }
  279. var s = this.getStroke();
  280. var stroke;
  281. if (!s || lang.isString(s) || lang.isArray(s))
  282. stroke = s;
  283. else {
  284. stroke = lang.mixin({}, this._defaults.stroke);
  285. stroke = lang.mixin(stroke, s);
  286. }
  287. this._applyRecusiveStyle(g, stroke, fill);
  288. },
  289. _applyRecusiveStyle : function(g, stroke, fill){
  290. // summary:
  291. // Apply the style on the geometry's shape recursively.
  292. // g: dojox.geo.openlayers.Geometry
  293. // The geometry.
  294. // stroke: Object
  295. // The stroke
  296. // fill:Object
  297. // The fill
  298. // tags:
  299. // private
  300. var shp = g.shape;
  301. if (shp.setFill)
  302. shp.setFill(fill);
  303. if (shp.setStroke)
  304. shp.setStroke(stroke);
  305. if (g instanceof Collection) {
  306. array.forEach(g.coordinates, function(i){
  307. this._applyRecusiveStyle(i, stroke, fill);
  308. }, this);
  309. }
  310. },
  311. setStroke : function(/* Object */s){
  312. // summary:
  313. // Set the stroke style to be applied on the rendered shape.
  314. // s: Object
  315. // The stroke style
  316. this._stroke = s;
  317. return this;
  318. },
  319. getStroke : function(){
  320. // summary:
  321. // Retrieves the stroke style
  322. // returns: Object
  323. // The stroke style
  324. return this._stroke;
  325. },
  326. setFill : function(/* Object */f){
  327. // summary:
  328. // Set the fill style to be applied on the rendered shape.
  329. // f: Object
  330. // The fill style
  331. this._fill = f;
  332. return this;
  333. },
  334. getFill : function(){
  335. // summary:
  336. // Retrieves the fill style
  337. // returns: Object
  338. // The fill style
  339. return this._fill;
  340. },
  341. remove : function(){
  342. // summary:
  343. // Removes the shape from the Surface.
  344. // Called when the feature is removed from the layer.
  345. var g = this._geometry;
  346. var shp = g.shape;
  347. g.shape = null;
  348. if (shp)
  349. shp.removeShape();
  350. if (g instanceof Collection) {
  351. array.forEach(g.coordinates, function(i){
  352. this.remove(i);
  353. }, this);
  354. }
  355. },
  356. _defaults : {
  357. fill : null,
  358. stroke : null,
  359. pointShape : {
  360. r : 30
  361. },
  362. lineStringShape : null
  363. }
  364. });
  365. });