2

ビデオ ゲーム バトルフィールド 2 の高さマップをアプリケーションで画像として表示しようとしています。
私は C++ と Qt が初めてで、簡単かもしれませんが、問題があるのはグレースケールの16-bit 1025x1025 2101250バイト画像を表示することです。ファイルにヘッダーはありません。表示されたピクセルにアクセスする必要があるため (ピクセル単位の精度である必要はありません)、ピクセルをポイントしてその値を取得できます。

私が試したこと

バイナリ データをQByteArrayQFile からロードし、QImage::fromData関数を使用して画像を作成しようとしましたが、多くの間違いを犯し、多くの時間を費やしています。ここに投稿することで、私が進歩するために必要な手がかりが得られることを願っています. これが私のコードです:

void LearningBinaryReader::setupReader()
{
    qDebug("Attempting to open file..");
    QFile file("HeightmapPrimary.raw");
    if (!file.open(QFile::ReadOnly))
    {
        qDebug("Could not open file");
        return;
    } else {
        qDebug() << file.fileName() << " opened";
    }
    QByteArray data = file.readAll();
    file.flush();
    file.close();

    qDebug() << data.count() << "bytes loaded.";
}

ここから、どうしようか迷ってしまいます。Qt のドキュメントをいくつか読んだことがありますが、この問題を理解して解決策を得るには、初心者なので正しい方向へのガイドが必要です。

はほとんど初心者なので、思いもよらなかった簡単な解決策を軽視しないでください。Qtフレームワークを使用してこれを行いたいと思います。

4

3 に答える 3

2

推測です。たぶん、このようなことを試してみませんか?

#include <QColor>
...
QByteArray data=file.readAll();

// create an empty image of the right size.  We'll use 32-bit RGB for simplicity
QImage img(1025,1025, QImage::Format_RGB32);

// Access the image at low level.  From the manual, a 32-bit RGB image is just a
// vector of QRgb (which is really just some integer typedef)
QRgb *pixels=reinterpret_cast<QRgb*>(img.bits());

// Now copy our image data in.  We'll assume 16-bit LE format for the input data.
// Since we only have 8 bits of grayscale color resolution in a 32-bit RGB, we'll
// just chop off the most significant 8 bits (the second byte of each pair) and 
// make a pixel out of that.  If this doesn't work, our assumption might be off --
// perhaps assume 16-bit BE format.  In that case we'd want the first byte of each
// pair.
for (size_t i=0;2*i<data.size();++i)
{
    uchar pixel_msb=data[2*i+1]; // or maybe try =data[2*i+0]
    pixels[i]=qRgb(pixel_msb, pixel_msb, pixel_msb);
}

// (do something with the resulting 'img')

編集:おっと、QImage::Format_RGB32代わりにQImage::Format_RGB

于 2012-06-28T06:53:48.287 に答える
1

loadFromDataは raw をサポートしていないため、使用できません(イメージ ファイルの読み取りと書き込みを参照)。

サポートされている形式で 16 ビット raw を見つけることができないため、最適な解決策は、画像の読み込みと画像の表示の間にコンバーターを使用することだと思います。

qt でサポートされている形式で、新しい QImage を作成します。

QImage* image = new QImage(1025, 1025, QImage::Format_RGB888);

次に、ソース イメージを読み込み、RGB888 に変換します。画像が非常に大きいため、readAll(). この単純なコンバーター (以下を参照) または既存のライブラリーからのコンバーター ( Magick++など) を使用できます。

QFile file("HeightmapPrimary.raw");
if (!file.open(QFile::ReadOnly))
{
    qDebug("Could not open file");
    return;
}
uint16_t buf;
uchar* dst = image->bits();
while (readData(&buf, 2)) {
  dst[0] = buf / 256; /* from 16bit to 8bit */
  dst[1] = buf / 256;
  dst[2] = buf / 256;
  dst += 3; /* next pixel */
}
于 2012-06-28T07:06:15.457 に答える
0

1.基本的に、ウィジェット内にピクセルを描画する必要があります。

したがって、最初にダイアログを持つアプリケーションを作成し、次の推奨事項を使用してダイアログを描画します。

Qt4ウィジェット内に描画する方法は?

QPainter のドキュメント: http://qt-project.org/doc/qt-4.8/QPainter.html

ピクセルを処理しながら QBrush を作成する必要があることに注意してください: http://doc.qt.nokia.com/4.7/qbrush.html

これはかなり遅くなります:(

2. 別のより高度なソリューションは、QImageReader と関連する Image IO プラグインを作成してフォーマット ( http://qt-project.org/doc/qt-4.8/qimagereader.html ) を読み取ってから、画像を含む QPixMap を作成することです。リーダー ( http://qt-project.org/doc/qt-4.8/qpixmap.html#fromImageReader ) を指定し、指定された QPixmap で QBrush を作成し、それを使用して描画します:)

于 2012-06-28T06:49:18.500 に答える