Move ControllerDefinition to its own file

This commit is contained in:
adelikat 2014-11-30 23:05:00 +00:00
parent b05bed93ac
commit c4768c102e
3 changed files with 163 additions and 170 deletions

View File

@ -0,0 +1,160 @@
using System;
using System.Collections.Generic;
using System.Linq;
namespace BizHawk.Emulation.Common
{
public class ControllerDefinition
{
public void ApplyAxisConstraints(string constraintClass, IDictionary<string, float> floatButtons)
{
if (AxisConstraints == null) return;
foreach (var constraint in AxisConstraints)
{
if (constraint.Class != constraintClass)
continue;
switch (constraint.Type)
{
case AxisConstraintType.Circular:
{
string xaxis = constraint.Params[0] as string;
string yaxis = constraint.Params[1] as string;
float range = (float)constraint.Params[2];
double xval = floatButtons[xaxis];
double yval = floatButtons[yaxis];
double length = Math.Sqrt(xval * xval + yval * yval);
if (length > range)
{
double ratio = range / length;
xval *= ratio;
yval *= ratio;
}
floatButtons[xaxis] = (float)xval;
floatButtons[yaxis] = (float)yval;
break;
}
}
}
}
public struct FloatRange
{
public readonly float Min;
public readonly float Max;
/// <summary>
/// default position
/// </summary>
public readonly float Mid;
public FloatRange(float min, float mid, float max)
{
Min = min;
Mid = mid;
Max = max;
}
// for terse construction
public static implicit operator FloatRange(float[] f)
{
if (f.Length != 3)
{
throw new ArgumentException();
}
return new FloatRange(f[0], f[1], f[2]);
}
}
public enum AxisConstraintType
{
Circular
}
public struct AxisConstraint
{
public string Class;
public AxisConstraintType Type;
public object[] Params;
}
public string Name { get; set; }
public List<string> BoolButtons { get; set; }
public List<string> FloatControls { get; private set; }
public List<FloatRange> FloatRanges { get; private set; }
public List<AxisConstraint> AxisConstraints { get; private set; }
public ControllerDefinition(ControllerDefinition source)
: this()
{
Name = source.Name;
BoolButtons.AddRange(source.BoolButtons);
FloatControls.AddRange(source.FloatControls);
FloatRanges.AddRange(source.FloatRanges);
AxisConstraints.AddRange(source.AxisConstraints);
}
public ControllerDefinition()
{
BoolButtons = new List<string>();
FloatControls = new List<string>();
FloatRanges = new List<FloatRange>();
AxisConstraints = new List<AxisConstraint>();
}
/// <summary>
/// Puts the controls in a logical order such as by controller number,
/// This is a default implementation that should work most of the time
/// </summary>
public virtual IEnumerable<IEnumerable<string>> ControlsOrdered
{
get
{
var list = FloatControls.Union(BoolButtons);
yield return list
.Where(x => !x.StartsWith("P1 ") && !x.StartsWith("P2 ") && !x.StartsWith("P3 ") && !x.StartsWith("P4 "));
yield return list
.Where(x => x.StartsWith("P1 "));
yield return list
.Where(x => x.StartsWith("P2 "));
yield return list
.Where(x => x.StartsWith("P3 "));
yield return list
.Where(x => x.StartsWith("P4 "));
}
}
// TODO: a more respectable logic here, and possibly per core implementation
public virtual int PlayerCount
{
get
{
var list = FloatControls.Union(BoolButtons);
if (list.Any(b => b.StartsWith("P8"))) { return 8; }
if (list.Any(b => b.StartsWith("P7"))) { return 7; }
if (list.Any(b => b.StartsWith("P6"))) { return 6; }
if (list.Any(b => b.StartsWith("P5"))) { return 5; }
if (list.Any(b => b.StartsWith("P4"))) { return 4; }
if (list.Any(b => b.StartsWith("P3"))) { return 3; }
if (list.Any(b => b.StartsWith("P2"))) { return 2; }
if (list.Any(b => b.StartsWith("P1"))) { return 1; }
if (list.Any(b => b.StartsWith("Up"))) { return 1; } // Hack for things like gameboy/ti-83 as opposed to genesis with no controllers plugged in
return 0;
}
}
public virtual bool Any()
{
return BoolButtons.Any() || FloatControls.Any();
}
}
}

View File

@ -49,6 +49,7 @@
<Compile Include="..\VersionInfo.cs">
<Link>VersionInfo.cs</Link>
</Compile>
<Compile Include="Base Implementations\ControllerDefinition.cs" />
<Compile Include="Base Implementations\NullController.cs" />
<Compile Include="Base Implementations\NullEmulator.cs" />
<Compile Include="CoreAttributes.cs" />

