円形の進行状況バーを手続き的にレンダリングするにはどうすればよいですか?


7

私はFlash AS3で作業していますが、疑似コードやその他の言語で問題ありません。

円形のプログレスバーを作成するにはどうすればよいですか?Pax Britanicaの船のバーのようなものは、こちらのスクリーンショット見ることができます

フレームごとに作成する以外に、ここで見逃している明らかな解決策はありますか?

通常のプログレスバーの四角形を引き伸ばす、または単純なマスクを使用するのと同じことを求めています(そのようなソリューションが存在する場合)。

(また、誰かが素晴らしいと思ったら担当者がいないため、これにサークルやプログレスバーのタグを付けることはできません)

回答:


19

最初に原理を説明し、次に描画部分を説明します。

私の例では、他に何でもできるとしても、0から100(%)の進行値があると想定しています。

直線上では、プログレスバーの現在の位置は単にそのプログレス値になります。

円上では、三角法でその位置を取得します。円の任意の点は次のように与えられます:

point.x = r * cos(angle);
point.y = r * sin(angle); 

ここで、rは円の半径です。ご覧のとおり、これらの方程式では角度のみが変数です。それはあなたがどういうわけかあなたの進歩を角度に統合しなければならないことを意味します。

解決策は簡単です。円を1回実行すると、2 * Pi(または360度)になります。その距離を100個の小さな部分に分割する必要があります。これにより、進行状況の値が100の場合、cos()およびsin()内の値は2 * pi(または360度)になります。

これは、2 * pi(または360度)を100で除算し、進行状況を乗算するだけで実現できます。

float step = 2*pi/100;

point.x = r * cos(progress * step);
point.y = r * sin(progress * step);

次に、描画部分に進みます。

Actionscript3(またはFlash)については何も知りません。そのため、正確な手順をお伝えすることはできませんが、一般的には次の2つの方法があります。

まず、(私の意見では2つのうちで簡単です):部分的な円を、特定の太さの色付きの線の接続として手動で描画します(テクスチャが必要なく、単純な色で十分な場合)、またはテクスチャーされた四角形の接続としての円(テクスチャリングが必要な場合)。

次に、完全に読み込まれた円を表す画像を描き、それをテクスチャとして読み込んで、四角形に配置してレンダリングします。次に、その四角形の上に手動で部分的な円をもう一度描き、テクスチャ付きの四角形のうち、その前にレンダリングされる部分だけをレンダリングします。たとえば、OpenGLでは、ステンシルバッファーを使用してこれを簡単に行うことができます。

サークル上のさまざまなポイントを計算して、それらを使用して必要なポリゴン/ラインを組み立てる方法を知りたい場合は、上記の方程式をもう一度見てみましょう。

point.x = r * cos(angle);
point.y = r * sin(angle); 

たとえば、0から現在の進行状況まで実行されるforループ内でこれらを実行できます。たとえば、それが一連​​の接続されたドットで構成される円の場合(c ++構文):

float granularity = 2*PI/required_granularity; //determines how smooth your circle will look
float step = 2*PI/100.0f;

list<Vector2> points; //list of all the calculated points
for(float angle=0; angle < progress*step; angle += granularity)
{
    Vector2 point(radius*cos(angle), radius*sin(angle));
    points.push_back(point); //adds the point to the list
}

これらの点はすべて座標系の原点を中心とするため、円を配置する位置に移動する必要があります。しかし、私はあなたがそれを自分で理解できると思います:P


4

弧を描きたいようです。太い弧。AS3でそれを行うためのこの記事を見つけました。下部にあるデモをご覧ください。


1
これはおそらく私が使用する方法です(それがAS3固有だからです)が、私はほとんどの人が検索するのを助けるためにすべての言語で機能する答えを受け入れました。ありがとうございました!
エイドリアンシーリー

1

私は以下を試していませんが、うまくいくようです。

次の2つの画像が必要です。

  1. 外側のHUDグラフィック、進行状況を表示する部分を透明にします
  2. ソリッドカラーの円のイメージ、進行状況メーターの半径、次に下半分を切り取り、透明にします(HUDの部分が残りの部分を覆うため、実際には半分の正方形になります)。

以下では、0%(および100%)のマークが9時の位置にあると想定しています。


進捗状況が50%以下の場合:

  • 半円を回転させて描画し、上部に目的のパーセントが表示されるようにします
  • 下半分の領域を長方形にカットして、下の領域に表示されている半円の左の始点を削除します
  • 最上層のHUDグラフィックを描画する

進捗状況が50%を超える場合:

  • 上半分全体(50%マーク)を埋めるように半円を描きます。回転は必要ありません
  • 残りのパーセンテージを反映するように、半円をもう一度回転させて描画します
  • たとえば、60%が必要な場合は、最初のコピーを描画して50%を表示し、次に2番目のコピーを回転して描画してさらに10%を表示します
  • 最上層のHUDグラフィックを描画する

AS3でこれを具体的に(またはそれが可能かどうか)行う方法がわかりません。これが理にかなっているといいのですが(ああ、実際に動作します!)。


0

私が見た別の方法は、シェーダーを使用することでした。

必要なのはHUD画像全体である1つの画像だけで、グラデーショングレースケールの進行領域があります。真っ白で0%位置(たとえば9時)から始め、100%位置で徐々に黒に進みます。

HUD部分にグレーを含めることはできません。白や黒は含まれません。これらの色を使用する必要がある場合は、グラデーションスケールに別の純色(他の場所では使用されていない色)を選択します。

'0.0'から '1.0'の範囲のプログレス値(または、シェーダー言語がその色の範囲に使用するスケール)をプログラムにシェーダーに渡させます。また、プレーヤーに警告するために空(またはフル)に色を動的に変更する場合は、シェーダーに進行状況バーの色(および必要に応じて「オフ」の色)を渡すこともできます。

シェーダーで各ソースピクセルを評価し、それが純粋なグレー(各R、G、Bの値が同じ)の場合、そのピクセルは進行状況メーターの一部です。元の色をそのまま通過しない場合。進行状況メーターのピクセルの場合は、「オン」カラーにするか「オフ」カラーにするかを決定する必要があります。単純にピクセルの色(純粋な灰色なので、「赤い」コンポーネントと言うだけでよい)をチェックして、渡された進行状況の値の上か下かを確認します。効果は、進行状況値の下の灰色がすべてオンになり、他の色はオフになることです。


3
OMG、円形断面のシェーダー...
Kromster 2011
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.