質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
86.12%
OpenGL

OpenGLは、プラットフォームから独立した、デスクトップやワークステーション、モバイルサービスで使用可能な映像処理用のAPIです。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。

解決済

FreeTypeライブラリで日本語を描画したい。

退会済みユーザー

退会済みユーザー

総合スコア0

OpenGL

OpenGLは、プラットフォームから独立した、デスクトップやワークステーション、モバイルサービスで使用可能な映像処理用のAPIです。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。

2回答

0グッド

0クリップ

2094閲覧

投稿2021/05/10 04:40

編集2021/05/10 10:18

Openglでfreetypeを使って日本語の文字を描画したいです。 提示サイトでは英語の文字表示をやり方が乗っているやり方では事前に用意したアルファベットの文字を描画していますが。日本語はまた違うはずです。提示コードの//////コメント内部のfor文ですが参考サイトを参考に
const char16_t型にキャストして日本語文字の描画を試みましたが字の枠しか描画されませんこれはどうしたらいいのでしょうか?

イメージ説明
参考サイト: http://blendgimper.hatenablog.jp/entry/2016/01/01/074615
参考サイト: https://learnopengl.com/In-Practice/Text-Rendering

cpp

1#include "Text.hpp" 2#include "glew/include/GL/glew.h" 3#include "glm/glm.hpp" 4 5#include "Window.hpp" 6#include <iostream> 7 8FrameWork::Text::Text(std::shared_ptr<Window> w, const char* vert, const char* frag) : FrameWork::Transform_2D(),Shader() 9{ 10 windowContext = w; //ウインドウコンテキスト 11 12 //シェーダー 13 if (vert == NULL && frag == NULL) 14 { 15 vert = "Shader/2D/BasicText_2D.vert"; 16 frag = "Shader/2D/BasicText_2D.frag"; 17 LoadShader(vert,frag); 18 } 19 else { 20 LoadShader(vert, frag); 21 } 22 23 //vao vbo 24 glGenVertexArrays(1, &vao); 25 glGenBuffers(1, &vbo); 26 glBindVertexArray(vao); 27 glBindBuffer(GL_ARRAY_BUFFER, vbo); 28 glBufferData(GL_ARRAY_BUFFER, sizeof(float) * 6 * 4, NULL, GL_DYNAMIC_DRAW); 29 glEnableVertexAttribArray(0); 30 glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 4 * sizeof(float), 0); 31 glBindBuffer(GL_ARRAY_BUFFER, 0); 32 glBindVertexArray(0); 33 34 35 //FreeTypeを初期化 36 // 37 //初期化 38 39 if (FT_Init_FreeType(&ft) != 0) 40 { 41 std::cout << "ERROR::FREETYPE: Could not init FreeType Library"<<std::endl; 42 assert(0); 43 } 44 45 //フェイス作成 46 47 if (FT_New_Face(ft, "C:\Windows\Fonts\meiryo.ttc", 0, &face) != 0) 48 { 49 std::cout<<"ERROR::FREETYPE: Failed to load font" << std::endl; 50 assert(0); 51 52 } 53 54 charSize = 24; //文字サイズを指定 55 FT_Set_Pixel_Sizes(face,0,charSize); //ピクセルサイズを指定 56 57 glPixelStorei(GL_UNPACK_ALIGNMENT, 1); // disable byte-alignment restriction 58 59 //アルファブレンドを有効 60 glEnable(GL_BLEND); 61 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 62} 63 64void FrameWork::Text::Draw(glm::vec2 pos,const char16_t* text,float scale, glm::vec3 color) 65{ 66 setEnable(); //シェーダーを有効にする 67 68 pos.y = windowContext->getSize().y - pos.y - charSize; 69 70 //テクスチャをアクティブ 71 glActiveTexture(GL_TEXTURE0); 72 glBindVertexArray(vao); 73 74 //Unform 75 setUniform3f("textColor",color); 76 setUniformMatrix4fv("uViewProjection", glm::ortho(0.0f, windowContext->getSize().x, 0.0f, windowContext->getSize().y)); 77 /////////////////////////////////////////////////////////////////////////////////////////////////////////////// 78 for (int i = 0; text[i] != '\0'; i++) 79 { 80 81 unsigned int texture = 0; 82 83 // load character glyph 84 FT_Load_Glyph(face, FT_Get_Char_Index(face, (char16_t)text[i]), FT_LOAD_RENDER); 85 86 87 // now store character for later use 88 Character ch = { 89 texture, 90 glm::ivec2(face->glyph->bitmap.width, face->glyph->bitmap.rows), 91 glm::ivec2(face->glyph->bitmap_left, face->glyph->bitmap_top), 92 (unsigned int)face->glyph->advance.x 93 94 }; 95 96 97 // generate texture 98 glGenTextures(1, &ch.textureID); 99 glBindTexture(GL_TEXTURE_2D, ch.textureID); 100 101 glTexImage2D( 102 GL_TEXTURE_2D, 103 0, 104 GL_RED, 105 face->glyph->bitmap.width, 106 face->glyph->bitmap.rows, 107 0, 108 GL_RED, 109 GL_UNSIGNED_BYTE, 110 face->glyph->bitmap.buffer 111 ); 112 // set texture options 113 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); 114 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); 115 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 116 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 117 // now store character for later use 118 119 120 121 float xpos = pos.x + ch.Bearing.x * scale; 122 float ypos = pos.y - (ch.Size.y - ch.Bearing.y) * scale; 123 124 float w = ch.Size.x * scale; 125 float h = ch.Size.y * scale; 126 // update VBO for each character 127 float vertices[6][4] = { 128 { xpos, ypos + h, 0.0f, 0.0f }, 129 { xpos, ypos, 0.0f, 1.0f }, 130 { xpos + w, ypos, 1.0f, 1.0f }, 131 132 { xpos, ypos + h, 0.0f, 0.0f }, 133 { xpos + w, ypos, 1.0f, 1.0f }, 134 { xpos + w, ypos + h, 1.0f, 0.0f } 135 }; 136 // render glyph texture over quad 137 // update content of VBO memory 138 glBindBuffer(GL_ARRAY_BUFFER, vbo); 139 glBufferSubData(GL_ARRAY_BUFFER, 0, sizeof(vertices), vertices); 140 glBindBuffer(GL_ARRAY_BUFFER, 0); 141 142 // render quad 143 glDrawArrays(GL_TRIANGLES, 0, 6); 144 145 146 147 // now advance cursors for next glyph (note that advance is number of 1/64 pixels) 148 pos.x += ((ch.Advance >> 6) * scale); // bitshift by 6 to get value in pixels (2^6 = 64) 149 } 150//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 151 glBindVertexArray(0); 152 glBindTexture(GL_TEXTURE_2D, 0); 153 setDisable(); //シェーダーを無効にする 154} 155 156 157 158FrameWork::Text::~Text() 159{ 160 //グリフ解放 161 FT_Done_Face(face); 162 FT_Done_FreeType(ft); 163 164} 165

