Exemplo n.º 1
0
g_error panel_set(struct widget *self,int property, glob data) {
  struct widget *w;
  g_error e;
  struct app_info **app;

  switch (property) {

  case PG_WP_SIZE:
    /* Alias 0 to our minimum rolled-up size */
    e = rdhandle((void **) &w, PG_TYPE_WIDGET, self->owner, DATA->hbar);
    errorcheck;
    if (data==0)
      data = w->in->split;
    widget_base_set(self,property,data);
    break;

  case PG_WP_SIDE:
    e = rdhandle((void **) &w, PG_TYPE_WIDGET, self->owner, DATA->hbar);
    errorcheck;
    switch (data) {    /* Invert the side for the panelbar */
    case PG_S_TOP:    widget_set(w,PG_WP_SIDE,PG_S_BOTTOM); break;
    case PG_S_BOTTOM: widget_set(w,PG_WP_SIDE,PG_S_TOP);    break;
    case PG_S_LEFT:   widget_set(w,PG_WP_SIDE,PG_S_RIGHT);  break;
    case PG_S_RIGHT:  widget_set(w,PG_WP_SIDE,PG_S_LEFT);   break;
    }
    return mkerror(ERRT_PASS,0);

  case PG_WP_THOBJ:
    DATA->bg->state = data;
    resizewidget(self);
    self->in->flags |= DIVNODE_NEED_RECALC;
    self->dt->flags |= DIVTREE_NEED_RECALC;
    break;
    
  case PG_WP_TEXT:
    e = rdhandle((void **) &w, PG_TYPE_WIDGET, self->owner, DATA->hlabel);
    errorcheck;
    app = appmgr_findapp(self);
    if (app && *app)
      (*app)->name = data;
    return widget_set(w,property,data);

  case PG_WP_IMAGE:
    e = rdhandle((void **) &w, PG_TYPE_WIDGET, self->owner, DATA->hlabel);
    errorcheck;
    return widget_set(w,property,data);

  case PG_WP_MARGIN:
    DATA->margin = data;
    DATA->margin_override = data >= 0;
    resizewidget(self);
    break;

  default:
    return mkerror(ERRT_PASS,0);

  }
  return success;
}
Exemplo n.º 2
0
/* Create an input filter to act as an adaptor between pgserver and
 * client-side input filters.
 */
g_error infilter_client_create(handle insertion, u32 accept_trigs, 
			       u32 absorb_trigs, handle *h, int owner) {
  struct infilter *insert_after;
  struct infilter **i;
  g_error e;

  /* Find the insertion point (it can be owned by anyone) 
   */
  e = rdhandle((void**)&insert_after,PG_TYPE_INFILTER,-1,insertion);
  errorcheck;
  if (insert_after)
    i = &insert_after->next;
  else
    i = &infilter_list;

  /* Insert the "adaptor" that sends events to the client 
   */
  e = infilter_insert(i, h, owner, &infilter_client_adaptor);
  errorcheck;

  (*i)->owner = owner;
  (*i)->accept_trigs = accept_trigs;
  (*i)->absorb_trigs = absorb_trigs;

  return success;
}
Exemplo n.º 3
0
void def_sprite_hide(struct sprite *spr) {
  static struct pgquad cr;
  struct divtree *dt;

  if (disable_output)
    return;

  if (iserror(rdhandle((void**)&dt, PG_TYPE_DIVTREE, -1, spr->dt)))
    return;
   
  if ( (!spr->onscreen) ||
       (spr->ox == -1) )
     return;

  cr.x1 = spr->x;
  cr.y1 = spr->y;
  cr.x2 = spr->x+spr->w-1;
  cr.y2 = spr->y+spr->h-1;

  /* Remove sprites above this one too */
  def_sprite_hide_above(spr);
   
  /* Put back the old image */
  VID(blit) (dt->display,spr->ox,spr->oy,spr->ow,spr->oh,
	     spr->backbuffer,0,0,PG_LGOP_NONE);
  add_updarea(dt,spr->ox,spr->oy,spr->ow,spr->oh);

  spr->onscreen = 0;
}
Exemplo n.º 4
0
/* Rebuild function for paragraph divnodes, issued by textbox_new_par_div */
void textbox_build_par_div(struct gropctxt *c, u16 state, struct widget *self) {
  struct paragraph *par;
  struct gropnode *grops = *c->headpp;

  /* Retrieve the paragraph pointer from the existing gropnodes */
  if (iserror(rdhandle((void**)&par,PG_TYPE_PARAGRAPH,-1,grops->next->param[0])) || !par)
    return;

  /* Text color, cursor color, cursor width */
  grops->param[0] = VID(color_pgtohwr)(theme_lookup(state,PGTH_P_FGCOLOR));
  par->cursor.color = grops->param[0];
  par->cursor.width = theme_lookup(state,PGTH_P_CURSOR_WIDTH);

  /* If we're displaying to a different width, rewrap it */
  if (par->width != c->r.w) {
    par->width = c->r.w;
    paragraph_wrap(par,1);
  }

  /* Set gropnode sizes */
  grops->next->r.x = c->r.x;
  grops->next->r.y = c->r.y;
  grops->next->r.w = c->r.w;
  grops->next->r.h = c->r.h;
  grops->next->next->r = grops->next->r;

  DBG("Build, size: %d,%d,%d,%d preferred: %d,%d\n",
      c->r.x,c->r.y,c->r.w,c->r.h,c->owner->preferred.w,c->owner->preferred.h);
}
Exemplo n.º 5
0
/*
  A widget has requested focus... Send out the ACTIVATE and DEACTIVATE
  triggers, and update necessary vars
*/
void request_focus(struct widget *self) {
  handle hself = hlookup(self,NULL);
  struct widget *kbdfocus;

  /* Already focused? */
  if (dts->top->focus==hself) return;

  kbdfocus = NULL;
  rdhandle((void**)&kbdfocus,PG_TYPE_WIDGET,-1,dts->top->focus);

  /* Deactivate the old widget, activate the new */
  send_trigger(kbdfocus,PG_TRIGGER_DEACTIVATE,NULL);
  dts->top->focus = hself;
  appmgr_focus(appmgr_findapp(self));
  send_trigger(self,PG_TRIGGER_ACTIVATE,NULL);

  /* Scroll in */
  scroll_to_divnode(self->in->div);

  /* If there's an active hotspot cursor, move it to this widget */
  if (dts->top->hotspot_cursor) {
    int x,y;
    divnode_hotspot_position(self->in->div, &x, &y);
    cursor_move(dts->top->hotspot_cursor,x,y,dts->top);
  }
}
Exemplo n.º 6
0
/* When the node under the cursor changes, notify the owning widget.
 */
