単なる長方形ではなく、複雑な形をした領域の塗りつぶしを考えます。指定された点とつながっていて指定された点と同じ色のパネルを別の色に塗り替えます。
考えた方としては
指定された点を出発点に「周囲に出発点と同じ色のパネルがあれば色を変える」処理を繰り返せばよい
ということになります。
ではさっそくやってみましょう。
まず[塗りつぶす]というラジオボタンを追加しました。
1 2 3 4 5 6 7 8 9 |
public enum CheckedRadioButton { Free = 0, Rectangle = 1, Line =2, Ellipse = 3, Selection = 4, FillsColor = 5, } |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
public class PanelEx : Panel { private void PanelEx_MouseDown(object sender, MouseEventArgs e) { Form1 f = (Form1)FindForm(); // 途中は省略 if(f.GetCheckedRadioButton() == Form1.CheckedRadioButton.FillsColor) { f.FillsColor(new XY(Column, Row)); } } } |
ラジオボタン[塗りつぶす]が選択されているときにパネルがクリックされたらFillsColorメソッドを呼び出します。FillsColorメソッドのなかでUndoできるようにSaveOldBitmapメソッドとInsertUndobufメソッドも呼んでおきます。
FillsColorメソッドのなかでFillColorメソッドを呼んでいます。FillColorメソッドのなかで上下左右のパネルの色を調べて必要であれば再帰呼び出しをしています。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 |
public partial class Form1 : Form { public void FillsColor(XY xy) { SaveOldBitmap(); Color oldColor = panels[xy.X, xy.Y].BackColor; FillColor(xy.X, xy.Y, oldColor, CurColor); InsertUndobuf(); } void FillColor(int x, int y, Color oldColor, Color newColor) { panels[x, y].BackColor = newColor; if(0 <= x && x < 32 && 0 <= y - 1 && y - 1 < 32 && panels[x, y-1].BackColor == oldColor) FillColor(x, y - 1, oldColor, newColor); if(0 <= x+1 && x + 1 < 32 && 0 <= y && y < 32 && panels[x + 1, y].BackColor == oldColor) FillColor(x + 1, y, oldColor, newColor); if(0 <= x && x < 32 && 0 <= y + 1 && y + 1 < 32 && panels[x, y + 1].BackColor == oldColor) FillColor(x, y + 1, oldColor, newColor); if(0 <= x-1 && x-1 < 32 && 0 <= y && y < 32 && panels[x - 1, y].BackColor == oldColor) FillColor(x - 1, y, oldColor, newColor); } } |