diff options
Diffstat (limited to 'Src/Plugins/Input/in_mp3/graphics')
-rw-r--r-- | Src/Plugins/Input/in_mp3/graphics/filterWater.cpp | 452 | ||||
-rw-r--r-- | Src/Plugins/Input/in_mp3/graphics/filterWater.h | 47 | ||||
-rw-r--r-- | Src/Plugins/Input/in_mp3/graphics/image.cpp | 209 | ||||
-rw-r--r-- | Src/Plugins/Input/in_mp3/graphics/image.h | 61 | ||||
-rw-r--r-- | Src/Plugins/Input/in_mp3/graphics/imageFilters.cpp | 91 | ||||
-rw-r--r-- | Src/Plugins/Input/in_mp3/graphics/imageFilters.h | 17 |
6 files changed, 877 insertions, 0 deletions
diff --git a/Src/Plugins/Input/in_mp3/graphics/filterWater.cpp b/Src/Plugins/Input/in_mp3/graphics/filterWater.cpp new file mode 100644 index 00000000..d6128738 --- /dev/null +++ b/Src/Plugins/Input/in_mp3/graphics/filterWater.cpp @@ -0,0 +1,452 @@ +#include ".\filterwater.h" +#include <math.h> + +#define random( min, max ) (( rand() % (int)((( max ) + 1 ) - ( min ))) + ( min )) + +MLImageFilterWater::MLImageFilterWater(void) +{ + hField1 = NULL; + hField2 = NULL; + hHandle = NULL; + + width = 0; + height = 0; + + drawWithLight = TRUE; + lightModifier = 1; + hPage = 0; + density = 5; + +} + +MLImageFilterWater::~MLImageFilterWater(void) +{ + ClearData(); +} + +void MLImageFilterWater::ClearData(void) +{ + if (hHandle) + { + if (hField1) HeapFree(hHandle, NULL, hField1); + if (hField2) HeapFree(hHandle, NULL, hField2); + HeapDestroy(hHandle); + hField1 = NULL; + hField2 = NULL; + hHandle = NULL; + } + +} + +BOOL MLImageFilterWater::CreateFor(const MLImage *image) +{ + ClearData(); + width = image->GetWidth(); + height = image->GetHeight(); + hPage = 0; + int len = height * width * sizeof(int); + hHandle = HeapCreate(NULL, 3*len, 3*len); + if (!hHandle) + { + width = 0; + height = 0; + return FALSE; + } + + hField1 = (int*)HeapAlloc(hHandle, HEAP_ZERO_MEMORY, len); + hField2 = (int*)HeapAlloc(hHandle, HEAP_ZERO_MEMORY, len); + return hField1 && hField2; +} + +void MLImageFilterWater::Render(MLImage* destination, const MLImage* source) +{ + if(!drawWithLight) DrawWaterNoLight(hPage, destination, source); + else DrawWaterWithLight(destination, source); + CalculateWater(hPage, density); +// CalcWaterBigFilter(hPage, density); + hPage ^= 1; +} + +void MLImageFilterWater::CalculateWater(int page, int density) +{ + int newh; + int count = width + 1; + int *newptr; + int *oldptr; + + if(page == 0) + { + newptr = hField1; + oldptr = hField2; + } + else + { + newptr = hField2; + oldptr = hField1; + } + + int x, y; + for (y = (height - 1) * width; count < y; count += 2) + { + for (x = count + width - 2; count < x; count++) + { + // This does the eight-pixel method. + + newh = ((oldptr[count + width] + + oldptr[count - width] + + oldptr[count + 1] + + oldptr[count - 1] + + oldptr[count - width - 1] + + oldptr[count - width + 1] + + oldptr[count + width - 1] + + oldptr[count + width + 1] + ) >> 2 ) + - newptr[count]; + newptr[count] = newh - (newh >> density); + /* + // This is the "sludge" method... + newh = (oldptr[count]<<2) + + oldptr[count-1-m_iWidth] + + oldptr[count+1-m_iWidth] + + oldptr[count-1+m_iWidth] + + oldptr[count+1+m_iWidth] + + ((oldptr[count-1] + + oldptr[count+1] + + oldptr[count-m_iWidth] + + oldptr[count+m_iWidth])<<1); + + newptr[count] = (newh-(newh>>6)) >> density; + */ + } + } +} + +void MLImageFilterWater::SmoothWater(int page) +{ + int newh; + int count = width + 1; + + int *newptr; + int *oldptr; + + if(page == 0) + { + newptr = hField1; + oldptr = hField2; + } + else + { + newptr = hField2; + oldptr = hField1; + } + + int x, y; + + for(y = 1; y < height; y++, count += 2) + { + for( x = 1; x < width; x++, count++) + { + // This does the eight-pixel method. + + newh = ((oldptr[count + width] + + oldptr[count - width] + + oldptr[count + 1] + + oldptr[count - 1] + + oldptr[count - width - 1] + + oldptr[count - width + 1] + + oldptr[count + width - 1] + + oldptr[count + width + 1] + ) >> 3 ) + + newptr[count]; + newptr[count] = newh>>1; + } + } +} +void MLImageFilterWater::FlattenWater(void) +{ + int len = width * height * sizeof(int); + SecureZeroMemory(hField1, len); + SecureZeroMemory(hField2, len); +} +void MLImageFilterWater::SineBlob(int x, int y, int radius, int height, int page) +{ + int cx, cy; + int left,top,right,bottom; + double square, dist; + double radsquare = radius * radius; + double length = double((1024.0/(double)radius)*(1024.0/(double)radius)); + int *newptr; + + if(page == 0) + { + newptr = hField1; + } + else + { + newptr = hField2; + } + + int t = (this->width - 2*radius - 1); + if (t == 0) t = 1; + if(x<0) x = 1 + radius + rand() % t; + t = (this->height - 2*radius - 1); + if (t == 0) t = 1; + if(y<0) y = 1 + radius + rand() % t; + + radsquare = (radius*radius); + + left = -radius; right = radius; + top = -radius; bottom = radius; + + // Perform edge clipping... + if(x - radius < 1) left -= (x-radius-1); + if(y - radius < 1) top -= (y-radius-1); + if(x + radius > this->width - 1) right -= (x + radius - this->width + 1); + if(y + radius > this->height - 1) bottom -= (y + radius - this->height + 1); + + for(cy = top; cy < bottom; cy++) + { + for(cx = left; cx < right; cx++) + { + square = cy*cy + cx*cx; + if(square < radsquare) + { + dist = sqrt(square*length); + newptr[this->width*(cy+y) + cx+x] += (int)((cos(dist)+0xffff)*(height)) >> 19; + } + } + } +} + +void MLImageFilterWater::WarpBlob(int x, int y, int radius, int height, int page) +{ + int cx, cy; + int left,top,right,bottom; + int square; + int radsquare = radius * radius; + int *newptr; + + if(page == 0) + { + newptr = hField1; + } + else + { + newptr = hField2; + } + + radsquare = (radius*radius); + + height /= 64; + + left=-radius; right = radius; + top=-radius; bottom = radius; + + // Perform edge clipping... + if(x - radius < 1) left -= (x-radius-1); + if(y - radius < 1) top -= (y-radius-1); + if(x + radius > this->width-1) right -= (x+ radius - this->width + 1); + if(y + radius > this->height-1) bottom-= (y + radius - this->height + 1); + + for(cy = top; cy < bottom; cy++) + { + for(cx = left; cx < right; cx++) + { + square = cy*cy + cx*cx; + if(square < radsquare) + { + newptr[this->width*(cy+y) + cx+x] += int((radius-sqrt((float)square))*(float)(height)); + } + } + } +} +void MLImageFilterWater::HeightBox (int x, int y, int radius, int height, int page) +{ + int cx, cy; + int left,top,right,bottom; + int *newptr; + + if(page == 0) + { + newptr = hField1; + } + else + { + newptr = hField2; + } + + int t = (this->width - 2*radius - 1); + if (t == 0) t = 1; + if(x<0) x = 1 + radius + rand() % t; + t = (this->height - 2*radius - 1); + if (t == 0) t = 1; + if(y<0) y = 1 + radius + rand() % t; + + left=-radius; right = radius; + top=-radius; bottom = radius; + + // Perform edge clipping... + if(x - radius < 1) left -= (x-radius-1); + if(y - radius < 1) top -= (y-radius-1); + if(x + radius > this->width-1) right -= (x+ radius - this->width + 1); + if(y + radius > this->height-1) bottom-= (y + radius - this->height + 1); + + for(cy = top; cy < bottom; cy++) + { + for(cx = left; cx < right; cx++) + { + newptr[this->width*(cy+y) + cx+x] = height; + } + } +} +void MLImageFilterWater::HeightBlob(int x, int y, int radius, int height, int page) +{ + int rquad; + int cx, cy; + int left, top, right, bottom; + + rquad = radius * radius; + + // Make a randomly-placed blob... + int t = (this->width - 2*radius - 1); + if (t == 0) t = 1; + if(x<0) x = 1 + radius + rand() % t; + t = (this->height - 2*radius - 1); + if (t == 0) t = 1; + if(y<0) y = 1 + radius + rand() % t; + + left = -radius; right = radius; + top = -radius; bottom = radius; + + // Perform edge clipping... + if(x - radius < 1) left -= (x-radius-1); + if(y - radius < 1) top -= (y-radius-1); + if(x + radius > this->width-1) right -= (x+ radius - this->width + 1); + if(y + radius > this->height-1) bottom-= (y + radius - this->height + 1); + + for(cy = top; cy < bottom; cy++) + { + int cyq = cy*cy; + for(cx = left; cx < right; cx++) + { + if(cx*cx + cyq < rquad) newptr[this->width * (cy+y) + (cx+x)] += height; + } + } +} + +void MLImageFilterWater::CalcWaterBigFilter(int page, int density) +{ + int newh; + int count = (2 * width) + 2; + + int *newptr; + int *oldptr; + + // Set up the pointers + if(page == 0) + { + newptr = hField1; + oldptr = hField2; + } + else + { + newptr = hField2; + oldptr = hField1; + } + + int x, y; + + for(y=2; y < height-2; y++, count += 4) + { + for(x=2; x < width-2; x++, count++) + { + // This does the 25-pixel method. It looks much okay. + + newh = ( + ( + ( + (oldptr[count + width] + + oldptr[count - width] + + oldptr[count + 1] + + oldptr[count - 1] + )<<1) + + ((oldptr[count - width - 1] + + oldptr[count - width + 1] + + oldptr[count + width - 1] + + oldptr[count + width + 1])) + + ( ( + oldptr[count - (width*2)] + + oldptr[count + (width*2)] + + oldptr[count - 2] + + oldptr[count + 2] + ) >> 1 ) + + ( ( + oldptr[count - (width*2) - 1] + + oldptr[count - (width*2) + 1] + + oldptr[count + (width*2) - 1] + + oldptr[count + (width*2) + 1] + + oldptr[count - 2 - width] + + oldptr[count - 2 + width] + + oldptr[count + 2 - width] + + oldptr[count + 2 + width] + ) >> 2 ) + ) + >> 3) + - (newptr[count]); + + + newptr[count] = newh - (newh >> density); + } + } +} + +void MLImageFilterWater::DrawWaterNoLight(int page, MLImage* destination, const MLImage* source) +{ + unsigned int brk = width * height; + + int *ptr = hField1; + + DWORD *dataS = (DWORD*)source->GetData(); + DWORD *dataD = (DWORD*)destination->GetData(); + + for (unsigned int offset = 0; offset < brk; offset++) + { + int dx = ptr[offset] - ptr[offset + 1]; + int dy = ptr[offset] - ptr[offset + width]; + unsigned int index = offset + width * (dy>>3) + (dx>>3); + dataD[offset] = (index < brk ) ? dataS[offset + width*(dy>>3) + (dx>>3)] : dataS[offset]; + } +} + +void MLImageFilterWater::DrawWaterWithLight(MLImage* destination, const MLImage* source) +{ + unsigned int brk = width * height; + + int *ptr = hField1; + + DWORD *dataS = (DWORD*)source->GetData(); + DWORD *dataD = (DWORD*)destination->GetData(); + + for (unsigned int offset = 0; offset < brk; offset++) + { + int dx = ptr[offset] - ptr[offset + 1]; + int dy = ptr[offset] - ptr[offset + width]; + unsigned int index = offset + width * (dy>>3) + (dx>>3); + dataD[offset] = (index < brk ) ? GetShiftedColor(dataS[index], dx) : dataS[offset]; + } +} +COLORREF MLImageFilterWater::GetShiftedColor(COLORREF color,int shift) +{ + int R,G, B; + int r, g, b; + + R = GetRValue(color)-shift; + G = GetGValue(color)-shift; + B = GetBValue(color)-shift; + + r = (R < 0) ? 0 : (R > 255) ? 255 : R; + g = (G < 0) ? 0 : (G > 255) ? 255 : G; + b = (B < 0) ? 0 : (B > 255) ? 255 : B; + + return RGB(r,g,b); +} diff --git a/Src/Plugins/Input/in_mp3/graphics/filterWater.h b/Src/Plugins/Input/in_mp3/graphics/filterWater.h new file mode 100644 index 00000000..21ed92c0 --- /dev/null +++ b/Src/Plugins/Input/in_mp3/graphics/filterWater.h @@ -0,0 +1,47 @@ +#ifndef NULLSOFT_ML_IMAGE_FILTERWATER_HEADER +#define NULLSOFT_ML_IMAGE_FILTERWATER_HEADER + +#include <windows.h> +#include ".\image.h" + +class MLImageFilterWater +{ +public: + MLImageFilterWater(void); + ~MLImageFilterWater(void); + +public: + BOOL CreateFor(const MLImage *image); + void Render(MLImage* destination, const MLImage* source); + + void CalculateWater(int page, int density); + void SmoothWater(int page); + void FlattenWater(void); + + void SineBlob(int x, int y, int radius, int height, int page); + void WarpBlob(int x, int y, int radius, int height, int page); + void HeightBox (int x, int y, int radius, int height, int page); + void HeightBlob(int x, int y, int radius, int height, int page); + +protected: + void ClearData(void); + void CalcWaterBigFilter(int page, int density); + void DrawWaterNoLight(int page,MLImage* destination, const MLImage* source); + void DrawWaterWithLight(MLImage* destination, const MLImage* source); + COLORREF GetShiftedColor(COLORREF color,int shift); + +private: + HANDLE hHandle; + int height; + int width; + + BOOL drawWithLight; + int lightModifier; + int hPage; + int density; + + int* hField1; + int* hField2; +}; + +#endif //#define NULLSOFT_ML_IMAGE_FILTERWATER_HEADER
\ No newline at end of file diff --git a/Src/Plugins/Input/in_mp3/graphics/image.cpp b/Src/Plugins/Input/in_mp3/graphics/image.cpp new file mode 100644 index 00000000..2e3cda46 --- /dev/null +++ b/Src/Plugins/Input/in_mp3/graphics/image.cpp @@ -0,0 +1,209 @@ +#include ".\image.h" + +MLImage::MLImage(void) +{ + loader = NULL; + loaderDelete = TRUE; + ResetData(); +} + +MLImage::MLImage(IMGLOADFUNC loader, BOOL deleteDone) +{ + ResetData(); + SetLoader(loader, deleteDone, FALSE); +} + +MLImage::MLImage(int width, int height) +{ + loader = NULL; + ResetData(); + Init(width,height); +} + +MLImage::~MLImage(void) +{ + ResetData(); +} + +INT_PTR MLImage::SetLoader(IMGLOADFUNC loader, BOOL deleteDone, BOOL forceLoad) +{ + this->loader = loader; + this->loaderDelete = deleteDone; + if (loader && forceLoad) Load(); + return (loader != NULL) ? (INT_PTR) this : FALSE; +} + +BOOL MLImage::Load(void) +{ + ResetData(); + + if (!loader) return FALSE; + HBITMAP hbmpLoaded = loader((INT_PTR)this); + if(hbmpLoaded == NULL) return FALSE; + + BITMAP bi; + if (GetObject(hbmpLoaded, sizeof(bi), &bi)) + { + hbmp = ConvertTo32BppDIB(hbmpLoaded, bi.bmWidth, bi.bmHeight, &info, &data); + } + + if (loaderDelete) DeleteObject(hbmpLoaded); + return (hbmp != NULL); +} + +void MLImage::ResetData(void) +{ + if (hbmp) DeleteObject(hbmp); + hbmp = NULL; + SecureZeroMemory(&info, sizeof(BITMAPINFO)); + data = NULL; +} + +BOOL MLImage::Draw(HDC hdcDest, int destX, int destY, int destWidth, int destHeight, int sourceX, int sourceY) +{ + if (!hbmp) return FALSE; + + int realheight = abs(info.bmiHeader.biHeight); + int rsX = min(sourceX, info.bmiHeader.biWidth); + int rsY = min(sourceY, info.bmiHeader.biWidth); + int height = min(destHeight, realheight - rsY); + + BOOL bResult = SetDIBitsToDevice( hdcDest, destX, destY, + min(destWidth, info.bmiHeader.biWidth - rsX), height, + rsX, realheight - height - rsY, + 0, height, + data, &info, DIB_RGB_COLORS); + return bResult; +} + +BOOL MLImage::Draw(HDC hdcDest, int destX, int destY) +{ + return (!hbmp) ? FALSE : SetDIBitsToDevice( hdcDest, destX, destY, + info.bmiHeader.biWidth, abs(info.bmiHeader.biHeight), + 0, 0, + 0, abs(info.bmiHeader.biHeight), + data, &info, DIB_RGB_COLORS); +} + +int MLImage::GetWidth(void) const +{ + return (hbmp) ? info.bmiHeader.biWidth : 0; +} + +int MLImage::GetHeight(void) const +{ + return (hbmp) ? abs(info.bmiHeader.biHeight) : 0; +} + +void* MLImage::GetData(void) const +{ + return data; +} + +HBITMAP MLImage::ConvertTo32BppDIB(HBITMAP bmpHandle, int bmpWidth, int bmpHeight, LPBITMAPINFO bmpInfo, LPVOID *bmpData) +{ + HBITMAP hbmpNew = NULL; + + HDC hdc = GetWindowDC(NULL); + HDC hdcTmp = CreateCompatibleDC(hdc); + HBITMAP hbmpTmp = CreateCompatibleBitmap(hdc, bmpWidth, bmpHeight); + HBITMAP hbmpOld = (HBITMAP) SelectObject(hdcTmp, hbmpTmp); + + // render original bitmap to the temp dc + HDC hdcBmp = CreateCompatibleDC(hdc); + SelectObject(hdcBmp, bmpHandle); + BitBlt(hdcTmp, 0, 0, bmpWidth, bmpHeight, hdcBmp, 0,0, SRCCOPY); + SelectObject(hdcBmp, NULL); + DeleteDC(hdcBmp); + + // Create a 32 bit bitmap + BITMAPINFO bih; + // create DIB Section + bih.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); + bih.bmiHeader.biWidth = bmpWidth; + bih.bmiHeader.biHeight = 0 - bmpHeight; + bih.bmiHeader.biPlanes = 1; + bih.bmiHeader.biBitCount = 32; + bih.bmiHeader.biCompression = BI_RGB; + bih.bmiHeader.biSizeImage = 0; + bih.bmiHeader.biXPelsPerMeter = 0; + bih.bmiHeader.biYPelsPerMeter = 0; + bih.bmiHeader.biClrUsed = 0; + bih.bmiHeader.biClrImportant = 0; + + // Create a DC which will be used to get DIB, then create DIBsection + hbmpNew = CreateDIBSection(hdc, (const BITMAPINFO*) &bih, DIB_RGB_COLORS, bmpData, NULL, 0); + + + DWORD* line = (DWORD*)(*bmpData); + // Copy the bits into our 32 bit dib.. + for(int i=0; i<bmpHeight; i++) + { + for(int j=0; j<bmpWidth; j++) + { + line[(i*bmpWidth) + j] = FIXCOLORREF(GetPixel(hdcTmp, j, i)); + } + } + + SelectObject(hdcTmp, hbmpOld); + ReleaseDC(NULL, hdc); + DeleteDC(hdcTmp); + + memcpy(bmpInfo, &bih, sizeof(BITMAPINFO)); + + return hbmpNew; +} + +MLImage* MLImage::Copy(MLImage* destination, const MLImage* original) +{ + if (!destination) return NULL; + + destination->ResetData(); + + destination->loader = original->loader; + destination->loaderDelete = original->loaderDelete; + destination->info = original->info; + HDC hdc = GetWindowDC(NULL); + destination->hbmp = CreateDIBSection(hdc, (const BITMAPINFO*) &destination->info, DIB_RGB_COLORS, &destination->data, NULL, 0); + + CopyMemory(destination->data, original->data, 4*destination->GetHeight() * destination->GetWidth()); + ReleaseDC(NULL, hdc); + return destination; +} + +MLImage* MLImage::Init(int width, int height) +{ + ResetData(); + + loader = NULL; + loaderDelete = TRUE; + + // create DIB Section + info.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); + info.bmiHeader.biWidth = width; + info.bmiHeader.biHeight = 0 - height; + info.bmiHeader.biPlanes = 1; + info.bmiHeader.biBitCount = 32; + info.bmiHeader.biCompression = BI_RGB; + info.bmiHeader.biSizeImage = 0; + info.bmiHeader.biXPelsPerMeter = 0; + info.bmiHeader.biYPelsPerMeter = 0; + info.bmiHeader.biClrUsed = 0; + info.bmiHeader.biClrImportant = 0; + + HDC hdc = GetWindowDC(NULL); + hbmp = CreateDIBSection(hdc, (const BITMAPINFO*) &info, DIB_RGB_COLORS, &data, NULL, 0); + ReleaseDC(NULL, hdc); + return this; +} + +MLImage* MLImage::Init(int width, int height, COLORREF color) +{ + Init(width, height); + + int rColor = FIXCOLORREF(color); + DWORD *line = (DWORD*)(data); + DWORD *end = line + GetHeight() * GetWidth(); + for(;line != end; line++) *line = rColor; + return this; +}
\ No newline at end of file diff --git a/Src/Plugins/Input/in_mp3/graphics/image.h b/Src/Plugins/Input/in_mp3/graphics/image.h new file mode 100644 index 00000000..72a4aa5d --- /dev/null +++ b/Src/Plugins/Input/in_mp3/graphics/image.h @@ -0,0 +1,61 @@ +#ifndef NULLSOFT_ML_IMAGE_HEADER +#define NULLSOFT_ML_IMAGE_HEADER + +#include <windows.h> + +#define RGBA(r,g,b,a) ((COLORREF)(((BYTE)(r)|((WORD)(g)<<8))|(((DWORD)(BYTE)(b))<<16)|(((DWORD)(BYTE)(a))<<24))) +#define FIXCOLORREF(clr) RGBA(GetBValue(clr),GetGValue(clr), GetRValue(clr),((DWORD)(clr)) >> 24) + +// loader function will be called every time MLImage need to +// reload picture. Input parameter - handle to the calling object +// Output - loaded bitmap +typedef HBITMAP (*IMGLOADFUNC)(INT_PTR handle); + +class MLImage +{ +public: + MLImage(void); + MLImage(IMGLOADFUNC loader, BOOL deleteDone); + MLImage(int width, int height); + ~MLImage(void); + +public: + // sets the loader function and returns handle to the class or NULL if error + // loader - pointer to the loader function + // deleteDone - if TRUE MLImage will delete HBITMAP object from loader every time it is done loading + // forceLoad - forcing to load bitamp immedialty by calling Load() + INT_PTR SetLoader(IMGLOADFUNC loader, BOOL deleteDone, BOOL forceLoad); + BOOL Load(void); // load image + + MLImage* Init(int width, int height); // init image (allocates memory) + MLImage* Init(int width, int height, COLORREF color); // init image (allocates memory) and set + + BOOL Draw(HDC hdcDest, int destX, int destY, int destWidth, int destHeight, int sourceX, int sourceY); // draw image + BOOL Draw(HDC hdcDest, int destX, int destY); // draw image + +public: + int GetWidth(void) const; + int GetHeight(void) const; + void* GetData(void) const; + + +private: + void ResetData(void); + +public: + static MLImage* Copy(MLImage* destination, const MLImage* original);// copy all data from the original object (including image data) to the destination + +private: + static HBITMAP ConvertTo32BppDIB(HBITMAP bmpHandle, int bmpWidth, int bmpHeight, LPBITMAPINFO bmpInfo, LPVOID *bmpData); + +private: + IMGLOADFUNC loader; // pointer to the loader function + BOOL loaderDelete; // TRUE - delete HBITMAP from loader after load + + HBITMAP hbmp; // my bitmap + BITMAPINFO info; + void *data; +}; + +#endif // NULLSOFT_ML_IMAGE_HEADER + diff --git a/Src/Plugins/Input/in_mp3/graphics/imageFilters.cpp b/Src/Plugins/Input/in_mp3/graphics/imageFilters.cpp new file mode 100644 index 00000000..59d994ed --- /dev/null +++ b/Src/Plugins/Input/in_mp3/graphics/imageFilters.cpp @@ -0,0 +1,91 @@ +#include ".\imagefilters.h" + +void MLImageFilter_GrayScale(MLImage *image) +{ + DWORD *line = (DWORD*)(image->GetData()); + DWORD *end = line + image->GetHeight() * image->GetWidth(); + for(;line != end; line++) + { + BYTE y = (BYTE)(0.3f * GetBValue(*line) + 0.59f *GetGValue(*line) + 0.11f *GetRValue(*line)); + *line = RGB(y,y,y); + } +} + +void MLImageFilter_Invert(MLImage *image) +{ + DWORD *line = (DWORD*)(image->GetData()); + DWORD *end = line + image->GetHeight() * image->GetWidth(); + for(;line != end; line++) *line = ((~*line) & 0x00FFFFFF) | (*line & 0xFF000000); +} + +void MLImageFilter_SetToColor(MLImage *image, COLORREF color) +{ + COLORREF rColor = FIXCOLORREF(color); + DWORD *line = (DWORD*)(image->GetData()); + DWORD *end = line + image->GetHeight() * image->GetWidth(); + for(;line != end; line++) *line = rColor; +} + +void MLImageFilter_Fader1(MLImage *dest, const MLImage* source, COLORREF color) +{ + int len = dest->GetHeight() * dest->GetWidth(); + BYTE r = GetRValue(color), g = GetGValue(color), b = GetBValue(color); + + DWORD *dataS = (DWORD*)(source->GetData()); + DWORD *dataD = (DWORD*)(dest->GetData()); + DWORD *end = dataD + len; + for(;dataD != end; dataD++, dataS++) + { + *dataD = RGB( max(b, GetRValue(*dataS)), max(g, GetGValue(*dataS)), max(r, GetBValue(*dataS))) ; + } +} + +void MLImageFilter_Fader2(MLImage *dest, const MLImage* source, COLORREF color) +{ + int len = dest->GetHeight() * dest->GetWidth(); + BYTE r = GetRValue(color), g = GetGValue(color), b = GetBValue(color); + + DWORD *dataS = (DWORD*)(source->GetData()); + DWORD *dataD = (DWORD*)(dest->GetData()); + DWORD *end = dataD + len; + for(;dataD != end; dataD++, dataS++) + { + *dataD = RGB( min(b, GetRValue(*dataS)), min(g, GetGValue(*dataS)), min(r, GetBValue(*dataS))) ; + } +} + +void MLImageFilter_Fader3(MLImage *dest, const MLImage* source, int koeff) +{ + int len = dest->GetHeight() * dest->GetWidth(); + + DWORD *dataS = (DWORD*)(source->GetData()); + DWORD *dataD = (DWORD*)(dest->GetData()); + DWORD *end = dataD + len; + for(;dataD != end; dataD++, dataS++) + { + *dataD = RGB(min(255,GetRValue(*dataS) + koeff), min(255,GetGValue(*dataS) + koeff), min(255, GetBValue(*dataS) + koeff)); + } +} + +void MLImageFilter_Blend1(MLImage *dest, MLImage *src1, int destX, int destY, int width, int height, const MLImage* src2, int srcX, int srcY, COLORREF color) +{ + int widthS1 = src1->GetWidth(); + int widthS2 = src2->GetWidth(); + + DWORD *dataD = (DWORD*)(dest->GetData()) + destY * widthS1 + destX; + DWORD *dataS1 = (DWORD*)(src1->GetData()) + destY * widthS1 + destX; + DWORD *dataS2 = (DWORD*)(src2->GetData()) + srcY * widthS2 + srcX; + + DWORD *curS1; + + for (int y = 0; y < height; y++) + { + DWORD *curD = dataD + y * widthS1; + curS1 = dataS1 + y * widthS1; + DWORD *curS2 = dataS2 + y * widthS2; + for (DWORD *end = curS1 + width; end != curS1; curD++, curS1++, curS2++) + { + *curD = (*curS1 == color) ? *curS2 : *curS1; + } + } +}
\ No newline at end of file diff --git a/Src/Plugins/Input/in_mp3/graphics/imageFilters.h b/Src/Plugins/Input/in_mp3/graphics/imageFilters.h new file mode 100644 index 00000000..ebb1c752 --- /dev/null +++ b/Src/Plugins/Input/in_mp3/graphics/imageFilters.h @@ -0,0 +1,17 @@ +#ifndef NULLSOFT_ML_IMAGE_FILTER_HEADER +#define NULLSOFT_ML_IMAGE_FILTER_HEADER + +#include <windows.h> +#include ".\image.h" +#include ".\filterwater.h" + +void MLImageFilter_GrayScale(MLImage *image); +void MLImageFilter_Invert(MLImage *image); +void MLImageFilter_SetToColor(MLImage *image, COLORREF color); +void MLImageFilter_Fader1(MLImage *dest, const MLImage* source, COLORREF color); +void MLImageFilter_Fader2(MLImage *dest, const MLImage* source, COLORREF color); +void MLImageFilter_Fader3(MLImage *dest, const MLImage* source, int koeff); +void MLImageFilter_Blend1(MLImage *dest, MLImage *src1, int destX, int destY, int width, int height, const MLImage* src2, int srcX, int srcY, COLORREF color); + + +#endif //NULLSOFT_ML_IMAGE_FILTER_HEADER |