Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Anvil recipies with NBT tags or anyDamage as input #21

Closed
0xebjc opened this issue Jul 18, 2019 · 19 comments
Closed

Anvil recipies with NBT tags or anyDamage as input #21

0xebjc opened this issue Jul 18, 2019 · 19 comments

Comments

@0xebjc
Copy link

0xebjc commented Jul 18, 2019

If you already have this feature and I missed it I apologize.

When creating an anvil recipe I want to set the input as an item with any damage.

Example:
Anvil.addRecipe(minecraft:golden_sword.anyDamage(), minecraft:diamond * 2, minecraft:diamond_sword, 2);

Then I would get out a diamond sword with full durability using a gold sword with any durability.

Additionally I would like to pass enchantments from one item to the next in the anvil recipes.

Example:
Anvil.addRecipe(minecraft:golden_sword.copyEnchantments(), minecraft:diamond * 2, minecraft:diamond_sword.appendEnchantments(), 2);

So If I put a gold sword with smite I would get out a diamond sword with smite.

@0xebjc
Copy link
Author

0xebjc commented Jul 18, 2019

I used the term appendEnchantment() because if the item being crafted already has nbt data, say from a mod or other preset nbt data then the goal would be not to overwrite that nbt data, just append the enchantments.

Additionally the anyDamage() method would be helpful to create repair recipes.

Example:
Anvil.addRecipe(minecraft:golden_sword.anyDamage(), minecraft:gold_ingot * 2, minecraft:golden_sword, 2);
This would repair the item.

@Mohron
Copy link
Member

Mohron commented Jul 19, 2019

Is item.copyEnchantments() a part of CraftTweaker? I wasn't able to find it in the docs (https://crafttweaker.readthedocs.io). Supporting CraftTweaker item conditions like item.anyDamage() on the other hand is something the mod should really be doing so I'll work on making it possible.

@0xebjc
Copy link
Author

0xebjc commented Jul 19, 2019

