1

現在、単純なペイント ツールを作成しようとしていますが、問題が発生したか、さらに提案が必要な場合があります。

ブラシを作成しようとしているので、特定のピクセル「中心」をペイントすると、近くのピクセルもペイントされます。

例えば:

1 pixel (center point)
[ ][ ][ ][ ][ ]
[ ][ ][ ][ ][ ]
[ ][ ][*][ ][ ]
[ ][ ][ ][ ][ ]
[ ][ ][ ][ ][ ]

2 pixel:
[ ][ ][ ][ ][ ]
[ ][ ][*][ ][ ]
[ ][*][*][*][ ]
[ ][ ][*][ ][ ]
[ ][ ][ ][ ][ ]

3 pixels:
[ ][ ][*][ ][ ]
[ ][*][*][*][ ]
[*][*][*][*][*]
[ ][*][*][*][ ]
[ ][ ][*][ ][ ]

また、中心点のみが色の 100% である必要があります。後で元の色を取り、少しフェードアウトするにはどうすればよいですか。

例:

1 ピクセル、100% カラー

2 ピクセル、中心点は色の 100%、近くのピクセルはわずかに色あせているか (50%)

10 ピクセル、中心点は色の 100%、中心点から最も離れたピクセルは、元の色が最も薄くなるはずです。

そのため、近くの色を計算するアルゴリズムと、ブラシ パターンを作成するアルゴリズムです。

助言がありますか?

Color Intensity メソッドの実装 (機能しません) Update 1: Math.Pow(x, y) に変更 - 遅く、機能しません

    public static Color GetColorIntensity(Color c, double r, Point position, Point centerPosition)
    {
        double distance = Math.Sqrt((Math.Pow(position.X, 2)) + (Math.Pow(position.Y, 2)));
        double relative_distance = distance / r;
        double alpha = (1.0 - relative_distance);

        return Color.FromArgb((int)alpha, c.R, c.G, c.B);
    }
4

2 に答える 2

4
  1. ブラシの中心から各ピクセルの距離を計算します。
  2. 1.0(ブラシの中心) から0.0(ブラシの端) への透明度スケーリングを割り当てます。

ユークリッド距離 を使用するd = sqrt(x^2 + y^2)と、円形のブラシが得られます。

タクシーの距離 を使用するd = abs(x) + abs(y)と、ダイヤモンド形のブラシが得られます。

ブラシx,y半径r. a = 1.0は「完全に不透明」をa = 0.0意味し、「完全に透明」を意味します。

def intensity(x,y,r):
    distance = sqrt( x**2 + y **2 )
    relative_distance = distance / r
    alpha = (1.0 - relative_distance)
    return alpha

そこにはおそらく off-by-one エラーがあります (ブラシは よりも 1 ピクセル小さくなりrます) が、自分で修正できます。

于 2012-05-10T12:03:57.167 に答える
1

編集 #2 パズルを解く必要があるため、他の人が答えた答えを参考にして、数学の間違いを修正し、あなたが探しているものとまったく同じだと思うものを思いつきました。

これを試してください私は新しいWindowsフォームアプリケーションを作成しました.numericupdown(ブラシのサイズ)、トラックバー(フェード強度)、およびボタンを追加しました。ボタンをクリックすると、パネルの塗りつぶしが開始されます。ブラシ番号は単色になり、フェード強度に応じて外側の各行がますますフェードします。

 public Form1()
    {
        InitializeComponent();
    }
    Panel[,] pb = new Panel[9, 9];
    private void Form1_Load(object sender, EventArgs e)
    {
       //this is just to add the panels to the screen.  
       //We are using panels to simulate zoomed in pixels so we can see what is going on
        for (int y = 0; y < 9; y++)
            for (int x = 0; x < 9; x++)
            {
                pb[x, y] = new Panel();
                pb[x, y].BackColor = Color.MistyRose;
                pb[x, y].BorderStyle = BorderStyle.FixedSingle;
                pb[x, y].Size = new Size(20, 20);
                pb[x, y].Location = new Point(x * 20, y * 20);
                this.Controls.Add(pb[x,y]);
            }
    }
    private void button1_Click(object sender, EventArgs e)
    {
        DrawPixel(new Point(4, 4), (int)numericUpDown1.Value,trackBar1.Value+1);
    }

    public void DrawPixel(Point pixel, int radius,int intensity)
    {
        radius--;
        for (int y = 0; y <= 8; y++)
            for (int x = 0; x <= 8; x++)
            {
                //clears the screen before starting
                pb[x, y].BackColor = Color.White;
                //calculate the distance from the center pixel
                double Distance = Math.Sqrt( ((x-pixel.X)*(x-pixel.X) + (y-pixel.Y) *(y-pixel.Y))-radius*radius );
                //determine color intensity
                int alpha = (int)Distance <= 0 ? 255 : (int)Distance > intensity ? 0 : (int)(intensity - Distance) * 50 > 255 ? 255 : (int)(intensity - Distance) * 50;

                if (alpha>0)
                    pb[x, y].BackColor = Color.FromArgb(alpha, Color.Red);
            }
    }
于 2012-05-29T18:43:01.277 に答える