1010import ch .njol .skript .lang .SkriptParser .ParseResult ;
1111import ch .njol .skript .lang .simplification .SimplifiedLiteral ;
1212import ch .njol .skript .lang .util .SimpleExpression ;
13- import ch .njol .skript .registrations .Feature ;
1413import ch .njol .skript .util .LiteralUtils ;
1514import ch .njol .skript .util .Patterns ;
1615import ch .njol .util .Kleenean ;
4847public class ExprElement <T > extends SimpleExpression <T > implements KeyProviderExpression <T > {
4948
5049 private static final Patterns <ElementType []> PATTERNS = new Patterns <>(new Object [][]{
51- {"[the] (first|1:last) element [out] of %objects%" , new ElementType [] {ElementType .FIRST_ELEMENT , ElementType .LAST_ELEMENT }},
52- {"[the] (first|1:last) %integer% elements [out] of %objects%" , new ElementType [] {ElementType .FIRST_X_ELEMENTS , ElementType .LAST_X_ELEMENTS }},
53- {"[a] random element [out] of %objects%" , new ElementType [] {ElementType .RANDOM }},
54- {"[the] %integer%(st|nd|rd|th) [1:[to] last] element [out] of %objects%" , new ElementType [] {ElementType .ORDINAL , ElementType .TAIL_END_ORDINAL }},
55- {"[the] elements (from|between) %integer% (to|and) %integer% [out] of %objects%" , new ElementType [] {ElementType .RANGE }},
56-
57- {"[the] (first|next|1:last) element (of|in) %queue%" , new ElementType [] {ElementType .FIRST_ELEMENT , ElementType .LAST_ELEMENT }},
58- {"[the] (first|1:last) %integer% elements (of|in) %queue%" , new ElementType [] {ElementType .FIRST_X_ELEMENTS , ElementType .LAST_X_ELEMENTS }},
59- {"[a] random element (of|in) %queue%" , new ElementType [] {ElementType .RANDOM }},
60- {"[the] %integer%(st|nd|rd|th) [1:[to] last] element (of|in) %queue%" , new ElementType [] {ElementType .ORDINAL , ElementType .TAIL_END_ORDINAL }},
61- {"[the] elements (from|between) %integer% (to|and) %integer% (of|in) %queue%" , new ElementType [] {ElementType .RANGE }},
50+ {"[the] (first|1:last) element [out] (of|in) %objects%" , new ElementType []{ElementType .FIRST_ELEMENT , ElementType .LAST_ELEMENT }},
51+ {"[the] (first|1:last) %integer% elements [out] (of|in) %objects%" , new ElementType []{ElementType .FIRST_X_ELEMENTS , ElementType .LAST_X_ELEMENTS }},
52+ {"[a] random element [out] (of|in) %objects%" , new ElementType []{ElementType .RANDOM }},
53+ {"[the] %integer%(st|nd|rd|th) [1:[to] last] element [out] (of|in) %objects%" , new ElementType []{ElementType .ORDINAL , ElementType .TAIL_END_ORDINAL }},
54+ {"[the] elements (from|between) %integer% (to|and) %integer% [out] (of|in) %objects%" , new ElementType []{ElementType .RANGE }},
6255 });
6356
6457 static {
@@ -132,23 +125,16 @@ public <T> Iterator<T> apply(Iterator<T> iterator, int startIndex, int endIndex)
132125 private final Map <Event , List <String >> cache = new WeakHashMap <>();
133126
134127 private Expression <? extends T > expr ;
135- private @ Nullable Expression <Integer > startIndex , endIndex ;
128+ private @ Nullable Expression <Integer > startIndex , endIndex ;
136129 private ElementType type ;
137- private boolean queue ;
138130 private boolean keyed ;
139131
140132 @ Override
141133 @ SuppressWarnings ("unchecked" )
142134 public boolean init (Expression <?>[] expressions , int matchedPattern , Kleenean isDelayed , ParseResult parseResult ) {
143135 ElementType [] types = PATTERNS .getInfo (matchedPattern );
144- this .queue = matchedPattern > 4 ;
145- if (queue && !this .getParser ().hasExperiment (Feature .QUEUES ))
146- return false ;
147- if (queue ) {
148- this .expr = (Expression <T >) expressions [expressions .length - 1 ];
149- } else {
150- this .expr = LiteralUtils .defendExpression (expressions [expressions .length - 1 ]);
151- }
136+ this .expr = LiteralUtils .defendExpression (expressions [expressions .length - 1 ]);
137+
152138 switch (type = types [parseResult .mark ]) {
153139 case RANGE :
154140 endIndex = (Expression <Integer >) expressions [1 ];
@@ -160,21 +146,31 @@ public boolean init(Expression<?>[] expressions, int matchedPattern, Kleenean is
160146 break ;
161147 }
162148 this .keyed = KeyProviderExpression .canReturnKeys (this .expr );
163- return queue || LiteralUtils .canInitSafely (expr );
149+ return LiteralUtils .canInitSafely (expr );
164150 }
165151
166152 @ Override
167153 protected T @ Nullable [] get (Event event ) {
168- if (queue )
169- return this .getFromQueue (event );
170154 if (keyed ) {
171155 KeyedValue .UnzippedKeyValues <T > unzipped = KeyedValue .unzip (keyedIterator (event ));
172156 cache .put (event , unzipped .keys ());
173157 //noinspection unchecked
174158 T [] empty = (T []) Array .newInstance (getReturnType (), 0 );
175159 return unzipped .values ().toArray (empty );
176160 }
177- Iterator <? extends T > iterator = iterator (event );
161+
162+ Iterator <? extends T > iterator ;
163+ if (expr .isSingle ()) {
164+ T single = expr .getSingle (event );
165+ if (single instanceof SkriptQueue queue ) {
166+ return this .getFromQueue (event , queue );
167+ } else {
168+ iterator = transformIterator (event , Iterators .singletonIterator (single ));
169+ }
170+ } else {
171+ iterator = transformIterator (event , expr .iterator (event ));
172+ }
173+
178174 assert iterator != null ;
179175 //noinspection unchecked
180176 return Iterators .toArray (iterator , (Class <T >) getReturnType ());
@@ -191,8 +187,13 @@ public boolean init(Expression<?>[] expressions, int matchedPattern, Kleenean is
191187
192188 @ Override
193189 public @ Nullable Iterator <? extends T > iterator (Event event ) {
194- if (queue )
195- return Optional .ofNullable (getFromQueue (event )).map (Iterators ::forArray ).orElse (null );
190+ if (expr .isSingle ()) {
191+ T single = expr .getSingle (event );
192+ if (single instanceof SkriptQueue queue ) {
193+ return Optional .ofNullable (getFromQueue (event , queue )).map (Iterators ::forArray ).orElse (null );
194+ }
195+ return Iterators .singletonIterator (single );
196+ }
196197 Iterator <? extends T > iterator = expr .iterator (event );
197198 return transformIterator (event , iterator );
198199 }
@@ -224,8 +225,7 @@ private <A> Iterator<A> transformIterator(Event event, @Nullable Iterator<A> ite
224225 }
225226
226227 @ SuppressWarnings ("unchecked" )
227- private T @ Nullable [] getFromQueue (Event event ) {
228- SkriptQueue queue = (SkriptQueue ) expr .getSingle (event );
228+ private T @ Nullable [] getFromQueue (Event event , SkriptQueue queue ) {
229229 if (queue == null )
230230 return null ;
231231 Integer startIndex = 0 , endIndex = 0 ;
@@ -242,11 +242,13 @@ private <A> Iterator<A> transformIterator(Event event, @Nullable Iterator<A> ite
242242 return switch (type ) {
243243 case FIRST_ELEMENT -> CollectionUtils .array ((T ) queue .pollFirst ());
244244 case LAST_ELEMENT -> CollectionUtils .array ((T ) queue .pollLast ());
245- case RANDOM -> CollectionUtils .array ((T ) queue .removeSafely (ThreadLocalRandom .current ().nextInt (0 , queue .size ())));
245+ case RANDOM ->
246+ CollectionUtils .array ((T ) queue .removeSafely (ThreadLocalRandom .current ().nextInt (0 , queue .size ())));
246247 case ORDINAL -> CollectionUtils .array ((T ) queue .removeSafely (startIndex - 1 ));
247248 case TAIL_END_ORDINAL -> CollectionUtils .array ((T ) queue .removeSafely (queue .size () - startIndex ));
248249 case FIRST_X_ELEMENTS -> CollectionUtils .array ((T []) queue .removeRangeSafely (0 , startIndex ));
249- case LAST_X_ELEMENTS -> CollectionUtils .array ((T []) queue .removeRangeSafely (queue .size () - startIndex , queue .size ()));
250+ case LAST_X_ELEMENTS ->
251+ CollectionUtils .array ((T []) queue .removeRangeSafely (queue .size () - startIndex , queue .size ()));
250252 case RANGE -> {
251253 boolean reverse = startIndex > endIndex ;
252254 T [] elements = CollectionUtils .array ((T []) queue .removeRangeSafely (Math .min (startIndex , endIndex ) - 1 , Math .max (startIndex , endIndex )));
@@ -284,7 +286,6 @@ public <R> Expression<? extends R> getConvertedExpression(Class<R>... to) {
284286 exprElement .startIndex = startIndex ;
285287 exprElement .endIndex = endIndex ;
286288 exprElement .type = type ;
287- exprElement .queue = queue ;
288289 return exprElement ;
289290 }
290291
@@ -295,37 +296,33 @@ public boolean isSingle() {
295296
296297 @ Override
297298 public Class <? extends T > getReturnType () {
298- if ( queue )
299- return ( Class <? extends T >) Object . class ;
300- return expr . getReturnType () ;
299+ Class <? extends T > returnType = expr . getReturnType ();
300+ //noinspection unchecked
301+ return returnType == SkriptQueue . class ? ( Class <? extends T >) Object . class : returnType ;
301302 }
302303
303304 @ Override
304305 public Class <? extends T >[] possibleReturnTypes () {
305- if (!queue ) {
306- return expr .possibleReturnTypes ();
307- }
308- return super .possibleReturnTypes ();
306+ Class <? extends T > returnType = expr .getReturnType ();
307+ //noinspection unchecked
308+ return returnType == SkriptQueue .class ? new Class []{Object .class } : expr .possibleReturnTypes ();
309309 }
310310
311311 @ Override
312312 public boolean canReturn (Class <?> returnType ) {
313- if (!queue ) {
314- return expr .canReturn (returnType );
315- }
316- return super .canReturn (returnType );
313+ return returnType == SkriptQueue .class || expr .canReturn (returnType );
317314 }
318-
319- @ Override
315+
316+ @ Override
320317 public Expression <? extends T > simplify () {
321- if (! queue && expr instanceof Literal <?>
322- && type != ElementType .RANDOM
323- && (startIndex == null || startIndex instanceof Literal <Integer >)
324- && (endIndex == null || endIndex instanceof Literal <Integer >)) {
318+ if (expr instanceof Literal <?>
319+ && type != ElementType .RANDOM
320+ && (startIndex == null || startIndex instanceof Literal <Integer >)
321+ && (endIndex == null || endIndex instanceof Literal <Integer >)) {
325322 return SimplifiedLiteral .fromExpression (this );
326323 }
327324 return this ;
328- }
325+ }
329326
330327 @ Override
331328 public String toString (@ Nullable Event event , boolean debug ) {
0 commit comments