描画タブレットと対話するペイント プログラムの作成を開始しました。タブレット上のペンの圧力に応じて、描画される線のアルファ値を変更します。その仕組みが働いています。
細い線はまともに見え、本物のスケッチに見えます。しかし、ペイントするために (Qt の落書きチュートリアルのように) 2 つの点の間に線を描いているので、線の継ぎ目の間にアルファ オーバーラップがあり、太いストロークでは非常に目立ちます。
これは、行から行への結合による効果です。
ご覧のとおり、線分の間に醜いアルファ ブレンドがあります。
これを解決するために、 a を使用QPainterPath
して線をレンダリングすることにしました。これには2つの問題があります:
- 長く連続した太いパスは、プログラムをすぐに遅らせます。
- パスは接続されているため、パスは 1 つとして機能するため、アルファ値を変更するとパス全体に影響します (ブレンド効果を維持したいので、これは望ましくありません)。
次の画像ではQPainterPath
.
残しておきたいブレンド効果。
次の画像は、パス全体のアルファと太さを変更する 2 番目の問題を示しています。
赤いテキストは次のようになります。「ペンをタブレットの表面から離さずに圧力を加えると、線が太くなります」(アルファが不透明になります)
もう 1 つのことは、このアプローチでは、暗い部分から明るい部分 (または太い部分から細い部分) へのブレンド トレイルしか得られず、明るい部分から暗い部分へのブレンド トレイルは得られないことです。この効果が発生する理由はわかりませんが、パスの線分が全体として更新されることに関係しているのではないかと推測されます。
タブレット上のペンの圧力に基づいて、プログラムでアルファと線の太さを増減させました。
問題は、アルファ オーバーラップなしで線をレンダリングし、望ましくないQPainterPath
パス全体のアルファと太さを更新することです。
パスを作成するコードは次のとおりです。
switch(event->type()){
case QEvent::TabletPress:
if(!onTablet){
onTablet = true;
//empty for new segment
freePainterPath();
path = new QPainterPath(event->pos());
} break;
case QEvent::TabletRelease:
if(onTablet)
onTablet = false;
break;
case QEvent::TabletMove:
if(path != NULL)
path->lineTo(event->pos());
if(onTablet){
//checks for pressure of pen on tablet to change alpha/line thickness
brushEffect(event);
QPainter painter(&pixmap);
//renders the path
paintPixmap(painter, event);
} break;
default:;
}
update();
単一のパスとして必要な効果 (Krita ペイント プログラムで作成された画像):