If you are willing to use command blocks, there is a pretty straightforwards way to do this with scoreboards.
First, you would want to setup your scoreboards:
/scoreboard objectives add Points dummy Points
/scoreboard objectives setdisplay sidebar Points
Then you would setup each team as follows:
/scoreboard teams add <team>
/scoreboard players set <team> Points 0
For example, for a team Griffindor
:
/scoreboard teams add Griffindor
/scoreboard players set Griffindor Points 0
For every player you want participating in the quests, you would have them join the team they participate in.
/scoreboard teams join <team> <player>
/scoreboard players set <player> Points 0
Lastly, in a command block that is on repeat OR a function that runs in the game loop, you would have something like this function:
/scoreboard players set temp Points 0
/scoreboard players operation temp Points += @a[team=Griffindor] Points
/scoreboard players operation Griffindor Points = temp Points
This must be repeated for every team you have, but once you have decided on the teams you want you can create this in a function then leave it. It is important that these commands run in sequence so I would recommend sticking this in a function file.
Finally, in game, when you want to reward a player for doing something, you would type:
/scoreboard players <player> add Points <x>
The game will automatically add their points to the sidebar, which will display the top players points. Since we made each team a ‘Player’, so to speak, the top teams will be on top of the leaderboard. If you want to completely hide players, you would make player points a separate objective, and change the function to:
/scoreboard players set temp playerpoints 0
/scoreboard players operation temp playerpoints+= @a[team=Griffindor] playerpoints
/scoreboard players operation Griffindor Points = temp playerpoints
Which might look nicer, but you have to remember to set points of players to playerpoints
and not Points
.