Skip to content

Commit

Permalink
Refactor code
Browse files Browse the repository at this point in the history
  • Loading branch information
aratakileo committed Sep 12, 2023
1 parent f182e18 commit b49f0d6
Show file tree
Hide file tree
Showing 8 changed files with 72 additions and 108 deletions.
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ SuggestionsAPI.registerResourceDependedInjector(
```

### How to dynamically inject suggestions?
The `Injector` interface is located in the directory `io.github.aratakileo.suggestionsapi.suggestion`.
The `Injector` interface is located in the directory `io.github.aratakileo.suggestionsapi.injector`.

There are two types of injectors: simple and asynchronous. To initialize them, the library also provides functions. The first argument of which will be a regex pattern.

Expand Down
2 changes: 1 addition & 1 deletion gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ loader_version=0.14.22

# Mod Properties
support_minecraft_version = 1.20.x
mod_version = 1.0.0
mod_version = 1.0.1
prev_mod_version = 1.0.0
maven_group = io.github.aratakileo
archives_base_name = suggestions-api
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package io.github.aratakileo.suggestionsapi;

import io.github.aratakileo.suggestionsapi.injector.Injector;
import io.github.aratakileo.suggestionsapi.suggestion.*;
import io.github.aratakileo.suggestionsapi.core.SuggestionsProcessor;
import net.fabricmc.api.ClientModInitializer;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
package io.github.aratakileo.suggestionsapi.core;

import com.mojang.brigadier.context.StringRange;
import io.github.aratakileo.suggestionsapi.suggestion.AsyncInjector;
import io.github.aratakileo.suggestionsapi.suggestion.Injector;
import io.github.aratakileo.suggestionsapi.injector.AsyncInjector;
import io.github.aratakileo.suggestionsapi.injector.Injector;
import io.github.aratakileo.suggestionsapi.suggestion.Suggestion;
import io.github.aratakileo.suggestionsapi.suggestion.SuggestionsInjector;
import io.github.aratakileo.suggestionsapi.injector.SuggestionsInjector;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.slf4j.Logger;
Expand All @@ -14,14 +14,15 @@
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.CompletableFuture;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.regex.Pattern;

public class SuggestionsProcessor {
private static final Pattern WHITESPACE_PATTERN = Pattern.compile("(\\s+)");
private static final Logger LOGGER = LoggerFactory.getLogger(SuggestionsProcessor.class);
private static final HashMap<AsyncInjector, CompletableFuture<Void>> asyncProcessors = new HashMap<>();

private final String textUptoCursor;
private final int wordStart;
Expand Down Expand Up @@ -51,7 +52,7 @@ public boolean process() {

final var currentExpression = textUptoCursor.substring(wordStart);
final var suggestionsInjectorsBuffer = new HashMap<SuggestionsInjector, Collection<Suggestion>>();
final var asyncInjectorsBuffer = new ArrayList<AsyncInjector>();
final var asyncInjectorsBuffer = new HashMap<AsyncInjector, Runnable>();

for (final var injector: injectors) {
var isActiveInjector = false;
Expand All @@ -71,31 +72,38 @@ public boolean process() {
if (injector instanceof AsyncInjector asyncInjector) {
isValidInjector = true;

final var willApplySuggestions = asyncInjector.initAsyncApplier(
currentExpression,
suggestionList -> {
if (suggestionList == null || suggestionList.isEmpty()) return;
final var asyncApplier = asyncInjector.getAsyncApplier(currentExpression);

final var mojangSuggestions = new ArrayList<com.mojang.brigadier.suggestion.Suggestion>();
final var offset = injector.getStartOffset();
if (asyncApplier != null) {
asyncInjectorsBuffer.put(asyncInjector, () -> {
final var suggestionList = asyncApplier.get();

suggestionList.forEach(suggestion -> {
if (suggestion.shouldShowFor(currentExpression.substring(offset)))
mojangSuggestions.add(new com.mojang.brigadier.suggestion.Suggestion(
StringRange.between(wordStart + offset, textUptoCursor.length()),
suggestion.getSuggestionText()
));
});
if (suggestionList == null || suggestionList.isEmpty()) {
asyncProcessors.remove(asyncInjector);
return;
}

final var mojangSuggestions = new ArrayList<com.mojang.brigadier.suggestion.Suggestion>();
final var offset = injector.getStartOffset();

if (mojangSuggestions.isEmpty()) return;
suggestionList.forEach(suggestion -> {
if (suggestion.shouldShowFor(currentExpression.substring(offset)))
mojangSuggestions.add(new com.mojang.brigadier.suggestion.Suggestion(
StringRange.between(wordStart + offset, textUptoCursor.length()),
suggestion.getSuggestionText()
));
});

newSuggestionsApplier.accept(textUptoCursor, mojangSuggestions);
if (mojangSuggestions.isEmpty()) {
asyncProcessors.remove(asyncInjector);
return;
}
);

if (willApplySuggestions) {
asyncInjectorsBuffer.add(asyncInjector);
newSuggestionsApplier.accept(textUptoCursor, mojangSuggestions);
});

isActiveInjector = true;
asyncProcessors.remove(asyncInjector);
}
}

Expand Down Expand Up @@ -158,12 +166,23 @@ public boolean process() {

var hasUsedAsyncInjector = false;

for (final var injector: asyncInjectorsBuffer) {
for (final var injectorEntry: asyncInjectorsBuffer.entrySet()) {
final var injector = injectorEntry.getKey();

if (minOffset != -1 && injector.isIsolated() && injector.getStartOffset() > minOffset) continue;

hasUsedAsyncInjector = true;

injector.runAsyncApplier();
CompletableFuture<Void> currentCompletableFuture;

if (
asyncProcessors.containsKey(injector) && !(
currentCompletableFuture = asyncProcessors.get(injector)
).isDone()
)
currentCompletableFuture.cancel(true);

asyncProcessors.put(injector, CompletableFuture.runAsync(injectorEntry.getValue()));
}

if (applicableMojangSuggestions.isEmpty() && !hasUsedAsyncInjector) return false;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package io.github.aratakileo.suggestionsapi.injector;

import io.github.aratakileo.suggestionsapi.suggestion.Suggestion;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import java.util.List;
import java.util.function.Supplier;

public interface AsyncInjector extends Injector {
@Nullable Supplier<@Nullable List<Suggestion>> getAsyncApplier(@NotNull String currentExpression);
}
Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
package io.github.aratakileo.suggestionsapi.suggestion;
package io.github.aratakileo.suggestionsapi.injector;

import io.github.aratakileo.suggestionsapi.util.TripleFunction;
import io.github.aratakileo.suggestionsapi.suggestion.Suggestion;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import java.util.List;
import java.util.concurrent.CompletableFuture;
import java.util.function.BiFunction;
import java.util.function.Consumer;
import java.util.function.Supplier;
import java.util.regex.Pattern;

public interface Injector {
Expand Down Expand Up @@ -60,70 +59,40 @@ public boolean isIsolated() {

static @NotNull AsyncInjector async(
@NotNull Pattern pattern,
TripleFunction<
BiFunction<
@NotNull String,
@NotNull Integer,
@NotNull Consumer<@Nullable List<Suggestion>>,
@Nullable Runnable
@Nullable List<Suggestion>
> uncheckedSupplierGetter
) {
return async(pattern, uncheckedSupplierGetter, false);
}

static @NotNull AsyncInjector async(
@NotNull Pattern pattern,
TripleFunction<
BiFunction<
@NotNull String,
@NotNull Integer,
@NotNull Consumer<@Nullable List<Suggestion>>,
@Nullable Runnable
@Nullable List<Suggestion>
> uncheckedSupplierGetter,
boolean isIsolated
) {
return new AsyncInjector() {
private int startOffset = 0;
private CompletableFuture<Void> currentProcess = null;
private Runnable applier = null;

@Override
@Nullable
public CompletableFuture<Void> getCurrentProcess() {
return currentProcess;
}

@Override
public void setCurrentProcess(@Nullable CompletableFuture<Void> currentProcess) {
this.currentProcess = currentProcess;
}

@Override
public @Nullable Runnable getApplier() {
return applier;
}

@Override
public void setApplier(@Nullable Runnable applier) {
this.applier = applier;
}

@Override
public boolean initAsyncApplier(
@NotNull String currentExpression,
@NotNull Consumer<@Nullable List<Suggestion>> applier
public Supplier<@Nullable List<Suggestion>> getAsyncApplier(
@NotNull String currentExpression
) {
final var lastMatchedStart = getLastMatchedStart(pattern, currentExpression);

if (lastMatchedStart == -1)
return false;

AsyncInjector.setApplier(
this,
uncheckedSupplierGetter.apply(currentExpression, lastMatchedStart, applier)
);
return null;

startOffset = lastMatchedStart;

return this.applier != null;
return () -> uncheckedSupplierGetter.apply(currentExpression, lastMatchedStart);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package io.github.aratakileo.suggestionsapi.suggestion;
package io.github.aratakileo.suggestionsapi.injector;

import io.github.aratakileo.suggestionsapi.suggestion.Suggestion;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

Expand Down

This file was deleted.

0 comments on commit b49f0d6

Please sign in to comment.