3

実際、それを実現する簡単な方法があると思いました。必要なのは純粋なアルファ値情報です。テスト用に、50 x 55ピクセルのPNGがあり、すべてのエッジで5x5ピクセルの長方形が完全に透明になっています。これらの領域では、アルファは0である必要があります。それ以外の場合は255である必要があります。PNGが正しく作成され、正しく表示されることを確認しました。

これが理論的に正しいかどうか教えてください。アルファチャネルのみを含み、他には何もないCGImageRefを作成しました。これは、パラメータとしてCGBitmapContextCreateとkCGImageAlphaOnlyを使用して行われます。CGBitmapContextGetBitsPerPixel(context)は私に1を返すので、ピクセルごとに実際には1つのコンポーネント(目的のアルファ値)しかないことを示しています。CGBitmapContextCreateが、指定された画像から新しく作成されたコンテキストへのすべての変換を処理することを読んでいます。私の画像は以前は透明度のあるPNG-24でしたが、Xcodeのpngcrunchはどういうわけかそれらを変換しているようです。

したがって、理論的には、この時点で、事前に乗算されていない正しいアルファに到達する機会はありますか?私が得る値はほぼ一致しているように見えますが、大きな5x5の透明な正方形では、19、197、210、0、0、0、98などの値が得られます。もしそれらが本当なら、私は画像から何かを見なければならないでしょう。画像自体は青一色です。

4

3 に答える 3

8

Premultiplication は、アルファ チャネルには影響しません。カラー チャネルに影響します。

ラスター合成 (1 つのラスター イメージを別のラスター イメージの上に重ねる) の式は次のとおりです。

dst.r = src.r * src.a + dst.r * (1.0 - src.a);
dst.g = src.g * src.a + dst.g * (1.0 - src.a);
dst.b = src.b * src.a + dst.b * (1.0 - src.a);

前乗算は、最初の乗算式を切り取ります。

dst.r = src.r′ + dst.r * (1.0 - src.a);
dst.g = src.g′ + dst.g * (1.0 - src.a);
dst.b = src.b′ + dst.b * (1.0 - src.a);

これが機能するのは、ソース カラー コンポーネントが既にアルファ コンポーネントによって乗算されているためです。すでに結果が得られているので、今は乗算する必要はありません。

前乗算されていないアルファ

アルファ成分自体は決して乗算されません。何を乗算しますか? 成分は alpha で事前に乗算さます。

于 2009-05-16T01:19:48.020 に答える
6

色値の事前乗算は次のように簡単です。

r = (r * a) / 255;
g = (g * a) / 255;
b = (b * a) / 255;

逆を取得すると、次のようになります。

if (a > 0) {
    r = (r * 255) / a;
    g = (g * 255) / a;
    b = (b * 255) / a;
}
于 2009-05-16T01:26:55.007 に答える
1

この式は正しくありません。目標は、後で同じ多重化された値になる多重化されていない (r、g、b) を見つけることです (ただし、元の r、g、b の値を見つけることはできません。

ただし、上記のフォーミュラーを使用すると、次の例が見つかります

alpha = 100
r_premulti = 1

再構成された r = 2;

後で、この r が再び多重化されると、2 * 100 / 255 = 0 が見つかりますが、代わりに r_premulti == 1 が必要です!!

正しいフォーミュラーは切り上げる必要があります。r-コンポーネントの例:

reconstruced r = ceiling(r_premulti * 255 / alpha)
于 2013-03-26T16:43:50.017 に答える