Jump to content
View in the app

A better way to browse. Learn more.

Forge Forums

A full-screen app on your home screen with push notifications, badges and more.

To install this app on iOS and iPadOS
  1. Tap the Share icon in Safari
  2. Scroll the menu and tap Add to Home Screen.
  3. Tap Add in the top-right corner.
To install this app on Android
  1. Tap the 3-dot menu (⋮) in the top-right corner of the browser.
  2. Tap Add to Home screen or Install app.
  3. Confirm by tapping Install.

Featured Replies

Posted

I'm trying to determine if there's a firework with particular colors/effects/shapes near a player. This is what I have so far:

 

double ax, ay, az, bx, by, bz;
double range = 32;
ax = player.getPosX() - range;
ay = player.getPosY() - range;
az = player.getPosZ() - range;
bx = player.getPosX() + range;
by = player.getPosY() + range;
bz = player.getPosZ() + range;
AxisAlignedBB boundingBox = new AxisAlignedBB(ax, ay, az, bx, by, bz);
List<FireworkRocketEntity> rocketsLotsOfRockets = world.getEntitiesWithinAABB(FireworkRocketEntity.class, boundingBox, null);
for(FireworkRocketEntity rocket : rocketsLotsOfRockets) {
    Set<String> tags = rocket.getTags();            
    if(player.isSneaking()) {
        SSoMM.PAUL_BUNYAN.log(Level.DEBUG, "Rocket data: " + tags.size() + " tags");
        for(String tag : tags) {
            SSoMM.PAUL_BUNYAN.log(Level.DEBUG, "\t" + tag);
        }
    }
}

 

But looking at the logs, all I get is (a spam of) "Rocket data: 0 tags". This is because rocket.getTags() is returning an (empty) array of Tag-system tags, not NBT tags, right?

 

How do I get the NBT data containing the colors and effects and so forth?

Edited by Fractangle
Solved!

  • Author

I'm not sure I understand what you mean by "replicate it" on the server side.

 

For context, I only care about the firework data on the server side - my use case is for the presence of a correctly-colored-patterned-etc firework to trigger the spawning of a mob, hence why I ruled out sending a custom packet from client to server. (Don't want a client spoofing the firework presence!)

  • Author

Ah okay, that makes sense! Thank you! I've got something that works, but it's a little gross (due to FireworkRocketEntity.FIREWORK_ITEM being private):

 

double ax, ay, az, bx, by, bz;
double range = 32;
ax = player.getPosX() - range;
ay = player.getPosY() - range;
az = player.getPosZ() - range;
bx = player.getPosX() + range;
by = player.getPosY() + range;
bz = player.getPosZ() + range;
AxisAlignedBB boundingBox = new AxisAlignedBB(ax, ay, az, bx, by, bz);
List<FireworkRocketEntity> rocketsLotsOfRockets = world.getEntitiesWithinAABB(FireworkRocketEntity.class, boundingBox, null);
for(FireworkRocketEntity rocket : rocketsLotsOfRockets) {
  List<EntityDataManager.DataEntry<?>> allRocketData = rocket.getDataManager().getAll();
  if(allRocketData == null) {
    SSoMM.PAUL_BUNYAN.log(Level.DEBUG, "Rocket data had no data");
    return false;
  }
  for(EntityDataManager.DataEntry<?> datum : allRocketData) {
    Object value = datum.getValue();
    if(value instanceof ItemStack) {
      ItemStack stack = (ItemStack) value;
      CompoundNBT tag = stack.getTag();
      SSoMM.PAUL_BUNYAN.log(Level.DEBUG, tag);
    }
  }
}

 

Might be a bit niche, but I figured I'd throw it out there in case anybody else can use it.

  • Author

Good point! (I've never done that before, hence why I overlooked it. Back in a bit with cleaner code once I've done some Learning™!)

 

Edit: As promised, the working reflection-based code:

 

double ax, ay, az, bx, by, bz;
double range = 32;
ax = player.getPosX() - range;
ay = player.getPosY() - range;
az = player.getPosZ() - range;
bx = player.getPosX() + range;
by = player.getPosY() + range;
bz = player.getPosZ() + range;
AxisAlignedBB boundingBox = new AxisAlignedBB(ax, ay, az, bx, by, bz);
List<FireworkRocketEntity> rocketsLotsOfRockets = world.getEntitiesWithinAABB(FireworkRocketEntity.class, boundingBox, null);
for(FireworkRocketEntity rocket : rocketsLotsOfRockets) {
  EntityDataManager rocketDataManager = rocket.getDataManager();
  Field fireworkItemField;
  try {
    fireworkItemField = FireworkRocketEntity.class.getDeclaredField("FIREWORK_ITEM");
    fireworkItemField.setAccessible(true);
    DataParameter<ItemStack> FIREWORK_ITEM = (DataParameter<ItemStack>)fireworkItemField.get(null);
    ItemStack stack = rocketDataManager.get(FIREWORK_ITEM);
    SSoMM.PAUL_BUNYAN.log(Level.DEBUG, stack.getTag());
  } catch(NoSuchFieldException e) {
    throw new WTFException("FireworkRocketEntity class was missing the FIREWORK_ITEM field...?!");
  } catch(IllegalAccessException e) {
    throw new WTFException("I literally just called setAccessible(true)");
  }
}

 

Edited by Fractangle
Added cleaner code than last time

  • Author

Whew, thanks for that one! I've got it using the SRG name now, and looking the field up only once.

 

public static final DataParameter<ItemStack> FIREWORK_ITEM = ObfuscationReflectionHelper.getPrivateValue(FireworkRocketEntity.class, null, "field_184566_a");

 

Edited by Fractangle
Accidental copypasta error semicolon

  • Author

Like this?

 

public static final String FIREWORK_ITEM_SRG = "field_184566_a";

// [a bunch of unrelated stuff in the class]

DataParameter<ItemStack> FIREWORK_ITEM = ObfuscationReflectionHelper.getPrivateValue(FireworkRocketEntity.class, null, FIREWORK_ITEM_SRG);
CompoundNBT fireworkData = rocketDataManager.get(FIREWORK_ITEM).getTag();

 

  • Author

Sixth time's the charm? 🤣

 

public static final String FIREWORK_ITEM_SRG = "field_184566_a";
public static final Field FIREWORK_ITEM_FIELD = ObfuscationReflectionHelper.findField(FireworkRocketEntity.class, FIREWORK_ITEM_SRG);

// [stuff]

DataParameter<ItemStack> FIREWORK_ITEM;
FIREWORK_ITEM_FIELD.setAccessible(true);
try {
  FIREWORK_ITEM = (DataParameter<ItemStack>) FIREWORK_ITEM_FIELD.get(rocket);
} catch(IllegalAccessException e) {
  throw new WTFException("I literally just called setAccessible(true)");
}

 

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

Important Information

By using this site, you agree to our Terms of Use.

Configure browser push notifications

Chrome (Android)
  1. Tap the lock icon next to the address bar.
  2. Tap Permissions → Notifications.
  3. Adjust your preference.
Chrome (Desktop)
  1. Click the padlock icon in the address bar.
  2. Select Site settings.
  3. Find Notifications and adjust your preference.