Skip to content

Commit

Permalink
Merge branch 'server-inventory' of https://github.com/Camotoy/Geyser
Browse files Browse the repository at this point in the history
…into server-inventory
  • Loading branch information
Camotoy committed Jan 14, 2021
2 parents 454fd10 + 6a9d4cd commit feae057
Show file tree
Hide file tree
Showing 60 changed files with 1,817 additions and 514 deletions.
47 changes: 32 additions & 15 deletions .github/ISSUE_TEMPLATE/bug_report.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,34 +7,51 @@ assignees: ''

---

<!--- DELETING THIS TEMPLATE WILL GET YOUR ISSUE CLOSED! --->

<!--- Please follow this format COMPLETELY and make sure the bug you are reporting has not been reported yet. Reports should contain as much information or context as possible to help us find the problem. Simply creating an issue on a vague topic will not help us at all, and if you are unsure if something should belong here, please contact us on [Discord](http://discord.geysermc.org).-->

<!--- Issues pertaining to connection problem, or anything of that covered on the [Common Issues](https://github.com/GeyserMC/Geyser/wiki/Common-Issues) do not belong here and only clutter this issue tracker. -->
<!--- Issues pertaining to connection problems, or anything of that covered on the [Common Issues](https://github.com/GeyserMC/Geyser/wiki/Common-Issues) do not belong here and only clutter this issue tracker. -->

**Describe the bug**
<!--- A clear and concise description of what the bug is. -->

A clear and concise description of what the bug is.

**To Reproduce**
<!--- Steps to reproduce the behavior: -->
<!--- 1. Go to '...' -->
<!--- 2. Click on '....' -->
<!--- 3. Scroll down to '....' -->
<!--- 4. See error -->

Steps to reproduce the behavior:
1. Go to '...'
2. Click on '....'
3. Scroll down to '....'
4. See error

**Expected behavior**
<!--- A clear and concise description of what you expected to happen. -->

A clear and concise description of what you expected to happen.

**Screenshots / Videos**
<!--- If applicable, add screenshots to help explain your problem. -->

**Server Version**
<!--- Give us the exact output from `/version`. Saying "latest" does not help us at all. -->
If applicable, add screenshots to help explain your problem.

**Server Version and Plugins**

If you just run Geyser-Spigot, you can leave this area blank as the next section covers this information.

**Geyser Version**
<!--- Give us the exact build number as well as branch if applicable. Saying "latest" does not help us at all. This info can be obtained from `/geyser version`.Please also include if you are running the standalone version, or specify which plugin version you are using. If your issue is a connection problem, please specify if you are using the Floodgate plugin. -->
If you're running a multi-server instance, or using Geyser Standalone:

- Give us the exact output from `/version` on all servers involved. Saying "latest" does not help us at all.
- Please list all plugins on all servers involved.

If this bug occurs on a server you do not control, please fill this in to the best of your knowledge.

**Geyser Dump**

If Geyser starts correctly, please also include the link to a dump by using `/geyser dump`. If you use the Standalone GUI, the option can be found under `Commands` => `Dump`. This provides us information about your server that we can use to debug your issue.

**Minecraft: Bedrock Edition Version**
<!-- The version of your Minecraft: Bedrock Edition client you tested with. -->

The version of your Minecraft: Bedrock Edition client you tested with, along with your device type (e.g. Windows 10, Switch...).

**Additional Context**
<!--- Add any other context about the problem here. Include any plugins on the Minecraft server that may cause problems. Please also include the link to a dump by using `/geyser dump` --->

Add any other context about the problem here.
30 changes: 29 additions & 1 deletion Jenkinsfile
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,27 @@ pipeline {
}

steps {
sh 'mvn javadoc:jar source:jar deploy -DskipTests'
rtMavenDeployer(
id: "maven-deployer",
serverId: "opencollab-artifactory",
releaseRepo: "maven-releases",
snapshotRepo: "maven-snapshots"
)
rtMavenResolver(
id: "maven-resolver",
serverId: "opencollab-artifactory",
releaseRepo: "release",
snapshotRepo: "snapshot"
)
rtMavenRun(
pom: 'pom.xml',
goals: 'javadoc:jar source:jar install -DskipTests',
deployerId: "maven-deployer",
resolverId: "maven-resolver"
)
rtPublishBuildInfo(
serverId: "opencollab-artifactory"
)
}
}
}
Expand Down Expand Up @@ -69,5 +89,13 @@ pipeline {
discordSend description: "**Build:** [${currentBuild.id}](${env.BUILD_URL})\n**Status:** [${currentBuild.currentResult}](${env.BUILD_URL})\n${changes}\n\n[**Artifacts on Jenkins**](https://ci.opencollab.dev/job/GeyserMC/job/Geyser)", footer: 'Open Collaboration Jenkins', link: env.BUILD_URL, successful: currentBuild.resultIsBetterOrEqualTo('SUCCESS'), title: "${env.JOB_NAME} #${currentBuild.id}", webhookURL: DISCORD_WEBHOOK
}
}
success {
script {
if (env.BRANCH_NAME == 'master') {
build propagate: false, wait: false, job: 'GeyserMC/Geyser-Fabric/java-1.16'
build propagate: false, wait: false, job: 'GeyserMC/GeyserAndroid/master'
}
}
}
}
}
2 changes: 1 addition & 1 deletion LICENSE
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
The MIT License

