FreeType2 my_draw_bitmap undefined - c++

I am trying to run "7. Simple text rendering" the "a. Basic code" from here but the function "my_draw_bitmap" seems to be undefined. I tried to use GLEW, but the issue is the same. Then I saw "pngwriter" library here, but the compilation for Visual Studio 2013 with Cmake give error.
Please someone help, where 'my_draw_bitmap' function is defined?

The tutorial states
The function my_draw_bitmap is not part of FreeType but must be provided by the application to draw the bitmap to the target surface. In this example, it takes a pointer to a FT_Bitmap descriptor and the position of its top-left corner as arguments.
What this means is that you need to implement the function for copying the glyphs to the texture or bitmap to be rendered yourself (assuming there isn't a suitable function available in the libraries you're using).
The below code should be appropriate for copying the pixels of a single glyph to an array that could be copied to a texture.
unsigned char **tex;
void makeTex(const unsigned int width, const unsigned int height)
{
tex = (unsigned char**)malloc(sizeof(char*)*height);
tex[0] = (unsigned char*)malloc(sizeof(char)*width*height);
memset(tex[0], 0, sizeof(char)*width*height);
for (int i = 1; i < height;i++)
{
tex[i] = tex[i*width];
}
}
void paintGlyph(FT_GlyphSlot glyph, unsigned int penX, unsigned int penY)
{
for (int y = 0; y<glyph->bitmap.rows; y++)
{
//src ptr maps to the start of the current row in the glyph
unsigned char *src_ptr = glyph->bitmap.buffer + y*glyph->bitmap.pitch;
//dst ptr maps to the pens current Y pos, adjusted for the current char row
unsigned char *dst_ptr = tex[penY + (glyph->bitmap.rows - y - 1)] + penX;
//copy entire row
for (int x = 0; x<glyph->bitmap.pitch; x++)
{
dst_ptr[x] = src_ptr[x];
}
}
}

Related

Loading a BMP image at a specific index in OpenGL

I have to load a 24 bit BMP file at a certain (x,y) index of glut window from a file using OpenGL. I have found a function that uses glaux library to do so. Here the color mentioned in ignoreColor is ignored during rendering.
void iShowBMP(int x, int y, char filename[], int ignoreColor)
{
AUX_RGBImageRec *TextureImage;
TextureImage = auxDIBImageLoad(filename);
int i,j,k;
int width = TextureImage->sizeX;
int height = TextureImage->sizeY;
int nPixels = width * height;
int *rgPixels = new int[nPixels];
for (i = 0, j=0; i < nPixels; i++, j += 3)
{
int rgb = 0;
for(int k = 2; k >= 0; k--)
{
rgb = ((rgb << 8) | TextureImage->data[j+k]);
}
rgPixels[i] = (rgb == ignoreColor) ? 0 : 255;
rgPixels[i] = ((rgPixels[i] << 24) | rgb);
}
glRasterPos2f(x, y);
glDrawPixels(width, height, GL_RGBA, GL_UNSIGNED_BYTE, rgPixels);
delete []rgPixels;
free(TextureImage->data);
free(TextureImage);
}
But the problem is that glaux is now obsolete. If I call this function, the image is rendered and shown for a minute, then an error pops up (without any error message) and the glut window disappears. From the returned value shown in the console, it seems like a runtime error.
Is there any alternative to this function that doesn't use glaux? I have seen cimg, devil etc but none of them seems to work like this iShowBMP function. I am doing my project in Codeblocks.
I have to load every frame to keep the implementation consistent with other parts of the program. Also, the bmp file whose name has been passed as a parameter to the function has both width and height in powers of 2.
The last two free() statements were not getting executed for some unknown reasons, so the memory consumption was increasing. That's why the program was crashing after a moment. Later I solved it using stb_image.h.

Rotating image using classes

