1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
package Torello.HTML.NodeSearch;

import Torello.HTML.DotPair;

/**
 * This exception is thrown when attempts to violate a <CODE><B>Cursor Boundary Window
 * Contract</B></CODE> <I>(possibly rendering the window invalid)</I> are made inside any of the
 * methods exported by the <CODE>AbstractHNLI, HNLI</CODE> or <CODE>HNLIInclusive</CODE> iterators.
 * 
 * <BR /><BR />A {@code Cursor Bounds Window} is created for a given {@code HTML Node List Iterator
 * (HNLI, or HNLIInclusive} by invoking the method {@code restrictCursor(...)}.  When such a
 * bounding limit is set for an {@code HNLI}, the returned {@code Iterator}-matches that lay
 * outside these limits shall be ignored <I>(cannot be returned)</I> by the {@code Iterator}.
 *
 * <BR /><BR />Internally, the {@code Iterator} code easily avoids returning such user-requested
 * out-of-bounds matches.  <B><I>However</I></B>, if any of the {@code HNLI} "setter" methods 
 * attempt to set a portion of the vectorized-html that is not within the bounds that were set
 * by the programmer, this exception shall throw.
 *
 * <BR /><BR /><EMBED CLASS="external-html" DATA-FILE-ID=EXPM>
 */
public class CursorException  extends IllegalArgumentException
{
    /** <EMBED CLASS="external-html" DATA-FILE-ID="SVUIDEX">  */
    public static final long serialVersionUID = 1;

    /**
     * <EMBED CLASS="external-html" DATA-FILE-ID="EXPF">
     * 
     * <BR /><BR />This will contain the value for {@code minCursor} defined in an {@code HTML Node
     * Iterator's} settings for the {@code Cursor Bounds}.
     */
    public final int minCursor;

    /**
     * <EMBED CLASS="external-html" DATA-FILE-ID="EXPF">
     * 
     * <BR /><BR />This will contain the value for {@code maxCursor} defined in an {@code HTML Node
     * Iterator's} settings for the {@code Cursor Bounds}.
     */
    public final int maxCursor;

    /**
     * <EMBED CLASS="external-html" DATA-FILE-ID="EXPF">
     * 
     * <BR /><BR />This will contain the value for passed to an {@code HNLI Iterator}
     * <B>'setter'</B> method which was not within the bounds of the supplied
     * {@code Cursor Boundary Window}.
     */
    public final int pos;

    /**
     * Constructs a new exception with the specified detail message, and the two {@code public,
     * final} parameters: {@code maxCursor, minCursor} and {@code pos}.
     * 
     * @param message the detail message.
     * 
     * @param minCursor This was the setting for the {@code Cursor Boundary Window} inside an
     * instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param maxCursor This was the setting for the {@code Cursor Boundary Window} inside an
     * instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param pos The position that generated this exception throw.
     * 
     * @see #minCursor
     * @see #maxCursor
     * @see #pos
     */
    public CursorException(String message, int minCursor, int maxCursor, int pos)
    {
        super(message);
        this.minCursor  = minCursor;
        this.maxCursor  = maxCursor;
        this.pos        = pos;
    }


    /**
     * Constructs a new exception with the specified detail message, and the two {@code public,
     * final} parameters: {@code maxCursor, minCursor} and {@code pos}.
     * 
     * @param message The detail message (which is saved for later retrieval by the
     * {@code Throwable.getMessage()} method).
     * 
     * @param cause the cause (which is saved for later retrieval by the
     * {@code Throwable.getCause()} method).  (A null value is permitted, and indicates that the
     * cause is nonexistent or unknown).
     * 
     * @param minCursor This was the setting for the {@code Cursor Boundary Window} inside an
     * instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param maxCursor This was the setting for the {@code Cursor Boundary Window} inside an
     * instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param pos The position that generated this exception throw.
     * 
     * @see #minCursor
     * @see #maxCursor
     * @see #pos
     */
    public CursorException
        (String message, Throwable cause, int minCursor, int maxCursor, int pos)
    {
        super(message);
        this.minCursor  = minCursor;
        this.maxCursor  = maxCursor;
        this.pos        = pos;
    }

