ゲームのメタデータを.pngファイルに保存するにはどうすればよいですか?


208

Sporeでは、.pngファイルをエクスポートすることで、プレイヤーが作成したクリーチャーを共有できます。これ.pngはクリーチャーの写真ですが、ゲームにインポートされた場合、クリーチャーの情報(テクスチャ、サイズ、形状など)も一緒に表示されます。

このような機能を実装するにはどうすればよいですか?


5
はるかに高いスコアを持っている必要があり、それは非常に興味深い質問です。
ピエールアラード14

3
アルファチャンネルは、部分的にこの...のために悪用される可能性
トビアスKienzler


1
このデータを別のファイルに保存する方が良いと思います。このファイルには、データを保存したいエンティティに関連するテクスチャファイルの名前が必要です。まず明示的に(png形式はグラフィックス用-「Portable Network Graphics」)、2番目:エンティティにさらに画像を保存したい状況を考えます。そのカスタムファイルから参照を追加できます。おそらく、1つのPNGに異なる画像(異なるサイズ、異なる深度など)を保存するのに問題があるでしょう。
luke1985

3
アルファチャンネルは頻繁に言及されており、PNGはとにかくメタデータをサポートしますが、左から右、上から下、固定の順序でチャンネルをステップスルーする、私が使用したテクニックを共有すると思いました、および値をオッズまたは偶数に丸めます - 値が増減するかどうかは関係ありません。どのチャネルでも1を変更しても目立った違いはなく、256x256の画像(もちろんピクセルあたり4ビット)では、印象的な32KBのデータを保存できます。さらに必要な場合は、代わりに%4に丸めることができます-多すぎると、古いGIFのように見え始めます。
Octopoid

回答:


56

本当に必要なのがPNGファイルだけだった場合、単にファイルに情報を追加しただけである可能性があります。これは実際にはステガノグラフィの実践です。多くの場合、これは一見公開されているように見えるものにペイロードまたは秘密のメッセージを隠すために使用されます。ただし、この場合、この方法が使用された可能性があります。典型的なStegongraphyは内容を隠すために邪魔になりませんが、ファイルの最後にある画像からデータを単に追加して取得できない理由はありません。

いくつかのツールがこのデータをエンコードします。Google検索では、少なくともthisthisが表示されます。

PNG $89の先頭にはバイト署名があるため、PNG構造自体の後に情報が挿入され、SPOREゲームによって単純に解析された可能性があります。

しかし、他の回答とグーグルでの検索によって行われたさらなる研究は、Sporeが実際にアルファビットの情報を隠すためにステゴノグラフィーの単なるバージョンを使用していることを明らかにしています。これを念頭に置いて、追加データまたはメタデータの可能性を排除できます。

データがローカルで解析されている場合、メタデータは依然として非常に実行可能な選択肢であることに注意してください。その情報がWeb上で共有されたり、再エンコードされたりする可能性がある場合、エクスポートはすべての情報を保持するとは限りません。ピクセルデータを使用すると、ロスレス変換を問題なく実行できます。


3
私の知る限り、胞子はメタデータをPNGのアルファチャネル内に保存していました。
タラ14

28
PNGが任意のメタデータチャンクをサポートするのに、なぜアルファチャネルまたはステガノグラフィを使用するのですか?
ラッセルボロゴーブ14

8
「PNGの先頭にはバイト署名「89」があるため、PNG構造自体の前または後に情報が挿入され、SPOREゲームによって単純に解析された可能性が非常に高いです。」 tはもうPNGファイルである必要はありません。つまり、一般的な画像ビューアでは表示できません。
svick 14

3
@RussellBorogoveかなり適切な理由:PNGがSpore以外の何かによってデコード/エンコードされた場合、任意のメタデータチャンクは実際の画像データよりも無視または失われる可能性が高くなります。イメージ内のデータをエンコードすると、表示できる場合はロードできる可能性が高くなります。
ティムS.

@svick実際、私は有効なPNGとRARの両方であるファイルで遊んでいます。RARヘッダーはPNGの後に開始され、RARエクストラクターは正常でした。他の方法でも問題なく動作します。
皮質14

153

PNG形式は、多かれ少なかれ任意のメタデータをサポートしています。PNG標準は、 PNGファイル、必要な(画像データを含む)されているいくつかの塊、本質的に一連の定義します。ただし、その他はオプションです。たとえば、ガンマ情報やヒストグラムデータを保存するためのチャンクがあります。