void cursor_change_under(struct cursor *crsr, handle old_under) {
  struct widget *new_w, *old_w;

  new_w = NULL;
  rdhandle((void**)&new_w, PG_TYPE_WIDGET, -1, crsr->ctx.widget_under);
  old_w = NULL;
  rdhandle((void**)&old_w, PG_TYPE_WIDGET, -1, old_under);

  if (new_w == old_w)
    return;

  if (new_w)
    widget_set_numcursors(new_w,new_w->numcursors+1,crsr);
  if (old_w)
    widget_set_numcursors(old_w,old_w->numcursors-1,crsr);
}
Exemplo n.º 7
0
g_error tabpage_set(struct widget *self,int property, glob data) {
  struct widget *w;
  g_error e;

  /* Redirect applicable properties to the tab */ 
  if (is_tab_property(property))
    if (!iserror(rdhandle((void**)&w, PG_TYPE_WIDGET, self->owner, DATA->htab)) && w)
      return widget_set(w, property, data);

  /* Redirect applicable properties to the tab bar */ 
  if (is_tab_bar_property(property))
    if (!iserror(rdhandle((void**)&w, PG_TYPE_WIDGET, self->owner, DATA->htab_bar)) && w)
      return widget_set(w, property, data);

  return WIDGET_PARENT->set(self,property,data);
}
Exemplo n.º 8
0
/* Given a pg_client_trigger in network byte order this will reconstruct
 * the trigparam union from it, and dispatch it to the proper input filter.
 */
g_error infilter_client_send(union pg_client_trigger *client_trig) {
  union trigparam tp;
  int i;
  struct infilter *from;
  g_error e;
  memset(&tp,0,sizeof(tp));

  /* Convert it all to host byte order 
   */
  for (i=0;i<(sizeof(client_trig->array)/sizeof(client_trig->array[0]));i++)
    client_trig->array[i] = ntohl(client_trig->array[i]);

  /* Reconstruct the trigparam union, depending on trigger type 
   */
  if (client_trig->content.type & PG_TRIGGERS_KEY) {
    tp.kbd.key     = client_trig->content.u.kbd.key;
    tp.kbd.mods    = client_trig->content.u.kbd.mods;
    tp.kbd.flags   = client_trig->content.u.kbd.flags;
    tp.kbd.consume = client_trig->content.u.kbd.consume;
    tp.kbd.divtree = client_trig->content.u.kbd.divtree;
  }
  else if (client_trig->content.type & PG_TRIGGERS_MOUSE) {
    tp.mouse.x          = client_trig->content.u.mouse.x;
    tp.mouse.y          = client_trig->content.u.mouse.y;
    tp.mouse.btn        = client_trig->content.u.mouse.btn;
    tp.mouse.chbtn      = client_trig->content.u.mouse.chbtn;
    tp.mouse.pressure   = client_trig->content.u.mouse.pressure;
    tp.mouse.is_logical = client_trig->content.u.mouse.is_logical;
    tp.mouse.divtree    = client_trig->content.u.mouse.divtree;
    e = rdhandle((void**)&tp.mouse.cursor, PG_TYPE_CURSOR, -1,
		 client_trig->content.u.mouse.cursor_handle);
    tp.mouse.ts_calibration = client_trig->content.u.mouse.ts_calibration;
    errorcheck;
  }
  else if (client_trig->content.type & PG_TRIGGER_MOTIONTRACKER) {
    memcpy(&tp.motion, &client_trig->content.u.motion, sizeof(tp.motion));
  }

  /* Get the source infilter */
  e = rdhandle((void**)&from,PG_TYPE_INFILTER,-1,client_trig->content.infilter_from);
  errorcheck;

  /* Send it out */
  infilter_send(from, client_trig->content.type, &tp);

  return success;
} 
Exemplo n.º 9
0
g_error textedit_set ( struct widget *self,
                       int property, 
                       glob data ) {
    struct pgstring *text;

    switch (property) {
    case PG_WP_TEXT: 
        if (iserror(rdhandle((void **) &text, PG_TYPE_PGSTRING, -1, 
                             (handle) data)))
            text = NULL;
        
        if (text) {
            text_backend_set_text(DATA, text);
        }
        break;
    case PG_WP_FONT:
        if (iserror(rdhandle((void **)&DATA->fd,
                             PG_TYPE_FONTDESC,-1,data)) || !DATA->fd) 
            return mkerror(PG_ERRT_HANDLE,44); 
        text_backend_build(DATA, DATA->width, DATA->height);
        break;
    case PG_WP_SELECTION:
        if (iserror(rdhandle((void **) &text, PG_TYPE_PGSTRING, -1, 
                             (handle) data)))
            text = NULL;
        if (text) 
            text_backend_set_selection(DATA, text);
        break;
    case PG_WP_READONLY:
        if (data) { 
            SET_FLAG(DATA->flags, TEXT_WIDGET_READONLY);
            UNSET_FLAG(DATA->flags, TEXT_WIDGET_FLASH_ON);
        } else {
            UNSET_FLAG(DATA->flags, TEXT_WIDGET_READONLY);
            SET_FLAG(DATA->flags, TEXT_WIDGET_FLASH_ON);
            DATA->cursor_state = 1;
            install_timer(self, FLASHTIME_ON);
        }
        break;
    }
    return success;
}
Exemplo n.º 10
0
/* Iterator function for widget_find */
g_error widget_find_iterator(const void **p, void *extra) {
  struct widget *w = (struct widget *) (*p);
  const struct pgstring *str;
  struct widget_find_data *data = (struct widget_find_data *) extra;

  if (iserror(rdhandle((void**)&str,PG_TYPE_PGSTRING,-1,w->name)) || !str)
    return success;
  if (!pgstring_cmp(data->string,str))
    data->result = w;
  return success;
}
Exemplo n.º 11
0
/* Get the window the cursor is in, falling back on the debug window */
static hwrbitmap magic_cursor_display(void) {
  struct cursor *c = cursor_get_default();
  struct divtree *dt;

  if (!c)
    return VID(window_debug)();
  if (iserror(rdhandle((void**)&dt, PG_TYPE_DIVTREE, -1, c->divtree)))
    return VID(window_debug)();

  return dt->display;
}
Exemplo n.º 12
0
void def_sprite_update(struct sprite *spr) {
  struct divtree *dt;
  if (iserror(rdhandle((void**)&dt, PG_TYPE_DIVTREE, -1, spr->dt)))
    return;

  (*vid->sprite_hide) (spr);
  def_sprite_showall();       /* Also re-show the sprites we hid with protectarea */

  /* Redraw */
  realize_updareas(dt);
}
Exemplo n.º 13
0
/* Retrieve the paragraph associated with a divnode */
struct paragraph *document_get_div_par(struct divnode *div) {
  struct paragraph *par;
  
  /* The second gropnode refers to the paragraph, extract the handle from it */
  if (!div->grop) return NULL;
  if (!div->grop->next) return NULL;
  
  if (iserror(rdhandle((void**)&par,PG_TYPE_PARAGRAPH,-1,div->grop->next->param[0])))
    return NULL;
  
