Friday, August 28, 2015

OL3 (v3.20.0 ), draw holes on polygons. (javascript)

As ol3 have not yet implemented the "draw hole" vector functionality, I did a bit of work to achive it. So, in the meantime, my approach may help you. After the last update it works using 3.20.0 latest openlayers3 version. Propably it works with older versions as well but havent tested.

Also not that I use jsts library in order to verify whether drawn hole vertex is inside a polygon. 

Here is a demo  here(jsfiddle) (updated on 16/12/2016)

preview




It only works for simple (not multi) polygons. But you may add as many holes you like in a single polygon. It also lucks the visual hole effect during drawing (fixed with the new update).
Also prevents the draw hole ouside the selected polygon. 
I ll try to work with these and if I get something better I ll let you know.

11 comments:

  1. Nice work.

    Is it possible to use a function that calls map.forEachFeatureAtPixel() to detect if the click event is over the selected feature, rather than using the isPointInPoly function? This way you could also prevent creating holes with vertices inside preexisting holes.

    I also noticed that when a draw is finished, its "selected" state is dependent on where your cursor is located. If the cursor is just inside the hole, the selected polygon will unselect itself, but if the cursor is just outside the hole, the polygon remains selected. I have a similar problem with the project I'm working on. The problem is that the selection event is always resolved after drawend. Do you know of a way to force the polygon to remain selected after drawend?

    ReplyDelete
    Replies
    1. Thanks for suggestions.
      I ll try to use the map.forEachFeatureAtPixel() function and I ll let you know.
      I cant reproduce your second comment, I still have the feature selected when 'drawend' event fires , whether my cursur is over the polygon or within the newly hole created. I checked it with both firefox and chrome. What browser do you use????

      Delete
    2. I too use chrome. I actually solved the second problem and posted the result in a jsfiddle on stackoverflow.

      http://jsfiddle.net/williemaddox/0um2ud3v/

      Regardless, it is very strange that your feature remains selected when your final mouse click is over a hole.

      Delete
    3. this is printscreen during hole draw.
      and this is when double click to finish hole and so drawend event fires
      I have used firefox for the printscreens.
      Your fiddle is nice , gave me some ideas. thanks for sharing.

      Delete
    4. For your first question map.forEachFeatureAtPixel() . Could not use it , though in order to avoid the side effect of drawing hole verts within an existing polygon hole, I made a new fiddle that solves the problem.
      But this fiddle uses the jsts topology suite in order to verify whether point drawn is inside the polygon (including holes and not just the exterior ring of the supplied polygon).
      You may check the fiddle here.

      Delete
    5. The autoselect problem I am seeing is when you finish the draw hole by letting the final point snap to the initial point.
      After it snaps, you have a small invisible circular area centered on the snap coordinate within which you can move the mouse around and remain in the snap state. If you stay within this "invisible" area, but move the mouse slightly such that it is also over the hole, then the original selected feature (new hole included) will unselect itself when you click to finish. Finishing a draw by double-clicking always keeps the original feature selected because the mouse position and the position of the final polygon coordinate are the same.

      Delete
    6. Ok now its clear. I managed to reproduse. It is happening because last click is taking place once select interaction is enabled back. So you click outside polygon and unselect action is taking place. And this is happening because the single-click event is taking place 251ms after you clicked. It is a known issue -->check it here. I use double-click to finish my drawing.
      You can comment out the last action of click event "selectInt.setActive(true);" (at the bottom of my js fiddle). But then you must have a method to enable back the select interaction. For example a button that enables/disables select interaction. In most cases i dont have at all the select interaction.
      One other think you may try is to renable the select interaction with delay. like so
      setTimeout(function(){
      selectInt.setActive(true)
      },300)
      ;
      I tried it and it worked well, though I hate setTimeout technique. But I guess soon or later OL3 should fix it.
      It depends on what you want to achieve. If you need to do something specific and can't get it, let me know if I can help. Thanks for the feedback.

      Delete
    7. I was merely trying to explain in detail the problem to see if you could reproduce it and I am glad that you could. I would have been stumped had it been a browser issue. I actually solved it in the fiddle I posted previously (i.e. on Oct. 16). Have a look at how I implemented the conditions for the Select interaction and it should be clear. I also didn't like the thought of using setTimeout to fix this. Not a proper workaround IMHO.

      Delete
  2. sorry I am not using so often "select interaction", so I am not very familiar with it. Thats why I have minimal configuration when initialising it (in the fiddle of topic) . I aslo use double click for 'drawend', so we had a bad combination and thus create the false reproduction::)))).
    I had a glance in your fiddle. Do you think this would work in the case above? I tried it but couldnt make it. Though is clear what you do. To be honest I didnt try so hard :)))))))). If you have some spare time try to make a fiddle so I can update the post.Ι would be more than greatful. Thanks again.

    ReplyDelete
  3. This comment has been removed by a blog administrator.

    ReplyDelete
  4. This comment has been removed by a blog administrator.

    ReplyDelete

Urban Growth Lab - UGLab

Proud to release a first version of the UGLab project .  UGLab is a python open source project capable to execute Urban Growth predictions f...