特に、任意のキー/値テキストのペアを保存するために使用できるtEXtチャンクがあります。このデータを使用して、任意の種類の任意のデータを配布できます。ただし、そのデータをテキストとして表現できる場合は(かなり可能性が高い)

これらの追加チャンク(参照ライブラリなど)にアクセスして操作できるPNGライブラリが必要になります。または、自分で作成する必要があります。次に、必要なデータをキー/値のペアとしてエンコードする方法を選択するだけです。次のことをお勧めします。

  • 粗雑な「名前空間」システムを作成する方法として、プロジェクトの名前またはコード名を接頭辞とするキー名を選択し、他のアプリケーションのデータ使用との潜在的な競合を回避する
  • この方法で実際のテクスチャを保存しようとしないでください。ゲーム独自のアセットデータベース内を指すテクスチャへの参照を保存してください。
  • クリーチャーやオブジェクトのサイズ、重量などのデータ-単純なスカラー、基本的に-は簡単に保存できます

より完全な回答を作成するために、別のアプローチ(以前は@Vaughnおよび@Alexisの回答で文書化されていました)があることも指摘します。必要な追加データを画像ピクセルに直接エンコードし、カラーチャネルの下位ビット。このアプローチでは、追加のメタデータを使用する必要がありません。つまり、それに依存したり、外部プログラムがそのメタデータを誤って処理することを心配せずに完全に実装できます。また、非常に高い「クール」係数があり、低次ビットのみを使用するため、画像は人間の目には正しく表示されます。ただし、画像サイズが保存できるデータ量の主な制御要因であることを意味します。より多くのストレージが必要な場合は、より多くのピクセルを画像に割り当てる必要があります。

他の人が指摘したように、このプロセスはとして知られているステガノグラフィ


3
一つは、単純にBase64を介してデータを送信し、単一の値として格納することができ
CodesInChaos

11
@ da4c30ffメタデータと同様に実用的ですが、ステガノグラフィーには、スパイファンタジーのクールな要素があり、私たちの群衆が抵抗するのは困難です。自分でこれを行っていた場合、Josh Petrieが提案したスケーラビリティの方法を使用しますが、ステガノグラフィを使用して画像自体のチェックサムを非表示にして、画像とテキストが互いに属していることを確認したいのですこれは便利または安全ですが、それはクールだからです。;)
DMGregory

ここで「テキスト」とはどういう意味ですか?ASCIIのみ(文字<= 127)?0以外のバイト?すべてのバイトですか?または、他の何か?(。これは、あなたがBASE64を必要とするか否かのバイナリデータ例えば書き込みに使用する必要があるのエンコードに影響します。)
svick

1
テキストチャンクの標準へのリンクで回答を更新しました。ただし、基本的に、テキストはISO 8859-1(8ビット、シングルバイト、Latin-1文字)に従って解釈されます。
ジョシュ

51

モナコの開発者は、実際に彼らとSporeの両方がこれを達成した方法について優れた記事を作成しました

彼らがすることの基本的な要約はかなり簡単です:

  • データをバイナリに変換します
  • ターゲット画像を生のビットマップに変換します
  • 予測可能なパターンで画像のピクセルに沿って歩きます(それらは単に左上隅から左から右に行います)。
  • 各ピクセルの各カラーチャネルの最下位ビットに1ビットを書き込みます
  • 変更したビットマップを再度PNGにエクスポートします

データを取得するには、これを逆に行うだけです。

このプロセスの背後にある基本的な考え方は、画像には多くのピクセルがあり、各カラーチャンネルの最下位ビットは大きな違いをもたらさないということです。さらに、書き込むビットの約半分は、画像のビットがすでにあったものになります。返されるのは基本的に正しいイメージですが、奇妙なアーティファクトがあります。これらのアーティファクトは、コントラスト/彩度を実際に上げてズームインした場合にのみ顕著であることに注意するのに時間がかかります。

記事から:

最後の画像で、ノイズにほとんど識別できない水平線があることに注目してください。これでレベルデータの終わりです。つまり、最下位ビットのみを使用して、265x120ピクセルの画像にすべてのレベルデータを実際に適合させることができます。

トリッキーな補遺:

私ができること、そして胞子の人々も同じことをしたと思いますが、実際には100%透明なピクセルのすべてのカラービットを使用しています。これらのピクセルは透明なので、設定する色は関係ありません。

ただし、画像全体を使用しているため、これを行うことはできません。つまり、使用する透明ピクセルがありません。

