diff --git a/Source/Plugins/BuilderModes/ClassicModes/LinedefsMode.cs b/Source/Plugins/BuilderModes/ClassicModes/LinedefsMode.cs index 8bdbde6..5292a52 100644 --- a/Source/Plugins/BuilderModes/ClassicModes/LinedefsMode.cs +++ b/Source/Plugins/BuilderModes/ClassicModes/LinedefsMode.cs @@ -69,6 +69,10 @@ namespace CodeImp.DoomBuilder.BuilderModes new private bool editpressed; private bool selectionfromhighlight; //mxd + // The blockmap makes is used to make finding lines faster + BlockMap blockmap; + + // Stores sizes of the text for text labels so that they only have to be computed once private Dictionary textlabelsizecache; @@ -540,9 +544,20 @@ namespace CodeImp.DoomBuilder.BuilderModes labels.Add(linedef, l); } } - + + /// + /// Create a blockmap containing linedefs. This is used to speed up determining the closest line + /// to the mouse cursor + /// + private void CreateBlockmap() + { + RectangleF area = MapSet.CreateArea(General.Map.Map.Vertices); + blockmap = new BlockMap(area); + blockmap.AddLinedefsSet(General.Map.Map.Linedefs); + } + #endregion - + #region ================== Events public override void OnHelp() @@ -594,6 +609,9 @@ namespace CodeImp.DoomBuilder.BuilderModes BuilderPlug.Me.MenusForm.SyncronizeThingEditButton.ToolTipText = "Synchronized Things Editing" + Environment.NewLine + BuilderPlug.Me.MenusForm.SyncronizeThingEditLinedefsItem.ToolTipText; General.Interface.EndToolbarUpdate(); //mxd + // Create the blockmap + CreateBlockmap(); + // Convert geometry selection to linedefs selection General.Map.Map.ConvertSelection(SelectionType.Linedefs); UpdateSelectionInfo(); //mxd @@ -931,6 +949,9 @@ namespace CodeImp.DoomBuilder.BuilderModes { base.OnUndoEnd(); + // Recreate the blockmap to not include the potentially un-done lines anymore + CreateBlockmap(); + // Select changed map elements if (BuilderPlug.Me.SelectChangedafterUndoRedo) { @@ -952,6 +973,9 @@ namespace CodeImp.DoomBuilder.BuilderModes { base.OnRedoEnd(); + // Recreate the blockmap to include the potentially re-done linedefs again + CreateBlockmap(); + // Select changed map elements if (BuilderPlug.Me.SelectChangedafterUndoRedo) { @@ -989,7 +1013,7 @@ namespace CodeImp.DoomBuilder.BuilderModes else if(paintselectpressed && !editpressed && !selecting) //mxd. Drag-select { // Find the nearest thing within highlight range - Linedef l = General.Map.Map.NearestLinedefRange(mousemappos, BuilderPlug.Me.HighlightRange / renderer.Scale); + Linedef l = MapSet.NearestLinedefRange(blockmap, mousemappos, BuilderPlug.Me.HighlightRange / renderer.Scale); if(l != null) { @@ -1021,11 +1045,11 @@ namespace CodeImp.DoomBuilder.BuilderModes else if(e.Button == MouseButtons.None) // Not holding any buttons? { // Find the nearest linedef within highlight range - Linedef l = General.Map.Map.NearestLinedefRange(mousemappos, BuilderPlug.Me.HighlightRange / renderer.Scale); + Linedef l = MapSet.NearestLinedefRange(blockmap, mousemappos, BuilderPlug.Me.HighlightRange / renderer.Scale); //mxd. Render insert vertex preview - Linedef sl = General.Map.Map.NearestLinedefRange(mousemappos, BuilderPlug.Me.StitchRange / renderer.Scale); - if(sl != null) + Linedef sl = MapSet.NearestLinedefRange(blockmap, mousemappos, BuilderPlug.Me.StitchRange / renderer.Scale); + if (sl != null) { bool snaptogrid = General.Interface.ShiftState ^ General.Interface.SnapToGrid; bool snaptonearest = General.Interface.CtrlState ^ General.Interface.AutoMerge; @@ -1520,6 +1544,9 @@ namespace CodeImp.DoomBuilder.BuilderModes General.Map.IsChanged = true; General.Map.Map.Update(); + // Recreate the blockmap since it shouldn't include the deleted linedefs anymore + CreateBlockmap(); + // Redraw screen SetupSectorLabels(); //mxd UpdateSelectionInfo(); //mxd @@ -1606,7 +1633,10 @@ namespace CodeImp.DoomBuilder.BuilderModes // Update cache values General.Map.IsChanged = true; General.Map.Map.Update(); - + + // Recreate the blockmap since it shouldn't include the dissolved linedefs anymore + CreateBlockmap(); + // Redraw screen SetupSectorLabels(); //mxd UpdateSelectionInfo(); //mxd diff --git a/Source/Plugins/BuilderModes/ClassicModes/SectorsMode.cs b/Source/Plugins/BuilderModes/ClassicModes/SectorsMode.cs index 8c39c87..606831c 100644 --- a/Source/Plugins/BuilderModes/ClassicModes/SectorsMode.cs +++ b/Source/Plugins/BuilderModes/ClassicModes/SectorsMode.cs @@ -76,6 +76,7 @@ namespace CodeImp.DoomBuilder.BuilderModes // The blockmap makes synchronized editing faster BlockMap blockmap; + bool addedlinedefstoblockmap; // Stores sizes of the text for text labels so that they only have to be computed once private Dictionary textlabelsizecache; @@ -755,6 +756,10 @@ namespace CodeImp.DoomBuilder.BuilderModes blockmap = new BlockMap(area); blockmap.AddSectorsSet(General.Map.Map.Sectors); blockmap.AddThingsSet(General.Map.Map.Things); + + // Don't add linedefs here. They are only needed for paint select, so let's save some + // time (and add them when paint select is used t he first time) + addedlinedefstoblockmap = false; } #endregion @@ -1162,8 +1167,15 @@ namespace CodeImp.DoomBuilder.BuilderModes } else if(paintselectpressed && !editpressed && !selecting) //mxd. Drag-select { + // If linedefs were not added to the blockmap yet add them here + if (!addedlinedefstoblockmap) + { + blockmap.AddLinedefsSet(General.Map.Map.Linedefs); + addedlinedefstoblockmap = true; + } + // Find the nearest linedef within highlight range - Linedef l = General.Map.Map.NearestLinedefRange(mousemappos, BuilderPlug.Me.HighlightRange / renderer.Scale); + Linedef l = MapSet.NearestLinedefRange(blockmap, mousemappos, BuilderPlug.Me.HighlightRange / renderer.Scale); Sector s = null; if(l != null) diff --git a/Source/Plugins/BuilderModes/ClassicModes/VerticesMode.cs b/Source/Plugins/BuilderModes/ClassicModes/VerticesMode.cs index e99d312..c00f1d3 100644 --- a/Source/Plugins/BuilderModes/ClassicModes/VerticesMode.cs +++ b/Source/Plugins/BuilderModes/ClassicModes/VerticesMode.cs @@ -56,6 +56,9 @@ namespace CodeImp.DoomBuilder.BuilderModes new private bool editpressed; private bool selectionfromhighlight; //mxd + // The blockmap makes is used to make finding lines faster + BlockMap blockmap; + #endregion #region ================== Properties @@ -70,6 +73,17 @@ namespace CodeImp.DoomBuilder.BuilderModes #region ================== Methods + /// + /// Create a blockmap containing linedefs. This is used to speed up determining the closest line + /// to the mouse cursor + /// + private void CreateBlockmap() + { + RectangleF area = MapSet.CreateArea(General.Map.Map.Vertices); + blockmap = new BlockMap(area); + blockmap.AddLinedefsSet(General.Map.Map.Linedefs); + } + public override void OnHelp() { General.ShowHelp("e_vertices.html"); @@ -107,6 +121,9 @@ namespace CodeImp.DoomBuilder.BuilderModes General.Interface.AddButton(BuilderPlug.Me.MenusForm.PerpendicularLinedef); //JBR General.Interface.AddButton(BuilderPlug.Me.MenusForm.ParallelLinedef); //JBR + // Create the blockmap + CreateBlockmap(); + // Convert geometry selection to vertices only General.Map.Map.ConvertSelection(SelectionType.Vertices); UpdateSelectionInfo(); //mxd @@ -304,7 +321,7 @@ namespace CodeImp.DoomBuilder.BuilderModes else if(!selecting) //mxd. We don't want to do this stuff while multiselecting { // Find the nearest linedef within highlight range - Linedef l = General.Map.Map.NearestLinedefRange(mousemappos, BuilderPlug.Me.SplitLinedefsRange / renderer.Scale); + Linedef l = MapSet.NearestLinedefRange(blockmap, mousemappos, BuilderPlug.Me.SplitLinedefsRange / renderer.Scale); if(l != null) { // Create undo @@ -481,7 +498,7 @@ namespace CodeImp.DoomBuilder.BuilderModes else if(e.Button == MouseButtons.None) // Not holding any buttons? { //mxd. Render insert vertex preview - Linedef l = General.Map.Map.NearestLinedefRange(mousemappos, BuilderPlug.Me.SplitLinedefsRange / renderer.Scale); + Linedef l = MapSet.NearestLinedefRange(blockmap, mousemappos, BuilderPlug.Me.SplitLinedefsRange / renderer.Scale); if(l != null) { @@ -555,6 +572,22 @@ namespace CodeImp.DoomBuilder.BuilderModes Highlight(null); } + public override void OnUndoEnd() + { + base.OnUndoEnd(); + + // Recreate the blockmap + CreateBlockmap(); + } + + public override void OnRedoEnd() + { + base.OnRedoEnd(); + + // Recreate the blockmap + CreateBlockmap(); + } + //mxd protected override void BeginViewPan() { @@ -851,7 +884,7 @@ namespace CodeImp.DoomBuilder.BuilderModes General.Map.UndoRedo.CreateUndo("Insert vertex"); // Snap to geometry? - Linedef l = General.Map.Map.NearestLinedefRange(mousemappos, BuilderPlug.Me.SplitLinedefsRange / renderer.Scale); + Linedef l = MapSet.NearestLinedefRange(blockmap, mousemappos, BuilderPlug.Me.SplitLinedefsRange / renderer.Scale); if(snaptonearest && (l != null)) { // Snip to grid also? @@ -912,7 +945,7 @@ namespace CodeImp.DoomBuilder.BuilderModes if(snaptonearest) { //mxd. Check if snapped vertex is still on top of a linedef - l = General.Map.Map.NearestLinedefRange(v.Position, BuilderPlug.Me.SplitLinedefsRange / renderer.Scale); + l = MapSet.NearestLinedefRange(blockmap, v.Position, BuilderPlug.Me.SplitLinedefsRange / renderer.Scale); if(l != null) {