ref: c9e889a6d73bcfcd63a93a8f74732411304ef257
dir: /n_button.c/
#include <u.h>
#include <libc.h>
#include <draw.h>
#include <event.h>
#include "nate.h"
#include "nate_construct.h"
#include "n_box.h"
#include "n_label.h"
#include "n_button.h"
#define N_TYPE NButton_Type
char *NButton_Type = "NButton";
static Rectangle
button_calcrect(Nelem *nelem, Image *screen, Rectangle r)
{
NButton *b = (NButton*)nelem;
GUARD(b);
b->box->slot = b->slot;
b->slot.r = ncallcalcrect(b->box, screen, r);
return b->slot.r;
}
static Point
button_desiredsize(Nelem *nelem, Image *screen)
{
NButton *b = (NButton*)nelem;
GUARD(b);
b->box->slot = b->slot;
return ncalldesiredsize(b->box, screen);
}
static void
button_draw(Nelem *nelem, Image *img)
{
NButton *b = (NButton*)nelem;
GUARD(b);
b->box->slot = b->slot;
ncalldraw(b->box, img);
}
static Nelem*
button_checkhit(Nelem *nelem, Image *screen, Mouse m)
{
NButton *b = (NButton*)nelem;
GUARD(b);
b->box->slot = b->slot;
return ncallcheckhit(b->box, screen, m);
}
static void
button_free(Nelem *nelem)
{
NButton *b = (NButton*)nelem;
GUARD(b);
if (nisroot(b) || nisroot(b->box))
return;
b->box->funcs->free(b->box);
free(b);
}
static Nlist*
button_getchildren(Nelem *nelem)
{
NButton *b = (NButton*)nelem;
GUARD(b);
return ncallgetchildren(b->box);
}
static Nelemfunctions Nbuttonfunctions = {
.calcrect = button_calcrect,
.desiredsize = button_desiredsize,
.draw = button_draw,
.checkhit = button_checkhit,
.free = button_free,
.getchildren = button_getchildren,
};
#define NTYPE NButton
#define NACCS NButtonAccessors
static NACCS*
button_slot(Nslot info, Nelemaccessors *a)
{
NButton *c;
Nelem *child = nc_get();
if (a->type != child->type)
sysfatal("invalid child type in slot");
nc_pop();
c = (NButton*)nc_get();
GUARD(c);
nc_push(c->box);
NCACCS(NBoxAccessors, c->box)->Slot(info, a);
nc_pop();
return (NACCS*)c->accs;
}
static NACCS*
button_border(int w, Image *i)
{
NButton *c = (NButton*)nc_get();
GUARD(c);
nc_push(c->box);
NCACCS(NBoxAccessors, c->box)->Border(w, i);
nc_pop();
return (NACCS*)c->accs;
}
static NACCS*
button_autosize(int n)
{
NButton *c = (NButton*)nc_get();
GUARD(c);
nc_push(c->box);
NCACCS(NBoxAccessors, c->box)->AutoSize(n);
nc_pop();
return (NACCS*)c->accs;
}
static NACCS*
button_onclick(OnclickHandler f, void *aux)
{
NButton *c = (NButton*)nc_get();
GUARD(c);
nc_push(c->box);
NCACCS(NBoxAccessors, c->box)->OnClick(f, aux);
nc_pop();
return NCACCS(NACCS, c);
}
static NACCS*
button_label(char *l)
{
NButton *c = (NButton*)nc_get();
GUARD(c);
nc_push(c->label);
NCACCS(NLabelAccessors, c->label)->Label(l);
nc_pop();
return (NACCS*)c->accs;
}
static NACCS*
button_labelfunc(StringGetter f)
{
NButton *c = (NButton*)nc_get();
GUARD(c);
nc_push(c->label);
NCACCS(NLabelAccessors, c->label)->LabelFunc(f);
nc_pop();
return (NACCS*)c->accs;
}
static NACCS*
button_font(Font *f)
{
NButton *c = (NButton*)nc_get();
GUARD(c);
nc_push(c->label);
NCACCS(NLabelAccessors, c->label)->Font(f);
nc_pop();
return (NACCS*)c->accs;
}
static NACCS*
button_color(Image *i)
{
NButton *c = (NButton*)nc_get();
GUARD(c);
nc_push(c->label);
NCACCS(NLabelAccessors, c->label)->Color(i);
nc_pop();
return (NACCS*)c->accs;
}
static NACCS accs = {
.Slot = button_slot,
.Border = button_border,
.AutoSize = button_autosize,
.OnClick = button_onclick,
.Label = button_label,
.LabelFunc = button_labelfunc,
.Font = button_font,
.Color = button_color,
};
NACCS*
New_Button(char *name)
{
NButton *b = MakeNelem(NButton, NButton_Type, &Nbuttonfunctions, &accs, name, 0);
NAssign(NBoxAccessors, &b->box, New_Box(name))
->Slot(NSlot(),
NAssign(NLabelAccessors, &b->label, New_Label(nil))
->Margin(NMargin2(5, 2))
);
/* pop box from stack */
nc_pop();
nc_push(b);
return &accs;
}