以下のような質問にはグッドを送りましょう

  • 質問内容が明確
  • 自分も答えを知りたい
  • 質問者以外のユーザにも役立つ

グッドが多くついた質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

気になる質問をクリップする

クリップした質問は、後からいつでもマイページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

下記のような質問は推奨されていません。

  • 間違っている
  • 質問になっていない投稿
  • スパムや攻撃的な表現を用いた投稿

適切な質問に修正を依頼しましょう。

2021/05/10 09:56依頼された後にこの質問は修正されています

こちらの質問が複数のユーザーから「過去の低評価」という指摘を受けました。

int32_t

2021/05/10 04:49 編集

Font/ariali.ttf に日本語のグリフは入っていますか? Text::Text() では文字コード0から127までのグリフしか用意していないのは理解していますか?
episteme

2021/05/10 04:59

参考サイトでは "メイリオ" 使ってますね↓ FT_New_Face(library, "C:\\Windows\\Fonts\\meiryo.ttc", 0, &face);
episteme

2021/05/10 08:56

> 参考サイトはちゃんと読んだのでしょうか。 「例示のとおりにやってない」か 「自分の問題に置き換えることができない」のいずれかでしょう。
m.ts10806

2021/05/10 10:05

>色々調べましたがわかりません。 そこでパッと提示された記事をどのように理解したのか書かないと 何をしたのか分かりません。 「読んだ」と「理解した」は別物です。 理解できたのかできなかったのか 理解できたならどこが理解できてどこが理解できてないのか 全く理解できてないなら「そもそも理解するためのベースは自身の中にあるのか」を疑う必要があります。
退会済みユーザー

