|
40 | 40 | import java.io.IOException; |
41 | 41 | import java.nio.ByteBuffer; |
42 | 42 | import java.util.ArrayList; |
| 43 | +import java.util.List; |
43 | 44 | import java.util.Optional; |
44 | 45 | import java.util.PrimitiveIterator; |
45 | 46 | import java.util.Random; |
@@ -105,6 +106,14 @@ public class BookBot extends Module { |
105 | 106 | .build() |
106 | 107 | ); |
107 | 108 |
|
| 109 | + private final Setting<Boolean> wordWrap = sgGeneral.add(new BoolSetting.Builder() |
| 110 | + .name("word-wrap") |
| 111 | + .description("Prevents words from being cut in the middle of lines.") |
| 112 | + .defaultValue(true) |
| 113 | + .visible(() -> mode.get() == Mode.File) |
| 114 | + .build() |
| 115 | + ); |
| 116 | + |
108 | 117 | private File file = new File(MeteorClient.FOLDER, "bookbot.txt"); |
109 | 118 | private final PointerBuffer filters; |
110 | 119 |
|
@@ -252,66 +261,110 @@ private void onTick(TickEvent.Post event) { |
252 | 261 | private void writeBook(PrimitiveIterator.OfInt chars) { |
253 | 262 | ArrayList<String> pages = new ArrayList<>(); |
254 | 263 | ArrayList<RawFilteredPair<Text>> filteredPages = new ArrayList<>(); |
255 | | - TextHandler.WidthRetriever widthRetriever = ((TextHandlerAccessor) mc.textRenderer.getTextHandler()).meteor$getWidthRetriever(); |
256 | | - |
257 | 264 | int maxPages = mode.get() == Mode.File ? 100 : this.pages.get(); |
258 | 265 |
|
259 | | - int pageIndex = 0; |
260 | | - int lineIndex = 0; |
261 | | - |
262 | | - final StringBuilder page = new StringBuilder(); |
263 | | - |
264 | | - float lineWidth = 0; |
265 | | - |
266 | | - while (chars.hasNext()) { |
267 | | - int c = chars.nextInt(); |
268 | | - |
269 | | - if (c == '\r' || c == '\n') { |
270 | | - page.append('\n'); |
271 | | - lineWidth = 0; |
272 | | - lineIndex++; |
273 | | - } else { |
274 | | - float charWidth = widthRetriever.getWidth(c, Style.EMPTY); |
| 266 | + if (wordWrap.get() && mode.get() == Mode.File) { |
| 267 | + StringBuilder text = new StringBuilder(); |
| 268 | + while (chars.hasNext()) { |
| 269 | + text.appendCodePoint(chars.nextInt()); |
| 270 | + } |
275 | 271 |
|
276 | | - // Reached end of line |
277 | | - if (lineWidth + charWidth > 114f) { |
| 272 | + // Use mc's own word wrapping logic |
| 273 | + List<StringVisitable> wrappedLines = mc.textRenderer.wrapLinesWithoutLanguage(Text.literal(text.toString()), 114); |
| 274 | + processLinesToPages(wrappedLines, pages, filteredPages, maxPages); |
| 275 | + } else { |
| 276 | + // Non-word-wrapping logic |
| 277 | + TextHandler.WidthRetriever widthRetriever = ((TextHandlerAccessor) mc.textRenderer.getTextHandler()).meteor$getWidthRetriever(); |
| 278 | + int pageIndex = 0; |
| 279 | + int lineIndex = 0; |
| 280 | + final StringBuilder page = new StringBuilder(); |
| 281 | + float lineWidth = 0; |
| 282 | + |
| 283 | + while (chars.hasNext()) { |
| 284 | + int c = chars.nextInt(); |
| 285 | + |
| 286 | + if (c == '\r' || c == '\n') { |
278 | 287 | page.append('\n'); |
279 | | - lineWidth = charWidth; |
| 288 | + lineWidth = 0; |
280 | 289 | lineIndex++; |
281 | | - // Wrap to next line, unless wrapping to next page |
282 | | - if (lineIndex != 14) page.appendCodePoint(c); |
283 | | - } else if (lineWidth == 0f && c == ' ') { |
284 | | - continue; // Prevent leading space from text wrapping |
285 | 290 | } else { |
286 | | - lineWidth += charWidth; |
287 | | - page.appendCodePoint(c); |
| 291 | + float charWidth = widthRetriever.getWidth(c, Style.EMPTY); |
| 292 | + |
| 293 | + // Reached end of line |
| 294 | + if (lineWidth + charWidth > 114f) { |
| 295 | + page.append('\n'); |
| 296 | + lineWidth = charWidth; |
| 297 | + lineIndex++; |
| 298 | + // Wrap to next line, unless wrapping to next page |
| 299 | + if (lineIndex != 14) page.appendCodePoint(c); |
| 300 | + } else if (lineWidth == 0f && c == ' ') { |
| 301 | + continue; // Prevent leading space from text wrapping |
| 302 | + } else { |
| 303 | + lineWidth += charWidth; |
| 304 | + page.appendCodePoint(c); |
| 305 | + } |
| 306 | + } |
| 307 | + |
| 308 | + // Reached end of page |
| 309 | + if (lineIndex == 14) { |
| 310 | + filteredPages.add(RawFilteredPair.of(Text.of(page.toString()))); |
| 311 | + pages.add(page.toString()); |
| 312 | + page.setLength(0); |
| 313 | + pageIndex++; |
| 314 | + lineIndex = 0; |
| 315 | + |
| 316 | + // No more pages |
| 317 | + if (pageIndex == maxPages) break; |
| 318 | + |
| 319 | + // Wrap to next page |
| 320 | + if (c != '\r' && c != '\n') { |
| 321 | + page.appendCodePoint(c); |
| 322 | + } |
288 | 323 | } |
289 | 324 | } |
290 | 325 |
|
291 | | - // Reached end of page |
292 | | - if (lineIndex == 14) { |
| 326 | + // No more characters, end current page |
| 327 | + if (!page.isEmpty() && pageIndex != maxPages) { |
293 | 328 | filteredPages.add(RawFilteredPair.of(Text.of(page.toString()))); |
294 | 329 | pages.add(page.toString()); |
295 | | - page.setLength(0); |
| 330 | + } |
| 331 | + } |
| 332 | + |
| 333 | + createBook(pages, filteredPages); |
| 334 | + } |
| 335 | + |
| 336 | + private void processLinesToPages(List<StringVisitable> lines, ArrayList<String> pages, ArrayList<RawFilteredPair<Text>> filteredPages, int maxPages) { |
| 337 | + int pageIndex = 0; |
| 338 | + int lineIndex = 0; |
| 339 | + StringBuilder currentPage = new StringBuilder(); |
| 340 | + |
| 341 | + for (StringVisitable line : lines) { |
| 342 | + String lineText = line.getString(); |
| 343 | + |
| 344 | + if (currentPage.length() > 0) { |
| 345 | + currentPage.append('\n'); |
| 346 | + } |
| 347 | + currentPage.append(lineText); |
| 348 | + lineIndex++; |
| 349 | + |
| 350 | + if (lineIndex == 14) { |
| 351 | + filteredPages.add(RawFilteredPair.of(Text.of(currentPage.toString()))); |
| 352 | + pages.add(currentPage.toString()); |
| 353 | + currentPage.setLength(0); |
296 | 354 | pageIndex++; |
297 | 355 | lineIndex = 0; |
298 | 356 |
|
299 | | - // No more pages |
300 | 357 | if (pageIndex == maxPages) break; |
301 | | - |
302 | | - // Wrap to next page |
303 | | - if (c != '\r' && c != '\n') { |
304 | | - page.appendCodePoint(c); |
305 | | - } |
306 | 358 | } |
307 | 359 | } |
308 | 360 |
|
309 | | - // No more characters, end current page |
310 | | - if (!page.isEmpty() && pageIndex != maxPages) { |
311 | | - filteredPages.add(RawFilteredPair.of(Text.of(page.toString()))); |
312 | | - pages.add(page.toString()); |
| 361 | + if (!currentPage.isEmpty() && pageIndex < maxPages) { |
| 362 | + filteredPages.add(RawFilteredPair.of(Text.of(currentPage.toString()))); |
| 363 | + pages.add(currentPage.toString()); |
313 | 364 | } |
| 365 | + } |
314 | 366 |
|
| 367 | + private void createBook(ArrayList<String> pages, ArrayList<RawFilteredPair<Text>> filteredPages) { |
315 | 368 | // Get the title with count |
316 | 369 | String title = name.get(); |
317 | 370 | if (count.get() && bookCount != 0) title += " #" + bookCount; |
|
0 commit comments