home *** CD-ROM | disk | FTP | other *** search
- //
- // DJ Mix Pro visualisation plugin example :
- //
- // Pulsing Star
- //
- // (C) 2001 Beatlock Technology
- //
- //
- // See comments in "DJMixPlugin.h"
- // but don't expect a real documentation
- //
- //
- // The resulting DLL is to be dropped in the DJ Mix Pro
- // plugins folder
- //
-
-
-
- /* includes for this plugin */
- #include "math.h"
- #include "windows.h"
- #include "windowsx.h"
- #include "string.h"
- #include "stdio.h"
-
- /* mandatory DJ Mix Pro plugin include */
- #include "Pulsing.h"
-
- //cache for costfull values
- short cosvals[256];
- short sinvals[256];
-
- //usual colors
- COLORREF BACKBRUSH = GetSysColor(COLOR_BTNFACE);
- COLORREF MONOBRUSH = GetSysColor(COLOR_BTNSHADOW);
- COLORREF BLUEBRUSH = RGB(0,0,255);
- COLORREF GREENBRUSH = RGB(0,255,0);
- COLORREF REDBRUSH = RGB(255,0,0);
- COLORREF YELLOWBRUSH= RGB(255,255,0) ;
- COLORREF PINKBRUSH= RGB(255,128,255) ;
- COLORREF BRAWNBRUSH = RGB(255,0,255);
- COLORREF ORANGEBRUSH = RGB(255,128,0);
- COLORREF VIOLETBRUSH = RGB(255,0,255);
- COLORREF CYANBRUSH = RGB(0,255,255);
- COLORREF OLIVEBRUSH = RGB(0,128,0);
- COLORREF WHITEBRUSH = RGB(255,255,255);
- COLORREF BLACKBRUSH = RGB(0,0,0);
-
- //name of plugin
- char* Pulsing::name = "Pulsing star";
-
- //events dispatcher, for a windows plugin
- LRESULT CALLBACK MainWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam){
- HDC hdc;
- PAINTSTRUCT ps;
-
- //get back object
- Pulsing* me =(Pulsing*) GetWindowLong(hwnd,GWL_USERDATA);
-
- //not yet.
- if ( ! me)
- return DefWindowProc(hwnd,msg,wParam,lParam);
-
- switch (msg) {
-
-
- case WM_PAINT:
- //redraw in window
- hdc = BeginPaint(hwnd,&ps);
- me->Redraw(hdc);
- EndPaint(hwnd,&ps);
- break;
-
-
- case WM_CLOSE:
- //we MUST notify DJ Mix Pro when plugin is closing
- SendMessage(me->parent, PLUGGINUNLOADED, 0, 0);
- break;
-
- }
- //Default windows processing
- return DefWindowProc(hwnd,msg,wParam,lParam);
- }
-
-
-
-
- //load is when user selects this plugin in menu
- void Pulsing::Load(HINSTANCE instance, HWND parent)
- {
- Pulsing::parent = parent;
- numrecorded=0;
- bpm = -1;
- lastclosest=0.;
- //cache sin and cos values
- #define PI 3.14159265358979323846
- for (int i = 0; i < 256; i++ ) {
- cosvals[i] = (short) ( (double)(1 << 14) * cos( i * 2. * PI / 256. ));
- sinvals[i] = (short) ( (double)(1 << 14) * sin( i * 2. * PI / 256. ));
- }
-
-
- //create window class
- WNDCLASS cls;
- const DWORD dwExStyle = 0;
- cls.hCursor = LoadCursor(NULL,IDC_ARROW);
- cls.hIcon = LoadIcon(instance,IDI_APPLICATION);
- cls.lpszMenuName = 0;
- cls.lpszClassName = "Pluggin";
- cls.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
- cls.hInstance = instance;
- cls.style = CS_BYTEALIGNCLIENT ;
- cls.lpfnWndProc = MainWndProc;
- cls.cbWndExtra = 0;
- cls.cbClsExtra = 0;
- RegisterClass(&cls);
-
- //create window itself, child of parent here.
- win=CreateWindowEx(dwExStyle,
- "Pluggin", // Class name
- "Pulsing star", // Caption
- WS_OVERLAPPEDWINDOW, // Style bits
- CW_USEDEFAULT, 0, // Position
- 200,200, // Size
- (HWND)parent, // Parent window
- (HMENU)NULL, // use class menu
- instance, // handle to window instance
- (LPSTR)NULL // no params to pass on
- );
-
- //if failed :
- if ( ! win) {
- //we MUST notify plugin is closing
- SendMessage(parent, PLUGGINUNLOADED, 0, 0);
- return;
- }
-
- //store object pointer
- SetWindowLong(win,GWL_USERDATA, (long)this);
-
- ShowWindow(win,SW_SHOW);
- }
- //unload is when another plugin is being loaded (changing)
- /* this plugin must then do some cleanup */
- void Pulsing::Unload()
- {
- if (win) {
- DestroyWindow(win);
- win = 0;
- }
- }
-
- //returns plugin name to DJ Mix Pro, to display in menu
- char* Pulsing::GetName() {
- return name;
- }
-
- //receive beat information . double parameters are in seconds,
- //but with no continuity guarantee. Programmer must
- //always check there was no position move in between
- //using "which" (gives the beat "number")
- //
- void Pulsing::Refresh(double where, double closest, long which){
- Pulsing::where = where;
- Pulsing::closest = closest;
-
-
- //record closest beat position
- //is supposed to smooth BPM value
- if ( lastwhich == -1){
- lastclosest= closest;
- lastwhich = which;
- }
- if ( lastwhich != which) {
- //check if there is a discontinuity
- if ( lastwhich +1 == which ) {
- lastclosesthist[numrecorded%NUMRECORDS] = closest-lastclosest;
- numrecorded++;
- }
- lastclosest= closest;
- lastwhich= which;
-
- if ( numrecorded >0) {
- double sum = 0;
- int count = 0;
- for ( int i = 0; i < numrecorded &&i <NUMRECORDS; i++){
- if (lastclosesthist[i]){
- sum += lastclosesthist[i];
- count++;
- }
-
- }
- if ( count) {
- sum /= numrecorded>NUMRECORDS?NUMRECORDS: numrecorded ;
- bpm = 60. / sum;
- }else {
- bpm = -1;
- }
-
- }else {
- //default value for unknown BPM
- bpm = -1;
- }
-
- }
- //force window to redraw
- RECT rc ;
- GetClientRect(win, &rc);
- InvalidateRect(win, &rc, FALSE);
- UpdateWindow(win);
- }
-
- void Pulsing::Redraw(HDC hdc)
- {
-
- //processing redraw order
- RECT rc ;
- //get window size
- GetClientRect(win, &rc);
- int w,h;
- w = rc.right - rc.left;
- h = rc.bottom - rc.top;
-
-
-
- //beatfactor is distance from here to closest beat in percent
- //( 100 on a beat, 0 just in the middle of 2 beats )
- //interval between 2 beats is 60. / bpm
- //so "here" is about between last beat and next beat
- //if we want to have 100% on a beat pos
- // and 0% in the middle here is the formula (trust me...)
- double beatFactor = 100. - fabs(where-closest) * 2 *100 / ( 60. / bpm );
- if ( beatFactor <0)
- beatFactor =0;
- if (beatFactor >100)
- beatFactor =100;
-
- //if beatFactor didnt change, nothing to redraw
- if ( beatFactor==lastBeatFactor)
- return;
-
- //smallest dimension of window
- int radius = w > h ? h:w;
- radius = (int)(radius * beatFactor / 250);
-
- // Paint (erase) the background in standard color
- HBRUSH hbr;
- hbr = (HBRUSH)SelectObject(hdc, CreateSolidBrush(BACKBRUSH));
- PatBlt(hdc, rc.left, rc.top, w , h , PATCOPY);
- DeleteObject(SelectObject(hdc, hbr));
-
- HPEN hpen = (HPEN) SelectObject(hdc,CreatePen( PS_NULL, 0, REDBRUSH ));
- hbr = (HBRUSH) SelectObject(hdc, CreateSolidBrush(REDBRUSH));
- //draw Filled Star ( 10 points, odd points have
- POINT p[10];
-
- //star is turning slowly
- int startangle = ((long)where) % 60 * 256 / 60;
- for ( int i = 0; i < 10; i++ ) {
- int pointradius;
- if ( i % 2 )
- pointradius = radius /2;
- else
- pointradius = radius*3/2;
- p[i].x = (rc.right +rc.left) / 2 + pointradius * sinvals[ ( startangle + i * 256 / 10 ) %256] / (1 << 14) ;
- p[i].y = (rc.bottom +rc.top) / 2 - pointradius * cosvals[ ( startangle + i * 256 / 10 ) %256] / (1 << 14);
- }
- Polygon( hdc, p,10);
-
- DeleteObject(SelectObject(hdc, hbr));
- DeleteObject(SelectObject(hdc, hpen));
-
- int TEXTMYHEIGHT = w > h ? h:w;
- TEXTMYHEIGHT /= 3;
-
- //now draw BPM text string
- char msg[32] ;
- if ( bpm > 0)
- sprintf (msg, "%3.1lf", bpm);
- else
- strcpy(msg, "???");
-
- int prevmode2 = SetBkMode(hdc, TRANSPARENT);
- COLORREF prevcolor2 = SetTextColor( hdc, YELLOWBRUSH);
- UINT lastAlign = SetTextAlign( hdc,TA_CENTER|TA_BASELINE );
-
- //this would need font caching for performance
- HFONT hfont = (HFONT) SelectObject(hdc,
- CreateFont( TEXTMYHEIGHT, // logical height of font
- 0, // logical average character width
- 0, // angle of escapement
- 0, // base-line orientation angle
- FW_NORMAL , // font weight
- FALSE, // italic attribute flag
- FALSE, // underline attribute flag
- FALSE, // strikeout attribute flag
- ANSI_CHARSET, // character set identifier
- OUT_DEFAULT_PRECIS, // output precision
- CLIP_DEFAULT_PRECIS , // clipping precision
- DEFAULT_QUALITY , // output quality
- DEFAULT_PITCH, // pitch and family
- 0 // pointer to typeface name string
- )
- );
-
- TextOut(hdc, (rc.right +rc.left) / 2, (rc.bottom +rc.top)/2+TEXTMYHEIGHT/4, msg, lstrlen(msg));
- DeleteObject(SelectObject(hdc, hfont));
-
- SetBkMode(hdc, prevmode2);
- SetTextColor( hdc, prevcolor2);
- SetTextAlign( hdc,lastAlign);
-
-
-
- }
-
- //only published func of the plugin DLL.
- //builds an object.
- //all other functions are vitual methods of object.
- extern "C"
- __declspec( dllexport ) DJMixPlugin* CreateFunc() {
- return new Pulsing();
- }