// // // // // $Revision$ // using System; using System.Collections.Generic; using System.Drawing; namespace ICSharpCode.TextEditor.Document { /// /// Manages the list of markers and provides ways to retrieve markers for specific positions. /// public sealed class MarkerStrategy { List textMarker = new List(); IDocument document; public IDocument Document { get { return document; } } public IEnumerable TextMarker { get { return textMarker.AsReadOnly(); } } public void AddMarker(TextMarker item) { markersTable.Clear(); textMarker.Add(item); } public void InsertMarker(int index, TextMarker item) { markersTable.Clear(); textMarker.Insert(index, item); } public void RemoveMarker(TextMarker item) { markersTable.Clear(); textMarker.Remove(item); } public void RemoveAll(Predicate match) { markersTable.Clear(); textMarker.RemoveAll(match); } public MarkerStrategy(IDocument document) { this.document = document; document.DocumentChanged += new DocumentEventHandler(DocumentChanged); } Dictionary> markersTable = new Dictionary>(); public List GetMarkers(int offset) { if (!markersTable.ContainsKey(offset)) { List markers = new List(); for (int i = 0; i < textMarker.Count; ++i) { TextMarker marker = (TextMarker)textMarker[i]; if (marker.Offset <= offset && offset <= marker.EndOffset) { markers.Add(marker); } } markersTable[offset] = markers; } return markersTable[offset]; } public List GetMarkers(int offset, int length) { int endOffset = offset + length - 1; List markers = new List(); for (int i = 0; i < textMarker.Count; ++i) { TextMarker marker = (TextMarker)textMarker[i]; if (// start in marker region marker.Offset <= offset && offset <= marker.EndOffset || // end in marker region marker.Offset <= endOffset && endOffset <= marker.EndOffset || // marker start in region offset <= marker.Offset && marker.Offset <= endOffset || // marker end in region offset <= marker.EndOffset && marker.EndOffset <= endOffset ) { markers.Add(marker); } } return markers; } public List GetMarkers(TextLocation position) { if (position.Y >= document.TotalNumberOfLines || position.Y < 0) { return new List(); } LineSegment segment = document.GetLineSegment(position.Y); return GetMarkers(segment.Offset + position.X); } void DocumentChanged(object sender, DocumentEventArgs e) { // reset markers table markersTable.Clear(); document.UpdateSegmentListOnDocumentChange(textMarker, e); } } }