Skip to content

Commit 791cb06

Browse files
committed
Added backwards compatibility
1 parent d951317 commit 791cb06

File tree

4 files changed

+87
-42
lines changed

4 files changed

+87
-42
lines changed

src/main/java/world/bentobox/level/LevelsManager.java

Lines changed: 56 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
package world.bentobox.level;
22

3+
import java.io.IOException;
34
import java.math.BigInteger;
45
import java.text.DecimalFormat;
6+
import java.text.ParseException;
57
import java.time.Instant;
68
import java.util.AbstractMap;
79
import java.util.Collections;
@@ -26,6 +28,7 @@
2628

2729
import world.bentobox.bentobox.database.Database;
2830
import world.bentobox.bentobox.database.objects.Island;
31+
import world.bentobox.level.calculators.EquationEvaluator;
2932
import world.bentobox.level.calculators.Results;
3033
import world.bentobox.level.events.IslandLevelCalculatedEvent;
3134
import world.bentobox.level.events.IslandPreLevelEvent;
@@ -130,7 +133,6 @@ private boolean fireIslandLevelCalcEvent(UUID targetPlayer, Island island, Resul
130133
return true;
131134
// Set the values if they were altered
132135
results.setLevel((Long) ilce.getKeyValues().getOrDefault("level", results.getLevel()));
133-
// TODO: results.setInitialLevel((Long) ilce.getKeyValues().getOrDefault("initialLevel", results.getInitialLevel()));
134136
results.setInitialCount((Long) ilce.getKeyValues().getOrDefault("initialCount", results.getInitialCount()));
135137
results.setDeathHandicap((int) ilce.getKeyValues().getOrDefault("deathHandicap", results.getDeathHandicap()));
136138
results.setPointsToNextLevel(
@@ -168,25 +170,66 @@ public String formatLevel(@Nullable Long lvl) {
168170
return level;
169171
}
170172

171-
/**
172-
* Get the initial level of the island. Used to zero island levels
173-
*
174-
* @param island - island
175-
* @return initial level of island
176-
*/
177-
/*TODO
178-
public long getInitialLevel(Island island) {
179-
return getLevelsData(island).getInitialLevel();
180-
}*/
181-
182173
/**
183174
* Get the initial count of the island. Used to zero island levels
184175
*
185176
* @param island - island
186177
* @return initial count of island
187178
*/
179+
@SuppressWarnings("deprecation")
188180
public long getInitialCount(Island island) {
189-
return getLevelsData(island).getInitialCount();
181+
Long initialLevel = getLevelsData(island).getInitialLevel(); // Backward compatibility check. For all new islands, this should be null.
182+
Long initialCount = getLevelsData(island).getInitialCount();
183+
if (initialLevel != null) {
184+
// Initial level exists so convert it
185+
if (initialCount == null) { // If initialCount is not null, then this is an edge case and initialCount will be used and initialLevel discarded
186+
// Convert from level to count
187+
initialCount = 0L;
188+
try {
189+
initialCount = getNumBlocks(initialLevel);
190+
} catch (Exception e) {
191+
addon.logError("Could not convert legacy initial level to count, so it will be set to 0. Error is: "
192+
+ e.getLocalizedMessage());
193+
initialCount = 0L;
194+
}
195+
}
196+
// Null out the old initial level and save
197+
getLevelsData(island).setInitialLevel(null);
198+
// Save
199+
this.setInitialIslandCount(island, initialCount);
200+
}
201+
// If initialCount doesn't exist, set it to 0L
202+
if (initialCount == null) {
203+
initialCount = 0L;
204+
getLevelsData(island).setInitialCount(0L);
205+
}
206+
return initialCount;
207+
}
208+
209+
/**
210+
* Runs the level calculation using the current formula until the level matches the initial value, or fails.
211+
* @param initialLevel - the old initial level
212+
* @return block count to obtain this level now
213+
* @throws ParseException if the formula for level calc is bugged
214+
* @throws IOException if the number of blocks cannot be found for this level
215+
*/
216+
private long getNumBlocks(final long initialLevel) throws ParseException, IOException {
217+
String calcString = addon.getSettings().getLevelCalc();
218+
int result = -1;
219+
long calculatedLevel = 0;
220+
String withCost = calcString.replace("level_cost", String.valueOf(this.addon.getSettings().getLevelCost()));
221+
long time = System.currentTimeMillis() + 10 * 1000; // 10 seconds
222+
do {
223+
result++;
224+
if (System.currentTimeMillis() > time) {
225+
throw new IOException("Timeout: Blocks cannot be found to create this initial level");
226+
}
227+
// Paste in the values to the formula
228+
String withValues = withCost.replace("blocks", String.valueOf(result));
229+
// Try and evaluate it
230+
calculatedLevel = (long) EquationEvaluator.eval(withValues);
231+
} while (calculatedLevel != initialLevel);
232+
return result;
190233
}
191234

192235
/**
@@ -433,23 +476,6 @@ public void removeEntry(World world, String uuid) {
433476
}
434477
}
435478

436-
/**
437-
* Set an initial island level
438-
*
439-
* @param island - the island to set. Must have a non-null world
440-
* @param lv - initial island level
441-
* @deprecated Use {@link #setInitialIslandCount(Island, long)}
442-
*/
443-
/*
444-
@Deprecated
445-
public void setInitialIslandLevel(@NonNull Island island, long lv) {
446-
// TODO convert to a count
447-
if (island.getWorld() == null)
448-
return;
449-
levelsCache.computeIfAbsent(island.getUniqueId(), IslandLevels::new).setInitialLevel(lv);
450-
handler.saveObjectAsync(levelsCache.get(island.getUniqueId()));
451-
}
452-
*/
453479
/**
454480
* Set an initial island count
455481
*

src/main/java/world/bentobox/level/calculators/IslandLevelCalculator.java

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -118,13 +118,13 @@ public IslandLevelCalculator(Level addon, Island island, CompletableFuture<Resul
118118
/**
119119
* Calculate the level based on the raw points
120120
*
121-
* @param blockAndDeathPoints - raw points counted on island
121+
* @param rawPoints - raw points counted on island
122122
* @return level of island
123123
*/
124-
private long calculateLevel(final long blockAndDeathPoints) {
124+
private long calculateLevel(final long rawPoints) {
125125
String calcString = addon.getSettings().getLevelCalc();
126126
// Reduce count by initial count, if zeroing is done
127-
long modifiedPoints = blockAndDeathPoints
127+
long modifiedPoints = rawPoints
128128
- (addon.getSettings().isZeroNewIslandLevels() ? results.initialCount.get() : 0);
129129
// Paste in the values to the formula
130130
String withValues = calcString.replace("blocks", String.valueOf(modifiedPoints)).replace("level_cost",

src/main/java/world/bentobox/level/objects/IslandLevels.java

Lines changed: 20 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -38,14 +38,13 @@ public class IslandLevels implements DataObject {
3838
/**
3939
* Initial level
4040
*/
41-
/*
4241
@Expose
43-
private long initialLevel;*/
42+
private Long initialLevel;
4443
/**
4544
* Initial count
4645
*/
4746
@Expose
48-
private long initialCount;
47+
private Long initialCount;
4948
/**
5049
* Points to next level
5150
*/
@@ -241,15 +240,31 @@ public void setMdCount(Map<Object, Integer> mdCount) {
241240
/**
242241
* @return the initialCount
243242
*/
244-
public long getInitialCount() {
243+
public Long getInitialCount() {
245244
return initialCount;
246245
}
247246

248247
/**
249248
* @param initialCount the initialCount to set
250249
*/
251-
public void setInitialCount(long initialCount) {
250+
public void setInitialCount(Long initialCount) {
252251
this.initialCount = initialCount;
253252
}
254253

254+
/**
255+
* @return the initialLevel
256+
* @deprecated only used for backwards compatibility. Use {@link #getInitialCount()} instead
257+
*/
258+
public Long getInitialLevel() {
259+
return initialLevel;
260+
}
261+
262+
/**
263+
* @param initialLevel the initialLevel to set
264+
* @deprecated only used for backwards compatil
265+
*/
266+
public void setInitialLevel(Long initialLevel) {
267+
this.initialLevel = initialLevel;
268+
}
269+
255270
}

src/test/java/world/bentobox/level/LevelsManagerTest.java

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -128,6 +128,7 @@ public static void beforeClass() {
128128
/**
129129
* @throws java.lang.Exception
130130
*/
131+
@SuppressWarnings("deprecation")
131132
@Before
132133
public void setUp() throws Exception {
133134
when(addon.getPlugin()).thenReturn(plugin);
@@ -208,15 +209,18 @@ public void setUp() throws Exception {
208209
List<Object> islands = new ArrayList<>();
209210
for (long i = -5; i < 5; i ++) {
210211
IslandLevels il = new IslandLevels(UUID.randomUUID().toString());
211-
il.setInitialCount(3);
212+
il.setInitialCount(null);
212213
il.setLevel(i);
213214
il.setPointsToNextLevel(3);
215+
il.setInitialLevel(26145L); // Legacy
214216
islands.add(il);
215217
}
216218
// Supply no island levels first (for migrate), then islands
217219
when(handler.loadObjects()).thenReturn(islands);
218220
when(handler.objectExists(anyString())).thenReturn(true);
219221
when(levelsData.getLevel()).thenReturn(-5L, -4L, -3L, -2L, -1L, 0L, 1L, 2L, 3L, 4L, 5L, 45678L);
222+
when(levelsData.getInitialLevel()).thenReturn(26145L, -4L, -3L, -2L, -1L, 0L, 1L, 2L, 3L, 4L, 5L, 45678L);
223+
when(levelsData.getInitialCount()).thenReturn(null);
220224
when(levelsData.getUniqueId()).thenReturn(uuid.toString());
221225
when(handler.loadObject(anyString())).thenReturn(levelsData );
222226

@@ -279,11 +283,11 @@ public void testCalculateLevel() {
279283

280284
/**
281285
* Test method for
282-
* {@link world.bentobox.level.LevelsManager#getInitialLevel(world.bentobox.bentobox.database.objects.Island)}.
286+
* {@link world.bentobox.level.LevelsManager#getInitialCount(world.bentobox.bentobox.database.objects.Island)}.
283287
*/
284288
@Test
285-
public void testGetInitialLevel() {
286-
assertEquals(0, lm.getInitialCount(island));
289+
public void testGetInitialCount() {
290+
assertEquals(2614500L, lm.getInitialCount(island));
287291
}
288292

289293
/**

0 commit comments

Comments
 (0)