View File

@ -1,174 +1,6 @@
using System;
using System.Collections.Generic;
using System.Linq;
namespace BizHawk.Emulation.Common
namespace BizHawk.Emulation.Common
{
// doesn't do what is desired
// http://connect.microsoft.com/VisualStudio/feedback/details/459307/extension-add-methods-are-not-considered-in-c-collection-initializers
/*
public static class UltimateMagic
{
public static void Add(this List<ControllerDefinition.FloatRange l, float Min, float Mid, float Max)
{
l.Add(new ControllerDefinition.FloatRange(Min, Mid, Max);
}
}
*/
public class ControllerDefinition
{
public void ApplyAxisConstraints(string constraintClass, IDictionary<string, float> floatButtons)
{
if (AxisConstraints == null) return;
foreach (var constraint in AxisConstraints)
{
if (constraint.Class != constraintClass)
continue;
switch (constraint.Type)
{
case AxisConstraintType.Circular:
{
string xaxis = constraint.Params[0] as string;
string yaxis = constraint.Params[1] as string;
float range = (float)constraint.Params[2];
double xval = floatButtons[xaxis];
double yval = floatButtons[yaxis];
double length = Math.Sqrt(xval * xval + yval * yval);
if (length > range)
{
double ratio = range / length;
xval *= ratio;
yval *= ratio;
}
floatButtons[xaxis] = (float)xval;
floatButtons[yaxis] = (float)yval;
break;
}
}
}
}
public struct FloatRange
{
public readonly float Min;
public readonly float Max;
/// <summary>
/// default position
/// </summary>
public readonly float Mid;
public FloatRange(float min, float mid, float max)
{
Min = min;
Mid = mid;
Max = max;
}
// for terse construction
public static implicit operator FloatRange(float[] f)
{
if (f.Length != 3)
{
throw new ArgumentException();
}
return new FloatRange(f[0], f[1], f[2]);
}
}
public enum AxisConstraintType
{
Circular
}
public struct AxisConstraint
{
public string Class;
public AxisConstraintType Type;
public object[] Params;
}
public string Name { get; set; }
public List<string> BoolButtons { get; set; }
public List<string> FloatControls { get; private set; }
public List<FloatRange> FloatRanges { get; private set; }
public List<AxisConstraint> AxisConstraints { get; private set; }
public ControllerDefinition(ControllerDefinition source)
: this()
{
Name = source.Name;
BoolButtons.AddRange(source.BoolButtons);
FloatControls.AddRange(source.FloatControls);
FloatRanges.AddRange(source.FloatRanges);
AxisConstraints.AddRange(source.AxisConstraints);
}
public ControllerDefinition()
{
BoolButtons = new List<string>();
FloatControls = new List<string>();
FloatRanges = new List<FloatRange>();
AxisConstraints = new List<AxisConstraint>();
}
/// <summary>
/// Puts the controls in a logical order such as by controller number,
/// This is a default implementation that should work most of the time
/// </summary>
public virtual IEnumerable<IEnumerable<string>> ControlsOrdered
{
get
{
var list = FloatControls.Union(BoolButtons);
yield return list
.Where(x => !x.StartsWith("P1 ") && !x.StartsWith("P2 ") && !x.StartsWith("P3 ") && !x.StartsWith("P4 "));
yield return list
.Where(x => x.StartsWith("P1 "));
yield return list
.Where(x => x.StartsWith("P2 "));
yield return list
.Where(x => x.StartsWith("P3 "));
yield return list
.Where(x => x.StartsWith("P4 "));
}
}
// TODO: a more respectable logic here, and possibly per core implementation
public virtual int PlayerCount
{
get
{
var list = FloatControls.Union(BoolButtons);
if (list.Any(b => b.StartsWith("P8"))) { return 8; }
if (list.Any(b => b.StartsWith("P7"))) { return 7; }
if (list.Any(b => b.StartsWith("P6"))) { return 6; }
if (list.Any(b => b.StartsWith("P5"))) { return 5; }
if (list.Any(b => b.StartsWith("P4"))) { return 4; }
if (list.Any(b => b.StartsWith("P3"))) { return 3; }
if (list.Any(b => b.StartsWith("P2"))) { return 2; }
if (list.Any(b => b.StartsWith("P1"))) { return 1; }
if (list.Any(b => b.StartsWith("Up"))) { return 1; } // Hack for things like gameboy/ti-83 as opposed to genesis with no controllers plugged in
return 0;
}
}
public virtual bool Any()
{
return BoolButtons.Any() || FloatControls.Any();
}
}
public interface IController
{
ControllerDefinition Type { get; }