mirror of
https://github.com/RandomityGuy/MBHaxe.git
synced 2026-04-27 05:01:38 +00:00
some mp optimizations
This commit is contained in:
parent
2dc95b0a3a
commit
c6802821e2
2 changed files with 90 additions and 85 deletions
|
|
@ -1492,13 +1492,31 @@ class MarbleWorld extends Scheduler {
|
||||||
return packets;
|
return packets;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline function hasPredictionFlag(mask:Int, clientId:Int):Bool {
|
||||||
|
return (mask & (1 << clientId)) != 0;
|
||||||
|
}
|
||||||
|
|
||||||
public function applyReceivedMoves() {
|
public function applyReceivedMoves() {
|
||||||
var needsPrediction = 0;
|
var needsPrediction = 0;
|
||||||
|
|
||||||
|
inline function correctPrediction(target:Marble, packet:MarbleUpdatePacket, tick:Int, bitMask:Int, ?pending:Array<MarbleUpdatePacket>) {
|
||||||
|
target.unpackUpdate(packet);
|
||||||
|
needsPrediction |= bitMask;
|
||||||
|
if (pending != null)
|
||||||
|
pending.insert(0, packet);
|
||||||
|
if (tick >= 0)
|
||||||
|
predictions.clearStatesAfterTick(target, tick);
|
||||||
|
}
|
||||||
|
|
||||||
if (!lastMoves.ourMoveApplied) {
|
if (!lastMoves.ourMoveApplied) {
|
||||||
var ourMove = lastMoves.myMarbleUpdate;
|
var ourMove = lastMoves.myMarbleUpdate;
|
||||||
if (ourMove != null) {
|
if (ourMove != null) {
|
||||||
var ourMoveStruct = Net.clientConnection.acknowledgeMove(ourMove.move, timeState);
|
var ourMoveStruct = Net.clientConnection.acknowledgeMove(ourMove.move, timeState);
|
||||||
lastMoves.ourMoveApplied = true;
|
lastMoves.ourMoveApplied = true;
|
||||||
|
|
||||||
|
var hasStruct = ourMoveStruct != null;
|
||||||
|
var ourTick = hasStruct ? ourMoveStruct.timeState.ticks : -1;
|
||||||
|
|
||||||
for (client => arr in lastMoves.otherMarbleUpdates) {
|
for (client => arr in lastMoves.otherMarbleUpdates) {
|
||||||
var lastMove = null;
|
var lastMove = null;
|
||||||
while (arr.packets.length > 0) {
|
while (arr.packets.length > 0) {
|
||||||
|
|
@ -1509,68 +1527,35 @@ class MarbleWorld extends Scheduler {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (lastMove != null) {
|
|
||||||
// clientMarbles[Net.clientIdMap[client]].unpackUpdate(lastMove);
|
if (lastMove == null || ourMove.serverTicks != lastMove.serverTicks)
|
||||||
// needsPrediction |= 1 << client;
|
continue;
|
||||||
// arr.insert(0, lastMove);
|
|
||||||
var clientMarble = clientMarbles[Net.clientIdMap[client]];
|
var connection = Net.clientIdMap[client];
|
||||||
if (clientMarble != null) {
|
if (connection == null)
|
||||||
if (ourMove.serverTicks == lastMove.serverTicks) {
|
continue;
|
||||||
if (ourMoveStruct != null) {
|
var clientMarble = clientMarbles[connection];
|
||||||
var otherPred = predictions.retrieveState(clientMarble, ourMoveStruct.timeState.ticks);
|
if (clientMarble == null)
|
||||||
if (otherPred != null) {
|
continue;
|
||||||
if (otherPred.getError(lastMove) > 0.01) {
|
|
||||||
// Debug.drawSphere(@:privateAccess clientMarbles[Net.clientIdMap[client]].newPos, 0.2, 0.5);
|
var mask = 1 << client;
|
||||||
// trace('Prediction error: ${otherPred.getError(lastMove)}');
|
if (hasStruct) {
|
||||||
// trace('Desync for tick ${ourMoveStruct.timeState.ticks}');
|
var otherPred = predictions.retrieveState(clientMarble, ourMoveStruct.timeState.ticks);
|
||||||
clientMarble.unpackUpdate(lastMove);
|
if (otherPred == null || otherPred.getError(lastMove) > 0.01) {
|
||||||
needsPrediction |= 1 << client;
|
correctPrediction(clientMarble, lastMove, ourTick, mask, arr.packets);
|
||||||
arr.packets.insert(0, lastMove);
|
|
||||||
predictions.clearStatesAfterTick(clientMarbles[Net.clientIdMap[client]], ourMoveStruct.timeState.ticks);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
// Debug.drawSphere(@:privateAccess clientMarbles[Net.clientIdMap[client]].newPos, 0.2, 0.5);
|
|
||||||
// trace('Desync for tick ${ourMoveStruct.timeState.ticks}');
|
|
||||||
clientMarble.unpackUpdate(lastMove);
|
|
||||||
needsPrediction |= 1 << client;
|
|
||||||
arr.packets.insert(0, lastMove);
|
|
||||||
predictions.clearStatesAfterTick(clientMarble, ourMoveStruct.timeState.ticks);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
// Debug.drawSphere(@:privateAccess clientMarbles[Net.clientIdMap[client]].newPos, 0.2, 0.5);
|
|
||||||
// trace('Desync in General');
|
|
||||||
clientMarble.unpackUpdate(lastMove);
|
|
||||||
needsPrediction |= 1 << client;
|
|
||||||
arr.packets.insert(0, lastMove);
|
|
||||||
// predictions.clearStatesAfterTick(clientMarbles[Net.clientIdMap[client]], ourMoveStruct.timeState.ticks);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// marble.unpackUpdate(ourMove);
|
|
||||||
// needsPrediction |= 1 << Net.clientId;
|
|
||||||
if (!Net.clientSpectate) {
|
|
||||||
if (ourMoveStruct != null) {
|
|
||||||
var ourPred = predictions.retrieveState(marble, ourMoveStruct.timeState.ticks);
|
|
||||||
if (ourPred != null) {
|
|
||||||
if (ourPred.getError(ourMove) > 0.01) {
|
|
||||||
// trace('Desync for tick ${ourMoveStruct.timeState.ticks}');
|
|
||||||
marble.unpackUpdate(ourMove);
|
|
||||||
needsPrediction |= 1 << Net.clientId;
|
|
||||||
predictions.clearStatesAfterTick(marble, ourMoveStruct.timeState.ticks);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
// trace('Desync for tick ${ourMoveStruct.timeState.ticks}');
|
|
||||||
marble.unpackUpdate(ourMove);
|
|
||||||
needsPrediction |= 1 << Net.clientId;
|
|
||||||
predictions.clearStatesAfterTick(marble, ourMoveStruct.timeState.ticks);
|
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// trace('Desync in General');
|
correctPrediction(clientMarble, lastMove, -1, mask, arr.packets);
|
||||||
marble.unpackUpdate(ourMove);
|
}
|
||||||
needsPrediction |= 1 << Net.clientId;
|
}
|
||||||
// predictions.clearStatesAfterTick(marble, ourMoveStruct.timeState.ticks);
|
if (!Net.clientSpectate) {
|
||||||
|
if (hasStruct) {
|
||||||
|
var ourPred = predictions.retrieveState(marble, ourTick);
|
||||||
|
if (ourPred == null || ourPred.getError(ourMove) > 0.01) {
|
||||||
|
correctPrediction(marble, ourMove, ourTick, 1 << Net.clientId);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
correctPrediction(marble, ourMove, -1, 1 << Net.clientId);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -46,41 +46,61 @@ class MarblePredictionStore {
|
||||||
}
|
}
|
||||||
|
|
||||||
public function storeState(marble:Marble, tick:Int) {
|
public function storeState(marble:Marble, tick:Int) {
|
||||||
var state = new MarblePrediction(marble, tick);
|
var arr = ensureHistory(marble);
|
||||||
if (predictions.exists(marble)) {
|
truncateFromTick(arr, tick);
|
||||||
var arr = predictions[marble];
|
arr.push(new MarblePrediction(marble, tick));
|
||||||
while (arr.length != 0 && arr[0].tick >= tick)
|
|
||||||
arr.shift();
|
|
||||||
arr.push(state);
|
|
||||||
} else {
|
|
||||||
predictions.set(marble, [state]);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public function retrieveState(marble:Marble, tick:Int) {
|
public function retrieveState(marble:Marble, tick:Int) {
|
||||||
if (predictions.exists(marble)) {
|
var arr = predictions.get(marble);
|
||||||
var arr = predictions[marble];
|
if (arr == null)
|
||||||
while (arr.length != 0 && arr[0].tick < tick)
|
|
||||||
arr.shift();
|
|
||||||
if (arr.length == 0)
|
|
||||||
return null;
|
|
||||||
var p = arr[0];
|
|
||||||
if (p.tick == tick)
|
|
||||||
return p;
|
|
||||||
return null;
|
return null;
|
||||||
}
|
|
||||||
return null;
|
dropBeforeTick(arr, tick);
|
||||||
|
return (arr.length != 0 && arr[0].tick == tick) ? arr[0] : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function clearStatesAfterTick(marble:Marble, tick:Int) {
|
public function clearStatesAfterTick(marble:Marble, tick:Int) {
|
||||||
if (predictions.exists(marble)) {
|
var arr = predictions.get(marble);
|
||||||
var arr = predictions[marble];
|
if (arr != null)
|
||||||
while (arr.length != 0 && arr[arr.length - 1].tick >= tick)
|
truncateFromTick(arr, tick);
|
||||||
arr.pop();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public function removeMarbleFromPrediction(marble:Marble) {
|
public function removeMarbleFromPrediction(marble:Marble) {
|
||||||
this.predictions.remove(marble);
|
this.predictions.remove(marble);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline function ensureHistory(marble:Marble) {
|
||||||
|
var arr = predictions.get(marble);
|
||||||
|
if (arr == null) {
|
||||||
|
arr = [];
|
||||||
|
predictions.set(marble, arr);
|
||||||
|
}
|
||||||
|
return arr;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline function dropBeforeTick(arr:Array<MarblePrediction>, tick:Int) {
|
||||||
|
var idx = lowerBound(arr, tick);
|
||||||
|
if (idx > 0)
|
||||||
|
arr.splice(0, idx);
|
||||||
|
}
|
||||||
|
|
||||||
|
inline function truncateFromTick(arr:Array<MarblePrediction>, tick:Int) {
|
||||||
|
var idx = lowerBound(arr, tick);
|
||||||
|
if (idx < arr.length)
|
||||||
|
arr.splice(idx, arr.length - idx);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline function lowerBound(arr:Array<MarblePrediction>, tick:Int) {
|
||||||
|
var lo = 0;
|
||||||
|
var hi = arr.length;
|
||||||
|
while (lo < hi) {
|
||||||
|
var mid = (lo + hi) >> 1;
|
||||||
|
if (arr[mid].tick < tick)
|
||||||
|
lo = mid + 1;
|
||||||
|
else
|
||||||
|
hi = mid;
|
||||||
|
}
|
||||||
|
return lo;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue