兵棋---棋盘绘制算法(六边形阵列算法)
最近玩一些手机游戏、ipad游戏、或者pc战棋游戏,感觉在很多游戏中融入了正六边形,作为地图模块中的最小单元,打破了常规的方块模式,不仅提升了趣味性,也刺激了我们开发者的味觉。其实,我早先就想过做一种新棋,有着自己特殊的规则和棋盘模式,最好能像机器人大战战棋游戏一样(我还是太爱机器人大战了,打小就开始玩),想法就是建立在正六边形或者三角形为最小单元的棋盘上(跳棋最小单元是三角模式、象棋最小单元是方块模式),今天这个算法,或许能在我以后闲的没事的时候,为做一些自己喜欢的东西开个引子。
代码是下午闲的无聊的时候,乱敲的,比较简单,可能不是那么规范,观者自查,见谅。
计算的方式:根据中心点,计算出下三边的位置然后绘制下三边,每一个六边形只绘制了下三边啊,六边绘制纯属浪费性能。
本算法极其简单,只绘制正六边形的阵列,不做寻路算法,那个谁喜欢做就去试试吧,应该也不是很难。可以用BFS算法,个人觉得,有步数限制的使用这种算法比较好。
1 using System; 2 using System.Drawing.Drawing2D; 3 using System.Drawing; 4 using System.Windows.Forms; 5 using System.Collections.Generic; 6 7 namespace SixSidesMap 8 { 9 public class SixSidesControl : Control 10 { 11 double G3 = Math.Sin(60 * Math.PI / 180);//二分之根号三 12 private int m_sideLength = 20; 13 14 public int SideLength 15 { 16 get { return m_sideLength; } 17 set 18 { 19 m_sideLength = value; 20 Invalidate(); 21 } 22 } 23 24 25 private float m_lineThickness = 1; 26 27 public float LineThickness 28 { 29 get { return m_lineThickness; } 30 set 31 { 32 m_lineThickness = value; 33 Invalidate(); 34 } 35 } 36 37 38 private Color m_lineColor = Color.Black; 39 40 public Color LineColor 41 { 42 get { return m_lineColor; } 43 set 44 { 45 m_lineColor = value; 46 Invalidate(); 47 } 48 } 49 50 public SixSidesControl() 51 { 52 SetStyle(ControlStyles.UserPaint, true); 53 SetStyle(ControlStyles.AllPaintingInWmPaint, true); 54 SetStyle(ControlStyles.DoubleBuffer, true); 55 } 56 57 protected override void OnPaint(PaintEventArgs pe) 58 { 59 //横线,三被的边长 60 //纵线,根号三倍的边长 61 List<float> xList = new List<float>(); 62 List<float> yList = new List<float>(); 63 64 int maxx = this.Width / (3 * m_sideLength); 65 int maxy = (int)(this.Height / (G3 * m_sideLength)); 66 67 for (int y = 0; y <= maxy; y++) 68 { 69 float curHeight =(float)( y * G3 * m_sideLength); 70 for (int x = 0; x <= maxx; x++) 71 { 72 float curWidth; 73 if (y % 2 == 0) 74 curWidth = (float)(x * 3 * m_sideLength); 75 else 76 curWidth = (float)((x * 3 + 1.5) * m_sideLength); 77 78 yList.Add(curHeight); 79 xList.Add(curWidth); 80 } 81 } 82 83 OnPaint(pe, xList.ToArray(), yList.ToArray()); 84 85 base.OnPaint(pe); 86 } 87 88 private void OnPaint(PaintEventArgs pe, float[] x, float[] y) 89 { 90 pe.Graphics.SmoothingMode = SmoothingMode.HighQuality; 91 using (Pen pen = new Pen(new SolidBrush(m_lineColor), m_lineThickness)) 92 { 93 pen.StartCap = LineCap.Round; 94 pen.EndCap = LineCap.Round; 95 96 for (int i = 0; i < x.Length; i++) 97 { 98 //9点方向的点 99 float px1 = (float)(x[i] - m_sideLength); 100 float py1 = (float)(y[i]); 101 102 ////11点方向的点 103 //float px2 = (float)(x[i] - 0.5 * m_sideLength); 104 //float py2 = (float)(y[i] - G3 * m_sideLength); 105 106 ////1点方向的点 107 //float px3 = (float)(x[i] + 0.5 * m_sideLength); 108 //float py3 = (float)(y[i] - G3 * m_sideLength); 109 110 //3点方向的点 111 float px4 = (float)(x[i] + m_sideLength); 112 float py4 = (float)(y[i]); 113 114 //5点方向的点 115 float px5 = (float)(x[i] + 0.5 * m_sideLength); 116 float py5 = (float)(y[i] + G3 * m_sideLength); 117 118 //7点方向的点 119 float px6 = (float)(x[i] - 0.5 * m_sideLength); 120 float py6 = (float)(y[i] + G3 * m_sideLength); 121 122 //pe.Graphics.DrawLine(pen, px1, py1, px2, py2); 123 //pe.Graphics.DrawLine(pen, px2, py2, px3, py3); 124 //pe.Graphics.DrawLine(pen, px3, py3, px4, py4); 125 //pe.Graphics.DrawLine(pen, px4, py4, px5, py5); 126 //pe.Graphics.DrawLine(pen, px5, py5, px6, py6); 127 //pe.Graphics.DrawLine(pen, px6, py6, px1, py1); 128 129 pe.Graphics.DrawLines(pen, new PointF[] 130 { 131 new PointF(px4, py4), 132 new PointF(px5, py5), 133 new PointF(px6, py6), 134 new PointF(px1, py1) 135 }); 136 } 137 } 138 } 139 } 140 }
这只是一个Control,请在C#下自建一个窗体,然后将此控件拖入即可使用。