提示コードのコメント内部のコードですがタイトル通り「 .pngファイルを直接読み込んでopenglにて描画させるまでの道のりが知りたい。 」
です。提示コードはチャンクデータをいじっていなので画像は表示されませんが直接.pngファイルを読み込むにはどういった手順が必要なのでしうか?取り出したデータをglTexImage2D();関数に入れても動作しないとう情報を得ました。どういった手順で描画できるのでしょうか?
質問2ですが.pngファイルのIDATのチャンクを列挙すると複数のIDATAチャンクが見つかりました。がこれは全部を繋げる必要があるのでしょうか?
1,ifstreamで画像をバイナリで読み込む
2,チャンクデータでIDATの実データを取り出す
3,ここから知りたい
cpp
1#include "Sprite_2D.hpp" 2 3#include <iostream> 4#include <fstream> 5 6#include <glm/glm.hpp> 7#include <glm/gtc/matrix_Transform.hpp> 8#include <glm/gtx/Transform.hpp> 9 10#include "Shader.hpp" 11 12 13//コンストラクタ 14Sprite_2D::Sprite_2D(std::shared_ptr<Window> w,const char* vert,const char* frag) : Transform_2D(w),Shader() 15{ 16 //シェーダー読み込み 17 Load(vert, frag); 18 19 20 //頂点情報 21 Vertex rectangleVertex[6] = 22 { 23 //頂点、頂点色 24 {-0.5f,0.5f, 0.0f,1.0f}, 25 {-0.5f,-0.5f, 0.0f,0.0f}, 26 {0.5f,0.5f, 1.0f,1.0f}, 27 28 {0.5f,0.5f, 1.0f,1.0f}, 29 {-0.5f,-0.5f, 0.0f,0.0f}, 30 {0.5f,-0.5f, 1.0f,0.0f}, 31 32 33 }; 34 35 //vao 36 glGenVertexArrays(1, &vao); 37 glBindVertexArray(vao); 38 39 //vbo 40 glGenBuffers(1, &vbo); 41 glBindBuffer(GL_ARRAY_BUFFER, vbo); 42 43 //頂点 44 GLint attrib = getAttribLocation("vertexPosition"); 45 glEnableVertexAttribArray(attrib); 46 glBufferData(GL_ARRAY_BUFFER, 6 * sizeof(Vertex), rectangleVertex, GL_STATIC_DRAW); 47 glVertexAttribPointer(attrib, 2, GL_FLOAT, GL_FALSE, 4 * sizeof(GLfloat), (GLvoid*)0); 48 setBindAttribVertex("vertexPosition"); 49 50 attrib = getAttribLocation("vertexUV"); 51 glEnableVertexAttribArray(attrib); 52 glBufferData(GL_ARRAY_BUFFER, 6 * sizeof(Vertex), rectangleVertex, GL_STATIC_DRAW); 53 glVertexAttribPointer(attrib, 2, GL_FLOAT, GL_FALSE, 4 * sizeof(GLfloat), (GLvoid*)(sizeof(GLfloat) * 2)); 54 setBindAttribVertex("vertexUV"); 55 56 57/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 58 59 // テクスチャIDの生成 60 glGenTextures(1, &texID); 61 62 // ファイルの読み込み 63 std::ifstream fstr("texture.png", std::ios::binary); 64 if (fstr.is_open() == true) { 65 const size_t fileSize = static_cast<size_t>(fstr.seekg(0, fstr.end).tellg()); 66 fstr.seekg(0, fstr.beg); 67 char* textureBuffer = new char[fileSize]; 68 fstr.read(textureBuffer, fileSize); 69 fstr.seekg(0, fstr.beg); 70 71 72 73 glPixelStorei(GL_UNPACK_ALIGNMENT, 1); 74 glBindTexture(GL_TEXTURE_2D, texID); 75 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, 256, 256, 0, GL_RGB, GL_UNSIGNED_BYTE, textureBuffer); 76 77 // テクスチャの設定 78 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); 79 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); 80 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); 81 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); 82 83 // テクスチャのアンバインド 84 delete[] textureBuffer; 85 } 86 else { 87 std::cerr << "ファイルが開けません" << std::endl; 88 } 89 90 91/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 92 93 94} 95 96//更新 97void Sprite_2D::Update() 98{ 99 100} 101 102//描画 103void Sprite_2D::Draw(glm::mat4 projection) 104{ 105 //setEnable(); 106 glBindVertexArray(vao); 107 glBindTexture(GL_TEXTURE_2D, texID); 108 109 setUniformMatrix4fv("uTranslate", translate); 110 setUniformMatrix4fv("uRotate", rotate); 111 setUniformMatrix4fv("uScale", scale); 112 setUniformMatrix4fv("uViewProjection",projection); 113 114 glDrawArrays(GL_TRIANGLES, 0, 6); 115 116 //setDisable(); 117 glBindVertexArray(0); 118 glBindTexture(GL_TEXTURE_2D, 0); 119 120} 121 122//デストラクタ 123Sprite_2D::~Sprite_2D() 124{ 125 glDeleteVertexArrays(1, &vao); 126 glDeleteBuffers(1, &vbo); 127} 128 129
IDATのチャンクとは何のことでしょうか?
https://teratail.com/questions/335653
以前の回答にあるベストアンサーの方法は試さなかったのでしょうか
この程度で詰まる知識では、PNGのローダーを自前で作るのは絶望的なので、
ライブラリを使用する、という一般的な方法を取るほうが無難だと思います
PNGから「glTexImage2D()」で使える形への展開など、書かれたところで理解できないと思うので
一様知りたいので質問しました。
stb_imageを使えば画像を描写できることは前に回答しました.
https://teratail.com/questions/335653
つまり,「stb_image.h」「stb_image.c」のコード(stbi_load関数)を見て学習すれば,貴方のやりたいことが実現できるはずです.
VisualStudioであれば関数をクリックして「F12」を押せば関数の定義へ飛んでいけます.
一度,自身で「stb_image」のコードとにらめっこして,どうしても理解できない場所があればteratailで質問しるのがよいと思います.質問するときは自分のコードをべた張りではなく,問題と関係ない部分は削るとよいかもしれません.
勉強目的なら一度コードを読んでみると良いと思いますし,もしゲームを作りたいのであれば,もっと勉強することもあるでしょうし,とっとと次に進むべきだと個人的には思います.
ライセンスも「This software is available under 2 licenses -- choose whichever you prefer.」で「MIT License」と「Public Domain」です.
https://github.com/nothings/stb/blob/master/LICENSE
私も大した技術力はないので変なことは言えないのですが,とりあえずライブラリの中身を読んでみてはいかがでしょうか.
> 質問2ですが.pngファイルのIDATのチャンクを列挙すると複数のIDATAチャンクが見つかりました。がこれは全部を繋げる必要があるのでしょうか?
PNGの仕様など調べた上で、上記のような質問がでるのであれば、あなたには不可能だと思います
逆にライブラリを使いたくない理由はあるのでしょうか
あなたが参考にしたサイトでも「stb_image.h」を使用する方法が書かれています
OpenGL自体も使っています、なぜこの部分だけ自前で実装しようとしているのか理解できません
本欄 [2021/05/01 16:52]の書き込みより:
> 一様知りたいので質問しました。
正:一応知りたい
誤:一様知りたい
[推奨していない質問] https://teratail.com/help/avoid-asking
から引用:
> teratailは困っている人の質問を解決するサービスです。そのため、漠然とした興味から票を募るような質問や、意見の主張をすることを目的とした投稿は推奨していません。
あなたの思い付きに発した興味の為に回答を消費するようなことはいい加減に止めなさいと言うのに。
自分の表現したいことがどちらなのか意味を理解して使った方がいい。
https://eigobu.jp/magazine/ichiyou
家族ですらあなたがどういう意図でした発言なのか知ることはできない
「書かれた通り」にしか取られない
それであたえた誤解をきちんと回収しないからどんどん指摘する人だけが増える
真面目にアドバイスしようと思う人がいなくなる。自ら人を遠ざけて、それを自分のせいではなく他人のせいにしてないか?自分の胸に手を当ててよく考えてみて。
脳死で質問投稿する前に。
その脳死質問でも回答つけちゃう人いるから、味を占めてずっと今の状態が続いてしまってるという。StackOverflowみたいに質問の連投自体にシステム的に制限掛けられない限りやめなさそう。
radianさん
アンケートで要望は送ってみました。
例えば低評価が一定以上なら回答できないように。とか。
それなりに指摘入ってるのに回答できる仕組みも前から考えものとは思っていました。大抵は本来アドバイスでしかない指摘より耳障りのいい回答に食いつきますから。
回答1件
あなたの回答
tips
プレビュー