toolbars.py 39 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975
  1. """
  2. MODULE: toolbar
  3. CLASSES:
  4. * AbstractToolbar
  5. * MapToolbar
  6. * GRToolbar
  7. * GCPToolbar
  8. * VDigitToolbar
  9. * ProfileToolbar
  10. PURPOSE: Toolbars for Map Display window
  11. AUTHORS: The GRASS Development Team
  12. Michael Barton, Martin Landa, Jachym Cepicky
  13. COPYRIGHT: (C) 2007-2008 by the GRASS Development Team
  14. This program is free software under the GNU General Public
  15. License (>=v2). Read the file COPYING that comes with GRASS
  16. for details.
  17. """
  18. import wx
  19. import os, sys
  20. import globalvar
  21. import gcmd
  22. import grassenv
  23. import gdialogs
  24. import vdigit
  25. from vdigit import VDigitSettingsDialog as VDigitSettingsDialog
  26. from debug import Debug as Debug
  27. from icon import Icons as Icons
  28. from preferences import globalSettings as UserSettings
  29. gmpath = os.path.join(globalvar.ETCWXDIR, "icons")
  30. sys.path.append(gmpath)
  31. class AbstractToolbar(object):
  32. """Abstract toolbar class"""
  33. def __init__():
  34. pass
  35. def InitToolbar(self, parent, toolbar, toolData):
  36. """Initialize toolbar, i.e. add tools to the toolbar
  37. @return list of ids (of added tools)
  38. """
  39. for tool in toolData:
  40. self.CreateTool(parent, toolbar, *tool)
  41. self._toolbar = toolbar
  42. def ToolbarData(self):
  43. """Toolbar data"""
  44. return None
  45. def CreateTool(self, parent, toolbar, tool, label, bitmap, kind,
  46. shortHelp, longHelp, handler):
  47. """Add tool to the toolbar
  48. @return id of tool
  49. """
  50. bmpDisabled=wx.NullBitmap
  51. if label:
  52. toolWin = toolbar.AddLabelTool(tool, label, bitmap,
  53. bmpDisabled, kind,
  54. shortHelp, longHelp)
  55. parent.Bind(wx.EVT_TOOL, handler, toolWin)
  56. else: # add separator
  57. toolbar.AddSeparator()
  58. return tool
  59. def GetToolbar(self):
  60. """Get toolbar widget reference"""
  61. return self._toolbar
  62. class MapToolbar(AbstractToolbar):
  63. """
  64. Main Map Display toolbar
  65. """
  66. def __init__(self, mapdisplay, map):
  67. self.mapcontent = map
  68. self.mapdisplay = mapdisplay
  69. self.toolbar = wx.ToolBar(parent=self.mapdisplay, id=wx.ID_ANY)
  70. self.toolbar.SetToolBitmapSize(globalvar.toolbarSize)
  71. self.InitToolbar(self.mapdisplay, self.toolbar, self.ToolbarData())
  72. # optional tools
  73. self.combo = wx.ComboBox(parent=self.toolbar, id=wx.ID_ANY, value='Tools',
  74. choices=['Digitize'], style=wx.CB_READONLY, size=(90, -1))
  75. self.comboid = self.toolbar.AddControl(self.combo)
  76. self.mapdisplay.Bind(wx.EVT_COMBOBOX, self.OnSelect, self.comboid)
  77. # realize the toolbar
  78. self.toolbar.Realize()
  79. def ToolbarData(self):
  80. """Toolbar data"""
  81. self.displaymap = wx.NewId()
  82. self.rendermap = wx.NewId()
  83. self.erase = wx.NewId()
  84. self.pointer = wx.NewId()
  85. self.query = wx.NewId()
  86. self.pan = wx.NewId()
  87. self.zoomin = wx.NewId()
  88. self.zoomout = wx.NewId()
  89. self.zoomback = wx.NewId()
  90. self.zoommenu = wx.NewId()
  91. self.analyze = wx.NewId()
  92. self.dec = wx.NewId()
  93. self.savefile = wx.NewId()
  94. self.printmap = wx.NewId()
  95. # tool, label, bitmap, kind, shortHelp, longHelp, handler
  96. return (
  97. (self.displaymap, "displaymap", Icons["displaymap"].GetBitmap(),
  98. wx.ITEM_NORMAL, Icons["displaymap"].GetLabel(), Icons["displaymap"].GetDesc(),
  99. self.mapdisplay.OnDraw),
  100. (self.rendermap, "rendermap", Icons["rendermap"].GetBitmap(),
  101. wx.ITEM_NORMAL, Icons["rendermap"].GetLabel(), Icons["rendermap"].GetDesc(),
  102. self.mapdisplay.OnRender),
  103. (self.erase, "erase", Icons["erase"].GetBitmap(),
  104. wx.ITEM_NORMAL, Icons["erase"].GetLabel(), Icons["erase"].GetDesc(),
  105. self.mapdisplay.OnErase),
  106. ("", "", "", "", "", "", ""),
  107. (self.pointer, "pointer", Icons["pointer"].GetBitmap(),
  108. wx.ITEM_RADIO, Icons["pointer"].GetLabel(), Icons["pointer"].GetDesc(),
  109. self.mapdisplay.OnPointer),
  110. (self.query, "queryDisplay", Icons["queryDisplay"].GetBitmap(),
  111. wx.ITEM_RADIO, Icons["queryDisplay"].GetLabel(), Icons["queryDisplay"].GetDesc(),
  112. self.mapdisplay.OnQuery),
  113. (self.pan, "pan", Icons["pan"].GetBitmap(),
  114. wx.ITEM_RADIO, Icons["pan"].GetLabel(), Icons["pan"].GetDesc(),
  115. self.mapdisplay.OnPan),
  116. (self.zoomin, "zoom_in", Icons["zoom_in"].GetBitmap(),
  117. wx.ITEM_RADIO, Icons["zoom_in"].GetLabel(), Icons["zoom_in"].GetDesc(),
  118. self.mapdisplay.OnZoomIn),
  119. (self.zoomout, "zoom_out", Icons["zoom_out"].GetBitmap(),
  120. wx.ITEM_RADIO, Icons["zoom_out"].GetLabel(), Icons["zoom_out"].GetDesc(),
  121. self.mapdisplay.OnZoomOut),
  122. (self.zoomback, "zoom_back", Icons["zoom_back"].GetBitmap(),
  123. wx.ITEM_NORMAL, Icons["zoom_back"].GetLabel(), Icons["zoom_back"].GetDesc(),
  124. self.mapdisplay.OnZoomBack),
  125. (self.zoommenu, "zoommenu", Icons["zoommenu"].GetBitmap(),
  126. wx.ITEM_NORMAL, Icons["zoommenu"].GetLabel(), Icons["zoommenu"].GetDesc(),
  127. self.mapdisplay.OnZoomMenu),
  128. ("", "", "", "", "", "", ""),
  129. (self.analyze, "analyze", Icons["analyze"].GetBitmap(),
  130. wx.ITEM_NORMAL, Icons["analyze"].GetLabel(), Icons["analyze"].GetDesc(),
  131. self.mapdisplay.OnAnalyze),
  132. ("", "", "", "", "", "", ""),
  133. (self.dec, "overlay", Icons["overlay"].GetBitmap(),
  134. wx.ITEM_NORMAL, Icons["overlay"].GetLabel(), Icons["overlay"].GetDesc(),
  135. self.mapdisplay.OnDecoration),
  136. ("", "", "", "", "", "", ""),
  137. (self.savefile, "savefile", Icons["savefile"].GetBitmap(),
  138. wx.ITEM_NORMAL, Icons["savefile"].GetLabel(), Icons["savefile"].GetDesc(),
  139. self.mapdisplay.SaveToFile),
  140. (self.printmap, "printmap", Icons["printmap"].GetBitmap(),
  141. wx.ITEM_NORMAL, Icons["printmap"].GetLabel(), Icons["printmap"].GetDesc(),
  142. self.mapdisplay.PrintMenu),
  143. ("", "", "", "", "", "", "")
  144. )
  145. def OnSelect(self, event):
  146. """
  147. Select / enable tool available in tools list
  148. """
  149. tool = event.GetString()
  150. if tool == "Digitize" and not self.mapdisplay.digittoolbar:
  151. self.mapdisplay.AddToolbar("digit")
  152. class GRToolbar(AbstractToolbar):
  153. """
  154. Georectify Display toolbar
  155. """
  156. def __init__(self, mapdisplay, map):
  157. self.mapcontent = map
  158. self.mapdisplay = mapdisplay
  159. self.toolbar = wx.ToolBar(parent=self.mapdisplay, id=wx.ID_ANY)
  160. # self.SetToolBar(self.toolbar)
  161. self.toolbar.SetToolBitmapSize(globalvar.toolbarSize)
  162. self.InitToolbar(self.mapdisplay, self.toolbar, self.ToolbarData())
  163. # realize the toolbar
  164. self.toolbar.Realize()
  165. def ToolbarData(self):
  166. """Toolbar data"""
  167. self.displaymap = wx.NewId()
  168. self.rendermap = wx.NewId()
  169. self.erase = wx.NewId()
  170. self.gcpset = wx.NewId()
  171. self.pan = wx.NewId()
  172. self.zoomin = wx.NewId()
  173. self.zoomout = wx.NewId()
  174. self.zoomback = wx.NewId()
  175. self.zoommenu = wx.NewId()
  176. # tool, label, bitmap, kind, shortHelp, longHelp, handler
  177. return (
  178. (self.displaymap, "displaymap", Icons["displaymap"].GetBitmap(),
  179. wx.ITEM_NORMAL, Icons["displaymap"].GetLabel(), Icons["displaymap"].GetDesc(),
  180. self.mapdisplay.OnDraw),
  181. (self.rendermap, "rendermap", Icons["rendermap"].GetBitmap(),
  182. wx.ITEM_NORMAL, Icons["rendermap"].GetLabel(), Icons["rendermap"].GetDesc(),
  183. self.mapdisplay.OnRender),
  184. (self.erase, "erase", Icons["erase"].GetBitmap(),
  185. wx.ITEM_NORMAL, Icons["erase"].GetLabel(), Icons["erase"].GetDesc(),
  186. self.mapdisplay.OnErase),
  187. ("", "", "", "", "", "", ""),
  188. (self.gcpset, "grGcpSet", Icons["grGcpSet"].GetBitmap(),
  189. wx.ITEM_RADIO, Icons["grGcpSet"].GetLabel(), Icons["grGcpSet"].GetDesc(),
  190. self.mapdisplay.OnPointer),
  191. (self.pan, "pan", Icons["pan"].GetBitmap(),
  192. wx.ITEM_RADIO, Icons["pan"].GetLabel(), Icons["pan"].GetDesc(),
  193. self.mapdisplay.OnPan),
  194. (self.zoomin, "zoom_in", Icons["zoom_in"].GetBitmap(),
  195. wx.ITEM_RADIO, Icons["zoom_in"].GetLabel(), Icons["zoom_in"].GetDesc(),
  196. self.mapdisplay.OnZoomIn),
  197. (self.zoomout, "zoom_out", Icons["zoom_out"].GetBitmap(),
  198. wx.ITEM_RADIO, Icons["zoom_out"].GetLabel(), Icons["zoom_out"].GetDesc(),
  199. self.mapdisplay.OnZoomOut),
  200. (self.zoomback, "zoom_back", Icons["zoom_back"].GetBitmap(),
  201. wx.ITEM_NORMAL, Icons["zoom_back"].GetLabel(), Icons["zoom_back"].GetDesc(),
  202. self.mapdisplay.OnZoomBack),
  203. (self.zoommenu, "zoommenu", Icons["zoommenu"].GetBitmap(),
  204. wx.ITEM_NORMAL, Icons["zoommenu"].GetLabel(), Icons["zoommenu"].GetDesc(),
  205. self.mapdisplay.OnZoomMenu),
  206. )
  207. class GCPToolbar(AbstractToolbar):
  208. """
  209. Toolbar for digitization
  210. """
  211. def __init__(self, parent, mapdisplay, map):
  212. self.parent = parent # GCP
  213. self.mapcontent = map
  214. self.mapdisplay = mapdisplay
  215. self.toolbar = wx.ToolBar(parent=self.mapdisplay, id=wx.ID_ANY)
  216. # self.SetToolBar(self.toolbar)
  217. self.toolbar.SetToolBitmapSize(globalvar.toolbarSize)
  218. self.InitToolbar(self.mapdisplay, self.toolbar, self.ToolbarData())
  219. # realize the toolbar
  220. self.toolbar.Realize()
  221. def ToolbarData(self):
  222. self.gcpSave = wx.NewId()
  223. self.gcpAdd = wx.NewId()
  224. self.gcpDelete = wx.NewId()
  225. self.gcpClear = wx.NewId()
  226. self.gcpReload = wx.NewId()
  227. self.rms = wx.NewId()
  228. self.georect = wx.NewId()
  229. self.settings = wx.NewId()
  230. self.quit = wx.NewId()
  231. return (
  232. (self.gcpSave, 'grGcpSave', Icons["grGcpSave"].GetBitmap(),
  233. wx.ITEM_NORMAL, Icons["grGcpSave"].GetLabel(), Icons["grGcpSave"].GetDesc(),
  234. self.parent.SaveGCPs),
  235. (self.gcpAdd, 'grGrGcpAdd', Icons["grGcpAdd"].GetBitmap(),
  236. wx.ITEM_NORMAL, Icons["grGcpAdd"].GetLabel(), Icons["grGcpAdd"].GetDesc(),
  237. self.parent.AddGCP),
  238. (self.gcpDelete, 'grGrGcpDelete', Icons["grGcpDelete"].GetBitmap(),
  239. wx.ITEM_NORMAL, Icons["grGcpDelete"].GetLabel(), Icons["grGcpDelete"].GetDesc(),
  240. self.parent.DeleteGCP),
  241. (self.gcpClear, 'grGcpClear', Icons["grGcpClear"].GetBitmap(),
  242. wx.ITEM_NORMAL, Icons["grGcpClear"].GetLabel(), Icons["grGcpClear"].GetDesc(),
  243. self.parent.ClearGCP),
  244. (self.gcpReload, 'grGcpReload', Icons["grGcpReload"].GetBitmap(),
  245. wx.ITEM_NORMAL, Icons["grGcpReload"].GetLabel(), Icons["grGcpReload"].GetDesc(),
  246. self.parent.ReloadGCPs),
  247. ("", "", "", "", "", "", ""),
  248. (self.rms, 'grGcpRms', Icons["grGcpRms"].GetBitmap(),
  249. wx.ITEM_NORMAL, Icons["grGcpRms"].GetLabel(), Icons["grGcpRms"].GetDesc(),
  250. self.parent.OnRMS),
  251. (self.georect, 'grGeorect', Icons["grGeorect"].GetBitmap(),
  252. wx.ITEM_NORMAL, Icons["grGeorect"].GetLabel(), Icons["grGeorect"].GetDesc(),
  253. self.parent.OnGeorect),
  254. ("", "", "", "", "", "", ""),
  255. (self.settings, 'grSettings', Icons["grSettings"].GetBitmap(),
  256. wx.ITEM_NORMAL, Icons["grSettings"].GetLabel(), Icons["grSettings"].GetDesc(),
  257. self.parent.OnSettings),
  258. (self.quit, 'grGcpQuit', Icons["grGcpQuit"].GetBitmap(),
  259. wx.ITEM_NORMAL, Icons["grGcpQuit"].GetLabel(), Icons["grGcpQuit"].GetDesc(),
  260. self.parent.OnQuit)
  261. )
  262. class VDigitToolbar(AbstractToolbar):
  263. """
  264. Toolbar for digitization
  265. """
  266. def __init__(self, parent, map, layerTree=None):
  267. self.mapcontent = map # Map class instance
  268. self.parent = parent # MapFrame
  269. self.layerTree = layerTree # reference to layer tree associated to map display
  270. # selected map to digitize
  271. self.layerSelectedID = None
  272. self.layers = []
  273. # default action (digitize new point, line, etc.)
  274. self.action = "addLine"
  275. self.type = "point"
  276. self.addString = ""
  277. self.comboid = None
  278. # only one dialog can be open
  279. self.settingsDialog = None
  280. # create toolbars (two rows optionaly)
  281. self.toolbar = []
  282. self.numOfRows = 1 # number of rows for toolbar
  283. for row in range(0, self.numOfRows):
  284. self.toolbar.append(wx.ToolBar(parent=self.parent, id=wx.ID_ANY))
  285. self.toolbar[row].SetToolBitmapSize(globalvar.toolbarSize)
  286. self.toolbar[row].Bind(wx.EVT_TOOL, self.OnTool)
  287. # create toolbar
  288. if self.numOfRows == 1:
  289. rowdata=None
  290. else:
  291. rowdata = row
  292. self.InitToolbar(self.parent, self.toolbar[row], self.ToolbarData(rowdata))
  293. # list of available vector maps
  294. self.UpdateListOfLayers(updateTool=True)
  295. # realize toolbar
  296. for row in range(0, self.numOfRows):
  297. self.toolbar[row].Realize()
  298. # disable undo/redo
  299. self.toolbar[0].EnableTool(self.undo, False)
  300. # toogle to pointer by default
  301. self.OnTool(None)
  302. def ToolbarData(self, row=None):
  303. """
  304. Toolbar data
  305. """
  306. data = []
  307. if row is None or row == 0:
  308. self.addPoint = wx.NewId()
  309. self.addLine = wx.NewId()
  310. self.addBoundary = wx.NewId()
  311. self.addCentroid = wx.NewId()
  312. self.moveVertex = wx.NewId()
  313. self.addVertex = wx.NewId()
  314. self.removeVertex = wx.NewId()
  315. self.splitLine = wx.NewId()
  316. self.editLine = wx.NewId()
  317. self.moveLine = wx.NewId()
  318. self.deleteLine = wx.NewId()
  319. self.additionalTools = wx.NewId()
  320. self.displayCats = wx.NewId()
  321. self.displayAttr = wx.NewId()
  322. self.copyCats = wx.NewId()
  323. data = [("", "", "", "", "", "", ""),
  324. (self.addPoint, "digAddPoint", Icons["digAddPoint"].GetBitmap(),
  325. wx.ITEM_RADIO, Icons["digAddPoint"].GetLabel(), Icons["digAddPoint"].GetDesc(),
  326. self.OnAddPoint),
  327. (self.addLine, "digAddLine", Icons["digAddLine"].GetBitmap(),
  328. wx.ITEM_RADIO, Icons["digAddLine"].GetLabel(), Icons["digAddLine"].GetDesc(),
  329. self.OnAddLine),
  330. (self.addBoundary, "digAddBoundary", Icons["digAddBoundary"].GetBitmap(),
  331. wx.ITEM_RADIO, Icons["digAddBoundary"].GetLabel(), Icons["digAddBoundary"].GetDesc(),
  332. self.OnAddBoundary),
  333. (self.addCentroid, "digAddCentroid", Icons["digAddCentroid"].GetBitmap(),
  334. wx.ITEM_RADIO, Icons["digAddCentroid"].GetLabel(), Icons["digAddCentroid"].GetDesc(),
  335. self.OnAddCentroid),
  336. (self.moveVertex, "digMoveVertex", Icons["digMoveVertex"].GetBitmap(),
  337. wx.ITEM_RADIO, Icons["digMoveVertex"].GetLabel(), Icons["digMoveVertex"].GetDesc(),
  338. self.OnMoveVertex),
  339. (self.addVertex, "digAddVertex", Icons["digAddVertex"].GetBitmap(),
  340. wx.ITEM_RADIO, Icons["digAddVertex"].GetLabel(), Icons["digAddVertex"].GetDesc(),
  341. self.OnAddVertex),
  342. (self.removeVertex, "digRemoveVertex", Icons["digRemoveVertex"].GetBitmap(),
  343. wx.ITEM_RADIO, Icons["digRemoveVertex"].GetLabel(), Icons["digRemoveVertex"].GetDesc(),
  344. self.OnRemoveVertex),
  345. (self.splitLine, "digSplitLine", Icons["digSplitLine"].GetBitmap(),
  346. wx.ITEM_RADIO, Icons["digSplitLine"].GetLabel(), Icons["digSplitLine"].GetDesc(),
  347. self.OnSplitLine),
  348. (self.editLine, "digEditLine", Icons["digEditLine"].GetBitmap(),
  349. wx.ITEM_RADIO, Icons["digEditLine"].GetLabel(), Icons["digEditLine"].GetDesc(),
  350. self.OnEditLine),
  351. (self.moveLine, "digMoveLine", Icons["digMoveLine"].GetBitmap(),
  352. wx.ITEM_RADIO, Icons["digMoveLine"].GetLabel(), Icons["digMoveLine"].GetDesc(),
  353. self.OnMoveLine),
  354. (self.deleteLine, "digDeleteLine", Icons["digDeleteLine"].GetBitmap(),
  355. wx.ITEM_RADIO, Icons["digDeleteLine"].GetLabel(), Icons["digDeleteLine"].GetDesc(),
  356. self.OnDeleteLine),
  357. (self.displayCats, "digDispCats", Icons["digDispCats"].GetBitmap(),
  358. wx.ITEM_RADIO, Icons["digDispCats"].GetLabel(), Icons["digDispCats"].GetDesc(),
  359. self.OnDisplayCats),
  360. (self.copyCats, "digCopyCats", Icons["digCopyCats"].GetBitmap(),
  361. wx.ITEM_RADIO, Icons["digCopyCats"].GetLabel(), Icons["digCopyCats"].GetDesc(),
  362. self.OnCopyCats),
  363. (self.displayAttr, "digDispAttr", Icons["digDispAttr"].GetBitmap(),
  364. wx.ITEM_RADIO, Icons["digDispAttr"].GetLabel(), Icons["digDispAttr"].GetDesc(),
  365. self.OnDisplayAttr),
  366. (self.additionalTools, "digAdditionalTools", Icons["digAdditionalTools"].GetBitmap(),
  367. wx.ITEM_RADIO, Icons["digAdditionalTools"].GetLabel(),
  368. Icons["digAdditionalTools"].GetDesc(),
  369. self.OnAdditionalToolMenu)]
  370. if row is None or row == 1:
  371. self.undo = wx.NewId()
  372. self.settings = wx.NewId()
  373. self.exit = wx.NewId()
  374. data.append(("", "", "", "", "", "", ""))
  375. data.append((self.undo, "digUndo", Icons["digUndo"].GetBitmap(),
  376. wx.ITEM_NORMAL, Icons["digUndo"].GetLabel(), Icons["digUndo"].GetDesc(),
  377. self.OnUndo))
  378. # data.append((self.undo, "digRedo", Icons["digRedo"].GetBitmap(),
  379. # wx.ITEM_NORMAL, Icons["digRedo"].GetLabel(), Icons["digRedo"].GetDesc(),
  380. # self.OnRedo))
  381. data.append((self.settings, "digSettings", Icons["digSettings"].GetBitmap(),
  382. wx.ITEM_NORMAL, Icons["digSettings"].GetLabel(), Icons["digSettings"].GetDesc(),
  383. self.OnSettings))
  384. data.append((self.exit, "digExit", Icons["quit"].GetBitmap(),
  385. wx.ITEM_NORMAL, Icons["digExit"].GetLabel(), Icons["digExit"].GetDesc(),
  386. self.OnExit))
  387. return data
  388. def OnTool(self, event):
  389. """Tool selected -> toggle tool to pointer"""
  390. id = self.parent.maptoolbar.pointer
  391. self.parent.maptoolbar.toolbar.ToggleTool(id, True)
  392. self.parent.maptoolbar.mapdisplay.OnPointer(event)
  393. if event:
  394. event.Skip()
  395. def OnAddPoint(self, event):
  396. """Add point to the vector map Laier"""
  397. Debug.msg (2, "VDigitToolbar.OnAddPoint()")
  398. self.action = "addLine"
  399. self.type = "point"
  400. self.parent.MapWindow.mouse['box'] = 'point'
  401. def OnAddLine(self, event):
  402. """Add line to the vector map layer"""
  403. Debug.msg (2, "VDigitToolbar.OnAddLine()")
  404. self.action = "addLine"
  405. self.type = "line"
  406. self.parent.MapWindow.mouse['box'] = 'line'
  407. self.parent.MapWindow.polycoords = [] # reset temp line
  408. def OnAddBoundary(self, event):
  409. """Add boundary to the vector map layer"""
  410. Debug.msg (2, "VDigitToolbar.OnAddBoundary()")
  411. self.action = "addLine"
  412. self.type = "boundary"
  413. self.parent.MapWindow.mouse['box'] = 'line'
  414. self.parent.MapWindow.polycoords = [] # reset temp line
  415. def OnAddCentroid(self, event):
  416. """Add centroid to the vector map layer"""
  417. Debug.msg (2, "VDigitToolbar.OnAddCentroid()")
  418. self.action = "addLine"
  419. self.type = "centroid"
  420. self.parent.MapWindow.mouse['box'] = 'point'
  421. def OnExit (self, event=None):
  422. """Quit digitization tool"""
  423. # stop editing of the currently selected map layer
  424. try:
  425. self.StopEditing(self.layers[self.layerSelectedID])
  426. except:
  427. pass
  428. # close dialogs if still open
  429. if self.settingsDialog:
  430. self.settingsDialog.OnCancel(None)
  431. if self.parent.dialogs['category']:
  432. self.parent.dialogs['category'].OnCancel(None)
  433. if self.parent.dialogs['attributes']:
  434. self.parent.dialogs['attributes'].OnCancel(None)
  435. # disable the toolbar
  436. self.parent.RemoveToolbar ("digit")
  437. def OnMoveVertex(self, event):
  438. """Move line vertex"""
  439. Debug.msg(2, "Digittoolbar.OnMoveVertex():")
  440. self.action = "moveVertex"
  441. self.parent.MapWindow.mouse['box'] = 'point'
  442. def OnAddVertex(self, event):
  443. """Add line vertex"""
  444. Debug.msg(2, "Digittoolbar.OnAddVertex():")
  445. self.action = "addVertex"
  446. self.parent.MapWindow.mouse['box'] = 'point'
  447. def OnRemoveVertex(self, event):
  448. """Remove line vertex"""
  449. Debug.msg(2, "Digittoolbar.OnRemoveVertex():")
  450. self.action = "removeVertex"
  451. self.parent.MapWindow.mouse['box'] = 'point'
  452. def OnSplitLine(self, event):
  453. """Split line"""
  454. Debug.msg(2, "Digittoolbar.OnSplitLine():")
  455. self.action = "splitLine"
  456. self.parent.MapWindow.mouse['box'] = 'point'
  457. def OnEditLine(self, event):
  458. """Edit line"""
  459. Debug.msg(2, "Digittoolbar.OnEditLine():")
  460. self.action="editLine"
  461. self.parent.MapWindow.mouse['box'] = 'line'
  462. def OnMoveLine(self, event):
  463. """Move line"""
  464. Debug.msg(2, "Digittoolbar.OnMoveLine():")
  465. self.action = "moveLine"
  466. self.parent.MapWindow.mouse['box'] = 'box'
  467. def OnDeleteLine(self, event):
  468. """Delete line"""
  469. Debug.msg(2, "Digittoolbar.OnDeleteLine():")
  470. self.action = "deleteLine"
  471. self.parent.MapWindow.mouse['box'] = 'box'
  472. def OnDisplayCats(self, event):
  473. """Display/update categories"""
  474. Debug.msg(2, "Digittoolbar.OnDisplayCats():")
  475. self.action="displayCats"
  476. self.parent.MapWindow.mouse['box'] = 'point'
  477. def OnDisplayAttr(self, event):
  478. """Display/update attributes"""
  479. Debug.msg(2, "Digittoolbar.OnDisplayAttr():")
  480. self.action="displayAttrs"
  481. self.parent.MapWindow.mouse['box'] = 'point'
  482. def OnCopyCats(self, event):
  483. """Copy categories"""
  484. Debug.msg(2, "Digittoolbar.OnCopyCats():")
  485. self.action="copyCats"
  486. self.parent.MapWindow.mouse['box'] = 'point'
  487. def OnUndo(self, event):
  488. """Undo previous changes"""
  489. self.parent.digit.Undo()
  490. event.Skip()
  491. def EnableUndo(self, enable=True):
  492. """Enable 'Undo' in toolbar
  493. @param enable False for disable
  494. """
  495. if enable:
  496. if self.toolbar[0].GetToolEnabled(self.undo) is False:
  497. self.toolbar[0].EnableTool(self.undo, True)
  498. else:
  499. if self.toolbar[0].GetToolEnabled(self.undo) is True:
  500. self.toolbar[0].EnableTool(self.undo, False)
  501. def OnSettings(self, event):
  502. """Show settings dialog"""
  503. if self.parent.digit is None:
  504. reload(vdigit)
  505. from vdigit import Digit as Digit
  506. self.parent.digit = Digit(mapwindow=self.parent.MapWindow)
  507. if not self.settingsDialog:
  508. self.settingsDialog = VDigitSettingsDialog(parent=self.parent, title=_("Digitization settings"),
  509. style=wx.DEFAULT_DIALOG_STYLE)
  510. self.settingsDialog.Show()
  511. def OnAdditionalToolMenu(self, event):
  512. """Menu for additional tools"""
  513. point = wx.GetMousePosition()
  514. toolMenu = wx.Menu()
  515. # Add items to the menu
  516. copy = wx.MenuItem(toolMenu, wx.ID_ANY, _('Copy features from (background) vector map'))
  517. toolMenu.AppendItem(copy)
  518. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnCopy, copy)
  519. flip = wx.MenuItem(toolMenu, wx.ID_ANY, _('Flip selected lines/boundaries'))
  520. toolMenu.AppendItem(flip)
  521. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnFlip, flip)
  522. merge = wx.MenuItem(toolMenu, wx.ID_ANY, _('Merge selected lines/boundaries'))
  523. toolMenu.AppendItem(merge)
  524. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnMerge, merge)
  525. breakL = wx.MenuItem(toolMenu, wx.ID_ANY, _('Break selected lines/boundaries at intersection'))
  526. toolMenu.AppendItem(breakL)
  527. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnBreak, breakL)
  528. snap = wx.MenuItem(toolMenu, wx.ID_ANY, _('Snap selected lines/boundaries (only to nodes)'))
  529. toolMenu.AppendItem(snap)
  530. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnSnap, snap)
  531. connect = wx.MenuItem(toolMenu, wx.ID_ANY, _('Connect two selected lines/boundaries'))
  532. toolMenu.AppendItem(connect)
  533. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnConnect, connect)
  534. query = wx.MenuItem(toolMenu, wx.ID_ANY, _('Query tool'))
  535. toolMenu.AppendItem(query)
  536. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnQuery, query)
  537. zbulk = wx.MenuItem(toolMenu, wx.ID_ANY, _('Z bulk-labeling of 3D lines'))
  538. toolMenu.AppendItem(zbulk)
  539. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnZBulk, zbulk)
  540. typeconv = wx.MenuItem(toolMenu, wx.ID_ANY, _('Feature type conversion'))
  541. toolMenu.AppendItem(typeconv)
  542. self.parent.MapWindow.Bind(wx.EVT_MENU, self.OnTypeConversion, typeconv)
  543. # Popup the menu. If an item is selected then its handler
  544. # will be called before PopupMenu returns.
  545. self.parent.MapWindow.PopupMenu(toolMenu)
  546. toolMenu.Destroy()
  547. def OnCopy(self, event):
  548. """Copy selected features from (background) vector map"""
  549. Debug.msg(2, "Digittoolbar.OnCopy():")
  550. self.action="copyLine"
  551. self.parent.MapWindow.mouse['box'] = 'box'
  552. def OnFlip(self, event):
  553. """Flip selected lines/boundaries"""
  554. Debug.msg(2, "Digittoolbar.OnFlip():")
  555. self.action="flipLine"
  556. self.parent.MapWindow.mouse['box'] = 'box'
  557. def OnMerge(self, event):
  558. """Merge selected lines/boundaries"""
  559. Debug.msg(2, "Digittoolbar.OnMerge():")
  560. self.action="mergeLine"
  561. self.parent.MapWindow.mouse['box'] = 'box'
  562. def OnBreak(self, event):
  563. """Break selected lines/boundaries"""
  564. Debug.msg(2, "Digittoolbar.OnBreak():")
  565. self.action="breakLine"
  566. self.parent.MapWindow.mouse['box'] = 'box'
  567. def OnSnap(self, event):
  568. """Snap selected features"""
  569. Debug.msg(2, "Digittoolbar.OnSnap():")
  570. self.action="snapLine"
  571. self.parent.MapWindow.mouse['box'] = 'box'
  572. def OnConnect(self, event):
  573. """Connect selected lines/boundaries"""
  574. Debug.msg(2, "Digittoolbar.OnConnect():")
  575. self.action="connectLine"
  576. self.parent.MapWindow.mouse['box'] = 'point'
  577. def OnQuery(self, event):
  578. """Query selected lines/boundaries"""
  579. Debug.msg(2, "Digittoolbar.OnQuery(): %s" % \
  580. UserSettings.Get(group='vdigit', key='query', subkey='type'))
  581. self.action="queryLine"
  582. self.parent.MapWindow.mouse['box'] = 'box'
  583. def OnZBulk(self, event):
  584. """Z bulk-labeling selected lines/boundaries"""
  585. Debug.msg(2, "Digittoolbar.OnZBulk():")
  586. self.action="zbulkLine"
  587. self.parent.MapWindow.mouse['box'] = 'line'
  588. def OnTypeConversion(self, event):
  589. """Feature type conversion
  590. Supported conversions:
  591. - point <-> centroid
  592. - line <-> boundary
  593. """
  594. Debug.msg(2, "Digittoolbar.OnTypeConversion():")
  595. self.action="typeConv"
  596. self.parent.MapWindow.mouse['box'] = 'box'
  597. def OnSelectMap (self, event):
  598. """
  599. Select vector map layer for editing
  600. If there is a vector map layer already edited, this action is
  601. firstly terminated. The map layer is closed. After this the
  602. selected map layer activated for editing.
  603. """
  604. if event.GetSelection() == 0: # create new vector map layer
  605. if self.layerSelectedID is not None:
  606. openVectorMap = self.layers[self.layerSelectedID].name.split('@')[0]
  607. else:
  608. openVectorMap = None
  609. mapName = gdialogs.CreateNewVector(self.parent,
  610. exceptMap=openVectorMap)
  611. if mapName:
  612. # add layer to map layer tree
  613. if self.layerTree:
  614. self.layerTree.AddLayer(ltype='vector',
  615. lname=mapName,
  616. lchecked=True,
  617. lopacity=1.0,
  618. lcmd=['d.vect', 'map=%s' % mapName])
  619. vectLayers = self.UpdateListOfLayers(updateTool=True)
  620. selection = vectLayers.index(mapName)
  621. else:
  622. pass # TODO (no Layer Manager)
  623. else:
  624. self.combo.SetValue(_('Select vector map'))
  625. return
  626. else:
  627. selection = event.GetSelection() - 1 # first option is 'New vector map'
  628. if self.layerSelectedID == selection:
  629. return False
  630. if self.layerSelectedID != None: # deactive map layer for editing
  631. self.StopEditing(self.layers[self.layerSelectedID])
  632. # select the given map layer for editing
  633. self.layerSelectedID = selection
  634. self.StartEditing(self.layers[self.layerSelectedID])
  635. event.Skip()
  636. return True
  637. def StartEditing (self, layerSelected):
  638. """
  639. Start editing of selected vector map layer.
  640. @param layerSelectedId id of layer to be edited
  641. @return True on success
  642. @return False on error
  643. """
  644. reload(vdigit)
  645. from vdigit import Digit as Digit
  646. self.parent.digit = Digit(mapwindow=self.parent.MapWindow)
  647. try:
  648. self.layerSelectedID = self.layers.index(layerSelected)
  649. mapLayer = self.layers[self.layerSelectedID]
  650. except:
  651. return False
  652. try:
  653. self.parent.digit.SetMapName(mapLayer.name)
  654. except gcmd.DigitError, e:
  655. self.layerSelectedID = None
  656. print >> sys.stderr, e # wxMessageBox
  657. return False
  658. # update toolbar
  659. self.combo.SetValue (layerSelected.name)
  660. self.parent.maptoolbar.combo.SetValue ('Digitize')
  661. # set initial category number for new features (layer=1), etc.
  662. Debug.msg (4, "VDigitToolbar.StartEditing(): layerSelectedID=%d layer=%s" % \
  663. (self.layerSelectedID, mapLayer.name))
  664. # deactive layer
  665. self.mapcontent.ChangeLayerActive(mapLayer, False)
  666. # change cursor
  667. if self.parent.MapWindow.mouse['use'] == 'pointer':
  668. self.parent.MapWindow.SetCursor(self.parent.cursors["cross"])
  669. # create pseudoDC for drawing the map
  670. self.parent.MapWindow.pdcVector = wx.PseudoDC()
  671. self.parent.digit.driver.SetDevice(self.parent.MapWindow.pdcVector)
  672. # self.parent.MapWindow.UpdateMap()
  673. if not self.parent.MapWindow.resize:
  674. self.parent.MapWindow.UpdateMap(render=True)
  675. return True
  676. def StopEditing (self, layerSelected):
  677. """
  678. Stop editing of selected vector map layer.
  679. """
  680. if self.layers[self.layerSelectedID] == layerSelected:
  681. self.layerSelectedID = None
  682. Debug.msg (4, "VDigitToolbar.StopEditing(): layer=%s" % \
  683. (layerSelected.name))
  684. self.combo.SetValue (_('Select vector map'))
  685. # save changes (only for vdigit)
  686. if UserSettings.Get(group='advanced', key='digitInterface', subkey='type') == 'vdigit':
  687. if UserSettings.Get(group='vdigit', key='saveOnExit', subkey='enabled') is False:
  688. dlg = wx.MessageDialog(parent=self.parent, message=_("Do you want to save changes "
  689. "in vector map <%s>?") % layerSelected.name,
  690. caption=_("Save changes?"),
  691. style=wx.YES_NO | wx.YES_DEFAULT | wx.ICON_QUESTION)
  692. if dlg.ShowModal() == wx.ID_NO:
  693. # revert changes
  694. self.parent.digit.Undo(0)
  695. dlg.Destroy()
  696. self.parent.digit.SetMapName(None) # -> close map
  697. # re-active layer
  698. item = self.parent.tree.FindItemByData('maplayer', layerSelected)
  699. if item and self.parent.tree.IsItemChecked(item):
  700. self.mapcontent.ChangeLayerActive(layerSelected, True)
  701. # change cursor
  702. self.parent.MapWindow.SetCursor(self.parent.cursors["default"])
  703. # disable pseudodc for vector map layer
  704. self.parent.MapWindow.pdcVector = None
  705. self.parent.digit.driver.SetDevice(None)
  706. self.parent.digit.__del__() # FIXME: destructor is not called here (del)
  707. self.parent.digit = None
  708. return True
  709. return False
  710. def UpdateListOfLayers (self, updateTool=False):
  711. """
  712. Update list of available vector map layers.
  713. This list consists only editable layers (in the current mapset)
  714. Optionaly also update toolbar
  715. """
  716. Debug.msg (4, "VDigitToolbar.UpdateListOfLayers(): updateTool=%d" % \
  717. updateTool)
  718. layerNameSelected = None
  719. if self.layerSelectedID != None: # name of currently selected layer
  720. layerNameSelected = self.layers[self.layerSelectedID].name
  721. # select vector map layer in the current mapset
  722. layerNameList = []
  723. self.layers = self.mapcontent.GetListOfLayers(l_type="vector",
  724. l_mapset=grassenv.GetGRASSVariable('MAPSET'))
  725. for layer in self.layers:
  726. if not layer.name in layerNameList: # do not duplicate layer
  727. layerNameList.append (layer.name)
  728. if updateTool: # update toolbar
  729. if self.layerSelectedID == None:
  730. value = _('Select vector map')
  731. else:
  732. value = layerNameSelected
  733. if not self.comboid:
  734. self.combo = wx.ComboBox(self.toolbar[self.numOfRows-1], id=wx.ID_ANY, value=value,
  735. choices=[_('New vector map'), ] + layerNameList, size=(105, -1),
  736. style=wx.CB_READONLY)
  737. self.comboid = self.toolbar[self.numOfRows-1].InsertControl(0, self.combo)
  738. self.parent.Bind(wx.EVT_COMBOBOX, self.OnSelectMap, self.comboid)
  739. else:
  740. self.combo.SetItems([_('New vector map'), ] + layerNameList)
  741. # update layer index
  742. try:
  743. self.layerSelectedID = layerNameList.index(value)
  744. except ValueError:
  745. self.layerSelectedID = None
  746. self.toolbar[self.numOfRows-1].Realize()
  747. return layerNameList
  748. class ProfileToolbar(AbstractToolbar):
  749. """
  750. Toolbar for digitization
  751. """
  752. def __init__(self, parent, mapdisplay, map):
  753. self.parent = parent
  754. self.mapcontent = map
  755. self.mapdisplay = mapdisplay
  756. self.toolbar = wx.ToolBar(parent=self.mapdisplay, id=wx.ID_ANY)
  757. # self.SetToolBar(self.toolbar)
  758. self.toolbar.SetToolBitmapSize(globalvar.toolbarSize)
  759. self.InitToolbar(self.mapdisplay, self.toolbar, self.ToolbarData())
  760. # realize the toolbar
  761. self.toolbar.Realize()
  762. def ToolbarData(self):
  763. """Toolbar data"""
  764. self.transect = wx.NewId()
  765. self.addraster = wx.NewId()
  766. self.draw = wx.NewId()
  767. self.options = wx.NewId()
  768. self.drag = wx.NewId()
  769. self.zoom = wx.NewId()
  770. self.unzoom = wx.NewId()
  771. self.erase = wx.NewId()
  772. self.save = wx.NewId()
  773. self.printer = wx.NewId()
  774. self.quit = wx.NewId()
  775. # tool, label, bitmap, kind, shortHelp, longHelp, handler
  776. return (
  777. (self.transect, 'transect', Icons["transect"].GetBitmap(),
  778. wx.ITEM_NORMAL, Icons["transect"].GetLabel(), Icons["transect"].GetDesc(),
  779. self.parent.OnDrawTransect),
  780. (self.addraster, 'raster', Icons["addrast"].GetBitmap(),
  781. wx.ITEM_NORMAL, Icons["addrast"].GetLabel(), Icons["addrast"].GetDesc(),
  782. self.parent.OnSelectRaster),
  783. (self.draw, 'profiledraw', Icons["profiledraw"].GetBitmap(),
  784. wx.ITEM_NORMAL, Icons["profiledraw"].GetLabel(), Icons["profiledraw"].GetDesc(),
  785. self.parent.OnCreateProfile),
  786. (self.options, 'options', Icons["profileopt"].GetBitmap(),
  787. wx.ITEM_NORMAL, Icons["profileopt"].GetLabel(), Icons["profileopt"].GetDesc(),
  788. self.parent.ProfileOptionsMenu),
  789. (self.drag, 'drag', Icons['pan'].GetBitmap(),
  790. wx.ITEM_NORMAL, Icons["pan"].GetLabel(), Icons["pan"].GetDesc(),
  791. self.parent.OnDrag),
  792. (self.zoom, 'zoom', Icons['zoom_in'].GetBitmap(),
  793. wx.ITEM_NORMAL, Icons["zoom_in"].GetLabel(), Icons["zoom_in"].GetDesc(),
  794. self.parent.OnZoom),
  795. (self.unzoom, 'unzoom', Icons['zoom_back'].GetBitmap(),
  796. wx.ITEM_NORMAL, Icons["zoom_back"].GetLabel(), Icons["zoom_back"].GetDesc(),
  797. self.parent.OnRedraw),
  798. (self.erase, 'erase', Icons["erase"].GetBitmap(),
  799. wx.ITEM_NORMAL, Icons["erase"].GetLabel(), Icons["erase"].GetDesc(),
  800. self.parent.OnErase),
  801. ("", "", "", "", "", "", ""),
  802. (self.save, 'save', Icons["savefile"].GetBitmap(),
  803. wx.ITEM_NORMAL, Icons["savefile"].GetLabel(), Icons["savefile"].GetDesc(),
  804. self.parent.SaveToFile),
  805. (self.printer, 'print', Icons["printmap"].GetBitmap(),
  806. wx.ITEM_NORMAL, Icons["printmap"].GetLabel(), Icons["printmap"].GetDesc(),
  807. self.parent.PrintMenu),
  808. (self.quit, 'quit', Icons["quit"].GetBitmap(),
  809. wx.ITEM_NORMAL, Icons["quit"].GetLabel(), Icons["quit"].GetDesc(),
  810. self.parent.OnQuit),
  811. )