なぜメタデータに保存するだけでなく、この手法を好むのですか?

  • おもしろい!:)
  • サービスはメタデータを破壊する可能性がありますが(プライバシー/セキュリティ機能として)、積極的な画像ホスティング要件(あなたを見て、facebook)がない限り、pngのピクセルを破壊すべきではありません。ただし、画像を完全に再エクスポートしている場合、確実にできることは何もありません。

追加クレジット:ノイズの目立ちやすさを減らすために、修正するピクセルを選択するために、固定シードを使用したPRNGを使用できます。同様の方法でカラーチャンネルの一部のみを変更することもできます。


6
モナコ方式よりも画像のスケーリング/色調整に対してより堅牢なステガノグラフィアルゴリズムがあります。(通常、かなり低い密度でデータを保存しますが)1つの例は、World of Warcraftのスクリーンショットで使用される透かしです。ownedcore.com
forums

@DMGregory素敵な発見!もちろん、選択する正確なアルゴリズムは、特定のユースケース(スペース、耐久性、機密性など)によって決定する必要があります。
アレクシスBeingessner 14

1
これは聞こえるかもしれませんが、それは悪い考えです。PNG画像は可逆画像圧縮を使用します。画像の低ビットをいじると、ファイルが大きくなり、同時に画像の品質が(わずかに)低下します。絶対にすべての情報を「テキスト」としてエンコードできるため、メタデータチャンクを使用するのが明らかに正しい方法です。実際にステガノグラフィを必要とせずに画像の一部をいじる人は、ただのウイリーを飛び出しているだけです。
dfeuer

1
@dfeuer-どうやらSporeとMonacoの両方が、.PNGを裸のビットマップにストリップするアセットロードパイプラインを備えたゲームフレームワークを使用していたため、メタデータチャンクは通過しませんでした。
ラッセルボロゴーブ14

1
@dfeuer素朴なテストをいくつか行いました。メタデータアプローチは、1920x1080pxの画像に100kBのランダムビットを書き込むときに、速記法によって追加されたサイズの約80%を追加するようです。空白の画像とデスクトップのスクリーンショットでテストしました。壊滅的な違いではありませんが、40kB以上を本当に心配している場合、meatadataは確かに優れています(より一貫性があります)。メタデータはまだ非常に非効率的でした。100kBのデータを書き込むことで181kBを得ました!文字列のエンコード方法などを最適化する余地があります。
アレクシスBeingessner 14

7

SporepediaからいくつかのSporeクリーチャーをダウンロードして調べました。私はそれから学んだ:

  • 画像には、標準画像データ以外の情報は含まれていません。
  • 速記データは画像を考慮せずに保存されており、透明部分が排他的に使用されていると想像できますが、そうではありません。
  • ストレージの使用は、保存する必要のある情報の量に依存します。一部の画像はデータストレージの最下位ビットのみを使用し、一部は最下位2ビットを使用し、一部はより多く使用する場合があります。
  • Spore形式は、画像の一部のみでビットを使用することを避け、最下位ビットは画像全体で変化します。2番目に最下位ビットが使用される場合、画像全体で使用されます。これはおそらくランダムなパディングを使用して行われます。これにより、ノイズ自体よりも視聴者の邪魔になる可能性のある品質の変化を回避できます。
  • 4つのチャネルはすべて等しく使用され、不透明度チャネルには特別な処理は行われません。したがって、透明ピクセルの一部はわずかに不透明ですが、不透明ピクセルの一部はわずかに透明です。

これはSporeが行うことであり、他のほとんどの懸念よりも単純さを優先する方法であることに注意する価値があります。

追加のデータブロックではなく速記法を使用するという選択は、スケーリングやJpeg圧縮には耐えられないものの、たとえばWebサイトによって画像が再エンコードされた場合でもデータが生き残ることを意味します。

最も顕著な代替案は、実際には画像内のIDのみをエンコードし、実際のデータを中央サーバーに保存し、このIDを正確なクリーチャーデータと交換できるようにすることだと思います。このようなIDは、スケーリングおよび圧縮に耐性のある速記形式でエンコードできるほど短くなります。

胞子フォーマットの可能な単純な改良点は次のとおりです。

  • 透明ピクセルのカラー値のみを使用するか、使用することを好みますが、視覚的な違いはありません。
  • 青のチャンネルをより多く使用し、緑のチャンネルをより少なく使用すると、青の色が画像に与える影響が少なくなります。
  • 各ピクセルの輝度を不変に近づけ、データをクロマでエンコードすると、このパラメーターのわずかなノイズは人間にはほとんど検出されません。
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.