I just made up "item.copyEnchantments()" as an example of the feature I was looking for. It does not exist. Crafttweaker does support recipe enchantment copy in a complex method, see ( https://docs.blamejared.com/en/#Vanilla/Recipes/Crafting/Recipe_Functions/ ) but it not the simplest method. I don't believe Rocky Core Anvil recipes supports anything like this? Basically just like when you repair an item in the Anvil your get back the same item with increased durability with all the same NBT data. I was hoping that the anvil recipe would allow a similar method for repairing items or a way to upgrade them and keep their NBT data.

@Mohron
Copy link
Member

Mohron commented Jul 19, 2019

Would you be willing to test out a build updated to support item conditions with some of your planed recipes? The enchantment thing is going to take some serious digging to see if it's even viable without an extra parameter which wouldn't be as flexible as being able to tag items in the recipe.

@0xebjc
Copy link
Author

0xebjc commented Jul 19, 2019

Sure. I am packing today for a 8 day road trip through, leaving tomorrow at 6am. So, definitely will help, but it will be after next Sunday when I can take a look.
-jc

@Mohron
Copy link
Member

Mohron commented Jul 21, 2019

Now that I feel like fully understand your ask, it's really a duplicate of two separate issues:
Item Conditions: #13
Recipe Functions: #11.

Mohron added a commit that referenced this issue Jul 21, 2019
@Mohron
Copy link
Member

Mohron commented Jul 21, 2019

If you would like to test this feature and provide feedback, a build is available here: https://github.com/DevOnTheRocks/RockyTweaks/releases/tag/0.6.0-PRE-RELEASE-1

@0xebjc
Copy link
Author

0xebjc commented Jul 29, 2019

I am testing your pre-release. The Item Conditions , i've tested <>.anyDamage() and it is working. for example.

Anvil.addRecipe(minecraft:golden_sword:*.anyDamage(), minecraft:diamond * 4, minecraft:diamond_sword, 8);

This works as expected. I can use a golden sword with any damage and get a new diamond sword.

@0xebjc
Copy link
Author

0xebjc commented Jul 29, 2019

I either do not understand your needed syntax for IRecipeFunction or this feature is not working. Here's my code.

Anvil.addRecipe(minecraft:golden_sword:*.anyDamage(), minecraft:diamond * 4, minecraft:diamond_sword, 8, function(out, ins, crafting){

        if(ins.input_item.tag has "ench") {
            return out.withTag({ench: ins.input_item.tag.ench});
        } else {
        	return <minecraft:diamond_sword>;
        }
});

when I place the input ingredients into the Anvil I get an error message printed in the chat log repeated eight times.

ERROR: Could not execute RecipeFunction:
ERROR: Could not execute RecipeFunction:
ERROR: Could not execute RecipeFunction:
ERROR: Could not execute RecipeFunction:
ERROR: Could not execute RecipeFunction:
ERROR: Could not execute RecipeFunction:
ERROR: Could not execute RecipeFunction:
ERROR: Could not execute RecipeFunction:

@0xebjc
Copy link
Author

0xebjc commented Jul 29, 2019

the above syntax for the function(out, ins, crafting) works in crafttweaker for recipe.addshaped

@0xebjc
Copy link
Author

0xebjc commented Jul 29, 2019

I also tried to use the funciton with out the item condition and got the same error message.

Code:

Anvil.addRecipe(<minecraft:golden_sword:*>, <minecraft:diamond> * 4, <minecraft:diamond_sword>, 8, function(out, ins, crafting){
        if(ins.input_item.tag has "ench") {
            return out.withTag({ench: ins.input_item.tag.ench});
        } else {
        	return <minecraft:diamond_sword>;
        }
});

@0xebjc
Copy link
Author

0xebjc commented Jul 29, 2019

FYI, I'm pasting in the code, but the form is stripping out the greater than and less than brackets.

@Mohron
Copy link
Member

Mohron commented Jul 29, 2019

Try using a code block:

```
code
```

Also, ins should have ins.left and ins.right as your inputs

@0xebjc
Copy link
Author

0xebjc commented Jul 29, 2019

Both features work now on client only game, awesome! Tested with mod items also. I will be testing on server/client next.

Here's the code that worked:

Anvil.remove(<carbonado:carbonado_sword>);
<carbonado:carbonado_sword>.displayName= "Black Diamond Sword";
//Anvil.addRecipe(<tp:wub_sword:*>, <carbonado:carbonado> * 4, <carbonado:carbonado_sword>, 8);


Anvil.addRecipe(<tp:wub_sword:*>.anyDamage(), <carbonado:carbonado> * 4, <carbonado:carbonado_sword>, 8, function(out, ins, cInfo){

	        if(ins.left.tag has "ench") {
	            return out.withTag({ench: ins.left.tag.ench});
	        } else {
	        	return <carbonado:carbonado_sword>;
	        }
    });


Anvil.addRecipe(<advancedcombat:advanced_stone_sword:*>, <carbonado:carbonado> * 4, <carbonado:carbonado_sword>, 8, function(out, ins, cInfo){

	        if(ins.left.tag has "ench") {
	            return out.withTag({ench: ins.left.tag.ench});
	        } else {
	        	return <carbonado:carbonado_sword>;
	        }
    });

Anvil.addRecipe(<minecraft:golden_sword:*>.anyDamage(), <carbonado:carbonado> * 4, <carbonado:carbonado_sword>, 8);

@0xebjc
Copy link
Author

0xebjc commented Jul 29, 2019

tested client/server no issues with mod'd and vanilla items, worked as expected with the previously posted code.

@Mohron
Copy link
Member

Mohron commented Jul 30, 2019

Glad to hear. What's your thoughts on me making a custom function instead of reusing the one from crafting table recipes? The Crafting Info parameter is completely useless and I feel like the input thing can be confusing. I could make a anvil specific function like function(output, left, right) or function(output, input).

@0xebjc
Copy link
Author

0xebjc commented Aug 2, 2019

I've actually used the crafting parameter for checking things like a players xp crafting.player.xp

//
//	<carbonado:carbonado_sword>, [
//
//    [null, 		<carbonado:carbonado>.transformConsume(4).onlyStack(4) * 4, 	<tp:stone_hammer>.reuse()],
//
//    [null,    	<tp:wub_sword:*>.marked("input_item"),    						null],
//
//    [null, 		<minecraft:anvil>.reuse(), 										null]],
//    
//    function(out, ins, crafting) {
//
//    	if crafting.player.xp >= 8 {
//    		crafting.player.sendChat("Players Level is " ~ crafting.player.xp);
//
//	        if(ins.input_item.tag has "ench") {
//	            return out.withTag({ench: ins.input_item.tag.ench});
//	        } else {
//	        	return <carbonado:carbonado_sword>;
//	        }
//	    } else {
//	    	return null;
//	    }
//    }, function(output, crafting, player) {
//    		var xpLevelCost = 8;
//	    	player.xp -= xpLevelCost;
//	    	player.sendChat("Removed " ~ xpLevelCost ~ " XP Levels.");
//	});```

but not sure if you really need anything like this since the anvil already handles xp deductions and assuming it validates available xp beforehand.

@0xebjc
Copy link
Author

0xebjc commented Aug 2, 2019

I would probably leave it because it offers a more universal option that aligns with crafttweaker syntax. If someone wants to implement something in crafttweaker or rockytweaks they would already understand the syntax.

@0xebjc
Copy link
Author

0xebjc commented Aug 2, 2019

What I think would be a great addition to creafttweaker that could be inherited by your mod would be a way to more easily handle NBT data from input to output items, simliar to

.anyDamage()
Ideas would be out.replaceNBT(input.NBT) or out.appendNBT(input.NBT), or out.appendNBT(input.NBT.onlyEnch)
recpies.addshaped(<minecraft:diamond_sword.appendNBT(input_weapon.onlyEnch), 
    [[null, <minecraft:diamond>, null],
    [<minecraft:diamond>, <minecraft:golden_sword>.maked("input_weapon"), <minecraft:diamond>],
    [null, <minecraft:diamond>, <minecraft:diamond>]]);
REPLACE THIS:

Anvil.addRecipe(<minecraft:golden_sword:*>.anyDamage(), <minecraft:diamond> * 4, <minecraft:diamond_sword>, 8, function(out, ins, cInfo){
	        if(ins.left.tag has "ench") {
	            return out.withTag({ench: ins.left.tag.ench});
	        } else {
	        	return out;
	        }
    });

WITH:

Anvil.addRecipe(<minecraft:golden_sword:*>.anyDamage(), <minecraft:diamond> * 4, <minecraft:diamond_sword>.appendNBT(in.left.NBT.onlyEnch), 8);

I would prefer to have options to append or replace nbt data because I have mods that have custom NBT data already added from within the class definition that I would not want to replace.

really, you've done a great job and I'm using your pre-release now, it does exactly what I was looking for, and it's just a matter of understanding the function parameter for crafting and how it works.

@0xebjc 0xebjc closed this as completed Aug 2, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Development

No branches or pull requests

2 participants