/* Control surfaces are an aspect of the Photon environment. This demo application needs to include the headers of the Photon toolkit. When you compile, you'll also need to specify that the linker should use the Photon library: cc -lph -o demo demo.c */ #include /* This is the function which is called when an event occurs for our rectangular control surface. When a user clicks on this surface, we'll tally up the clicks and print how many have occured. */ static int rect_surface_callback(PtWidget_t *widget,PtSurface_t *surface,PhEvent_t *event) { static int rclicks = 1; printf("Rectangle clicks: %d\n",rclicks++); return(Pt_END); } /* This is the function which draws the contents of our rectangular control surface. This is a very simple example, it draws a red rectangle. */ static void rect_surface_draw(PtWidget_t *widget,PtSurface_t *surface,PhTile_t *damage) { PgSetFillColor(Pg_RED); PgDrawRect(PtSurfaceRect(surface,NULL),Pg_DRAW_FILL); } /* This is the function keeps the size of the control surface in sync with the size of the widget. The function PtWidgetExtent returns a rect containing the current size of the widget. PtSurfaceRect is a macro; this means that you have direct access to the data within your control surface. You do not need to call any functions to change its size. Change the data directly. */ static void rect_surface_calc(PtWidget_t *widget,PtSurface_t *surface,uint8_t post) { /* only do after widget has extented */ if(post) { /* rect occupies top left quadrant of window */ PhRect_t *extent; PhRect_t *srect; extent = PtWidgetExtent(widget,NULL); srect = PtSurfaceRect(surface,NULL); srect->ul = extent->ul; srect->lr.x = (extent->ul.x + extent->lr.x) / 2; srect->lr.y = (extent->ul.y + extent->lr.y) / 2; } } /* This is the function which is called when an event occurs for our elliptical control surface. When a user clicks on this surface, we'll tally up the clicks and print how many have occured. */ static int ell_surface_callback(PtWidget_t *widget,PtSurface_t *surface,PhEvent_t *event) { static int eclicks = 1; printf("Ellipse clicks: %d\n",eclicks++); return(Pt_END); } /* This is the function which draws the contents of our elliptical control surface. This is a very simple example, it draws a green ellipse. */ static void ell_surface_draw(PtWidget_t *widget,PtSurface_t *surface,PhTile_t *damage) { PhRect_t *s = PtSurfaceRect(surface,NULL); PgSetFillColor(Pg_GREEN); PgDrawEllipse(&(s->ul),&(s->lr),Pg_DRAW_FILL | Pg_EXTENT_BASED); } /* This is our main function. We create a window, initialize our application with the Photon server and create two control surfaces. Notice that the second surface doesn't supply the last parameter - the extent calculation function. This isn't needed because of the fifthparameter - the height and width stored in a point structure. This is a pointer to the actual point structure within the window widget. Thus, if the window's extent changes, changing the extent point structure, the control surface is automatically updated with the new values! */ int main(int argc,char **argv) { PtArg_t args[1]; PtWidget_t *window; const PhDim_t dim = { 200,200 }; PtSetArg(&args[0],Pt_ARG_DIM,&dim,0); window = PtAppInit(NULL,&argc,argv,1,args); /* create a rectangular control surface */ PtCreateSurface( window, 0, 0, Pt_SURFACE_RECT, NULL, Ph_EV_BUT_PRESS, rect_surface_callback, rect_surface_draw, rect_surface_calc); /* create an elliptical control surface to fill window */ PtCreateSurface( window, 0, 0, Pt_SURFACE_ELLIPSE, (PhPoint_t*)PtWidgetExtent(window,NULL), Ph_EV_BUT_PRESS, ell_surface_callback, ell_surface_draw, NULL); PtRealizeWidget(window); PtMainLoop(); return(EXIT_SUCCESS); }