Beispiel #1
0
void WIMP_Poll(_THIS, int waitTime)
{
	_kernel_swi_regs regs;
	int message[64];
	unsigned int code;
	int pollMask = 0;
	int doPoll = 1;
	int sysEvent;
	int sdlWindow = this->hidden->window_handle;

    if (this->PumpEvents != WIMP_PumpEvents) return;

    if (waitTime > 0)
    {
		_kernel_swi(OS_ReadMonotonicTime, &regs, &regs);
		waitTime += regs.r[0];
    }

    while (doPoll)
    {
        if (waitTime <= 0)
        {
        	regs.r[0] = pollMask; /* Poll Mask */
        	 /* For no wait time mask out null event so we wait until something happens */
        	if (waitTime < 0) regs.r[0] |= 1;
        	regs.r[1] = (int)message;
        	_kernel_swi(Wimp_Poll, &regs, &regs);
        } else
        {
        	regs.r[0] = pollMask;
        	regs.r[1] = (int)message;
        	regs.r[2] = waitTime;
        	_kernel_swi(Wimp_PollIdle, &regs, &regs);
        }

		/* Flag to specify if we post a SDL_SysWMEvent */
		sysEvent = 0;
        
        code = (unsigned int)regs.r[0];

		switch(code)
		{
		case 0:  /* Null Event - drop out for standard processing*/
		   doPoll = 0;
		   break;

		case 1:     /* Redraw window */
        	_kernel_swi(Wimp_RedrawWindow, &regs,&regs);
			if (message[0] == sdlWindow)
			{
        		while (regs.r[0])
        		{
        			WIMP_PlotSprite(this, message[1], message[2]);
        			_kernel_swi(Wimp_GetRectangle, &regs, &regs);
        		}
			} else
			{
				/* TODO: Currently we just eat them - we may need to pass them on */
        		while (regs.r[0])
        		{
        			_kernel_swi(Wimp_GetRectangle, &regs, &regs);
        		}
			}
        	break;
        	
		case 2:		/* Open window */
		   if ( resizeOnOpen && message[0] == sdlWindow)
		   {
		      /* Ensure window is correct size */
		      resizeOnOpen = 0;
		      message[3] = message[1] + (this->screen->w << this->hidden->xeig);
		      message[4] = message[2] + (this->screen->h << this->hidden->yeig);       
		   }
        	_kernel_swi(Wimp_OpenWindow, &regs, &regs);
       	    break;
        	
		case 3:		/* Close window */
			if (message[0] == sdlWindow)
			{
				/* Documentation makes it looks as if the following line is correct:
				**    if (SDL_PrivateQuit() == 1) _kernel_swi(Wimp_CloseWindow, &regs, &regs);
				** However some programs don't process this message and so sit there invisibly
				** in the background so I just post the quit message and hope the application
				** does the correct thing.
				*/
				SDL_PrivateQuit();
			} else
				sysEvent = 1;
        	doPoll = 0;
        	break;

		case 4: /* Pointer_Leaving_Window */
			if (message[0] == sdlWindow)
			{
				mouseInWindow = 0;
				//TODO: Lose buttons / dragging
				 /* Reset to default pointer */
   				 regs.r[0] = 106;
				 regs.r[1] = 1;
				 regs.r[2] = 0;
				 _kernel_swi(OS_Byte, &regs, &regs);
				 SDL_PrivateAppActive(0, SDL_APPMOUSEFOCUS);
			} else
				sysEvent = 1;
			break;

		case 5: /* Pointer_Entering_Window */
			if (message[0] == sdlWindow) 
			{
				mouseInWindow = 1;
				WIMP_ReshowCursor(this);
				SDL_PrivateAppActive(1, SDL_APPMOUSEFOCUS);
			} else sysEvent = 1;
			break;

		case 6:		/* Mouse_Click */
			if (hasFocus == 0)
			{
			   /* First click gives focus if it's not a menu */
			   /* we only count non-menu clicks on a window that has the focus */
			   WIMP_SetFocus(message[3]);
			} else
				doPoll = 0; // So PollMouse gets a chance to pick it up
		   break;

		case 7: /* User_Drag_Box - Used for mouse release */
			//TODO: May need to implement this in the future
			sysEvent = 1;
			break;

		case 8: /* Keypressed */
			doPoll = 0; /* PollKeyboard should pick it up */
			if (message[0] != sdlWindow) sysEvent = 1;
			/*TODO: May want to always pass F12 etc to the wimp
			{
				regs.r[0] = message[6];
				_kernel_swi(Wimp_ProcessKey, &regs, &regs);
			}
			*/
			break;

		case 11: /* Lose Caret */
			 hasFocus = 0;
			 if (message[0] == sdlWindow) SDL_PrivateAppActive(0, SDL_APPINPUTFOCUS);
			 else sysEvent = 1;
			 break;

		case 12: /* Gain Caret */
			 hasFocus = 1;
			 if (message[0] == sdlWindow) SDL_PrivateAppActive(1, SDL_APPINPUTFOCUS);
			 else sysEvent = 1;
			 break;
        	
		case 17:
		case 18:
			sysEvent = 1; /* All messages are passed on */

			switch(message[4])
			{
			case 0: /* Quit Event */
				/* No choice - have to quit */
			   SDL_Quit();
        	   exit(0);
			   break;

			case 8: /* Pre Quit */
				SDL_PrivateQuit();
				break;

			case 0x400c1: /* Mode change */
				WIMP_ModeChanged(this);
				resizeOnOpen = 1;
				break;

			case 9:      /* Palette changed */
				WIMP_PaletteChanged(this);
				break;
			}
			break;

		default:
			/* Pass unknown events on */
			sysEvent = 1;
			break;
		}

		if (sysEvent)
		{
	        SDL_SysWMmsg wmmsg;

			SDL_VERSION(&wmmsg.version);
			wmmsg.eventCode = code;
			memcpy(wmmsg.pollBlock, message, 64 * sizeof(int));

			/* Fall out of polling loop if message is successfully posted */
			if (SDL_PrivateSysWMEvent(&wmmsg)) doPoll = 0;
		}

    }
}
/* Setup the Window to display the surface */
unsigned int WIMP_SetupWindow(_THIS, SDL_Surface *surface)
{
	_kernel_swi_regs regs;
	int window_data[23];
    int	*window_block = window_data+1;
	int x = (this->hidden->screen_width - surface->w) / 2;
	int y = (this->hidden->screen_height - surface->h) / 2;
	int xeig = this->hidden->xeig;
	int yeig = this->hidden->yeig;

    mouseInWindow = 0;
    
	/* Always delete the window and recreate on a change */
	if (this->hidden->window_handle) WIMP_DeleteWindow(this);

	/* Setup window co-ordinates */
   window_block[0] = x << xeig;
   window_block[1] = y << yeig;
   window_block[2] = window_block[0] + (surface->w << xeig);
   window_block[3] = window_block[1] + (surface->h << yeig);

   
   window_block[4] = 0;				  /* Scroll offsets */
   window_block[5] = 0;
   window_block[6] = -1;			  /* Open on top of window stack */

   window_block[7] = 0x85040042;      /* Window flags */
   if (riscos_closeaction != 0) window_block[7] |= 0x2000000;

   /* TODO: Take into account surface->flags */

   window_block[8] = 0xff070207;      /* Window colours */
   window_block[9] = 0x000c0103;
   window_block[10] = 0;                    /* Work area minimum */
   window_block[11] = -surface->h << yeig;
   window_block[12] = surface->w << xeig;   /* Work area maximum */
   window_block[13] = 0;
   window_block[14] = 0x2700013d;    /* Title icon flags */
   window_block[15] = 0x00003000;	 /* Work area flags - Mouse click down reported */
   window_block[16] = 1;             /* Sprite area control block pointer */
   window_block[17] = 0x00100010;	 /* Minimum window size (width & height) (16x16)*/
   window_block[18] = (int)this->hidden->title;    /* Title data */
   window_block[19] = -1;
   window_block[20] = 256;
   window_block[21] = 0;			 /* Number of icons */

   regs.r[1] = (unsigned int)(window_block);
   
   /* Create the window */
   if (_kernel_swi(Wimp_CreateWindow, &regs, &regs) == NULL)
   {
	   this->hidden->window_handle = window_data[0] = regs.r[0];

	   /* Show the window on the screen */
	   regs.r[1] = (unsigned int)window_data;
       if (_kernel_swi(Wimp_OpenWindow, &regs, &regs) == NULL)
       {
          WIMP_SetFocus(this->hidden->window_handle);
       } else
       {
		  WIMP_DeleteWindow(this);
	   }
   }
   
   return this->hidden->window_handle;
}