package com.nicewuerfel.blockown.protection; import com.nicewuerfel.blockown.Material; import com.nicewuerfel.blockown.User; import java.text.SimpleDateFormat; import java.util.Date; import java.util.Objects; import javax.annotation.Nonnull; import javax.annotation.Nullable; /** * An immutable object containing information about a single action on the protection database.<br> * Can't be instantiated directly, the class {@link ProtectAction.Builder} must be used. * * @author Pheasn */ public final class ProtectAction { @Nonnull private final Type type; @Nonnull private final User owner; @Nullable private final User user; @Nullable private final Material material; private final long timeStamp; /** * Describes the type of {@link ProtectAction action} to be performed. */ public enum Type { /** * Protect a {@link Material} against other players, except friends. */ PROTECT, /** * Revert {@link #PROTECT}. */ UNPROTECT, /** * Protects a {@link Material} against all players, even friends. */ LOCK, /** * Revert {@link #LOCK}. */ UNLOCK, /** * Adds a {@link User} to the friend list of this {@link ProtectAction action's} main user. */ FRIEND, /** * Revert {@link #FRIEND}. */ UNFRIEND, /** * Drop all occurrences of this player in any {@link Protection}-related data.<br> * This means the player won't have any locked or protected {@link Material materials}, no * friends and would be removed from all friend-lists of other players. */ DROP } /** * A builder class for {@link ProtectAction} objects. * * @author Pheasn */ public static class Builder { private Type type; private User owner; private Material material; private User user; /** * Creates a new Builder instance. * * @param owner the main {@link User} this action is about */ public Builder(@Nonnull User owner) { this.owner = Objects.requireNonNull(owner); } /** * Sets the type to {@link Type#PROTECT} and specifies the {@link Material} to protect. * * @param material the {@link Material} * @return this {@link Builder} */ public Builder protect(@Nonnull Material material) { this.material = Objects.requireNonNull(material); type = Type.PROTECT; return this; } /** * Sets the type to {@link Type#UNPROTECT} and specifies the {@link Material} to unprotect. * * @param material the {@link Material} * @return this {@link Builder} */ public Builder unprotect(@Nonnull Material material) { this.material = Objects.requireNonNull(material); type = Type.UNPROTECT; return this; } /** * Sets the type to {@link Type#LOCK} and specifies the {@link Material} to lock. * * @param material the {@link Material} * @return this {@link Builder} */ public Builder lock(@Nonnull Material material) { this.material = Objects.requireNonNull(material); type = Type.LOCK; return this; } /** * Sets the type to {@link Type#UNLOCK} and specifies the {@link Material} to unlock. * * @param material the {@link Material} * @return this {@link Builder} */ public Builder unlock(@Nonnull Material material) { this.material = Objects.requireNonNull(material); type = Type.UNLOCK; return this; } /** * Sets the type to {@link Type#FRIEND} and specifies the {@link User} to add as a friend for * the main user. * * @param user the {@link User} * @return this {@link Builder} */ public Builder friend(@Nonnull User user) { this.user = Objects.requireNonNull(user); type = Type.FRIEND; return this; } /** * Sets the type to {@link Type#UNFRIEND} and specifies the {@link User} to remove from the main * user's friend list. * * @param user the {@link User} * @return this {@link Builder} */ public Builder unfriend(@Nonnull User user) { this.user = user; type = Type.UNFRIEND; return this; } /** * Sets the type to {@link Type#DROP}. * * @return this {@link Builder} */ public Builder drop() { type = Type.DROP; return this; } /** * Returns an instance of {@link ProtectAction}. * * @return the {@link ProtectAction} * @throws IllegalStateException if this is called without calling any other method first */ public ProtectAction build() { if (type == null) { throw new IllegalStateException("No type selected"); } return new ProtectAction(type, owner, material, user); } } private ProtectAction(Type type, User owner, Material material, User user) { this.type = type; this.owner = owner; this.material = material; this.user = user; this.timeStamp = System.currentTimeMillis(); } /** * Gets the {@link Type}. * * @return the {@link Type} */ @Nonnull public Type getActionType() { return type; } /** * Gets the main {@link User} this action is about. * * @return the {@link User} */ @Nonnull public User getOwner() { return owner; } /** * Gets the second {@link User} to {@link Type#FRIEND FRIEND} or {@link Type#UNFRIEND UNFRIEND}. * <br> * If the type is none of the above, returns null. * * @return the {@link User} */ @Nullable public User getUser() { return user; } /** * Gets the {@link Material} to {@link Type#PROTECT PROTECT}, {@link Type#UNPROTECT UNPROTECT}, * {@link Type#LOCK LOCK} or {@link Type#UNLOCK UNLOCK}.<br> * If the type is none of the above, returns null. * * @return the {@link Material} */ @Nullable public Material getMaterial() { return material; } /** * Returns the value of {@link System#currentTimeMillis()} at the time of this object's creation. * * @return the Unix time stamp in milliseconds */ public long getTimeStamp() { return timeStamp; } @Override public int hashCode() { final int prime = 31; int result = 17; result = prime * result + ((material == null) ? 0 : material.hashCode()); result = prime * result + owner.hashCode(); result = prime * result + type.hashCode(); result = prime * result + (int) (timeStamp ^ (timeStamp >>> 32)); result = prime * result + ((user == null) ? 0 : user.hashCode()); return result; } @Override public boolean equals(Object obj) { if (this == obj) { return true; } if (!(obj instanceof ProtectAction)) { return false; } ProtectAction other = (ProtectAction) obj; if (material == null) { if (other.material != null) { return false; } } else if (!material.equals(other.material)) { return false; } if (!owner.equals(other.owner)) { return false; } if (type != other.type) { return false; } if (timeStamp != other.timeStamp) { return false; } if (user == null) { if (other.user != null) { return false; } } else if (!user.equals(other.user)) { return false; } return true; } @Override public String toString() { return "ProtectAction [protectActionType=" + type + ", owner=" + owner + ", user=" + user + ", material=" + material + ", timeStamp=" + new SimpleDateFormat().format(new Date(timeStamp)) + "]"; } }