I wonder if you can help me and see if I am on the right track.
We have an assignment for basic image processing, I understand about coursework so I'm not looking for the answer just guidance.
So we have been given a basic program that when run loads and image file and saves a copy. The we have been given an image handler library that actually handles the loading and saving.
What we have been tasked to do is to modify the basic program with a function that rotates the image 180 degrees then saves it. No mention of using special graphics handlers etc.
Now the image handler loads the image into an array called PIXELS{WIDTH}{HEIGHT}
I'm working along the lines of creating a function that manipulates the array swapping the width and height values. Using a for loop. Am I on the right track here?
Just so you are aware of the knowledge we have gained so far, it is quite basic. Strings, Loops, Arrays and developing functions. We haven't gone into calling up different libraries or built in functions in C++
we need to know exactly what pixels is, or your image format.
you seem to be on the right track, but if pixel array is unsigned char of an RGB image, it will be broken badly if you flip rows and columns blindly, you have to move 3 bytes at a time in that instance. If its a different type, like 1 byte greyscale, a simple flip will indeed work. Or if pixles is an array of some custom type that encapsulates your pixels, a simple flip will work.
bool loadImage(unsigned pixels[WIDTH][HEIGHT], constchar* fileName)
{
bool result; // Flag used to indicate successful operation
// Load image file from the directory the application is in
if( !Image.load(QCoreApplication::applicationDirPath() + "\\" + fileName))
{
// If unsuccessful, return false
result = false;
}
else
{
// For each row and column ...
for (int row = 0; row < HEIGHT; row++)
{
for (int col = 0; col < WIDTH; col++)
{
// Get pixel colour value
pixels[col][row] = Image.pixel(col, row);
}
}
// Return true to indicate succesful load operation
result = true;
}
return result;
}
usingnamespace std;
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
constchar LogoFile[] = "Logo.png";
unsigned PixelGrid[WIDTH][HEIGHT]; // Image loaded from file
// If the file cannot be loaded ...
if (!loadImage(PixelGrid, LogoFile))
{
// Display an error message
cout << "Error loading file \"" << LogoFile << "\"" << endl;
}
else
{
cout << "File \"" << LogoFile << "\" opened successfully" << endl;
// Demo of use of saveImage - to create a copy as "Logo.png"
// This should be modified to save the new images as specified
if (saveImage(PixelGrid, "LogoCopy.png"))
{
cout << "File \"LogoCopy.png\" saved successfully" << endl;
}
else
{
cout << "Could not save \"LogoCopy.png\"" << endl;
}
}
return a.exec();
}
As I said I'm not looking for the answer but just guidance that I am on the right track.
ok, so unsigned is storing the rgb values for you, so you can safely swap pixels as a unit. its possible to do it without a second image (by doing it in place in the original), but one easy solution is to copy into a new image from the old one.
that aside I think you are on the right track. Ask if you get into trouble.
Thanks for looking at that, gives me confidence that I'm going in the right direction.
We only started C++ programming a couple of months ago, though I've done bits and bobs prior.
Well good news is I have been got my code working to rotate the image.
Now I'm struggling to turn it into a function that works. We have been instructed it has to be a void() function, but I'm cocking something up. Any pointers?
I'm trying to pass the PixelGrid[WIDTH][HEIGHT] to the function but for my function call when I compile I get the following error.
error: invalid conversion from 'unsigned int' to 'unsigned int (*)[59]' [-fpermissive]
rotateImage(PixelGrid[WIDTH][HEIGHT]);
I suspect I have goofed up in some simple way but I just can't see. Pointers appreciated.
When you declare an array, you use [] to define the size of the array.
However, when using that array, you use [] to specify a particular element of the array.
So, at line 30:
rotateImage(PixelGrid[WIDTH][HEIGHT]);
you are not passing in the whole array, but one single element - that is, an unsigned int.
Well, actually, what you're passing in isn't an element of the array - it's a value read from memory past the end of your array. But it's still a single unsigned int, not an array.
Hmmm, it compiles fine, but when it runs I get the console, notification that the image file was opened successfully but then a pop-up informing me Graphics.cpp has crashed.
I've written and called functions before, I'm just struggling to see what I am missing.
void rotateImage(unsigned PixelGrid[WIDTH][HEIGHT])
{
int tempArr[WIDTH][HEIGHT];
for (int w = 0; w <= WIDTH/2; w++)
{
for (int h = 0; h <=HEIGHT; h++){
tempArr[WIDTH][HEIGHT]= PixelGrid[w][h];
PixelGrid[w][h] = PixelGrid[WIDTH-w][HEIGHT-h];
PixelGrid[WIDTH-w][HEIGHT-h] = tempArr[WIDTH][HEIGHT];
}
}
}
It seems you have some difficulties to grasp the concept of arrays. See this:
Actually when you use WIDTH/HEIGHT as an index they are out of bounds because an array starts with 0 and thus the range is 0...array_size-1. So PixelGrid[WIDTH-w][HEIGHT-h]; is out of bounds as well when w/h are 0.
Out of bounds means undefined behavior which may lead to a crash but it is not predictable what actually happens.