  return par;
}
Exemplo n.º 14
0
glob panel_get(struct widget *self,int property) {
  struct widget *w;
  g_error e;

  switch (property) {

  case PG_WP_THOBJ:
    return DATA->bg->state;

  case PG_WP_TEXT:
    e = rdhandle((void **) &w, PG_TYPE_WIDGET, self->owner, DATA->hlabel);
    errorcheck;
    return widget_get(w,property);

  case PG_WP_IMAGE:
    e = rdhandle((void **) &w, PG_TYPE_WIDGET, self->owner, DATA->hlabel);
    errorcheck;
    return widget_get(w,property);

  case PG_WP_PANELBAR:
    return DATA->hbar;

  case PG_WP_PANELBAR_LABEL:
    return DATA->hlabel;

  case PG_WP_PANELBAR_CLOSE:
    return DATA->hclose;

  case PG_WP_PANELBAR_ROTATE:
    return DATA->hrotate;

  case PG_WP_PANELBAR_ZOOM:
    return DATA->hzoom;

  case PG_WP_MARGIN:
    return DATA->margin;

  }
  return widget_base_get(self,property);
}
Exemplo n.º 15
0
glob tabpage_get(struct widget *self,int property) {
  struct widget *w;

  /* Redirect applicable properties to the tab */ 
  if (is_tab_property(property))
    if (!iserror(rdhandle((void**)&w, PG_TYPE_WIDGET, self->owner, DATA->htab)) && w)
      return widget_get(w, property);

  /* Redirect applicable properties to the tab bar */ 
  if (is_tab_bar_property(property))
    if (!iserror(rdhandle((void**)&w, PG_TYPE_WIDGET, self->owner, DATA->htab_bar)) && w)
      return widget_get(w, property);

  switch (property) {

  case PG_WP_TAB:
    return DATA->htab;

  case PG_WP_TAB_BAR:
    return DATA->htab_bar;

  }
  return WIDGET_PARENT->get(self,property);
}
Exemplo n.º 16
0
void panel_resize(struct widget *self) {
  struct widget *bar = NULL;
  rdhandle((void **) &bar, PG_TYPE_WIDGET, self->owner, DATA->hbar);

  if (DATA->margin_override)
    DATA->bg->split = DATA->margin;
  else
    DATA->bg->split = theme_lookup(DATA->bg->state,PGTH_P_MARGIN);
  self->in->div->split = theme_lookup(DATA->bg->state,PGTH_P_BORDER_SIZE);

  /* The minimum setting on the panelbar needs to leave room for the margin
   * on both sides, and the panelbar width itself.
   */
  if (bar)
    widget_set(bar, PG_WP_MINIMUM, widget_get(bar, PG_WP_SIZE) + 
	       (self->in->div->split << 1));
}
Exemplo n.º 17
0
/* This is used in transparent widgets - it propagates a redraw through
   the container the widget is in, in order to redraw the background
*/
void redraw_bg(struct widget *self) {
  struct widget *container;

  /* Dereference the handle */
  if (iserror(rdhandle((void **)&container,PG_TYPE_WIDGET,-1,
		       self->container)) || ! container) return;

  /* Flags! Redraws automatically propagate through all child nodes of the
     container's div.
  */
#ifndef CONFIG_NOPANELBAR
  if (container->type == PG_WIDGET_PANEL) /* Optimize for panels: don't redraw panelbar */
    container->in->div->div->next->flags |= DIVNODE_NEED_REDRAW;
  else
#endif
    container->in->flags |= DIVNODE_NEED_REDRAW;
  if ( container->dt ) container->dt->flags |= DIVTREE_NEED_REDRAW;
}
Exemplo n.º 18
0
void scroll_to_divnode(struct divnode *div) {
  s16 dx = 0,dy = 0;
  struct divnode *ds = div->divscroll;
  struct widget *w;

  if (!ds)
    return;

  /* If the divnode is larger or equal size to the scrolled
   * container, no need to scroll it in.
   * This fixes some confusing scroll behavior when focusing the textbox widget.
   */
  if ( (div->r.x <= ds->calc.x && (div->r.x + div->r.w) > (ds->calc.x + ds->calc.w)) ||
       (div->r.y <= ds->calc.y && (div->r.y + div->r.h) > (ds->calc.y + ds->calc.h)) )
    return;

  /* Figure out how much to scroll, if any. */

  if (div->r.x < ds->calc.x)
    dx = div->r.x - ds->calc.x;
  else if ( (div->r.x + div->r.w) > (ds->calc.x + ds->calc.w) )
    dx = (div->r.x + div->r.w) - (ds->calc.x + ds->calc.w);
  if (div->r.y < ds->calc.y)
    dy = div->r.y - ds->calc.y;
  else if ( (div->r.y + div->r.h) > (ds->calc.y + ds->calc.h) )
    dy = (div->r.y + div->r.h) - (ds->calc.y + ds->calc.h);

  /* No scrolling? */
  if (!(dx || dy))
    return;

  /* Get a pointer to the scroll bar */
  if (!iserror(rdhandle((void **)&w,PG_TYPE_WIDGET,-1,
			ds->owner->scrollbind)) && w) {
    
    if (dx)
      widget_set(w,PG_WP_SCROLL_X,widget_get(w,PG_WP_SCROLL_X) + dx);    
    if (dy)
      widget_set(w,PG_WP_SCROLL_Y,widget_get(w,PG_WP_SCROLL_Y) + dy);
    
    update(NULL,1);
  }
}
Exemplo n.º 19
0
/* Sends a trigger to all of a widget's children */
void r_send_trigger(struct widget *w, s32 type,
		    union trigparam *param, int *stop,int forward) {
  struct widget *bar;
  
  if (!w || (*stop) > 0)
    return;
  send_trigger(w,type,param);
  
  /* Also traverse the panelbar if there is one */
  if (!iserror(rdhandle((void**)&bar, PG_TYPE_WIDGET, w->owner, 
			widget_get(w,PG_WP_PANELBAR))) && bar) {
    r_send_trigger(bar, type, param, stop,0);
    if ((*stop) > 0)
      return;
  }
  
  r_send_trigger(widget_traverse(w,PG_TRAVERSE_CHILDREN,0),type,param,stop,1);
  if (forward)
    r_send_trigger(widget_traverse(w,PG_TRAVERSE_FORWARD,1),type,param,stop,1);
}
Exemplo n.º 20
0
void cursor_getposition(struct cursor *crsr, int *x, int *y, struct divtree **dt) {
  if (!crsr)
    crsr = cursor_get_default();
  if (!crsr) {
    /* Start cursors out near the top-left corner */
    *x = 16;
    *y = 16;
    if (dt)
      *dt = dts->top;
  }
  else {
    *x = crsr->x;
    *y = crsr->y;

    if (dt) {
      if (iserror(rdhandle((void**)dt, PG_TYPE_DIVTREE, -1, crsr->divtree)) || !*dt)
	*dt = dts->top;
    }
  }
}
Exemplo n.º 21
0
g_error panelbar_set(struct widget *self,int property, glob data) {
  g_error e;
  struct widget *w;

  switch (property) {
    
  case PG_WP_BIND:
    e = rdhandle((void **)&w,PG_TYPE_WIDGET,self->owner,data);
    errorcheck;
    DATA->bindto = data;
    break;

  case PG_WP_MINIMUM:
    DATA->minimum = data;
    break;

  default:
    return mkerror(ERRT_PASS,0);
  }
  return success;
}
Exemplo n.º 22
0
/* Create a standard panel button.
 * Note that the app owns these handles, so an app may delete one or more buttons.
 * This means that we _must_ only refer to the buttons by their handle unless of
 * course we're in a callback triggered by that button.
 */
