@Override
  public void performEffect(IMasterRitualStone ritualStone) {
    String owner = ritualStone.getOwner();

    int currentEssence = SoulNetworkHandler.getCurrentEssence(owner);
    World world = ritualStone.getWorld();
    int x = ritualStone.getXCoord();
    int y = ritualStone.getYCoord();
    int z = ritualStone.getZCoord();

    if (world.getWorldTime() % 200 != 0) {
      return;
    }

    OmegaStructureParameters param =
        OmegaStructureHandler.getStructureStabilityFactor(world, x, y, z, 5, new Int3(0, 1, 0));
    int stab = param.stability;
    int enchantability = param.enchantability;
    int enchantmentLevel = param.enchantmentLevel;

    if (stab <= 0) {
      return;
    }

    //        System.out.println("Stability: " + stab + ", Enchantability: " + enchantability + ",
    // Enchantment Level: " + enchantmentLevel);

    double range = 0.5;

    List<EntityPlayer> playerList =
        SpellHelper.getPlayersInRange(world, x + 0.5, y + 1.5, z + 0.5, range, range);

    Reagent reagent = null;

    Map<Reagent, Integer> reagentMap = new HashMap();
    for (int i = 0; i < 4; i++) {
      Int3 jarLoc = this.getJarLocation(i);
      TileEntity tile =
          world.getTileEntity(x + jarLoc.xCoord, y + jarLoc.yCoord, z + jarLoc.zCoord);
      if (tile instanceof IReagentHandler) {
        IReagentHandler container = (IReagentHandler) tile;
        ReagentContainerInfo[] containerInfoArray = container.getContainerInfo(ForgeDirection.UP);
        if (containerInfoArray == null) {
          continue;
        }

        for (ReagentContainerInfo containerInfo : containerInfoArray) {
          ReagentStack containedReagent = containerInfo.reagent;
          if (containedReagent == null) {
            continue;
          }
          Reagent rea = containedReagent.reagent;
          int amt = containedReagent.amount;
          if (reagentMap.containsKey(rea)) {
            reagentMap.put(rea, reagentMap.get(rea) + amt);
          } else {
            reagentMap.put(rea, amt);
          }
        }
      }
    }

    for (Entry<Reagent, Integer> entry : reagentMap.entrySet()) {
      if (entry.getValue() >= drainTotal) {
        reagent = entry.getKey();
        break;
      }
    }

    if (reagent == null) {
      return;
    }

    int tickDuration =
        isTesting ? 20 * 30 : 15 * 20 * 60 + (int) ((15 * 20 * 60) * Math.sqrt(stab / 700));

    int affinity = 0;

    for (EntityPlayer player : playerList) {
      OmegaParadigm waterParadigm = OmegaRegistry.getParadigmForReagent(reagent);
      if (waterParadigm != null
          && waterParadigm.convertPlayerArmour(
              player, x, y, z, stab, affinity, enchantability, enchantmentLevel)) {
        APISpellHelper.setPlayerCurrentReagentAmount(player, tickDuration);
        APISpellHelper.setPlayerMaxReagentAmount(player, tickDuration);
        APISpellHelper.setPlayerReagentType(player, reagent);
        APISpellHelper.setCurrentAdditionalMaxHP(player, waterParadigm.getMaxAdditionalHealth());
        NewPacketHandler.INSTANCE.sendTo(
            NewPacketHandler.getReagentBarPacket(
                reagent,
                APISpellHelper.getPlayerCurrentReagentAmount(player),
                APISpellHelper.getPlayerMaxReagentAmount(player)),
            (EntityPlayerMP) player);

        if (!isTesting) {
          int drainLeft = this.drainTotal;
          for (int i = 0; i < 4; i++) {
            if (drainLeft <= 0) {
              break;
            }
            Int3 jarLoc = this.getJarLocation(i);
            TileEntity tile =
                world.getTileEntity(x + jarLoc.xCoord, y + jarLoc.yCoord, z + jarLoc.zCoord);
            if (tile instanceof IReagentHandler) {
              IReagentHandler container = (IReagentHandler) tile;
              ReagentStack drained =
                  container.drain(ForgeDirection.UP, new ReagentStack(reagent, drainLeft), true);
              if (drained != null) {
                drainLeft -= drained.amount;
                world.markBlockForUpdate(x + jarLoc.xCoord, y + jarLoc.yCoord, z + jarLoc.zCoord);
                world.addWeatherEffect(
                    new EntityLightningBolt(
                        world, x + jarLoc.xCoord, y + jarLoc.yCoord, z + jarLoc.zCoord));
              }
            }
          }

          ritualStone.setActive(false);
        }

        break;
      }
    }
  }