/// <summary> /// Calculates the next position after a layer rotation /// </summary> /// <param name="layer">Rotation layer</param> /// <param name="direction">Rotation direction</param> public void NextFlag(CubeFlag layer, bool direction) { CubeFlag newFlags = CubeFlagService.NextFlags(Flags, layer, direction); this.X = CubeFlagService.FirstXFlag(newFlags); this.Y = CubeFlagService.FirstYFlag(newFlags); this.Z = CubeFlagService.FirstZFlag(newFlags); }
/// <summary> /// Transforms the layer move /// </summary> /// <param name="rotationLayer">Transformation layer</param> /// <returns>Transformed layer move</returns> public IMove Transform(CubeFlag rotationLayer) { bool switchDir = CubeFlagService.IsYFlag(rotationLayer) && this.Layer.HasFlag(CubeFlag.MiddleSlice) || CubeFlagService.IsXFlag(rotationLayer) && this.Layer.HasFlag(CubeFlag.MiddleLayer) || CubeFlagService.IsZFlag(rotationLayer) && this.Layer.HasFlag(CubeFlag.MiddleSliceSides); LayerMove newMove = new LayerMove(CubeFlagService.NextCubeFlag(this.Layer, rotationLayer, true), this.Direction ^ switchDir, this.Twice); return(newMove); }
/// <summary> /// Returns the next flags of the old flags after a layer rotation /// </summary> /// <param name="rotationLayer">Rotation layer</param> /// <param name="direction">Rotation direction</param> /// <returns>Next cube flags</returns> public static CubeFlag NextFlags(CubeFlag flags, CubeFlag rotationLayer, bool direction = true) { CubeFlag newFlags = CubeFlag.None; IEnumerable <Enum> lstFlags = GetFlags(flags); foreach (CubeFlag flag in lstFlags) { newFlags |= CubeFlagService.NextCubeFlag(flag, rotationLayer, direction); } return(newFlags); }
// *** METHODS *** /// <summary> /// Parses a notation string into a LayerMove /// </summary> /// <param name="notation">Defines to string to be parsed</param> /// <returns></returns> public static LayerMove Parse(string notation) { string layer = notation[0].ToString(); CubeFlag rotationLayer = CubeFlagService.Parse(layer); char[] ccwChars = new char[] { '\'', 'i' }; bool direction = !ccwChars.Any(c => notation.Contains(c)); bool twice = notation.Contains("2"); return(new LayerMove(rotationLayer, direction, twice)); }
// *** CONSTRUCTORS *** /// <summary> /// Constructor /// </summary> /// <param name="layer">Defines the layer to be moved</param> /// <param name="direction">Defines the direction (true == clockwise and false == counter-clockwise)</param> /// <param name="twice">Defines whether this layer will be turned twice or not</param> /// <exception cref="System.Exception">Thrown when layer contains more than one flag</exception> public LayerMove(CubeFlag layer, bool direction = true, bool twice = false) { if (CubeFlagService.CountFlags(layer) == 1) { this.Layer = layer; this.Direction = direction; this.Twice = twice; } else { throw new Exception("Impossible movement"); } }
/// <summary> /// Adds an item at the end of the collection /// </summary> /// <param name="item">Defines the item which is meant to be added</param> /// <exception cref="System.Exception">Thrown if this movement would be impossible</exception> public void Add(LayerMove item) { CubeFlag flag = item.Layer; foreach (LayerMove m in _moves) { flag |= m.Layer; } if (CubeFlagService.IsPossibleMove(flag)) { _moves.Add(item); } else { throw new Exception("Impossible movement"); } }
/// <summary> /// Parses a notation string into a layer move /// </summary> /// <param name="notation">String to be parsed</param> /// <param name="move">The resulting layer move</param> /// <returns>True, if the string was successfully parsed into a layermove</returns> public static bool TryParse(string notation, out LayerMove move) { move = null; string layer = notation[0].ToString(); CubeFlag rotationLayer = CubeFlagService.Parse(layer); char[] ccwChars = new char[] { '\'', 'i' }; bool direction = !ccwChars.Any(c => notation.Contains(c)); bool twice = notation.Contains("2"); if (CubeFlagService.CountFlags(rotationLayer) == 1) { move = new LayerMove(rotationLayer, direction, twice); return(true); } else { return(false); } }
/// <summary> /// Constructor with one CubeFlag /// </summary> /// <param name="flags">Defines the CubeFlag where the X-, Y- and ZFlag are filtered out</param> public CubePosition(CubeFlag flags) : this(CubeFlagService.FirstXFlag(flags), CubeFlagService.FirstYFlag(flags), CubeFlagService.FirstZFlag(flags)) { }
/// <summary> /// Returns the single flags in this CubeFlag /// </summary> /// <returns></returns> public IEnumerable <Enum> GetFlags() { return(CubeFlagService.GetFlags(Flags)); }
/// <summary> /// Returns the next flag after a layer rotation /// </summary> /// <param name="rotationLayer">Rotation layer</param> /// <param name="direction">Rotation direction</param> /// <returns>Next cube flag</returns> public static CubeFlag NextCubeFlag(CubeFlag flag, CubeFlag rotationLayer, bool direction = true) { CubeFlag nextFlag = CubeFlag.None; if (CountFlags(flag) == 1) { if (CubeFlagService.IsXFlag(rotationLayer)) { if (rotationLayer == CubeFlag.LeftSlice) { direction = !direction; } if (!direction && !IsXFlag(flag)) { flag = CubeFlagService.GetOppositeFlag(flag); } switch (flag) { case CubeFlag.FrontSlice: nextFlag = CubeFlag.TopLayer; break; case CubeFlag.MiddleSlice: nextFlag = CubeFlag.MiddleLayer; break; case CubeFlag.BackSlice: nextFlag = CubeFlag.BottomLayer; break; case CubeFlag.TopLayer: nextFlag = CubeFlag.BackSlice; break; case CubeFlag.MiddleLayer: nextFlag = CubeFlag.MiddleSlice; break; case CubeFlag.BottomLayer: nextFlag = CubeFlag.FrontSlice; break; default: nextFlag = flag; break; } } else if (CubeFlagService.IsYFlag(rotationLayer)) { if (rotationLayer == CubeFlag.BottomLayer) { direction = !direction; } if (!direction && !IsYFlag(flag)) { flag = CubeFlagService.GetOppositeFlag(flag); } switch (flag) { case CubeFlag.FrontSlice: nextFlag = CubeFlag.LeftSlice; break; case CubeFlag.MiddleSlice: nextFlag = CubeFlag.MiddleSliceSides; break; case CubeFlag.BackSlice: nextFlag = CubeFlag.RightSlice; break; case CubeFlag.LeftSlice: nextFlag = CubeFlag.BackSlice; break; case CubeFlag.MiddleSliceSides: nextFlag = CubeFlag.MiddleSlice; break; case CubeFlag.RightSlice: nextFlag = CubeFlag.FrontSlice; break; default: nextFlag = flag; break; } } else if (CubeFlagService.IsZFlag(rotationLayer)) { if (rotationLayer == CubeFlag.BackSlice) { direction = !direction; } if (!direction && !IsZFlag(flag)) { flag = CubeFlagService.GetOppositeFlag(flag); } switch (flag) { case CubeFlag.TopLayer: nextFlag = CubeFlag.RightSlice; break; case CubeFlag.MiddleLayer: nextFlag = CubeFlag.MiddleSliceSides; break; case CubeFlag.BottomLayer: nextFlag = CubeFlag.LeftSlice; break; case CubeFlag.LeftSlice: nextFlag = CubeFlag.TopLayer; break; case CubeFlag.MiddleSliceSides: nextFlag = CubeFlag.MiddleLayer; break; case CubeFlag.RightSlice: nextFlag = CubeFlag.BottomLayer; break; default: nextFlag = flag; break; } } } return(CubeFlagService.ExceptFlag(nextFlag, CubeFlag.None)); }