Created
July 21, 2013 19:02
-
-
Save philip-goh/6049574 to your computer and use it in GitHub Desktop.
CS344 Udacity Problem Set 1 solution. The tricky bit is working out the x and y offsets in the kernel.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Homework 1 | |
// Color to Greyscale Conversion | |
//A common way to represent color images is known as RGBA - the color | |
//is specified by how much Red, Grean and Blue is in it. | |
//The 'A' stands for Alpha and is used for transparency, it will be | |
//ignored in this homework. | |
//Each channel Red, Blue, Green and Alpha is represented by one byte. | |
//Since we are using one byte for each color there are 256 different | |
//possible values for each color. This means we use 4 bytes per pixel. | |
//Greyscale images are represented by a single intensity value per pixel | |
//which is one byte in size. | |
//To convert an image from color to grayscale one simple method is to | |
//set the intensity to the average of the RGB channels. But we will | |
//use a more sophisticated method that takes into account how the eye | |
//perceives color and weights the channels unequally. | |
//The eye responds most strongly to green followed by red and then blue. | |
//The NTSC (National Television System Committee) recommends the following | |
//formula for color to greyscale conversion: | |
//I = .299f * R + .587f * G + .114f * B | |
//Notice the trailing f's on the numbers which indicate that they are | |
//single precision floating point constants and not double precision | |
//constants. | |
//You should fill in the kernel as well as set the block and grid sizes | |
//so that the entire image is processed. | |
#include "reference_calc.cpp" | |
#include "utils.h" | |
#include <stdio.h> | |
__global__ | |
void rgba_to_greyscale(const uchar4* const rgbaImage, | |
unsigned char* const greyImage, | |
int numRows, int numCols) | |
{ | |
//TODO | |
//Fill in the kernel to convert from color to greyscale | |
//the mapping from components of a uchar4 to RGBA is: | |
// .x -> R ; .y -> G ; .z -> B ; .w -> A | |
// | |
//The output (greyImage) at each pixel should be the result of | |
//applying the formula: output = .299f * R + .587f * G + .114f * B; | |
//Note: We will be ignoring the alpha channel for this conversion | |
//First create a mapping from the 2D block and grid locations | |
//to an absolute 2D location in the image, then use that to | |
//calculate a 1D offset | |
int tx = threadIdx.x + blockIdx.x * blockDim.x; | |
int ty = threadIdx.y + blockIdx.y * blockDim.y; | |
int k = tx + ty * numCols; | |
greyImage[k] = rgbaImage[k].x * 0.299f + rgbaImage[k].y * 0.587f + rgbaImage[k].z * 0.114f; | |
} | |
void your_rgba_to_greyscale(const uchar4 * const h_rgbaImage, uchar4 * const d_rgbaImage, | |
unsigned char* const d_greyImage, size_t numRows, size_t numCols) | |
{ | |
//You must fill in the correct sizes for the blockSize and gridSize | |
//currently only one block with one thread is being launched | |
int block_width = 16; | |
int block_height = 16; | |
int grid_width = numCols / block_width; | |
if (grid_width * block_width < numCols) | |
grid_width++; | |
int grid_height = numRows / block_height; | |
if (grid_height * block_height < numRows) | |
grid_height++; | |
const dim3 blockSize(block_width, block_height ); //TODO | |
const dim3 gridSize( grid_width, grid_height ); //TODO | |
rgba_to_greyscale<<<gridSize, blockSize>>>(d_rgbaImage, d_greyImage, numRows, numCols); | |
cudaDeviceSynchronize(); checkCudaErrors(cudaGetLastError()); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment