title: Rendering Freetype glyph to OpenGL (3.3+) texture results in repeated texture with artifacts
body: <p>I was simply trying to display a glyph (letter Ě) loaded from Freetype as a bitmap picture onto an OpenGL texture that is stretched across the whole window. Result is here: </p>
  
  <p><img src="https://i.imgur.com/R8r6FGZ.png" alt="OpenGL + Freetype"></p>
  
  <p>To get to this result I had to set an extremely large FT_Set_Pixel_Sizes to 450 otherwise the resulting image looks even worse.</p>
  
  <p>I am using <a href="https://github.com/OpenGLInsights/OpenGLInsightsCode/blob/master/Chapter%2017%20Real-Time%20Physically%20Based%20Deformation%20Using%20Transform%20Feedback/TransformFeedback_Cloth/GLSLShader.h" rel="nofollow noreferrer">GLSLShader loader class</a> by M.M. Mobeen, GLEW, SDL2 and GLM.</p>
  
  <p><strong>shaders/shader.vert</strong></p>
  
  <pre><code>#version 330 core
  layout(location=0) in vec4 vVertex; //object space vertex
  out vec2 vUV;   // texture coordinates for texture lookup in the fragment shader
  
  void main()
  {
      gl_Position = vec4(vVertex.xy,0,1);
      vUV = vVertex.zw; // texture coordinate
  }
  </code></pre>
  
  <p><strong>shaders/shader.frag</strong></p>
  
  <pre><code>#version 330 core
  layout (location=0) out vec4 vFragColor;
  smooth in vec2 vUV;
  uniform sampler2D textureMap;
  
  void main()
  {                                              
      vFragColor = texture(textureMap, vUV);
  }
  </code></pre>
  
  <p><strong>main.cpp</strong></p>
  
  <pre><code>#include &lt;glew.h&gt;
  #include &lt;glm/glm.hpp&gt;
  
  #include "SDL2/SDL.h"
  #include "SDL2/SDL_opengl.h"
  
  #include &lt;ft2build.h&gt;
  #include FT_FREETYPE_H    
  
  #include "GLSLShader.h" // https://github.com/bagobor/opengl33_dev_cookbook_2013/blob/master/Chapter3/src/GLSLShader.h
  
  //shader reference
  GLSLShader shader;
  
  //vertex array and vertex buffer object IDs
  GLuint vaoID;
  GLuint vboVerticesID;
  GLuint vboIndicesID;
  
  //texture ID
  GLuint textureID;
  
  //quad vertices and indices
  glm::vec4 vertices[4];
  GLushort indices[6];
  
  int main( int argc, const char* argv[] )
  {
      if( SDL_Init( SDL_INIT_EVERYTHING ) == -1 ) return EXIT_FAILURE;
  
      SDL_GL_SetAttribute( SDL_GL_CONTEXT_MAJOR_VERSION, 3 );
      SDL_GL_SetAttribute( SDL_GL_CONTEXT_MINOR_VERSION, 2 );
      SDL_GL_SetAttribute( SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_CORE );
      SDL_GL_SetAttribute( SDL_GL_DOUBLEBUFFER, 1 );
      SDL_GL_SetAttribute( SDL_GL_DEPTH_SIZE, 24 );
  
      SDL_Window* window = SDL_CreateWindow( "OpenGL + Freetype",
                                             SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED,
                                             1024, 768,
                                             SDL_WINDOW_OPENGL | SDL_WINDOW_SHOWN );
  
      SDL_GLContext glcontext = SDL_GL_CreateContext( window );
  
      if( glcontext == nullptr ) return EXIT_FAILURE;
  
      glewExperimental = GL_TRUE;
  
      if( glewInit() != GLEW_OK ) return EXIT_FAILURE;
  
      SDL_GL_SetSwapInterval( 1 );
  
      shader.LoadFromFile( GL_VERTEX_SHADER, "shaders/shader.vert" );
      shader.LoadFromFile( GL_FRAGMENT_SHADER, "shaders/shader.frag" );
  
      //compile and link shader
      shader.CreateAndLinkProgram();
      shader.Use();
          shader.AddAttribute( "vVertex" );
          shader.AddUniform( "textureMap" );
          glUniform1i( shader( "textureMap" ), 0 );
      shader.UnUse();
  
      //setup quad geometry
      vertices[0] = glm::vec4( -1.0, -1.0, 0, 1 );
      vertices[1] = glm::vec4( 1.0, 1.0, 1, 0 );
      vertices[2] = glm::vec4( 1.0, -1.0, 1, 1 );
      vertices[3] = glm::vec4( -1.0, 1.0, 0, 0 );
  
      //fill quad indices array
      GLushort* id = &amp;indices[0];
      *id++ = 0;
      *id++ = 1;
      *id++ = 2;
      *id++ = 0;
      *id++ = 1;
      *id++ = 3;
  
      glGenVertexArrays( 1, &amp;vaoID );
      glGenBuffers( 1, &amp;vboVerticesID );
      glGenBuffers( 1, &amp;vboIndicesID );
  
      glBindVertexArray( vaoID );
  
      glBindBuffer( GL_ARRAY_BUFFER, vboVerticesID );
      glBufferData( GL_ARRAY_BUFFER, sizeof( vertices ), &amp;vertices[0], GL_DYNAMIC_DRAW );
  
      glEnableVertexAttribArray( shader["vVertex"] );
      glVertexAttribPointer( shader["vVertex"], sizeof( shader["vVertex"] ), GL_FLOAT, GL_FALSE, 0, 0 );
  
      glBindBuffer( GL_ELEMENT_ARRAY_BUFFER, vboIndicesID );
      glBufferData( GL_ELEMENT_ARRAY_BUFFER, sizeof( indices ), &amp;indices[0], GL_STATIC_DRAW );
  
      glGenTextures( 1, &amp;textureID );
      glActiveTexture( GL_TEXTURE0 );
      glBindTexture( GL_TEXTURE_2D, textureID );
  
      glPixelStorei( GL_UNPACK_ALIGNMENT, 1 );
      glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE );
      glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE );
      glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
  
      FT_Library  library;
      FT_Face     face;
  
      bool error = FT_Init_FreeType( &amp;library );
  
      if( error ) return EXIT_FAILURE;
  
      error = FT_New_Face( library,
                           "dejavu.ttf",
                           0,
                           &amp;face );
  
      if( error ) return EXIT_FAILURE;
  
      error = FT_Set_Pixel_Sizes( face, 0, 16 );
  
      if( error ) return EXIT_FAILURE;
  
      FT_Set_Pixel_Sizes( face, 0, 450 );
  
      FT_UInt glyph_index = FT_Get_Char_Index( face, 282 ); // letter Ě
  
      error = FT_Load_Glyph( face, glyph_index, FT_LOAD_DEFAULT );
  
      if( error ) return EXIT_FAILURE;
  
      error = FT_Render_Glyph( face-&gt;glyph, FT_RENDER_MODE_NORMAL );
  
      if( error ) return EXIT_FAILURE;
  
      glTexImage2D( GL_TEXTURE_2D,
                    0,
                    GL_RGB,
                    face-&gt;glyph-&gt;bitmap.width,
                    face-&gt;glyph-&gt;bitmap.rows,
                    0,
                    GL_RGB,
                    GL_UNSIGNED_BYTE,
                    face-&gt;glyph-&gt;bitmap.buffer
                  );
  
      bool running = true;
      while( running )
      {
          SDL_Event e;
  
          if( SDL_PollEvent( &amp;e ) )
          {
              switch( e.type )
              {
                  case SDL_QUIT:
                      running = false;
                      break;
                  default:
                      break;
              }
          }
  
          glClearColor( 1, 1, 1, 1 );
          glClear( GL_COLOR_BUFFER_BIT );
  
          shader.Use(); // bind shader
              glDrawElements( GL_TRIANGLES, sizeof( indices ), GL_UNSIGNED_SHORT, 0 );
          shader.UnUse(); // unbind shader
  
          SDL_GL_SwapWindow( window );
      }
  
      return 0;
  }
  </code></pre>