g_error panel_std_button(handle *h, struct widget *self, int thobj, int thobj_on, int thobj_hilight, int exev,
			 int (*callback)(int event, struct widget *from, s32 param, int owner, const u8 *data)) {
  struct widget *w, *bar;
  g_error e;

  e = rdhandle((void **) &bar, PG_TYPE_WIDGET, self->owner, DATA->hbar);
  errorcheck;

  w = NULL;
  e = widget_derive(&w,h,PG_WIDGET_BUTTON,bar,DATA->hbar,PG_DERIVE_INSIDE,self->owner);
  errorcheck;

  w->callback = callback;
  w->callback_owner = self;

  widget_set(w, PG_WP_THOBJ_BUTTON, thobj);
  widget_set(w, PG_WP_THOBJ_BUTTON_ON, thobj_on);
  widget_set(w, PG_WP_THOBJ_BUTTON_HILIGHT, thobj_hilight);
  widget_set(w, PG_WP_THOBJ_BUTTON_ON_NOHILIGHT, thobj_on);
  widget_set(w, PG_WP_EXTDEVENTS, exev);

  return success;
}
Exemplo n.º 23
0
/* Traverse to other widgets in a given direction (PG_TRAVERSE_*) */
struct widget *widget_traverse(struct widget *w, int direction, int count) {
  struct widget *p;
  struct divnode *d;
  struct app_info **appinfo_p, *appinfo;
  
  switch (direction) {

    /* Traverse to the first child, then go forward 
     */
  case PG_TRAVERSE_CHILDREN:
    if (!w)
      return NULL;
    /* Make sure not only that this widget has an occupied child
     * attachment point, but make sure that the thing attached to it is
     * really the "in" connector on another widget. This is necessary to avoid
     * an improper result when this is called with a widget used inside another
     * widget as a container.
     */
    if (!w->sub || !*w->sub || (*w->sub)->owner->in != *w->sub)
      return NULL;
    return widget_traverse((*w->sub)->owner,PG_TRAVERSE_FORWARD,count);

    /* Go forward by 'count' widgets
     */
  case PG_TRAVERSE_FORWARD:
    for (;w && count;count--) {
      if (!w->out || !*w->out || (*w->out)->owner->in != *w->out)
	return NULL;
      w = (*w->out)->owner;
    }
    break;

    /* Go up by 'count' container levels 
     */
  case PG_TRAVERSE_CONTAINER:
    for (;w && count;count--) {
      if (iserror(rdhandle((void**) &w, PG_TYPE_WIDGET, -1, w->container)))
	return NULL;
    }
    break;

    /* Traversing backwards is harder, since there's no 'parent' pointer in the divnode
     */
  case PG_TRAVERSE_BACKWARD:
    for (;w && count;count--) {
      /* Find a suitable subtree */
      if (iserror(rdhandle((void**) &p, PG_TYPE_WIDGET, -1, w->container)))
	return NULL;
      if (p)
	d = p->in;
      else
        d = w->dt->head;

      /* Find parent divnode */
      d = divnode_findparent(d, w->in);
      if (!d)
	return NULL;
      if (d->next != w->in)   /* div child doesn't count */
	return NULL;
      w = d->owner;
    }
    break;

    /* Traverse through the application list */
  case PG_TRAVERSE_APP:
    if (w) {
      /* Find the appinfo structure associated with this widget */
      appinfo_p = appmgr_findapp(w);
      if (!appinfo_p)
	return NULL;
      
      /* Traverse the appinfo list */
      for (appinfo=*appinfo_p;appinfo && count;count--)
	appinfo = appinfo->next;
    }
    else {
      /* If they passed a 0 widget, start them off with the first app */
      appinfo = applist;
    }

    /* Return the root widget */
    if (!appinfo)
      return NULL;
    if (iserror(rdhandle((void**) &w, PG_TYPE_WIDGET, -1, appinfo->rootw)))
      return NULL;
    break;
  }

