001package jmri.jmrit.display.layoutEditor;
002
003import java.util.List;
004import java.util.stream.Stream;
005
006import javax.annotation.Nonnull;
007
008/**
009 * This interface serves as a manager for the overall layout model via
010 * collections of i.e. LayoutTurnout, LayoutBlock,
011 * PositionablePoint, Track Segment, LayoutSlip and LevelXing objects
012 * along with their corresponding *View objects.
013 * (Having *View objects here, which are specific to a panel, may
014 * only be here as a temporary measure)
015 * <p>
016 * Provides a temporary setDirty()/isDirty() and redrawPanel() mechanism
017 * for marking changes. That may have to grow and/or change. For
018 * example, redrawPanel()  (which could be renamed) might fire listeners to cause repaints.
019 * 
020 *
021 * @see LayoutEditorFindItems
022 * @see LayoutEditorAuxTools
023 *
024 * @author Bob Jacobsen Copyright: (c) 2020
025 */
026public interface LayoutModels {
027
028    /**
029     * Check the dirty state
030     *
031     * @return true if contents of models have changed,
032     */
033    public boolean isDirty();
034
035    public void setDirty();
036
037    /**
038     * A change has happen that might not need to be stored,
039     * but should cause the presentation to be updated.
040     */
041    public void redrawPanel();
042
043    // ====================================
044    // Access to related navigation objects
045    // ====================================
046
047    @Nonnull
048    public LayoutEditorAuxTools getLEAuxTools();
049        
050
051    // ====================================
052    // Access to (lists of) model objects
053    // ====================================
054
055    //
056    // General access. (temporary) Is this actually preferred to all those specific ones?
057    //
058
059    @Nonnull
060    Stream<LayoutTrack> getLayoutTracksOfClass(Class<? extends LayoutTrack> layoutTrackClass);
061
062    //
063    // General access. (temporary) Is this actually preferred to all those specific ones?
064    //
065    
066    @Nonnull
067    Stream<LayoutTrackView> getLayoutTrackViewsOfClass(Class<? extends LayoutTrackView> layoutTrackViewClass);
068    
069    @Nonnull
070    List<PositionablePointView> getPositionablePointViews();
071
072    @Nonnull
073    List<PositionablePoint> getPositionablePoints();
074
075    @Nonnull
076    List<LayoutSlip> getLayoutSlips();
077
078    @Nonnull
079    List<TrackSegmentView> getTrackSegmentViews();
080
081    @Nonnull
082    List<TrackSegment> getTrackSegments();
083
084    @Nonnull
085    List<LayoutTurnout> getLayoutTurnouts();
086
087    @Nonnull
088    List<LayoutTurntable> getLayoutTurntables();
089
090    @Nonnull
091    List<LayoutTraverser> getLayoutTraversers();
092
093    @Nonnull
094    List<LevelXing> getLevelXings();
095
096    @Nonnull
097    List<LevelXingView> getLevelXingViews();
098
099    /**
100     * Read-only access to the list of LayoutTrack family objects.
101     * The returned list will throw UnsupportedOperationException
102     * if you attempt to modify it.
103     * @return unmodifiable copy of layout track list.
104     */
105    @Nonnull
106    List<LayoutTrack> getLayoutTracks();
107
108    /**
109     * Read-only access to the list of LayoutTrackView family objects.
110     * The returned list will throw UnsupportedOperationException
111     * if you attempt to modify it.
112     * @return unmodifiable copy of track views.
113     */
114    @Nonnull
115    List<LayoutTrackView> getLayoutTrackViews();
116
117    // temporary
118    LayoutTrackView getLayoutTrackView(LayoutTrack trk);
119    
120    // temporary
121    LevelXingView getLevelXingView(LevelXing xing);
122    
123    // temporary
124    LayoutTurnoutView getLayoutTurnoutView(LayoutTurnout to);
125    
126    // temporary
127    LayoutTurntableView getLayoutTurntableView(LayoutTurntable to);
128
129    // temporary
130    LayoutTraverserView getLayoutTraverserView(LayoutTraverser to);
131        
132    // temporary
133    TrackSegmentView getTrackSegmentView(TrackSegment to);
134
135    // temporary
136    PositionablePointView getPositionablePointView(PositionablePoint to);
137        
138    /**
139     * Add a LayoutTrack and LayoutTrackView to the list of 
140     * LayoutTrack family objects.
141     * @param trk to be stored
142     * @param v corresponding view
143     */
144    void addLayoutTrack(@Nonnull LayoutTrack trk, @Nonnull LayoutTrackView v);
145
146    /**
147     * If item present, delete from the list of LayoutTracks
148     * and force a dirty redraw.
149     * @param trk the layout track to remove.
150     */
151    void removeLayoutTrack(@Nonnull LayoutTrack trk);
152    
153    @Nonnull
154    List<LayoutTurnout> getLayoutTurnoutsAndSlips();
155
156    @Nonnull
157    List<LayoutShape> getLayoutShapes();
158
159    /**
160     * Compute octagonal direction of vector from p1 to p2.
161     * <p>
162     * The octagonal (8) directions are: North, North-East, East,
163     * South-East, South, South-West, West and North-West; see
164     * {@link jmri.Path} for more on this.
165     *
166     * <p>
167     * This method must eventually be in terms _other_ than
168     * the screen geometry of the associated LayoutTrackView objects, 
169     * as it's meant to be the track connectivity direction not the
170     * on the screen implementation.
171     *
172     * @param trk1 track at "from" end
173     * @param h1 the hit point for "from" end
174     * @param trk2 the track at the "to" end
175     * @param h2 the hit at the "to" end
176     * @return the octagonal direction from p1 to p2
177     */
178    public int computeDirection(@Nonnull LayoutTrack trk1, @Nonnull HitPointType h1, 
179                                @Nonnull LayoutTrack trk2, @Nonnull HitPointType h2);
180
181    public int computeDirectionToCenter( @Nonnull LayoutTrack trk1, @Nonnull HitPointType h1, @Nonnull PositionablePoint p);
182    
183    public int computeDirectionFromCenter( @Nonnull PositionablePoint p, @Nonnull LayoutTrack trk1, @Nonnull HitPointType h1);
184
185    default public int computeDirectionAB( @Nonnull LayoutTurnout track) {
186        LayoutTurnoutView tv = getLayoutTurnoutView(track);
187        return jmri.Path.computeDirection(tv.getCoordsA(), tv.getCoordsB());
188    }
189
190    default public int computeDirectionAC( @Nonnull LayoutTurnout track) {
191        LayoutTurnoutView tv = getLayoutTurnoutView(track);
192        return jmri.Path.computeDirection(tv.getCoordsA(), tv.getCoordsC());
193    }
194
195    default public int computeDirectionAD( @Nonnull LayoutTurnout track) {
196        LayoutTurnoutView tv = getLayoutTurnoutView(track);
197        return jmri.Path.computeDirection(tv.getCoordsA(), tv.getCoordsD());
198    }
199
200    default public int computeDirectionBC( @Nonnull LayoutTurnout track) {
201        LayoutTurnoutView tv = getLayoutTurnoutView(track);
202        return jmri.Path.computeDirection(tv.getCoordsB(), tv.getCoordsC());
203    }
204
205    default public int computeDirectionBD( @Nonnull LayoutTurnout track) {
206        LayoutTurnoutView tv = getLayoutTurnoutView(track);
207        return jmri.Path.computeDirection(tv.getCoordsB(), tv.getCoordsD());
208    }
209
210    default public int computeDirectionCD( @Nonnull LayoutTurnout track) {
211        LayoutTurnoutView tv = getLayoutTurnoutView(track);
212        return jmri.Path.computeDirection(tv.getCoordsC(), tv.getCoordsD());
213    }
214
215    /**
216     * Invoked to display a warning about removal.
217     * Lists the attached items that prevent removing the layout track item.
218     * <p>
219     * The default implementation refers this to a View object for displaying a Dialog.
220     *
221     * @param track The involved track
222     * @param itemList A list of the attached heads, masts and/or sensors.
223     * @param typeKey  The object type such as Turnout, Level Crossing, etc.
224     */
225    default public void displayRemoveWarning(LayoutTrack track, List<String> itemList, String typeKey) {
226        getLayoutTrackView(track).displayRemoveWarningDialog(itemList, typeKey);
227    }
228
229
230}