I'm having trouble rotating an image 90 degrees, the images are 768 x 768 pixels. The code I have shown here is able to create a new image, but the function I've written isn't manipulating it at all. My image class and function that's in the driver to rotate it is below. I have to rotate all the pictures 90 degrees clockwise and counterclockwise; I think my issue is trying to get the pointers to correctly switch the pixels around.
class image {
public:
image(); //the image constructor (initializes everything)
image(string filename); //a image constructor that directly loads an image from disk
image(image &other); //copy constructor
~image(); //the image destructor (deletes the dynamically created pixel array)
pixel** getPixels(); //return the 2-dimensional pixels array
int getWidth(); //return the width of the image
int getHeight(); //return the height of the image
void createNewImage(int width, int height);
private:
pixel** pixels; // pixel data array for image
int width, height; // stores the image dimensions
void pixelsToCImage(CImage* myImage);
};
void RotateClockWise(image *imageIn)
{
image rotateImg;
image *ptr = (image*) &rotateImg;
*ptr = *imageIn;
int height = rotateImg.getHeight();
int width = rotateImg.getWidth();
pixel** rotatePix = rotateImg.getPixels();
for (int i = 0; i < height; i++)
{
for (int j = 0; j < width; j++)
{
rotatePix[i][j] = rotatePix[j][i];
*(ptr + j * height + (height - i - 1)) = *(ptr + i * width + j);
}
}
}
First your code is very c style. This is cool, I love this kind of coding, but you can make your life easier with references.
Solution for your code:
You never set point to imageIn, just the copy the value from image in to rotateImg:
image rotateImg;
image *ptr = (image*) &rotateImg;
*ptr = *imageIn;
This means you just modify the local variable rotateImg and not the object which is given by the pointer.
And here just a plain NO:
ptr points on an image. Each +j means "go to the next image" or more precissly: ptr = ptr + sizeof(image); which should be around 12 bytes + vtable. Dont do this. You You can just do this when you loop over an 1 dimensional pixel array.
*(ptr + j * height + (height - i - 1)) = *(ptr + i * width + j); //BAD
Here is some C style code which solves the problem. I did not know you could give a 2 dimensional array via a double pointer **ptr (indirect pointers).
void RotateClockWise(image* imageIn)
{
image rotateImg;
rotateImg = *imageIn;
image *ptr = imageIn;
int height = rotateImg.getHeight();
int width = imageIn->getWidth();
pixel** normalPix = rotateImg.getPixels();
pixel** rotatePix = imageIn->getPixels();
for (int i = 0; i < height; i++)
{
for (int j = 0; j < width; j++)
{
rotatePix[i][j] = normalPix[(height-1)-j][(width-1)-i];
}
}
}
I am to lazy to code it in C++ Style, but have a look at the Reference
void RotateClockWise(image& imageIn)
You have imageIn argument that probably points to image you want to rotate. However, you create rotateImg object, get pointer to this object (ptr) and duplicate imageIn to this ptr. So, now you manipulate image copy instead of image itself, that is why object pointed by imageIn never changes its value.

reading TGA files in OpenGl to create a 3d ouse

I have a TGA file and a library that allready has everything that I need to read TGA and use them.
This class has a method called pixels(), that returns a pointer that is pointed to the memory area where pixel are stored as RGBRGBRGB...
My question is, how can I take the pixel value?
Cause if I make something like this:
img.load("foo.tga");
printf ("%i", img.pixels());
It gives back to me what is proprably the address.
I've found this code on this site:
struct Pixel2d
{
static const int SIZE = 50;
unsigned char& operator()( int nCol, int nRow, int RGB)
{
return pixels[ ( nCol* SIZE + nRow) * 3 + RGB];
}
unsigned char pixels[SIZE * SIZE * 3 ];
};
int main()
{
Pixel2d p2darray;
glReadPixels(50,50, 1, 1, GL_RGB, GL_UNSIGNED_BYTE, &p.pixels);
for( int i = 0; i < Pixel2d::SIZE ; ++i )
{
for( int j = 0; j < Pixel2d::SIZE ; ++j )
{
unsigned char rpixel = p2darray(i , j , 0);
unsigned char gpixel = p2darray(i , j , 1);
unsigned char bpixel = p2darray(i , j , 2);
}
}
}
I think that It can work great for me, but how can I tell the program to read from my img?
Tga supports different pixel depths. And we don't know what library you're using. But generally speaking pixels() should return a pointer to a buffer containing pixels. Say for sake of argument it unpacks the pixels into 8-bit per channel subpixels, then each pixel is represented by 3 bytes.
So to access a pixel at a given offset in the buffer:
const u8* pixelBuffer = img.pixels():
u8 red = pixelBuffer[(offset*3)+0];
u8 green = pixelBuffer[(offset*3)+1];
u8 blue = pixelBuffer[(offset*3)+2];
If you know the width of the image buffer then you can get a pixel by its x and y coordinates:
u8 red = pixelBuffer[((x+(y*width))*3)+0];

Reorganize image/picture arrays in OpenGL to fit power of 2 textures size