  return w;
}
Exemplo n.º 24
0
g_error widget_base_set(struct widget *w, int property, glob data) {
  char *str;
  struct divnode *maindiv = w->in->div ? w->in->div : w->in;

  switch (property) {
    
    /* Set the size, assuming initial split at w->in.
     * Calls resize handler if it exists, and sets the
     * appropriate flags.
     */
  case PG_WP_SIDE:
    if (!VALID_SIDE(data)) return mkerror(PG_ERRT_BADPARAM,2);
    w->in->flags &= SIDEMASK;
    w->in->flags |= ((sidet)data) | DIVNODE_NEED_RECALC;
    resizewidget(w);
    w->dt->flags |= DIVTREE_NEED_RECALC;
    redraw_bg(w);

    if (w->auto_orientation) {
      /* Set orientation on all child widgets */

      struct widget *p;
      p = widget_traverse(w, PG_TRAVERSE_CHILDREN, 0);
      while (p) {
	switch (data) {

	case PG_S_LEFT:
	case PG_S_RIGHT:
	   
	  if (w->auto_orientation & PG_AUTO_DIRECTION)
	    widget_set(p, PG_WP_DIRECTION, PG_DIR_VERTICAL);

	  if (w->auto_orientation & PG_AUTO_SIDE)
	    switch (widget_get(p, PG_WP_SIDE)) {
		
	    case PG_S_LEFT:
	      widget_set(p, PG_WP_SIDE, PG_S_TOP);
	      break;
		
	    case PG_S_RIGHT:
	      widget_set(p, PG_WP_SIDE, PG_S_BOTTOM);
	      break;
		
	    }
	  break;

	case PG_S_TOP:
	case PG_S_BOTTOM:

	  if (w->auto_orientation & PG_AUTO_DIRECTION)
	    widget_set(p, PG_WP_DIRECTION, PG_DIR_HORIZONTAL);

	  if (w->auto_orientation & PG_AUTO_SIDE)
	    switch (widget_get(p, PG_WP_SIDE)) {
		
	    case PG_S_TOP:
	      widget_set(p, PG_WP_SIDE, PG_S_LEFT);
	      break;
		
	    case PG_S_BOTTOM:
	      widget_set(p, PG_WP_SIDE, PG_S_RIGHT);
	      break;
		
	    }
	  break;

	}
	p = widget_traverse(p, PG_TRAVERSE_FORWARD,1);
      }
    }
    break;

  case PG_WP_SIZE:
    if (data<0) {
      /* Automatic sizing */
      w->in->flags |= DIVNODE_SIZE_AUTOSPLIT;
      w->dt->flags |= DIVTREE_NEED_RESIZE;
    }
    else {
      w->in->split = data;
      w->in->flags &= ~DIVNODE_SIZE_AUTOSPLIT;     /* No auto resizing */
    }
    w->in->flags |= DIVNODE_NEED_RECALC;
    w->dt->flags |= DIVTREE_NEED_RECALC;
    redraw_bg(w);
    break;

  case PG_WP_SIZEMODE:
    w->in->flags &= ~DIVNODE_SIZE_AUTOSPLIT;     /* No auto resizing */
    w->in->flags &= ~PG_SZMODEMASK;
    w->in->flags |= data & PG_SZMODEMASK;
    redraw_bg(w);
    break;
      
  case PG_WP_SCROLL_X:
    if (data > w->in->child.w - w->in->r.w)
      data = w->in->child.w - w->in->r.w;
    if (data < 0)
      data = 0;
    if (maindiv->translation.x != -data) {
      maindiv->translation.x = -data;
      maindiv->flags |= DIVNODE_SCROLL_ONLY | DIVNODE_NEED_RECALC;
      w->dt->flags |= DIVTREE_NEED_REDRAW;
      hotspot_free();
    }
    maindiv->flags |= DIVNODE_DIVSCROLL | DIVNODE_EXTEND_WIDTH;
    break;

  case PG_WP_SCROLL_Y:
    if (data > w->in->child.h - w->in->r.h)
      data = w->in->child.h - w->in->r.h;
    if (data < 0)
      data = 0;
    if (maindiv->translation.y != -data) {
      maindiv->translation.y = -data;
      maindiv->flags |= DIVNODE_SCROLL_ONLY | DIVNODE_NEED_RECALC;
      w->dt->flags |= DIVTREE_NEED_REDRAW;
      hotspot_free();
    }
    maindiv->flags |= DIVNODE_DIVSCROLL | DIVNODE_EXTEND_HEIGHT;
    break;

  case PG_WP_NAME:
    if (iserror(rdhandle((void **)&str,PG_TYPE_PGSTRING,-1,data))) 
      return mkerror(PG_ERRT_HANDLE,18);
    w->name = handle_canonicalize((handle) data);
    break;

  case PG_WP_PUBLICBOX:
    w->publicbox = data;
    break;

  case PG_WP_BIND:
    w->scrollbind = data;
    break;

  case PG_WP_THOBJ:
    maindiv->state = data;
    resizewidget(w);
    w->in->flags |= DIVNODE_NEED_RECALC;
    w->dt->flags |= DIVTREE_NEED_RECALC;
    break;

  case PG_WP_TRIGGERMASK:
    w->trigger_mask = data;
    break;
     
  case PG_WP_HILIGHTED:
    {
      struct widget *p;
      
      //
      // Pass the message onto the other sub widgets
      //
      p = widget_traverse(w, PG_TRAVERSE_CHILDREN, 0);
      while (p) {
	widget_set(p, PG_WP_HILIGHTED, data);
	p = widget_traverse(p, PG_TRAVERSE_FORWARD,1);
      }
    }
    break;

  case PG_WP_AUTO_ORIENTATION:
    w->auto_orientation = data;
    break;

  default:
    return mkerror(PG_ERRT_BADPARAM,6);   /* Unknown property */
  }
  return success;
}
Exemplo n.º 25
0
void infilter_pntr_dispatch_handler(struct infilter *self, u32 trigger, union trigparam *param) {
  struct widget *under;
  int release_captured = 0;
  int accepted = 0;

  /* In order to dispatch a pointing event, it must have an associated cursor.
   * The normalize filter should have given us a cursor whether the driver had
   * one or not, but in case an event was inserted into the pipe with no cursor,
   * pass it on. This will usually just run the event off the end of the
   * filter chain, but this makes it theoretically possible for a client to pick
   * up the cursorless events.
   */
  if (!param->mouse.cursor) {
    infilter_send(self, trigger, param);
    return;
  }

  /* Move the cursor */
  if (trigger==PG_TRIGGER_MOVE) {
    int cx,cy;
    struct divtree *new_dt, *old_dt;

    /* Default to the topmost divtree, but allow the event to override */
    if (iserror(rdhandle((void**)&new_dt, PG_TYPE_DIVTREE, -1, 
			 param->mouse.divtree)) || !new_dt)
      new_dt = dts->top;

    /* If the cursor is already at the destination, throw away this event */
    cursor_getposition(param->mouse.cursor,&cx,&cy,&old_dt);
    if (cx == param->mouse.x && cy == param->mouse.y && new_dt == old_dt)
      return;

    cursor_move(param->mouse.cursor,param->mouse.x,param->mouse.y,new_dt);
  }

  inactivity_reset();

  /* Read which widget is under the cursor */
  under = NULL;
  rdhandle((void**)&under, PG_TYPE_WIDGET, -1, param->mouse.cursor->ctx.widget_under);

  /* If the capture_btn is released, release the capture 
   */
  if ((!(param->mouse.btn & param->mouse.cursor->ctx.capture_btn)) && 
      param->mouse.cursor->ctx.widget_capture && 
      param->mouse.cursor->ctx.widget_capture != param->mouse.cursor->ctx.widget_under) {
    struct widget *capture;
    
    if ((!iserror(rdhandle((void**)&capture, PG_TYPE_WIDGET, -1,
			   param->mouse.cursor->ctx.widget_capture))) && capture)
      release_captured = send_trigger(capture,PG_TRIGGER_RELEASE,param);
    accepted++;

    param->mouse.cursor->ctx.widget_capture = 0;
    param->mouse.cursor->ctx.capture_btn = 0;
  }

  if (under) {
    /* There's an interactive widget under the cursor */
  
    /* Keep track of the most recently clicked widget 
     */
    if (trigger==PG_TRIGGER_DOWN) {
      param->mouse.cursor->ctx.widget_last_clicked = param->mouse.cursor->ctx.widget_under;
      
      /* Also, allow clicks to focus applications */
      appmgr_focus(appmgr_findapp(under));
    }

    /* First send the 'raw' event, then handle the cooked ones. */
    if (!release_captured)
      accepted += send_propagating_trigger(under,trigger,param);
    
    /* If the mouse is clicked in a widget, it 'captures' future MOVE and RELEASE events
     * until this button is released.
     */
    if (trigger==PG_TRIGGER_DOWN && !param->mouse.cursor->ctx.widget_capture) {
      param->mouse.cursor->ctx.widget_capture = param->mouse.cursor->ctx.widget_under;
      param->mouse.cursor->ctx.capture_btn = param->mouse.chbtn;
    }
  }

  /* If a captured widget accepts PG_TRIGGER_DRAG, send it even when the
   * mouse is outside its divnodes. 
   */
  if (trigger==PG_TRIGGER_MOVE && param->mouse.cursor->ctx.widget_capture) {
    struct widget *capture;
    
    if ((!iserror(rdhandle((void**)&capture, PG_TYPE_WIDGET, -1,
			   param->mouse.cursor->ctx.widget_capture))) && capture)
      accepted += send_trigger(capture,PG_TRIGGER_DRAG,param);
  }

  /* If nothing has accepted the event so far, pass it on */
  if (!accepted)
    infilter_send(self,trigger,param);
}
Exemplo n.º 26
0
g_error textedit_set_font ( struct widget *self,
                            handle font ) {
    return rdhandle((void **)&(DATA->fd), PG_TYPE_FONTDESC, -1, font);
}
Exemplo n.º 27
0
void panelbar_trigger_sprite(struct widget *self,s32 type,union trigparam *param) {
  bool force = 0;
  struct widget *boundwidget;
  int s;

  switch (type) {

  case PG_TRIGGER_ENTER:
    DATA->over = 1;
    break;

  case PG_TRIGGER_LEAVE:
    /* If we're dragging, the mouse didn't REALLY leave */
    if (DATA->on) return;
    DATA->over=0;
    break;

  case PG_TRIGGER_DOWN:
    if (param->mouse.chbtn != 1) return;

    /* If we're bound to another widget (we should be) save its current size */
    if (!iserror(rdhandle((void**)&boundwidget,PG_TYPE_WIDGET,self->owner,
			  DATA->bindto)) && boundwidget) {
      DATA->oldsize = widget_get(boundwidget,PG_WP_SIZE);

      /* If we're not rolled up, save this as the unrolled split */
      if (DATA->oldsize > DATA->minimum)
	DATA->unrolled = DATA->oldsize;
    }

    DATA->on = 1;
    DATA->x = param->mouse.x;
    DATA->y = param->mouse.y;
    DATA->draglen = 0;
     
    /* Update the screen now, so we have an up-to-date picture
       of the panelbar stored in DATA->s */
    themeify_panelbar(self,1);

    VID(sprite_hideall) ();   /* This line combined with the zero flag on */
    update(NULL,0);             /*  the next gets a clean spriteless grab */

    /* In case there was no release trigger (bug in input driver) */
    if (DATA->s) {
       free_sprite(DATA->s);
       DATA->s = NULL;
    }
    if (DATA->sbit) {
       VID(bitmap_free) (DATA->sbit);
       DATA->sbit = NULL;
    }
     
    /* Allocate the new sprite */
    if(iserror(new_sprite(&DATA->s,self->dt,DATA->panelbar->r.w,DATA->panelbar->r.h))) {
       DATA->s = NULL;
       return;
    }
    if (iserror(VID(bitmap_new) (&DATA->sbit,DATA->panelbar->r.w,DATA->panelbar->r.h,vid->bpp))) {
       free_sprite(DATA->s);
       DATA->s = NULL;
       DATA->sbit = NULL;
       return;
    }
    DATA->s->bitmap = &DATA->sbit;
    
    /* Grab a bitmap of the panelbar to use as the sprite */
    VID(blit) (DATA->sbit,0,0,DATA->panelbar->r.w,DATA->panelbar->r.h,
	       self->dt->display,DATA->s->x = DATA->panelbar->r.x,DATA->s->y = DATA->panelbar->r.y,
	       PG_LGOP_NONE);

    /* Clip the sprite to the travel allowed by boundwidget's parent */
    if (!iserror(rdhandle((void**)&boundwidget,PG_TYPE_WIDGET,self->owner,
			  DATA->bindto)) && boundwidget) {
      DATA->s->clip_to = boundwidget->in;
    }

    return;

  case PG_TRIGGER_UP:
  case PG_TRIGGER_RELEASE:
    if (!DATA->on) return;
    if (!(param->mouse.chbtn & 1)) return;

    if (!iserror(rdhandle((void**)&boundwidget,PG_TYPE_WIDGET,self->owner,
			  DATA->bindto)) && boundwidget) {

      s = panel_calcsplit(self,param->mouse.x,param->mouse.y,
			  widget_get(boundwidget,PG_WP_SIDE));
      
      if (DATA->draglen < MINDRAGLEN) {
	/* This was a click, not a drag */
	DATA->over = 0;
	
	widget_set(boundwidget,PG_WP_SIZEMODE,PG_SZMODE_PIXEL);
	if (DATA->oldsize > DATA->minimum)
	  /* Roll up the panel */
	  widget_set(boundwidget,PG_WP_SIZE,DATA->minimum);
	else
	  /* Unroll the panel */
	  widget_set(boundwidget,PG_WP_SIZE,DATA->unrolled);
      }
      else {
	s += panel_effective_split(boundwidget->in);

	/* Save this as the new unrolled split,
	 * Unless the user manually rolled up the panel */
	if ((s-DATA->minimum) > MAXROLLUP) 
	  DATA->unrolled = s;
	else
	  s = DATA->minimum;
	
	widget_set(boundwidget,PG_WP_SIZEMODE,PG_SZMODE_PIXEL);
	widget_set(boundwidget,PG_WP_SIZE,s);

	DATA->over = 1;
      }
    }

    VID(bitmap_free) (DATA->sbit);
    free_sprite(DATA->s);
    DATA->s = NULL;
    DATA->sbit = NULL;
    force = 1;           /* Definitely draw the new position */
     
    DATA->on = 0;
    break;

  case PG_TRIGGER_MOVE:
  case PG_TRIGGER_DRAG:
    if (!DATA->on) return;
     /* Ok, button 1 is dragging through our widget... */
     
    if (panel_throttle(self))
      return;
     
     /* Race condition prevention?
      * Without this, sometimes segfaults because DATA->s is NULL.
      * Possibly events_pending() triggered another event? */
     if (!DATA->s) return;
      
     /* Determine where to blit the bar to... */
     switch (self->in->flags & (~SIDEMASK)) {
     case PG_S_TOP:
     case PG_S_BOTTOM:
       DATA->s->x = DATA->panelbar->r.x;
       DATA->draglen += abs(param->mouse.y - DATA->y + DATA->panelbar->r.y - DATA->s->y);
       DATA->s->y = param->mouse.y - DATA->y + DATA->panelbar->r.y;
       break;
     case PG_S_LEFT:
     case PG_S_RIGHT:
       DATA->s->y = DATA->panelbar->r.y;
       DATA->draglen += abs(param->mouse.x - DATA->x + DATA->panelbar->r.x - DATA->s->x);
       DATA->s->x = param->mouse.x - DATA->x + DATA->panelbar->r.x;
       break;
     }

    /* Reposition sprite */
    VID(sprite_update) (DATA->s);
    return;
  }

  themeify_panelbar(self,force);
}
Exemplo n.º 28
0
/* Set the video mode using the current driver. This is the implementation
 * of the setmode client request */