退会済みユーザー

2021/05/10 11:55 編集

> const char16_t型にキャストして日本語文字の描画を試みましたが字の枠しか描画されませんこれはどうしたらいいのでしょうか? キャストして……? どう出力されることを期待しているのか、呼び出し側が提示されていないためわかりません。
退会済みユーザー

退会済みユーザー

2021/05/18 12:34

呼び出し側のコードも書いてください 「std::string text」から「const char16_t* text」へ変更したようですが、 文字通りキャストしたのであれば描画されるわけがありません まず、「char16_t」が何かから理解する必要があるでしょう

回答2

1

参考サイト: https://learnopengl.com/In-Practice/Text-Rendering

こっちのサイトのコードは日本語の文字については未対応で、これをベースに日本語対応させるのはなかなかたいへんです。

  • ASCII文字だけ事前にロードしているが、それを日本語に使う全文字に拡張するのは現実的ではない
  • std::string を工夫なしで使っているため、 U+100 以上の文字に対応するのが難しい

公開されているコードを参考するのは良いのですが、必ず何をしているコードなのか理解して参考にしましょう。理解しながらコードを取り込んでいれば、ASCII以外の文字は扱えないことは既知のはずです。

参考サイト: http://blendgimper.hatenablog.jp/entry/2016/01/01/074615

こちらを参考に作り直すのがよいのではないかと思います。

投稿2021/05/10 05:24

編集2021/05/10 07:01
int32_t

総合スコア17111

退会済みユーザー👍を押しています

良いと思った回答にはグッドを送りましょう。
グッドが多くついた回答ほどページの上位に表示されるので、他の人が素晴らしい回答を見つけやすくなります。

下記のような回答は推奨されていません。

  • 間違っている回答
  • 質問の回答になっていない投稿
  • スパムや攻撃的な表現を用いた投稿

このような回答には修正を依頼しましょう。

0

ベストアンサー

呼び出し部でプレフィックスuをつけることでconst char16_t型として文字を受け取り描画することができました。

FrameWork::Text text(windowContext); text.Draw(glm::vec2(100,100),u"テスト",1.0f,glm::vec3(255,0,0));

投稿2021/05/19 04:09

退会済みユーザー

退会済みユーザー

総合スコア0

良いと思った回答にはグッドを送りましょう。
グッドが多くついた回答ほどページの上位に表示されるので、他の人が素晴らしい回答を見つけやすくなります。

下記のような回答は推奨されていません。

  • 間違っている回答
  • 質問の回答になっていない投稿
  • スパムや攻撃的な表現を用いた投稿

このような回答には修正を依頼しましょう。

2021/06/23 01:07

こちらの回答が複数のユーザーから「過去の低評価」という指摘を受けました。

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
86.12%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問

同じタグがついた質問を見る

OpenGL

OpenGLは、プラットフォームから独立した、デスクトップやワークステーション、モバイルサービスで使用可能な映像処理用のAPIです。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。