package Roguelike;
import Roguelike.Entity.Entity;
import Roguelike.Entity.GameEntity;
import Roguelike.GameEvent.Damage.DamageObject;
import Roguelike.GameEvent.GameEventHandler;
import Roguelike.Levels.Level;
import Roguelike.Levels.LevelManager;
import Roguelike.Lights.Light;
import Roguelike.Quests.QuestManager;
import Roguelike.RoguelikeGame.ScreenEnum;
import Roguelike.Save.SaveFile;
import Roguelike.Save.SaveLevel;
import Roguelike.Screens.GameScreen;
import Roguelike.Screens.LoadingScreen;
import Roguelike.Sound.Mixer;
import Roguelike.Sound.RepeatingSoundEffect;
import Roguelike.Tiles.GameTile;
import Roguelike.Tiles.GameTile.LightData;
import Roguelike.Tiles.Point;
import Roguelike.UI.ClassList;
import Roguelike.UI.LayeredDrawable;
import Roguelike.UI.Seperator;
import Roguelike.UI.TabPanel;
import Roguelike.UI.Tooltip.TooltipStyle;
import Roguelike.Util.Controls;
import Roguelike.Util.EnumBitflag;
import Roguelike.Util.FastEnumMap;
import com.badlogic.gdx.graphics.Color;
import com.badlogic.gdx.graphics.Colors;
import com.badlogic.gdx.graphics.Pixmap;
import com.badlogic.gdx.graphics.Pixmap.Format;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.g2d.BitmapFont;
import com.badlogic.gdx.graphics.g2d.NinePatch;
import com.badlogic.gdx.math.MathUtils;
import com.badlogic.gdx.scenes.scene2d.ui.*;
import com.badlogic.gdx.scenes.scene2d.ui.CheckBox.CheckBoxStyle;
import com.badlogic.gdx.scenes.scene2d.ui.Label.LabelStyle;
import com.badlogic.gdx.scenes.scene2d.ui.ProgressBar.ProgressBarStyle;
import com.badlogic.gdx.scenes.scene2d.ui.TextField.TextFieldStyle;
import com.badlogic.gdx.scenes.scene2d.utils.NinePatchDrawable;
import com.badlogic.gdx.scenes.scene2d.utils.TextureRegionDrawable;
import com.badlogic.gdx.utils.*;
import com.badlogic.gdx.utils.XmlReader.Element;
import exp4j.Helpers.EquationHelper;
import net.objecthunter.exp4j.Expression;
import net.objecthunter.exp4j.ExpressionBuilder;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Random;
public class Global
{
// ----------------------------------------------------------------------
public static final boolean CanMoveDiagonal = false;
// ----------------------------------------------------------------------
public static final int NUM_ABILITY_SLOTS = 5;
// ----------------------------------------------------------------------
public static boolean MovementTypePathfind = false;
// ----------------------------------------------------------------------
public static float MusicVolume = 1;
public static float AmbientVolume = 1;
public static float EffectVolume = 1;
// ----------------------------------------------------------------------
public static RoguelikeGame Game;
// ----------------------------------------------------------------------
public static Controls Controls = new Controls();
// ----------------------------------------------------------------------
public static AbstractApplicationChanger ApplicationChanger;
// ----------------------------------------------------------------------
public static boolean ANDROID = false;
public static boolean RELEASE = false;
// ----------------------------------------------------------------------
public static GameEntity CurrentDialogue = null;
// ----------------------------------------------------------------------
public static float AnimationSpeed = 1;
// ----------------------------------------------------------------------
public static int FPS = 0;
// ----------------------------------------------------------------------
public static int[] ScreenSize = { 600, 400 };
// ----------------------------------------------------------------------
public static int[] Resolution = { 600, 400 };
// ----------------------------------------------------------------------
public static int[] TargetResolution = { 600, 400 };
// ----------------------------------------------------------------------
public static int TileSize = 32;
// ----------------------------------------------------------------------
public static LevelManager LevelManager;
public static QuestManager QuestManager;
// ----------------------------------------------------------------------
public static Level CurrentLevel;
// ----------------------------------------------------------------------
public static ObjectMap<String, String> WorldFlags = new ObjectMap<String, String>();
public static ObjectMap<String, String> RunFlags = new ObjectMap<String, String>();
public static ObjectMap<String, String> WorldFlagsCopy = new ObjectMap<String, String>( );
// ----------------------------------------------------------------------
public static boolean CharGenMode = false;
// ----------------------------------------------------------------------
public static Mixer BGM;
// ----------------------------------------------------------------------
public static float AUT = 0;
public static int lives;
// ----------------------------------------------------------------------
public static float DayNightFactor = 1;
// ----------------------------------------------------------------------
public static Pool<Point> PointPool = Pools.get( Point.class, Integer.MAX_VALUE );
public static Pool<Light> LightPool = Pools.get( Light.class, Integer.MAX_VALUE );
public static Pool<LightData> LightDataPool = Pools.get( LightData.class, Integer.MAX_VALUE );
// ----------------------------------------------------------------------
static
{
Colors.put( "Name", Color.GREEN );
Colors.put( "Place", Color.CYAN );
}
// ----------------------------------------------------------------------
public static void updateVolume()
{
if (BGM != null) { BGM.updateVolume(); }
if (CurrentLevel != null)
{
for (RepeatingSoundEffect rse : CurrentLevel.ambientSounds)
{
rse.updateVolume();
}
}
}
// ----------------------------------------------------------------------
public static SaveFile load()
{
SaveFile save = null;
try
{
save = new SaveFile();
save.load();
}
catch (Exception e)
{
return null;
}
Global.QuestManager = new QuestManager();
Global.QuestManager.usedQuests = save.usedQuests;
Global.QuestManager.deferredFlags = save.deferredFlags;
Global.WorldFlags = save.worldFlags;
Global.WorldFlagsCopy = save.worldFlagsCopy;
Global.RunFlags = save.runFlags;
Global.lives = save.lives;
LevelManager = save.levelManager;
return save;
}
// ----------------------------------------------------------------------
public static void save()
{
SaveFile save = new SaveFile();
save.levelManager = LevelManager;
save.usedQuests = QuestManager.usedQuests;
save.worldFlags = WorldFlags;
save.worldFlagsCopy = WorldFlagsCopy;
save.runFlags = RunFlags;
save.deferredFlags = QuestManager.deferredFlags;
save.lives = lives;
if ( CurrentLevel != null && LevelManager.current != null && LevelManager.current.currentLevel != null )
{
LevelManager.current.currentLevel.store( Global.CurrentLevel );
save.isDead = CurrentLevel.player.HP <= 0;
}
else
{
save.isDead = true;
}
save.save();
}
// ----------------------------------------------------------------------
public static void newWorld()
{
lives = 0;
LevelManager = new LevelManager();
QuestManager = new QuestManager();
AUT = 0;
WorldFlags.clear();
WorldFlagsCopy.clear();
RunFlags.clear();
Global.WorldFlags.put( "tavern", "1" );
Global.WorldFlags.put( "startingfunds", "50" );
GameScreen.Instance.queueMessage( "Welcome to A Skin of Others",
"For as long as anyone in your village can remember creatures have been attacking out from beneath Melet mountain." +
"At night they spring from the darkness and snatch the unwary and unvigilant, dragging them away to who knows where. " +
"The imperial capital has been unwilling to send aid, despite numerous requests, so the task of saving the village falls to you. " +
"Strike out into the forest, save those within, and fight your way down into the depths of the mountain to seal the portal the creatures" +
" are coming from.");
GameScreen.Instance.queueMessage( "Controls",
"Click in a direction to move there (or use the arrow keys)." +
" Click on your character to pass a turn (or press space). " +
"Move into an enemy to attack them, or into an NPC to talk to them." +
" Click an ability on the left to ready it, then on a blue target to use it.");
}
// ----------------------------------------------------------------------
public static void testWorld()
{
LevelManager = new LevelManager();
LevelManager.current = LevelManager.root.getLabelledLevel( "EnchantedForest" );
QuestManager = new QuestManager();
AUT = 0;
WorldFlags.clear();
WorldFlagsCopy.clear();
RunFlags.clear();
Global.WorldFlags.put( "tavern", "1" );
Global.WorldFlags.put( "startingfunds", "50" );
SaveLevel firstLevel = new SaveLevel( "EnchantedForest", 1, LevelManager.current.getExtraRooms( "Forest", 1, new Random() ), MathUtils.random( Long.MAX_VALUE - 1 ) );
LevelManager.current.currentLevel = firstLevel;
Array<ClassList.ClassDesc> classes = ClassList.parse();
GameEntity player = classes.get( 0 ).male;
for (Statistic stat : Statistic.BaseValues)
{
player.statistics.put( stat, 100 );
}
player.isVariableMapDirty = true;
LoadingScreen.Instance.set( firstLevel, player, "PlayerSpawn", null );
RoguelikeGame.Instance.switchScreen( ScreenEnum.LOADING );
}
// ----------------------------------------------------------------------
public static void newGame( GameEntity player )
{
LevelManager = new LevelManager();
QuestManager = new QuestManager();
AUT = 0;
DayNightFactor = (float) ( 0.1f + ( ( ( Math.sin( AUT / 100.0f ) + 1.0f ) / 2.0f ) * 0.9f ) );
RunFlags.clear();
SaveLevel firstLevel = new SaveLevel( LevelManager.current.levelName, 1, LevelManager.current.getExtraRooms( "NewGame", 1, new Random() ), MathUtils.random( Long.MAX_VALUE - 1 ) );
LevelManager.current.currentLevel = firstLevel;
GameScreen.Instance.displayLevelEntryMessage( LevelManager.current.levelTitle, LevelManager.current.levelDescription );
LoadingScreen.Instance.set( firstLevel, player, "PlayerSpawn", null );
RoguelikeGame.Instance.switchScreen( ScreenEnum.LOADING );
}
// ----------------------------------------------------------------------
public static void changeBGM(String bgmName)
{
if ( BGM != null )
{
BGM.mix( bgmName, 1 );
}
else
{
BGM = new Mixer( bgmName, 1f );
}
}
// ----------------------------------------------------------------------
public static void changeLevel( Level level, GameEntity player, Object travelData )
{
if ( CurrentLevel != null )
{
for ( RepeatingSoundEffect sound : CurrentLevel.ambientSounds )
{
sound.stop();
}
CurrentLevel.player.tile[0][0].entity = CurrentLevel.player;
}
CurrentLevel = level;
changeBGM(level.bgmName);
if ( player != null )
{
boolean placed = false;
level.player = player;
if ( travelData instanceof String )
{
String travelKey = (String) travelData;
outer:
for ( int x = 0; x < level.width; x++ )
{
for ( int y = 0; y < level.height; y++ )
{
GameTile tile = level.getGameTile( x, y );
if ( tile.metaValue != null )
{
if ( tile.metaValue.equals( travelKey ) )
{
tile.addGameEntity( player );
placed = true;
break outer;
}
}
}
}
}
else if ( travelData instanceof Point )
{
GameTile tile = level.getGameTile( (Point) travelData );
tile.addGameEntity( player );
placed = true;
}
if (!placed)
{
while (!placed)
{
int x = MathUtils.random( level.width );
int y = MathUtils.random( level.height );
GameTile tile = level.getGameTile( x, y );
if (tile.getPassable( player.getTravelType(), player ))
{
tile.addGameEntity( player );
placed = true;
}
}
}
}
CurrentLevel.advance( 0 );
save();
}
// ----------------------------------------------------------------------
public static void calculateDamage( Entity attacker, Entity defender, int atk, int def, int pen, boolean doEvents )
{
if ( atk <= 0 ) { return; }
// attack range
atk += atk * MathUtils.random( -0.1f, 0.1f );
int applicableDef = Math.max( 0, def - pen );
float reduction = applicableDef / 100.0f;
int damage = atk - (int)Math.ceil((float)atk * reduction);
if ( damage <= 0 )
{
damage = 1;
}
DamageObject damObj = new DamageObject(damage);
if ( doEvents )
{
for ( GameEventHandler handler : attacker.getAllHandlers() )
{
handler.onDealDamage( defender, damObj );
}
for ( GameEventHandler handler : defender.getAllHandlers() )
{
handler.onReceiveDamage( defender, damObj );
}
}
defender.applyDamage( damObj.damage, attacker );
}
// ----------------------------------------------------------------------
public static int calculateScaledAttack( HashMap<String, Integer> attackVariableMap, HashMap<String, Integer> attackerVariableMap )
{
int baseAtk = attackVariableMap.get( Statistic.ATTACK.toString().toLowerCase() );
int totalAtk = baseAtk;
for ( Statistic stat : Statistic.ModifierValues )
{
int atkStat = attackVariableMap.get( stat.toString().toLowerCase() );
if (atkStat == 0) { continue; }
float atkerStat = attackerVariableMap.get( stat.toString().toLowerCase() ) / 5.0f;
float sclVal = atkerStat * atkStat;
float falloff = (float)Math.sqrt( sclVal );
float modifier = falloff / 10.0f;
int dam = (int) ( baseAtk * modifier );
totalAtk += dam;
}
return totalAtk;
}
// ----------------------------------------------------------------------
public static int getQuality()
{
int quality = Math.max( 1, Global.LevelManager.totalDepth / 5 + Math.max( 0, (int)(MathUtils.random.nextFloat() * MathUtils.random.nextFloat() * MathUtils.random.nextFloat() * 2.0f) ) );
return quality;
}
// ----------------------------------------------------------------------
public static boolean isNumber( String string )
{
if ( string == null || string.isEmpty() ) { return false; }
int i = 0;
if ( string.charAt( 0 ) == '-' )
{
if ( string.length() > 1 )
{
i++;
}
else
{
return false;
}
}
for ( ; i < string.length(); i++ )
{
if ( !Character.isDigit( string.charAt( i ) ) ) { return false; }
}
return true;
}
// ----------------------------------------------------------------------
public static String expandNames( String input )
{
String[] split = input.split( "\\$" );
boolean skip = !input.startsWith( "\\$" );
String output = "";
for ( int i = 0; i < split.length; i++ )
{
if ( skip )
{
output += split[i];
}
else if ( WorldFlags.containsKey( split[i].toLowerCase() ) )
{
output += WorldFlags.get( split[i].toLowerCase() );
}
else if ( RunFlags.containsKey( split[i].toLowerCase() ) )
{
output += RunFlags.get( split[i].toLowerCase() );
}
skip = !skip;
}
return output;
}
// ----------------------------------------------------------------------
public static String capitalizeString( String s )
{
String[] parts = s.split( "_" );
String output = "";
for (String part : parts)
{
output += part.substring( 0, 1 ).toUpperCase() + part.substring( 1 ).toLowerCase() + " ";
}
return output.trim();
}
// ----------------------------------------------------------------------
public static int TaxiDist(Point p1, Point p2)
{
return TaxiDist( p1.x, p1.y, p2.x, p2.y );
}
// ----------------------------------------------------------------------
public static int TaxiDist(int x1, int y1, int x2, int y2)
{
int xdiff = Math.abs( x1 - x2 );
int ydiff = Math.abs( y1 - y2 );
return Math.max( xdiff, ydiff );
}
// ----------------------------------------------------------------------
public static String join( String seperator, Iterable<String> strings )
{
Iterator<String> itr = strings.iterator();
String out = itr.next();
while (itr.hasNext())
{
out += seperator + itr.next();
}
return out;
}
// ----------------------------------------------------------------------
private static Skin skin = null;
public static Skin loadSkin()
{
if (skin != null)
{
return skin;
}
skin = new Skin();
BitmapFont font = AssetManager.loadFont( "Sprites/Unpacked/font.ttf", 12, new Color( 0.97f, 0.87f, 0.7f, 1 ), 1, Color.BLACK, false );
skin.add( "default", font );
BitmapFont titlefont = AssetManager.loadFont( "Sprites/Unpacked/font.ttf", 20, new Color( 1f, 0.9f, 0.8f, 1 ), 1, Color.BLACK, true );
skin.add( "title", titlefont );
Pixmap pixmap = new Pixmap( 1, 1, Format.RGBA8888 );
pixmap.setColor( Color.WHITE );
pixmap.fill();
skin.add( "white", new Texture( pixmap ) );
TextFieldStyle textField = new TextFieldStyle();
textField.fontColor = Color.WHITE;
textField.font = skin.getFont( "default" );
textField.background = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/TextField.png" ), 6, 6, 6, 6 ) );
textField.focusedBackground = ((NinePatchDrawable)textField.background).tint( new Color( 0.9f, 0.9f, 0.9f, 1.0f ) );
textField.cursor = skin.newDrawable( "white", Color.WHITE );
textField.selection = skin.newDrawable( "white", Color.LIGHT_GRAY );
skin.add( "default", textField );
LabelStyle label = new LabelStyle();
label.font = skin.getFont( "default" );
skin.add( "default", label );
LabelStyle titleLabel = new LabelStyle();
titleLabel.font = skin.getFont( "title" );
skin.add( "title", titleLabel );
CheckBoxStyle checkButton = new CheckBoxStyle();
checkButton.checkboxOff = new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/Unchecked.png" ) );
checkButton.checkboxOn = new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/Checked.png" ) );
checkButton.font = skin.getFont( "default" );
checkButton.fontColor = Color.LIGHT_GRAY;
checkButton.overFontColor = Color.WHITE;
skin.add( "default", checkButton );
TextButton.TextButtonStyle textButton = new TextButton.TextButtonStyle();
textButton.up = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) );
textButton.font = skin.getFont( "default" );
textButton.fontColor = Color.LIGHT_GRAY;
textButton.overFontColor = Color.WHITE;
//textButton.checked = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/ButtonDown.png" ), 12, 12, 12, 12 ) );
textButton.over = ((NinePatchDrawable)textButton.up).tint( new Color( 0.9f, 0.9f, 0.9f, 1.0f ) );
skin.add( "default", textButton );
TextButton.TextButtonStyle bigTextButton = new TextButton.TextButtonStyle();
bigTextButton.up = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) );
bigTextButton.font = skin.getFont( "title" );
bigTextButton.fontColor = Color.LIGHT_GRAY;
bigTextButton.overFontColor = Color.WHITE;
//bigTextButton.checked = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/ButtonDown.png" ), 12, 12, 12, 12 ) );
bigTextButton.over = ((NinePatchDrawable)bigTextButton.up).tint( new Color( 0.9f, 0.9f, 0.9f, 1.0f ) );
skin.add( "big", bigTextButton );
TextButton.TextButtonStyle keyBindingButton = new TextButton.TextButtonStyle();
keyBindingButton.up = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/TextField.png" ), 6, 6, 6, 6 ) );
keyBindingButton.font = skin.getFont( "default" );
keyBindingButton.fontColor = Color.LIGHT_GRAY;
keyBindingButton.overFontColor = Color.WHITE;
//textButton.checked = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/ButtonDown.png" ), 12, 12, 12, 12 ) );
keyBindingButton.over = ((NinePatchDrawable)keyBindingButton.up).tint( new Color( 0.9f, 0.9f, 0.9f, 1.0f ) );
skin.add( "keybinding", keyBindingButton );
TooltipStyle toolTip = new TooltipStyle();
toolTip.background = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Tooltip.png" ), 21, 21, 21, 21 ) );
skin.add( "default", toolTip );
ProgressBarStyle progressBar = new ProgressBarStyle();
progressBar.background = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/TextField.png" ), 6, 6, 6, 6 ) );
progressBar.knobBefore = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/ProgressIndicator.png" ), 8, 8, 8, 8 ) );
skin.add( "default-horizontal", progressBar );
Button.ButtonStyle buttonStyle = new Button.ButtonStyle( );
buttonStyle.up = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) );
buttonStyle.over = ((NinePatchDrawable)buttonStyle.up).tint( new Color( 0.9f, 0.9f, 0.9f, 1.0f ) );
skin.add( "default", buttonStyle );
Button.ButtonStyle sheathButton = new Button.ButtonStyle( );
sheathButton.up = new LayeredDrawable(
new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) ),
new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/Unsheathed.png" ) ) );
sheathButton.checked = new LayeredDrawable(
new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) ),
new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/Sheathed.png" ) ) );
skin.add( "sheath", sheathButton );
Button.ButtonStyle examineButton = new Button.ButtonStyle( );
examineButton.up = new LayeredDrawable(
new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) ),
new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/QuestionMark.png" ) ) );
examineButton.checked = new LayeredDrawable(
new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) ),
new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/Eye.png" ) ) );
skin.add( "examine", examineButton );
Button.ButtonStyle menuButton = new Button.ButtonStyle( );
menuButton.up = new LayeredDrawable(
new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) ),
new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/Cog.png" ) ) );
skin.add( "menu", menuButton );
Seperator.SeperatorStyle horiSeperatorStyle = new Seperator.SeperatorStyle( );
horiSeperatorStyle.vertical = false;
horiSeperatorStyle.thickness = 6;
horiSeperatorStyle.background = new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/SeperatorHorizontal.png" ) );
skin.add( "horizontal", horiSeperatorStyle );
Seperator.SeperatorStyle vertSeperatorStyle = new Seperator.SeperatorStyle( );
vertSeperatorStyle.vertical = true;
vertSeperatorStyle.thickness = 6;
vertSeperatorStyle.background = new TextureRegionDrawable( AssetManager.loadTextureRegion( "Sprites/GUI/SeperatorVertical.png" ) );
skin.add( "vertical", vertSeperatorStyle );
ScrollPane.ScrollPaneStyle scrollPaneStyle = new ScrollPane.ScrollPaneStyle( );
scrollPaneStyle.vScroll = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/TextField.png" ), 6, 6, 6, 6 ) );
scrollPaneStyle.vScrollKnob = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) );
skin.add( "default", scrollPaneStyle );
List.ListStyle listStyle = new List.ListStyle( );
listStyle.background = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Tooltip.png" ), 21, 21, 21, 21 ) );
listStyle.font = skin.getFont( "default" );
listStyle.selection = skin.newDrawable( "white", Color.LIGHT_GRAY );
skin.add( "default", listStyle );
SelectBox.SelectBoxStyle selectBoxStyle = new SelectBox.SelectBoxStyle( );
selectBoxStyle.fontColor = Color.WHITE;
selectBoxStyle.font = skin.getFont( "default" );
selectBoxStyle.background = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/TextField.png" ), 6, 6, 6, 6 ) );
selectBoxStyle.scrollStyle = scrollPaneStyle;
selectBoxStyle.listStyle = listStyle;
selectBoxStyle.backgroundOver = ((NinePatchDrawable)selectBoxStyle.background).tint( new Color( 0.9f, 0.9f, 0.9f, 1.0f ) );
skin.add( "default", selectBoxStyle );
Slider.SliderStyle sliderStyle = new Slider.SliderStyle( );
sliderStyle.background = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/TextField.png" ), 6, 6, 6, 6 ) );
sliderStyle.knob = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) );
sliderStyle.knobOver = ((NinePatchDrawable)sliderStyle.knob).tint( new Color( 0.9f, 0.9f, 0.9f, 1.0f ) );
sliderStyle.knobDown = ((NinePatchDrawable)sliderStyle.knob).tint( Color.LIGHT_GRAY );
skin.add( "default-horizontal", sliderStyle );
TabPanel.TabPanelStyle tabPanelStyle = new TabPanel.TabPanelStyle( );
tabPanelStyle.font = skin.getFont( "default" );
tabPanelStyle.fontColor = Color.LIGHT_GRAY;
tabPanelStyle.overFontColor = Color.WHITE;
tabPanelStyle.bodyBackground = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/TextField.png" ), 6, 6, 6, 6 ) ).tint( new Color( 1, 1, 1, 0.2f ) );
tabPanelStyle.titleButtonUnselected = new NinePatchDrawable( new NinePatch( AssetManager.loadTextureRegion( "Sprites/GUI/Button.png" ), 12, 12, 12, 12 ) );
tabPanelStyle.titleButtonSelected = ((NinePatchDrawable)tabPanelStyle.titleButtonUnselected).tint( new Color( 0.8f, 0.8f, 0.8f, 1.0f ) );
skin.add( "default", tabPanelStyle );
return skin;
}
// ----------------------------------------------------------------------
public enum Rarity
{
VERYCOMMON,
COMMON,
UNCOMMON,
RARE,
LEGENDARY,
MYTHICAL
}
// ----------------------------------------------------------------------
public enum ScaleLevel
{
F,
E,
D,
C,
B,
A,
S,
SS
}
// ----------------------------------------------------------------------
public enum Direction
{
CENTER( 0, 0, "C" ),
NORTH( 0, 1, "N" ),
SOUTH( 0, -1, "S" ),
EAST( 1, 0, "E" ),
WEST( -1, 0, "W" ),
NORTHEAST( 1, 1, "NE" ),
NORTHWEST( -1, 1, "NW" ),
SOUTHEAST( 1, -1, "SE" ),
SOUTHWEST(-1, -1, "SW" );
static
{
// Setup neighbours
Direction.CENTER.clockwise = Direction.CENTER;
Direction.CENTER.anticlockwise = Direction.CENTER;
Direction.NORTH.anticlockwise = Direction.NORTHWEST;
Direction.NORTH.clockwise = Direction.NORTHEAST;
Direction.NORTHEAST.anticlockwise = Direction.NORTH;
Direction.NORTHEAST.clockwise = Direction.EAST;
Direction.EAST.anticlockwise = Direction.NORTHEAST;
Direction.EAST.clockwise = Direction.SOUTHEAST;
Direction.SOUTHEAST.anticlockwise = Direction.EAST;
Direction.SOUTHEAST.clockwise = Direction.SOUTH;
Direction.SOUTH.anticlockwise = Direction.SOUTHEAST;
Direction.SOUTH.clockwise = Direction.SOUTHWEST;
Direction.SOUTHWEST.anticlockwise = Direction.SOUTH;
Direction.SOUTHWEST.clockwise = Direction.WEST;
Direction.WEST.anticlockwise = Direction.SOUTHWEST;
Direction.WEST.clockwise = Direction.NORTHWEST;
Direction.NORTHWEST.anticlockwise = Direction.WEST;
Direction.NORTHWEST.clockwise = Direction.NORTH;
// Setup is cardinal
Direction.NORTH.isCardinal = true;
Direction.SOUTH.isCardinal = true;
Direction.EAST.isCardinal = true;
Direction.WEST.isCardinal = true;
}
public final String identifier;
private final int x;
private final int y;
private final float angle; // In degrees
private Direction clockwise;
private Direction anticlockwise;
private boolean isCardinal = false;
Direction( int x, int y, String identifier )
{
this.x = x;
this.y = y;
this.identifier = identifier;
// basis vector = 0, 1
double dot = 0 * x + 1 * y; // dot product
double det = 0 * y - 1 * x; // determinant
angle = (float) Math.atan2( det, dot ) * MathUtils.radiansToDegrees;
}
public static Direction getDirection( int[] dir )
{
return getDirection( dir[0], dir[1] );
}
public static Direction getDirection( int dx, int dy )
{
dx = MathUtils.clamp( dx, -1, 1 );
dy = MathUtils.clamp( dy, -1, 1 );
Direction d = Direction.CENTER;
for ( Direction dir : Direction.values() )
{
if ( dir.getX() == dx && dir.getY() == dy )
{
d = dir;
break;
}
}
return d;
}
public static Direction getCardinalDirection( int dx, int dy )
{
if (dx == 0 && dy == 0)
{
return Direction.CENTER;
}
if (Math.abs( dx ) > Math.abs( dy ))
{
if (dx < 0)
{
return Direction.WEST;
}
else
{
return Direction.EAST;
}
}
else
{
if (dy < 0)
{
return Direction.SOUTH;
}
else
{
return Direction.NORTH;
}
}
}
public int getX()
{
return x;
}
public int getY()
{
return y;
}
public static Direction getDirection( GameTile t1, GameTile t2 )
{
return getDirection( t2.x - t1.x, t2.y - t1.y );
}
public static Array<Point> buildCone( Direction dir, Point start, int range )
{
Array<Point> hitTiles = new Array<Point>();
Direction anticlockwise = dir.getAnticlockwise();
Direction clockwise = dir.getClockwise();
Point acwOffset = PointPool.obtain().set( dir.getX() - anticlockwise.getX(), dir.getY() - anticlockwise.getY() );
Point cwOffset = PointPool.obtain().set( dir.getX() - clockwise.getX(), dir.getY() - clockwise.getY() );
hitTiles.add( PointPool.obtain().set( start.x + anticlockwise.getX(), start.y + anticlockwise.getY() ) );
hitTiles.add( PointPool.obtain().set( start.x + dir.getX(), start.y + dir.getY() ) );
hitTiles.add( PointPool.obtain().set( start.x + clockwise.getX(), start.y + clockwise.getY() ) );
for ( int i = 2; i <= range; i++ )
{
int acx = start.x + anticlockwise.getX() * i;
int acy = start.y + anticlockwise.getY() * i;
int nx = start.x + dir.getX() * i;
int ny = start.y + dir.getY() * i;
int cx = start.x + clockwise.getX() * i;
int cy = start.y + clockwise.getY() * i;
// add base tiles
hitTiles.add( PointPool.obtain().set( acx, acy ) );
hitTiles.add( PointPool.obtain().set( nx, ny ) );
hitTiles.add( PointPool.obtain().set( cx, cy ) );
// add anticlockwise - mid
for ( int ii = 1; ii <= range; ii++ )
{
int px = acx + acwOffset.x * ii;
int py = acy + acwOffset.y * ii;
hitTiles.add( PointPool.obtain().set( px, py ) );
}
// add mid - clockwise
for ( int ii = 1; ii <= range; ii++ )
{
int px = cx + cwOffset.x * ii;
int py = cy + cwOffset.y * ii;
hitTiles.add( PointPool.obtain().set( px, py ) );
}
}
PointPool.free( acwOffset );
PointPool.free( cwOffset );
return hitTiles;
}
public Direction getClockwise()
{
return clockwise;
}
public Direction getAnticlockwise()
{
return anticlockwise;
}
public boolean isCardinal()
{
return isCardinal;
}
public float getAngle()
{
return angle;
}
public Direction getOpposite()
{
return getDirection( x * -1, y * -1 );
}
}
// ----------------------------------------------------------------------
public enum Passability
{
WALK( Statistic.WALK ), LEVITATE( Statistic.LEVITATE ), LIGHT( Statistic.LIGHT ), ENTITY( Statistic.ENTITY );
public final Statistic stat;
Passability( Statistic stat )
{
this.stat = stat;
}
public static EnumBitflag<Passability> variableMapToTravelType( HashMap<String, Integer> stats )
{
EnumBitflag<Passability> travelType = new EnumBitflag<Passability>();
for ( Passability p : Passability.values() )
{
String checkString = p.stat.toString().toLowerCase();
if ( stats.containsKey( checkString ) )
{
int val = stats.get( checkString );
if ( val > 0 )
{
travelType.setBit( p );
}
}
}
return travelType;
}
public static EnumBitflag<Passability> parse( String passable )
{
EnumBitflag<Passability> passableBy = new EnumBitflag<Passability>();
if ( passable != null )
{
if ( passable.equalsIgnoreCase( "true" ) )
{
// all
for ( Passability p : Passability.values() )
{
passableBy.setBit( p );
}
}
else if ( passable.equalsIgnoreCase( "false" ) )
{
// none
}
else
{
String[] split = passable.split( "," );
for ( String p : split )
{
passableBy.setBit( Passability.valueOf( p.toUpperCase() ) );
}
}
}
return passableBy;
}
public static EnumBitflag<Passability> parseArray( String passable )
{
EnumBitflag<Passability> passableBy = new EnumBitflag<Passability>();
if ( passable != null )
{
if ( passable.equalsIgnoreCase( "true" ) )
{
// all
for ( Passability p : Passability.values() )
{
passableBy.setBit( p );
}
}
else if ( passable.equalsIgnoreCase( "false" ) )
{
// none
}
else
{
String[] split = passable.split( "," );
for ( String p : split )
{
passableBy.setBit( Passability.valueOf( p.toUpperCase() ) );
}
}
}
return passableBy;
}
}
// ----------------------------------------------------------------------
public enum Statistic
{
// Passability
WALK,
LEVITATE,
LIGHT,
ENTITY,
// Base stats
ATTACK, // Base Damage
DEFENSE, // Defense
PENETRATION, // Penetration
// Modifier stats
STRENGTH, // Melee dam
PERCEPTION, // Sight range + range dam
WILLPOWER, // magic dam
CONSTITUTION, // Health + Blood dam
SPEED; // Speed
public static Statistic[] PassabilityValues = { Statistic.WALK, Statistic.LEVITATE, Statistic.LIGHT, Statistic.ENTITY };
public static Statistic[] BaseValues = { Statistic.ATTACK, Statistic.DEFENSE };
public static Statistic[] ModifierValues = {
Statistic.STRENGTH,
Statistic.PERCEPTION,
Statistic.WILLPOWER,
Statistic.CONSTITUTION,
Statistic.SPEED };
public static HashMap<String, Integer> emptyMap = new HashMap<String, Integer>();
static
{
for ( Statistic s : Statistic.values() )
{
emptyMap.put( s.toString().toLowerCase(), 0 );
}
}
public static HashMap<String, Integer> statsBlockToVariableBlock( FastEnumMap<Statistic, Integer> stats )
{
HashMap<String, Integer> variableMap = new HashMap<String, Integer>();
for ( Statistic key : Statistic.values() )
{
Integer val = stats.get( key );
if ( val != null )
{
variableMap.put( key.toString().toLowerCase(), val );
}
}
return variableMap;
}
public static FastEnumMap<Statistic, Integer> getStatisticsBlock()
{
FastEnumMap<Statistic, Integer> stats = new FastEnumMap<Statistic, Integer>( Statistic.class );
for ( Statistic stat : Statistic.values() )
{
stats.put( stat, 0 );
}
return stats;
}
public static FastEnumMap<Statistic, Integer> load( Element xml, FastEnumMap<Statistic, Integer> values )
{
for ( int i = 0; i < xml.getChildCount(); i++ )
{
Element el = xml.getChild( i );
Statistic stat = Statistic.valueOf( el.getName().toUpperCase() );
String eqn = el.getText().toLowerCase();
int newVal = values.get( stat );
if ( Global.isNumber( eqn ) )
{
newVal = Integer.parseInt( eqn );
}
else
{
ExpressionBuilder expB = EquationHelper.createEquationBuilder( eqn );
expB.variable( "value" );
expB.variable( "val" );
Expression exp = EquationHelper.tryBuild( expB );
if ( exp != null )
{
exp.setVariable( "value", newVal );
exp.setVariable( "val", newVal );
newVal = (int) exp.evaluate();
}
}
values.put( stat, newVal );
}
return values;
}
public static FastEnumMap<Statistic, Integer> copy( FastEnumMap<Statistic, Integer> map )
{
FastEnumMap<Statistic, Integer> newMap = new FastEnumMap<Statistic, Integer>( Statistic.class );
for ( Statistic e : Statistic.values() )
{
newMap.put( e, map.get( e ) );
}
return newMap;
}
public static String formatString( String input )
{
String[] words = input.split( "_" );
String output = "";
for ( String word : words )
{
word = word.toLowerCase();
output += word + " ";
}
return output.trim();
}
}
}