g_error video_setmode(u16 xres,u16 yres,u16 bpp,u16 flagmode,u32 flags) {
   g_error e;
   struct divtree *tree;
   struct sprite *spr;
   u8 converting_mode,oldbpp;

   /* Must be done first */
   if (vidwrap->exitmode) {
      e = VID(exitmode)();
      errorcheck;
   }
   
   /* Default values, combine flags */
   if (!xres) xres = vid->xres;
   if (!yres) yres = vid->yres;
   if (!bpp)  bpp  = vid->bpp;
   switch (flagmode) {
    case PG_FM_ON:
      flags |= vid->flags;
      break;      
    case PG_FM_OFF:
      flags = vid->flags & (~flags);
      break;
    case PG_FM_TOGGLE:
      flags ^= vid->flags;
      break;
   }
   vid->flags = flags;

   /* If the new bpp is different, use modeconvert/modeunconvert */
   oldbpp = vid->bpp;
   converting_mode = (bpp != vid->bpp);
   if (converting_mode) {
      e = bitmap_iterate((handle_iterator)vid->bitmap_modeunconvert, NULL);
      errorcheck;
      e = handle_iterate(PG_TYPE_PALETTE,(handle_iterator)array_hwrtopg, NULL);
      errorcheck;
   }
      
   /* Might want to tell the driver! */
   e = (*vid->setmode) (xres,yres,bpp,flags);
   errorcheck;

   /* By default logical coordinates are also physical */
   vid->lxres = vid->xres;
   vid->lyres = vid->yres;
   
   /* Synchronize vid->display info automatically if we're using stdbitmap */
   if (vid->display && vid->bitmap_getsize==def_bitmap_getsize) {
     if (((struct stdbitmap *)vid->display)->rend)
       g_free(((struct stdbitmap *)vid->display)->rend);
     ((struct stdbitmap *)vid->display)->freebits = 0;
     ((struct stdbitmap *)vid->display)->w = vid->xres;
     ((struct stdbitmap *)vid->display)->h = vid->yres;
     ((struct stdbitmap *)vid->display)->bpp = vid->bpp;
   }
      
   /* Reset wrapper library (before using VID macro) */
   vidwrap_static = vidlib_static;
   vidwrap = &vidwrap_static;
   
   {
     /* Generate text colors table */

     u32 *tc;
     int i;

     /* Default VGA 16-color palette, copied from the Linux console */
     static const u32 default_palette[] = {
       0x000000, 0xaa0000, 0x00aa00, 0xaaaa00, 0x0000aa, 0xaa00aa, 0x00aaaa, 0xaaaaaa,
       0x555555, 0xff5555, 0x55ff55, 0xffff55, 0x5555ff, 0xff55ff, 0x55ffff, 0xffffff,
     };

     /* Allocate space for textcolors if we haven't already */
     if (!res[PGRES_DEFAULT_TEXTCOLORS]) {
       u32 *ptr;
       e = g_malloc((void**)&ptr,sizeof(u32)*17);
       errorcheck;
       ptr[0] = 16;
       e = mkhandle(&res[PGRES_DEFAULT_TEXTCOLORS],PG_TYPE_PALETTE,-1,(void*)ptr);
       errorcheck;
     }

     e = rdhandle((void **) &tc, PG_TYPE_PALETTE, -1, res[PGRES_DEFAULT_TEXTCOLORS]);
     errorcheck;
      
     /* Transcribe our static palette */
     memcpy(tc+1, default_palette, sizeof(default_palette));
     
     /* If we won't be doing it anyway later, go ahead and convert these to hwrcolors */
     if (!converting_mode) {
       e = array_pgtohwr(&tc);
       errorcheck;
     }
   }
     
   /* Add wrapper libraries if necessary. At compile-time, support adding
    * 90, 180, or 270 degrees as a hardware rotation
    */

#ifdef CONFIG_ROTATIONBASE_90                  /***** 90 degree default */
#ifdef CONFIG_ROTATE180
   if (vid->flags & PG_VID_ROTATE90) {
      vidwrap_rotate180(vidwrap);
      vid->lxres = vid->xres;
      vid->lyres = vid->yres;
   }
#endif   
#ifdef CONFIG_ROTATE270
   if (vid->flags & PG_VID_ROTATE180) {
      vidwrap_rotate270(vidwrap);
      vid->lxres = vid->yres;
      vid->lyres = vid->xres;
   }
#endif   
#ifdef CONFIG_ROTATE
   if (!(vid->flags & PG_VID_ROTATEMASK)) {
      vidwrap_rotate90(vidwrap);
      vid->lxres = vid->yres;
      vid->lyres = vid->xres;
   }
#endif
#else
#ifdef CONFIG_ROTATIONBASE_180                  /***** 180 degree default */
#ifdef CONFIG_ROTATE
   if (vid->flags & PG_VID_ROTATE270) {
      vidwrap_rotate90(vidwrap);
      vid->lxres = vid->yres;
      vid->lyres = vid->xres;
   }
#endif   
#ifdef CONFIG_ROTATE270
   if (vid->flags & PG_VID_ROTATE90) {
      vidwrap_rotate270(vidwrap);
      vid->lxres = vid->yres;
      vid->lyres = vid->xres;
   }
#endif   
#ifdef CONFIG_ROTATE180
   if (!(vid->flags & PG_VID_ROTATEMASK)) {
      vidwrap_rotate180(vidwrap);
      vid->lxres = vid->xres;
      vid->lyres = vid->yres;
   }
#endif
#else
#ifdef CONFIG_ROTATIONBASE_270                  /***** 270 degree default */
#ifdef CONFIG_ROTATE
   if (vid->flags & PG_VID_ROTATE180) {
      vidwrap_rotate90(vidwrap);
      vid->lxres = vid->yres;
      vid->lyres = vid->xres;
   }
#endif   
#ifdef CONFIG_ROTATE180
   if (vid->flags & PG_VID_ROTATE270) {
      vidwrap_rotate180(vidwrap);
      vid->lxres = vid->xres;
      vid->lyres = vid->yres;
   }
#endif   
#ifdef CONFIG_ROTATE270
   if (!(vid->flags & PG_VID_ROTATEMASK)) {
      vidwrap_rotate270(vidwrap);
      vid->lxres = vid->yres;
      vid->lyres = vid->xres;
   }
#endif
#else                                           /***** 0 degree default */
#ifdef CONFIG_ROTATE
   if (vid->flags & PG_VID_ROTATE90) {
      vidwrap_rotate90(vidwrap);
      vid->lxres = vid->yres;
      vid->lyres = vid->xres;
   }
#endif   
#ifdef CONFIG_ROTATE180
   if (vid->flags & PG_VID_ROTATE180) {
      vidwrap_rotate180(vidwrap);
      vid->lxres = vid->xres;
      vid->lyres = vid->yres;
   }
#endif   
#ifdef CONFIG_ROTATE270
   if (vid->flags & PG_VID_ROTATE270) {
      vidwrap_rotate270(vidwrap);
      vid->lxres = vid->yres;
      vid->lyres = vid->xres;
   }
#endif   
#endif
#endif
#endif

   /* Should we ignore the base screen rotation for keyboard events? */
#ifdef CONFIG_ROTATIONBASE_NOKEYS
   vidwrap->coord_keyrotate = &def_coord_keyrotate;
#ifdef CONFIG_ROTATE
   if (vid->flags & PG_VID_ROTATE90)
     vidwrap->coord_keyrotate = &rotate90_coord_keyrotate;
#endif   
#ifdef CONFIG_ROTATE180
   if (vid->flags & PG_VID_ROTATE180)
     vidwrap->coord_keyrotate = &rotate180_coord_keyrotate;
#endif   
#ifdef CONFIG_ROTATE270
   if (vid->flags & PG_VID_ROTATE270)
     vidwrap->coord_keyrotate = &rotate270_coord_keyrotate;
#endif
#endif /* CONFIG_ROTATIONBASE_NOKEYS */

   /* Ignore the base screen rotation for pointing events? */
#ifdef CONFIG_ROTATIONBASE_NOPOINTING
   vidwrap->coord_physicalize = &def_coord_logicalize;
   vidwrap->coord_logicalize = &def_coord_logicalize;
#ifdef CONFIG_ROTATE
   if (vid->flags & PG_VID_ROTATE90) {
     vidwrap->coord_physicalize = &rotate90_coord_physicalize;
     vidwrap->coord_logicalize = &rotate90_coord_logicalize;
   }
#endif   
#ifdef CONFIG_ROTATE180
   if (vid->flags & PG_VID_ROTATE180) {
     vidwrap->coord_physicalize = &rotate180_coord_logicalize;
     vidwrap->coord_logicalize = &rotate180_coord_logicalize;
   }
#endif   
#ifdef CONFIG_ROTATE270
   if (vid->flags & PG_VID_ROTATE270) {
     vidwrap->coord_physicalize = &rotate270_coord_physicalize;
     vidwrap->coord_logicalize = &rotate270_coord_logicalize;
   }
#endif
#endif /* CONFIG_ROTATIONBASE_NOPOINTING */

   /* Since changing video modes pretty much obliterates all onscreen
    * sprites, and the previous location might be offscreen now,
    * reset the backbuffer on all sprites */
   for (spr=spritelist;spr;spr=spr->next)
     spr->onscreen = 0;
   
   /* Resize the root divnodes of all divtrees in the dtstack */
   if (dts)   /* (if this is in early init, dtstack isn't here yet) */
     for (tree=dts->top;tree;tree=tree->next) {
	tree->head->r.w = vid->lxres;
	tree->head->r.h = vid->lyres;
	tree->head->calc.w = vid->lxres;
	tree->head->calc.h = vid->lyres;
	tree->head->flags |= DIVNODE_NEED_RECALC | DIVNODE_FORCE_CHILD_RECALC | DIVNODE_NEED_REBUILD;
	tree->flags |= DIVTREE_NEED_RECALC | DIVTREE_ALL_REDRAW | DIVTREE_CLIP_POPUP;
     }

   /* Convert to the new color depth if necessary */
   if (converting_mode) {
      e = bitmap_iterate((handle_iterator)vid->bitmap_modeconvert, NULL);
      errorcheck;
      e = handle_iterate(PG_TYPE_PALETTE,(handle_iterator)array_pgtohwr, NULL);
      errorcheck;
   }
   
   /* Done swtiching the mode, give the driver a shot at changing
    * things around */
   e = VID(entermode)();
   errorcheck;
   
   /* Reload things when increasing color depth */
   if (oldbpp < bpp) {
    
      /* Reload any themes the server is responsible for */
      e = reload_initial_themes();
      errorcheck;
      
      /* FIXME: notify all clients that they can reload here */    
   }
  
   return success;
}
Exemplo n.º 29
0
void panelbar_trigger_solid(struct widget *self,s32 type,union trigparam *param) {
  bool force = 0;
  struct widget *boundwidget;
  int s;

  switch (type) {

  case PG_TRIGGER_ENTER:
    DATA->over = 1;
    break;
  case PG_TRIGGER_LEAVE:
    DATA->over=0;
    break;

  case PG_TRIGGER_DOWN:
    if (param->mouse.chbtn != 1) return;

    /* If we're bound to another widget (we should be) save its current size */
    if (!iserror(rdhandle((void**)&boundwidget,PG_TYPE_WIDGET,self->owner,
			  DATA->bindto)) && boundwidget) {
      DATA->oldsize = widget_get(boundwidget,PG_WP_SIZE);

      /* To make things easier during dragging,
       * get the effective split to equal the split
       */
      widget_set(boundwidget, PG_WP_SIZEMODE, PG_SZMODE_PIXEL);
      widget_set(boundwidget, PG_WP_SIZE,
		 panel_effective_split(boundwidget->in));	 
    }

    DATA->on = 1;
    DATA->x = param->mouse.x;
    DATA->y = param->mouse.y;
    DATA->draglen = 0;
    break;

  case PG_TRIGGER_UP:
  case PG_TRIGGER_RELEASE:
    if (!DATA->on) return;
    if (!(param->mouse.chbtn & 1)) return;

    if (!iserror(rdhandle((void**)&boundwidget,PG_TYPE_WIDGET,self->owner,
			  DATA->bindto)) && boundwidget) {

      if (DATA->draglen < MINDRAGLEN) {
	/* This was a click, not a drag */
	DATA->over = 0;
	
	widget_set(boundwidget,PG_WP_SIZEMODE,PG_SZMODE_PIXEL);
	if (DATA->oldsize > DATA->minimum)
	  /* Roll up the panel */
	  widget_set(boundwidget,PG_WP_SIZE,DATA->minimum);
	else
	  /* Unroll the panel */
	  widget_set(boundwidget,PG_WP_SIZE,DATA->unrolled);

	update(NULL,1);
      }
      else {
	s = panel_effective_split(boundwidget->in);

	/* Save this as the new unrolled split,
	 * Unless the user manually rolled up the panel */
	if ((s-DATA->minimum) > MAXROLLUP) 
	  DATA->unrolled = s;
	else
	  s = DATA->minimum;
      }
    }

    DATA->on = 0;
    break;

  case PG_TRIGGER_MOVE:
  case PG_TRIGGER_DRAG:
     if (!DATA->on) return;
     if (panel_throttle(self))
       return;
     
     if (!iserror(rdhandle((void**)&boundwidget,PG_TYPE_WIDGET,self->owner,
			   DATA->bindto)) && boundwidget) {
     
       s = panel_calcsplit(self,param->mouse.x,param->mouse.y,
			   widget_get(boundwidget,PG_WP_SIDE));
       DATA->draglen += abs(s);
       
       if (s) {
	 s += boundwidget->in->split;

	 /* FIXME: This isn't quite right, in solid dragging mode the panelbar
	  * can get out of sync with the cursor when this s < DATA->minimum code
	  * comes into effect.
	  */
	 if (s < DATA->minimum)
	   s = DATA->minimum;
	 else {
	   DATA->x = param->mouse.x;
	   DATA->y = param->mouse.y;
	 }

	 widget_set(boundwidget, PG_WP_SIZE,s);
	 update(NULL,1);
       }
     }
     return;
  }

  themeify_panelbar(self,force);
}
Exemplo n.º 30
0
void guru(const char *fmt, ...) {
  struct font_descriptor *df=NULL;
  char msgbuf[512];  /* Cruftee! */
  char *p,*pline;
  char c;
  va_list ap;
  struct pgquad screenclip;
  static int semaphore = 0;
   
  if (!vid) return;
  if (semaphore) {
    fprintf(stderr, "GURU re-entered!\n");
    return;
  }
  semaphore++;

  /* Format and print message */
  va_start(ap,fmt);
  vsnprintf(msgbuf,512,fmt,ap);
  va_end(ap);
  
  if (!disable_output) {

    /* Setup */
    VID(rect) (VID(window_debug)(),0,0,vid->lxres,vid->lyres,VID(color_pgtohwr)(0),
	       PG_LGOP_NONE);
    rdhandle((void**)&df,PG_TYPE_FONTDESC,-1,res[PGRES_DEFAULT_FONT]);
    screenclip.x1 = screenclip.y1 = 0;
    screenclip.x2 = vid->lxres-1;
    screenclip.y2 = vid->lyres-1;
    
#ifdef CONFIG_FORMAT_XBM
    /* Icon (if this fails, no big deal) */
    {
      hwrbitmap icon;
      if (!iserror(VID(bitmap_loadxbm) (&icon,deadcomp_bits,
					deadcomp_width,deadcomp_height,
					VID(color_pgtohwr) (0xFFFF80),
					VID(color_pgtohwr) (0x000000)))) {
	VID(blit) (VID(window_debug)(),5,5,deadcomp_width,deadcomp_height,
		   icon,0,0,PG_LGOP_NONE);
	VID(bitmap_free) (icon);
      }
    }
#else
    /* To appease the below code */
# define deadcomp_width 0
#endif
  
    df->lib->draw_string(df,VID(window_debug)(),xy_to_pair(10+deadcomp_width,5),
			 VID(color_pgtohwr)(0xFFFFFF),pgstring_tmpwrap(msgbuf),
			 &screenclip,PG_LGOP_NONE,0);
    VID(update) (VID(window_debug)(),0,0,vid->lxres,vid->lyres);    
  }
  
#ifdef CONFIG_STDERR_GURU
  /* Mirror the message on stderr, prefix each line with "GURU:  " */
  for (c=1,pline=msgbuf;c;pline=p+1) {
    for (p=pline;*p && *p!='\n';p++);
    c=*p; *p=0;
    fprintf(stderr,"GURU:  %s\n",pline); 
  }
#endif
    
  semaphore--;
}