I am having troubles in OpenGL due to the fact that textures have to be power of 2 in OpenGL.
What I am doing is the following:
I Load a PNG file into an array of unsigned char, using PNGLIB or SOIL. The idea is that I can run though this array and "Select" the parts that are relevant for me. For example, imagining I've loaded a person, but I just want to store the head in a separate texture. So im looping through the array and selecting only the necessary parts.
First Question: I believe that the data in the array is stored in RGBA mode, but I'm yet not sure if the data is filled rowise or columnwise. Is it possible to know this information?
Second Question: Since there is the need to always create power of 2 textures, it can happen that i have an image with 513pixels width so that I will need a texture with 1024px width. So what is happening is that the picture looks like it gets completly "destroyed" because the pixels are not on the places they should be - The texture has a different size than the relevant data filled in the array. So how can I manage to reorganize the array in order to get the contents of the image again? I tried the following but it doesn't work:
unsigned char* new_memory = 0;
int index = 0;
int new_index = 0;
new_memory = new unsigned char[new_tex_width * new_tex_height * 4];
for(int i=0; i<picture.width; i++) // WIDTH
{
for(int j=0; j<picture.height; j++) // HEIGHT
{
for(int k=0; k<4; k++) // DEPTH
new_memory[new_index++] = picture.memory[index++];//picture.memory[i + picture.height * (j + 4 * k)];
}
new_index += new_tex_height - picture.height;
}
glGenTextures(1, &png_texture);
glBindTexture(GL_TEXTURE_2D, png_texture);
glTexImage2D(GL_TEXTURE_2D, 0, 3, new_tex_width, new_tex_height, 0 , GL_RGBA, GL_UNSIGNED_BYTE, new_memory);
Non power of two textures has been supported since a good while back. However, creating textures atlases and rearranging textures still have a lot of merit, the way we do it is to simply use freeimage as they handle all of this for you and supports some of the compressed formats.
If you want to do it your way, and know that it's just a bitmap, then I'd do it more along the lines of ( not tested, and does not check inputs, but should give you an idea ):
void Blit( int xOffset, int yOffset, int targetW, int sourceW, int sourceH, unsigned char* source, unsigned char* target, unsigned int bpp )
{
for( unsigned int i = 0; i < sourceH; ++i )
{
memcpy( target + bpp * ( targetW * ( yOffset + i ) + xOffset ), source + sourceW * i * bpp, sourceW * bpp );
}
}
Basically, just take each row and memcpy it over.

How to access image Data from a RGB image (3channel image) in opencv

I am trying to take the imageData of image in this where w= width of image and h = height of image
for (int i = x; i < x+h; i++) //height of frame pixels
{
for (int j = y; j < y+w; j++)//width of frame pixels
{
int pos = i * w * Channels + j; //channels is 3 as rgb
// if any data exists
if (data->imageData[pos]>0) //Taking data (here is the problem how to take)
{
xPos += j;
yPos += i;
nPix++;
}
}
}
jeff7 gives you a link to a very old version of OpenCV. OpenCV 2.0 has a new C++ wrapper that is much better than the C++ wrapper mentioned in the link. I recommend that you read the C++ reference of OpenCV for information on how to access individual pixels.
Another thing to note is: you should have the outer loop being the loop in y-direction (vertical) and the inner loop be the loop in x-direction. OpenCV is in C/C++ and it stores the values in row major.
See good explanation here on multiple methods for accessing pixels in an IplImage in OpenCV.
From the code you've posted your problem lies in your position variable, you'd want something like int pos = i*w*Channels + j*Channels, then you can access the RGB pixels at
unsigned char r = data->imageData[pos];
unsigned char g = data->imageData[pos+1];
unsigned char b = data->imageData[pos+2];
(assuming RGB, but on some platforms I think it can be stored BGR).
uchar* colorImgPtr;
for(int i=0; i<colorImg->width; i++){
for(int j=0; j<colorImg->height; j++){
colorImgPtr = (uchar *)(colorImg->imageData) + (j*colorImg->widthStep + i-colorImg->nChannels)
for(int channel = 0; channel < colorImg->nChannels; channel++){
//colorImgPtr[channel] here you have each value for each pixel for each channel
}
}
}
There are quite a few methods to do this (the link provided by jeff7 is very useful).
My preferred method to access image data is the cvPtr2D method. You'll want something like:
for(int x = 0; x < width; ++x)
{
for(int y = 0; y < height; ++y)
{
uchar* ptr = cvPtr2D(img, y, x, NULL);
// blue channel can now be accessed with ptr[0]
// green channel can now be accessed with ptr[1]
// red channel can now be accessed with ptr[2]
}
}
(img is an IplImage* in the above code)
Not sure if this is the most efficient way of doing this etc. but I find it the easiest and simplest way of doing it.
You can find documentation for this method here.