@@ -129,12 +129,12 @@ object BreakManager : RequestHandler<BreakRequest>(
129129 }
130130
131131 listen<WorldEvent .BlockUpdate .Server >(priority = Int .MIN_VALUE ) { event ->
132+ if (event.pos == ReBreakManager .reBreak?.context?.expectedPos) return @listen
133+
132134 breakInfos
133135 .filterNotNull()
134136 .firstOrNull { it.context.expectedPos == event.pos }
135137 ?.let { info ->
136- if (event.pos == ReBreakManager .reBreak?.context?.expectedPos) return @listen
137-
138138 // if not broken
139139 if (! isBroken(info.context.checkedState, event.newState)) {
140140 this @BreakManager.warn(" Break at ${event.pos.toShortString()} was rejected with ${event.newState} instead of ${info.context.checkedState.brokenState} " )
@@ -203,8 +203,7 @@ object BreakManager : RequestHandler<BreakRequest>(
203203
204204 if (request.fresh) populateFrom(request)
205205
206- if (! atMaxBreakInfos(request.build.breaking)) run processNewBreaks@ {
207- if (! performInstantBreaks(request)) return @processNewBreaks
206+ if (performInstantBreaks(request)) {
208207 processNewBreaks(request)
209208 }
210209
@@ -215,7 +214,7 @@ object BreakManager : RequestHandler<BreakRequest>(
215214 .filterNotNull()
216215 .filter { ! it.isRedundant }
217216 .also {
218- rotationRequest = it.firstOrNull { it .breakConfig.rotateForBreak }
217+ rotationRequest = it.firstOrNull { info -> info .breakConfig.rotateForBreak }
219218 ?.let { info ->
220219 val rotation = info.context.rotation
221220 if (instantBreaks.isEmpty()) info.request.rotation.request(rotation, false ) else rotation
@@ -251,7 +250,7 @@ object BreakManager : RequestHandler<BreakRequest>(
251250 private fun SafeContext.populateFrom (request : BreakRequest ) {
252251 // Sanitize the new breaks
253252 val newBreaks = request.contexts
254- .filter { ctx -> canAccept(ctx) }
253+ .filter { ctx -> canAccept(ctx, request.build.breaking ) }
255254 .toMutableList()
256255
257256 // Update the current break infos or cancel if abandoned
@@ -281,14 +280,16 @@ object BreakManager : RequestHandler<BreakRequest>(
281280 /* *
282281 * @return if the break context can be accepted.
283282 */
284- private fun SafeContext.canAccept (ctx : BreakContext ): Boolean {
283+ private fun SafeContext.canAccept (ctx : BreakContext , breakConfig : BreakConfig ): Boolean {
285284 if (pendingBreaks.any { it.context.expectedPos == ctx.expectedPos }) return false
286285
287- breakInfos
288- .firstOrNull { it != null && ! it.isRedundant }
289- ?.let { info ->
290- if (ctx.hotbarIndex != info.context.hotbarIndex) return false
291- }
286+ if (breakConfig.doubleBreak) {
287+ breakInfos
288+ .firstOrNull { it != null && ! it.isRedundant }
289+ ?.let { info ->
290+ if (ctx.hotbarIndex != info.context.hotbarIndex) return false
291+ }
292+ }
292293
293294 return ! blockState(ctx.expectedPos).isAir
294295 }
@@ -449,27 +450,23 @@ object BreakManager : RequestHandler<BreakRequest>(
449450 if (isPrimary) {
450451 abortBreakPacket(world, interaction)
451452 nullify()
452- return @runSafe
453- }
454- if (isSecondary && breakConfig.unsafeCancels) {
453+ } else if (isSecondary && breakConfig.unsafeCancels) {
455454 makeRedundant()
456455 }
456+
457+ internalOnCancel()
457458 }
458459
459460 /* *
460461 * Nullifies the break. If the block is not broken, the [BreakInfo.internalOnCancel] callback gets triggered
461462 */
462- private fun BreakInfo.nullify () {
463- type.nullify()
464- if (! broken && ! pending && ! isReBreaking && ! isRedundant) internalOnCancel()
465- }
463+ private fun BreakInfo.nullify () = type.nullify()
466464
467465 /* *
468466 * Makes the [BreakInfo] redundant and triggers the [BreakInfo.internalOnCancel] callback
469467 */
470468 private fun BreakInfo.makeRedundant () {
471469 type = BreakType .RedundantSecondary
472- internalOnCancel()
473470 }
474471
475472 /* *
@@ -494,15 +491,15 @@ object BreakManager : RequestHandler<BreakRequest>(
494491 val ctx = info.context
495492 val hitResult = ctx.result
496493
497- if (gamemode.isCreative && world.worldBorder.contains(ctx.expectedPos)) {
494+ if (gamemode.isCreative && world.worldBorder.contains(ctx.expectedPos) && info.breaking ) {
498495 if (info.isRedundant) {
499496 onBlockBreak(info)
500497 return true
501498 }
502499 breakCooldown = info.breakConfig.breakDelay
503500 lastPosStarted = ctx.expectedPos
501+ onBlockBreak(info)
504502 interaction.sendSequencedPacket(world) { sequence ->
505- onBlockBreak(info)
506503 PlayerActionC2SPacket (Action .START_DESTROY_BLOCK , ctx.expectedPos, hitResult.side, sequence)
507504 }
508505 val swing = info.breakConfig.swing
@@ -535,6 +532,7 @@ object BreakManager : RequestHandler<BreakRequest>(
535532 }
536533 if (! startBreaking(info)) {
537534 info.nullify()
535+ info.internalOnCancel()
538536 return false
539537 }
540538 val swing = info.breakConfig.swing
@@ -547,6 +545,7 @@ object BreakManager : RequestHandler<BreakRequest>(
547545 val blockState = blockState(ctx.expectedPos)
548546 if (blockState.isAir) {
549547 info.nullify()
548+ info.internalOnCancel()
550549 return false
551550 }
552551
@@ -595,8 +594,8 @@ object BreakManager : RequestHandler<BreakRequest>(
595594 val swing = info.breakConfig.swing
596595 if (overBreakThreshold) {
597596 if (info.isPrimary) {
597+ onBlockBreak(info)
598598 interaction.sendSequencedPacket(world) { sequence ->
599- onBlockBreak(info)
600599 PlayerActionC2SPacket (Action .STOP_DESTROY_BLOCK , ctx.expectedPos, hitResult.side, sequence)
601600 }
602601 } else {
@@ -626,8 +625,8 @@ object BreakManager : RequestHandler<BreakRequest>(
626625
627626 if (gamemode.isCreative) {
628627 lastPosStarted = ctx.expectedPos
628+ onBlockBreak(info)
629629 interaction.sendSequencedPacket(world) { sequence: Int ->
630- onBlockBreak(info)
631630 PlayerActionC2SPacket (Action .START_DESTROY_BLOCK , ctx.expectedPos, ctx.result.side, sequence)
632631 }
633632 breakCooldown = info.breakConfig.breakDelay
0 commit comments