@@ -30,8 +30,13 @@ import com.lambda.event.listener.SafeListener.Companion.listen
3030import com.lambda.event.listener.UnsafeListener.Companion.listenUnsafe
3131import com.lambda.graphics.renderer.esp.builders.buildFilled
3232import com.lambda.graphics.renderer.esp.builders.buildOutline
33+ import com.lambda.interaction.construction.blueprint.Blueprint.Companion.toStructure
34+ import com.lambda.interaction.construction.blueprint.StaticBlueprint.Companion.toBlueprint
3335import com.lambda.interaction.construction.context.BreakContext
3436import com.lambda.interaction.construction.processing.ProcessorRegistry
37+ import com.lambda.interaction.construction.result.BreakResult
38+ import com.lambda.interaction.construction.simulation.BuildSimulator.simulate
39+ import com.lambda.interaction.construction.verify.TargetState
3540import com.lambda.interaction.request.ManagerUtils.isPosBlocked
3641import com.lambda.interaction.request.PositionBlocking
3742import com.lambda.interaction.request.Priority
@@ -126,6 +131,28 @@ object BreakManager : RequestHandler<BreakRequest>(
126131 override fun load (): String {
127132 super .load()
128133
134+ listen<TickEvent .Pre >(priority = Int .MIN_VALUE ) {
135+ // Cancelled but double breaking so requires break manager to continue the simulation
136+ breakInfos
137+ .asSequence()
138+ .filterNotNull()
139+ .filter { it.abandoned && ! it.isRedundant }
140+ .forEach { info ->
141+ with (info.request) {
142+ info.context.blockPos
143+ .toStructure(TargetState .Empty )
144+ .toBlueprint()
145+ .simulate(player.eyePos, interact, rotation, inventory, build)
146+ .asSequence()
147+ .filterIsInstance<BreakResult .Break >()
148+ .sorted()
149+ .let { sim ->
150+ info.updateInfo(sim.firstOrNull()?.context ? : return @forEach)
151+ }
152+ }
153+ }
154+ }
155+
129156 listen<TickEvent .Post >(priority = Int .MIN_VALUE ) {
130157 if (breakCooldown > 0 ) {
131158 breakCooldown--
@@ -200,7 +227,7 @@ object BreakManager : RequestHandler<BreakRequest>(
200227 world,
201228 info.context.blockPos,
202229 info.breakConfig,
203- player.inventory.getStack(info.context.hotbarIndex)
230+ if ( ! info.isRedundant) player.inventory.getStack(info.context.hotbarIndex) else null
204231 )
205232 val progress = (info.breakingTicks * breakDelta).let {
206233 if (info.isPrimary) it * (2 - info.breakConfig.breakThreshold)
@@ -337,9 +364,17 @@ object BreakManager : RequestHandler<BreakRequest>(
337364 .filterNotNull()
338365 .forEach { info ->
339366 newBreaks.find { ctx -> ctx.blockPos == info.context.blockPos }?.let { ctx ->
340- if (! info.updatedThisTick) {
367+ if (! info.updatedThisTick || info.abandoned ) {
341368 info.updateInfo(ctx, request)
342- info.request.onUpdate?.invoke(info.context.blockPos)
369+ if (info.isRedundant) {
370+ info.type = BreakType .Secondary
371+ info.request.onStart?.invoke(info.context.blockPos)
372+ } else if (info.abandoned) {
373+ info.abandoned = false
374+ info.request.onStart?.invoke(info.context.blockPos)
375+ } else {
376+ info.request.onUpdate?.invoke(info.context.blockPos)
377+ }
343378 }
344379 newBreaks.remove(ctx)
345380 return @forEach
@@ -530,8 +565,9 @@ object BreakManager : RequestHandler<BreakRequest>(
530565 if (isPrimary) {
531566 if (breaking) abortBreakPacket(world, interaction)
532567 nullify()
533- } else if (isSecondary && breakConfig.unsafeCancels) {
534- makeRedundant()
568+ } else if (isSecondary) {
569+ if (breakConfig.unsafeCancels) makeRedundant()
570+ else abandoned = true
535571 }
536572
537573 internalOnCancel()
@@ -755,7 +791,7 @@ object BreakManager : RequestHandler<BreakRequest>(
755791 item : ItemStack ? = null
756792 ) = runSafe {
757793 var delta = calcItemBlockBreakingDelta(player, world, pos, item ? : player.inventory.mainHandStack)
758- // This setting requires some fixes / improvements in the player movement prediction to work properly. Currently, its broken
794+ // ToDo: This setting requires some fixes / improvements in the player movement prediction to work properly. Currently, it's broken
759795 if (config.desyncFix) {
760796 val nextTickPrediction = buildPlayerPrediction().next()
761797 if (player.isOnGround && ! nextTickPrediction.onGround) {
0 commit comments