So I'm using this code to set ppl into teams. PHP: $players = $this->getServer()->getLevelByName("gamelevel")->getPlayers(); $count = count($players); $blues = array_slice($players, $count / 2);$reds = array_slice($players, 0, $count / 2); This successfully sorts say 6 players into 2 teams of 3 ppl. How can I change this code so that it sets ppl into 4 teams? red, blue, green and yellow. I tried PHP: $players = $this->getServer()->getLevelByName("gamelevel")->getPlayers(); $count = count($players); $blues = array_slice($players, $count / 4);$reds = array_slice($players, 0, $count / 4);$greens = array_slice($players, 0, $count / 4);$yellows = array_slice($players, 0, $count / 4); but when players join the game, the players arnt distributed to each team equally. if 4 players join all 4 are blue. not 1 blue 1 green 1 yellow 1 red etc. How can I change the code to achieve this. Many thanks
I know this wont solve your issue but...use array_chunk. PHP: $players = $this->getServer()->getLevelByName("gamelevel")->getPlayers();//Suppose there are 15 players.$chunked = array_chunk($players, 4, true);/*** $chunked = [* 0 => [4 players]* 1 => [4 players]* 2 => [4 players]* 3 => [3 players]* ];*/if(isset($chunked[0], $chunked[1], $chunked[2], $chunked[3])){//4 teams can be formed.//$chunked[0] is an array of players of first team.//$chunked[1] is an array of players of second team.//$chunked[2] is an array of players of third team.//$chunked[3] is an array of players of fourth team.}
Coming back to your issue... PHP: /** @var Players[] $players */$cnt = count($players);if($cnt <= 1){ //Match cannot be started. //$player = array_values($players)[0]; //if($player instanceof Player) $player->sendMessage("Match cannot be started. Need one more player."); return;}$split = 2;if($cnt % 4 === 0){ $split = 4;}elseif($cnt % 3 === 0){ $split = 3;}$chunk = array_chunk($players, --$split, true);$reds = $chunk[0];$yellows = $chunk[1];$greens = $chunk[2] ?? [];$blues = $chunk[3] ?? [];// "?? []" will return the value [] if $chunk[*] is not set. So if there are no people in $greens, $greens will be [].//You can do a check using//if(empty($greens)){// no players in $greens.//} Yeah, I could've done $split -= $split but that would consume a whole line, so that's why I decremented the value of $split instead. You have to decrement it as count() gives the count in natural numbers while arrays use whole numbers and start off with 0.
Dont use array_chunk, it doesnt work right when having a non-integer as result, use this function: PHP: public function partition( $list, $p ) { $listlen = count( $list ); $partlen = floor( $listlen / $p ); $partrem = $listlen % $p; $partition = array(); $mark = 0; for ($px = 0; $px < $p; $px++) { $incr = ($px < $partrem) ? $partlen + 1 : $partlen; $partition[$px] = array_slice( $list, $mark, $incr ); $mark += $incr; } return $partition;}$part = $this->partition($this->getPlayers(), 2);$blues = $part[0];$reds = $part[1];
It works right. Where did you read that? My chestshop plugin (which chunks items with their nbts) uses array_chunk. I've used it for my server's duels and auction house mechanisms too.
I had it in my old plugin, it created team splitting issues when as example 3 players should be splitten up in 2 teams. Many people on stackoverflow confirmed it.
I have no idea how you got it. If you want to preserve the keys during the chunking, use the 3rd argument. Maybe you were using an associative array.