Copyright (c) 2019-2020 GeyserMC. http://geysermc.org
Copyright (c) 2019-2021 GeyserMC. http://geysermc.org

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ The ultimate goal of this project is to allow Minecraft: Bedrock Edition users t

Special thanks to the DragonProxy project for being a trailblazer in protocol translation and for all the team members who have now joined us here!

### Currently supporting Minecraft Bedrock v1.16.100/v1.16.101/v1.16.200 and Minecraft Java v1.16.4.
### Currently supporting Minecraft Bedrock v1.16.100 - v1.16.201 and Minecraft Java v1.16.4.

## Setting Up
Take a look [here](https://github.com/GeyserMC/Geyser/wiki#Setup) for how to set up Geyser.
Expand Down
4 changes: 2 additions & 2 deletions bootstrap/bungeecord/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -86,8 +86,8 @@
<shadedPattern>org.geysermc.platform.bungeecord.shaded.dom4j</shadedPattern>
</relocation>
<relocation>
<pattern>net.kyori.adventure</pattern>
<shadedPattern>org.geysermc.platform.bungeecord.shaded.adventure</shadedPattern>
<pattern>net.kyori</pattern>
<shadedPattern>org.geysermc.platform.bungeecord.shaded.kyori</shadedPattern>
</relocation>
</relocations>
</configuration>
Expand Down
4 changes: 2 additions & 2 deletions bootstrap/spigot/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -97,8 +97,8 @@
<shadedPattern>org.geysermc.platform.spigot.shaded.dom4j</shadedPattern>
</relocation>
<relocation>
<pattern>net.kyori.adventure</pattern>
<shadedPattern>org.geysermc.platform.spigot.shaded.adventure</shadedPattern>
<pattern>net.kyori</pattern>
<shadedPattern>org.geysermc.platform.spigot.shaded.kyori</shadedPattern>
</relocation>
</relocations>
</configuration>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@
import org.geysermc.platform.spigot.command.GeyserSpigotCommandExecutor;
import org.geysermc.platform.spigot.command.GeyserSpigotCommandManager;
import org.geysermc.platform.spigot.command.SpigotCommandSender;
import org.geysermc.platform.spigot.world.GeyserSpigot1_11CraftingListener;
import org.geysermc.platform.spigot.world.GeyserSpigotBlockPlaceListener;
import org.geysermc.platform.spigot.world.manager.*;
import us.myles.ViaVersion.api.Pair;
Expand Down Expand Up @@ -146,8 +147,9 @@ public void onEnable() {
geyserLogger.debug("Legacy version of Minecraft (1.15.2 or older) detected; not using 3D biomes.");
}

boolean isPre1_12 = !isCompatible(Bukkit.getServer().getVersion(), "1.12.0");
// Set if we need to use a different method for getting a player's locale
SpigotCommandSender.setUseLegacyLocaleMethod(!isCompatible(Bukkit.getServer().getVersion(), "1.12.0"));
SpigotCommandSender.setUseLegacyLocaleMethod(isPre1_12);

if (connector.getConfig().isUseAdapters()) {
try {
Expand Down Expand Up @@ -191,9 +193,13 @@ public void onEnable() {
geyserLogger.debug("Using default world manager: " + this.geyserWorldManager.getClass());
}
GeyserSpigotBlockPlaceListener blockPlaceListener = new GeyserSpigotBlockPlaceListener(connector, this.geyserWorldManager);

Bukkit.getServer().getPluginManager().registerEvents(blockPlaceListener, this);

if (isPre1_12) {
// Register events needed to send all recipes to the client
Bukkit.getServer().getPluginManager().registerEvents(new GeyserSpigot1_11CraftingListener(this, connector), this);
}

this.getCommand("geyser").setExecutor(new GeyserSpigotCommandExecutor(connector));
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,197 @@
/*
* Copyright (c) 2019-2021 GeyserMC. http://geysermc.org
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
* @author GeyserMC
* @link https://github.com/GeyserMC/Geyser
*/

package org.geysermc.platform.spigot.world;

import com.github.steveice10.mc.protocol.MinecraftConstants;
import com.github.steveice10.mc.protocol.data.game.entity.metadata.ItemStack;
import com.github.steveice10.mc.protocol.data.game.recipe.Ingredient;
import com.github.steveice10.mc.protocol.data.game.recipe.RecipeType;
import com.github.steveice10.mc.protocol.data.game.recipe.data.ShapedRecipeData;
import com.github.steveice10.mc.protocol.data.game.recipe.data.ShapelessRecipeData;
import com.nukkitx.protocol.bedrock.data.inventory.CraftingData;
import com.nukkitx.protocol.bedrock.data.inventory.ItemData;
import com.nukkitx.protocol.bedrock.packet.CraftingDataPacket;
import org.bukkit.Bukkit;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.player.PlayerJoinEvent;
import org.bukkit.inventory.Recipe;
import org.bukkit.inventory.ShapedRecipe;
import org.bukkit.inventory.ShapelessRecipe;
import org.geysermc.connector.GeyserConnector;
import org.geysermc.connector.network.session.GeyserSession;
import org.geysermc.connector.network.translators.item.ItemTranslator;
import org.geysermc.connector.network.translators.item.RecipeRegistry;
import org.geysermc.platform.spigot.GeyserSpigotPlugin;
import us.myles.ViaVersion.api.Pair;
import us.myles.ViaVersion.api.data.MappingData;
import us.myles.ViaVersion.api.protocol.Protocol;
import us.myles.ViaVersion.api.protocol.ProtocolRegistry;
import us.myles.ViaVersion.api.protocol.ProtocolVersion;
import us.myles.ViaVersion.protocols.protocol1_13to1_12_2.Protocol1_13To1_12_2;

import java.util.*;

/**
* Used to send all available recipes from the server to the client, as a valid recipe book packet won't be sent by the server.
* Requires ViaVersion.
*/
public class GeyserSpigot1_11CraftingListener implements Listener {

private final GeyserConnector connector;
/**
* Specific mapping data for 1.12 to 1.13. Used to convert the 1.12 item into 1.13.
*/
private final MappingData mappingData1_12to1_13;
/**
* The list of all protocols from the client's version to 1.13.
*/
private final List<Pair<Integer, Protocol>> protocolList;
private final ProtocolVersion version;

public GeyserSpigot1_11CraftingListener(GeyserSpigotPlugin plugin, GeyserConnector connector) {
this.connector = connector;
this.mappingData1_12to1_13 = ProtocolRegistry.getProtocol(Protocol1_13To1_12_2.class).getMappingData();
this.protocolList = ProtocolRegistry.getProtocolPath(MinecraftConstants.PROTOCOL_VERSION,
ProtocolVersion.v1_13.getVersion());
this.version = plugin.getServerProtocolVersion();
}

@EventHandler
public void onPlayerJoin(PlayerJoinEvent event) {
GeyserSession session = null;
for (GeyserSession otherSession : connector.getPlayers()) {
if (otherSession.getName().equals(event.getPlayer().getName())) {
session = otherSession;
break;
}
}
if (session == null) {
return;
}

System.out.println("Sending recipes!");
sendServerRecipes(session);
}

public void sendServerRecipes(GeyserSession session) {
int netId = RecipeRegistry.LAST_RECIPE_NET_ID;

CraftingDataPacket craftingDataPacket = new CraftingDataPacket();
craftingDataPacket.setCleanRecipes(true);
Iterator<Recipe> recipeIterator = Bukkit.getServer().recipeIterator();
while (recipeIterator.hasNext()) {
Recipe recipe = recipeIterator.next();
Pair<ItemStack, ItemData> outputs = translateToBedrock(session, recipe.getResult());
ItemStack javaOutput = outputs.getKey();
ItemData output = outputs.getValue();
if (output.getId() == 0) continue; // If items make air we don't want that
boolean isNotAllAir = false; // Check for all-air recipes
if (recipe instanceof ShapedRecipe) {
ShapedRecipe shapedRecipe = (ShapedRecipe) recipe;
int size = shapedRecipe.getShape().length * shapedRecipe.getShape()[0].length();
Ingredient[] ingredients = new Ingredient[size];
ItemData[] input = new ItemData[size];
for (int i = 0; i < input.length; i++) {
// Index is converting char to integer, adding i then converting back to char based on ASCII code
Pair<ItemStack, ItemData> result = translateToBedrock(session, shapedRecipe.getIngredientMap().get((char) ('a' + i)));
ingredients[i] = new Ingredient(new ItemStack[]{result.getKey()});
input[i] = result.getValue();
isNotAllAir = isNotAllAir || input[i].getId() != 0;
}
if (!isNotAllAir) continue;
UUID uuid = UUID.randomUUID();
// Add recipe to our internal cache
ShapedRecipeData data = new ShapedRecipeData(shapedRecipe.getShape()[0].length(), shapedRecipe.getShape().length,
"", ingredients, javaOutput);
session.getCraftingRecipes().put(netId,
new com.github.steveice10.mc.protocol.data.game.recipe.Recipe(RecipeType.CRAFTING_SHAPED, uuid.toString(), data));
// Add recipe for Bedrock
craftingDataPacket.getCraftingData().add(CraftingData.fromShaped(uuid.toString(),
shapedRecipe.getShape()[0].length(), shapedRecipe.getShape().length, Arrays.asList(input),
Collections.singletonList(output), uuid, "crafting_table", 0, netId++));
} else if (recipe instanceof ShapelessRecipe) {
ShapelessRecipe shapelessRecipe = (ShapelessRecipe) recipe;
Ingredient[] ingredients = new Ingredient[shapelessRecipe.getIngredientList().size()];
ItemData[] input = new ItemData[shapelessRecipe.getIngredientList().size()];
for (int i = 0; i < input.length; i++) {
Pair<ItemStack, ItemData> result = translateToBedrock(session, shapelessRecipe.getIngredientList().get(i));
ingredients[i] = new Ingredient(new ItemStack[]{result.getKey()});
input[i] = result.getValue();
isNotAllAir = isNotAllAir || input[i].getId() != 0;
}
if (!isNotAllAir) continue;
UUID uuid = UUID.randomUUID();
// Add recipe to our internal cache
ShapelessRecipeData data = new ShapelessRecipeData("", ingredients, javaOutput);
session.getCraftingRecipes().put(netId,
new com.github.steveice10.mc.protocol.data.game.recipe.Recipe(RecipeType.CRAFTING_SHAPELESS, uuid.toString(), data));
// Add recipe for Bedrock
craftingDataPacket.getCraftingData().add(CraftingData.fromShapeless(uuid.toString(),
Arrays.asList(input), Collections.singletonList(output), uuid, "crafting_table", 0, netId++));
}
}

session.sendUpstreamPacket(craftingDataPacket);
}

@SuppressWarnings("deprecation")
private Pair<ItemStack, ItemData> translateToBedrock(GeyserSession session, org.bukkit.inventory.ItemStack itemStack) {
if (itemStack != null && itemStack.getData() != null) {
if (itemStack.getType().getId() == 0) {
return new Pair<>(null, ItemData.AIR);
}
int legacyId = (itemStack.getType().getId() << 4) | (itemStack.getData().getData() & 0xFFFF);
if (itemStack.getType().getId() == 355 && itemStack.getData().getData() == (byte) 0) { // Handle bed color since the server will always be pre-1.12
legacyId = (itemStack.getType().getId() << 4) | ((byte) 14 & 0xFFFF);
}
// old version -> 1.13 -> 1.13.1 -> 1.14 -> 1.15 -> 1.16 and so on
int itemId;
if (mappingData1_12to1_13.getItemMappings().containsKey(legacyId)) {
itemId = mappingData1_12to1_13.getNewItemId(legacyId);
} else if (mappingData1_12to1_13.getItemMappings().containsKey((itemStack.getType().getId() << 4) | (0))) {
itemId = mappingData1_12to1_13.getNewItemId((itemStack.getType().getId() << 4) | (0));
} else {
// No ID found, just send back air
return new Pair<>(null, ItemData.AIR);
}

for (int i = protocolList.size() - 1; i >= 0; i--) {
MappingData mappingData = protocolList.get(i).getValue().getMappingData();
if (mappingData != null) {
itemId = mappingData.getNewItemId(itemId);
}
}

ItemStack mcItemStack = new ItemStack(itemId, itemStack.getAmount());
ItemData finalData = ItemTranslator.translateToBedrock(session, mcItemStack);
return new Pair<>(mcItemStack, finalData);
}
// Empty slot, most likely
return new Pair<>(null, ItemData.AIR);
}

}
Loading

0 comments on commit feae057

Please sign in to comment.