Sunday, February 12, 2012

Potions and Their Particle Colors

Question

Just a Normal Day in Minecraft When...

I was drinking potions to see how many status effects i could get at once. Then while in behind camera view i noticed that the potion particle effect was a greenish-gray color.

Some further Testing

It seems like color of the particle effect is determined by what the potions' colors mixed together would look like.

Is this true?

Asked by Jonny B

Answer

Examining the Minecraft source reveals the exact algorithm for determining the color of potions. Here's the function that seems to do it:

public static int getPotionColor(Collection collection)
{
    int waterColor = 0x385dc6;
    if (collection == null || collection.isEmpty())
    {
        return waterColor;
    }
    float r = 0.0F;
    float g = 0.0F;
    float b = 0.0F;
    float numColors = 0.0F;
    for (Iterator iterator = collection.iterator(); iterator.hasNext();)
    {
        PotionEffect potioneffect = (PotionEffect)iterator.next();
        int potionColor = Potion.potionTypes[potioneffect.getPotionID()].getLiquidColor();
        int i = 0;
        while (i <= potioneffect.getAmplifier())
        {
            r += (float)(potionColor >> 16 & 0xff) / 255F;
            g += (float)(potionColor >> 8 & 0xff) / 255F;
            b += (float)(potionColor >> 0 & 0xff) / 255F;
            numColors++;
            i++;
        }
    }    r = (hBit / numColors) * 255F;
    g = (mBit / numColors) * 255F;
    b = (lBit / numColors) * 255F;
    return (int)r << 16 | (int)g << 8 | (int)b;
}

This large, complex piece of code actually does something quite simple. It does basically just take all the different colors and average them together. Even so, it has a few extra quirks. First of all, this code checks to see if there are any potion effects to begin with. If not, it just uses the water color. I don't think that's ever used in the game, though.

It then creates a bunch of variables. Colors in Minecraft are stored in hexadecimal RGB format, so it creates a variable for red, green, and blue. It then loops through all the potions that are currently active. It then gets the amplifier, or potion level, and weights each color based on its level. Higher level potions have more influence on the resulting color.

Next is a bunch of bitwise math to average all the values, and in the end, all the values are divided by the total (to actually get an average) and spliced back into a single number, which is then returned as the particle color.

Answered by Jake King

No comments:

Post a Comment