    /**
     * Checks that a supplied position parameter, {@code 'pos'}, is within the bounds of a
     * given window, and throws an appropriately formatted exception if it is not.
     * 
     * @param minCursor This is the setting for a {@code Cursor Boundary Window} which was applied
     * to an instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param maxCursor This is the setting for a {@code Cursor Boundary Window} which was applied
     * to an instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param pos This is the position to be checked against the window bounds.
     * 
     * @throws CursorException Throws this exception if the provided position parameter
     * {@code 'pos'} is not within the supplied {@code Cursor Bounds}.
     * 
     * @see #minCursor
     * @see #maxCursor
     * @see #pos
     */
    public static void check (int minCursor, int maxCursor, int pos)
    {
        if ((maxCursor == -1) && (minCursor == -1)) return;

        if (pos < minCursor) throw new CursorException(
            "This iterator has had a Minimum-Cursor index [" + minCursor + "] set using the " +
            "restrictCursor(...) method.  Unfortunately, the position passed as a " +
            "parameter [" + pos + "], is less than this minimum-cursor index.",
            minCursor, maxCursor, pos
        );

        if (pos > maxCursor) throw new CursorException(
            "This iterator has had a Maximum-Cursor index [" + maxCursor + "] set using the " +
            "restrictCursor(...) method.  Unfortunately, the DotPair 'range' passed as a " +
            "parameter [" + pos + "], is greater than this maximum-cursor index.",
            minCursor, maxCursor, pos
        );
    }

    /**
     * Checks that a supplied {@code DotPair} parameter, {@code 'dp'}, is <B>FULLY</B> within the
     * bounds (READ: <I>both</I> {@code DotPair.start} <I>and</I> {@code DotPair.end}) of a given
     * window, and throws an appropriately formatted exception if it is not.
     * 
     * @param minCursor This is the setting for a {@code Cursor Boundary Window} which was applied
     * to an instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param maxCursor This is the setting for a {@code Cursor Boundary Window} which was applied
     * to an instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param dp This is the sub-list or sub-section to be checked against the window bounds.
     * It must <I>fully lay within the provided window</I> in order for this method to avoid
     * throwing the {@code CursorException}.
     * 
     * @throws CursorException Throws this exception if the provided position parameter
     * {@code 'pos'} is not within the supplied {@code Cursor Bounds}.
     * 
     * @see #minCursor
     * @see #maxCursor
     * @see #pos
     */
    public static void check(int minCursor, int maxCursor, DotPair dp)
    {
        if ((maxCursor == -1) && (minCursor == -1)) return;

        if (dp.start < minCursor) throw new CursorException(
            "This iterator has had a Minimum-Cursor index [" + minCursor + "] set using the " +
            "restrictCursor(...) method.  Unfortunately, the DotPair 'range' " + dp + " passed " +
            "as a paremter starts before this minimum-cursor index.",
            minCursor, maxCursor, dp.start
        );

        if (dp.end > maxCursor) throw new CursorException(
            "This iterator has had a Maximum-Cursor index [" + maxCursor + "] set using the " +
            "restrictCursor(...) method.  Unfortunately, the DotPair 'range' " + dp + " passed " +
            "as a paremter extends past this maximum-cursor index.",
            minCursor, maxCursor, dp.end
        );
    }

    /**
     * Checks that each an every index-position from a supplied position-array parameter, 
     * {@code 'posArr'}, is within the bounds of a given window, and throws an appropriately
     * formatted exception if <I>any of the indices in {@code 'posArr'} are not within
     * the windows bounds.</I>
     * 
     * @param minCursor This is the setting for a {@code Cursor Boundary Window} which was applied
     * to an instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param maxCursor This is the setting for a {@code Cursor Boundary Window} which was applied
     * to an instance of {@code HTML Node List Iterator}, when an exception threw.
     * 
     * @param posArr This is the {@code int[]} position-array to be checked against the window
     * bounds.  It value in this array <I>must be within the provided window</I> in order for this
     * method to avoid throwing the {@code CursorException}.
     * 
     * @throws CursorException Throws this exception if the provided position parameter
     * {@code 'pos'} is not within the supplied {@code Cursor Bounds}.
     * 
     * @see #minCursor
     * @see #maxCursor
     * @see #pos
     */
    public static void check(int minCursor, int maxCursor, int[] posArr)
    {
        if ((maxCursor == -1) && (minCursor == -1)) return;

        int pos; // Temp Var

        for (int i=0; i < posArr.length; i++)
            if ((pos=posArr[i]) < minCursor) throw new CursorException(
                "This iterator has had a Minimum-Cursor, index [" + minCursor + "] set using " +
                "the restrictCursor(...) method.  Unfortunately, One of the elements of the " +
                "indices-list var-args array (parameter 'posArr') contains a Vector-position " +
                "index [" + pos + "], at varargs-array index [" + i + "] that is less than " +
                "this Minimum Cursor Vale.", minCursor, maxCursor, pos
            );
            else if (pos > maxCursor) throw new CursorException(
                "This iterator has had a Maximum-Cursor, index [" + maxCursor + "] set using " +
                "the setCursorBounds(...) method.  Unfortunately, One of the elements of the " +
                "indices-list var-args array (parameter 'posArr') contains a Vector-position " +
                "index [" + pos + "], at varargs-array index [" + i + "] that is greater than " +
                "this Maximum Cursor Vale.", minCursor, maxCursor, pos
            );
    }
}