Skip to content

Commit

Permalink
more work - changes to api, expect more.
Browse files Browse the repository at this point in the history
  • Loading branch information
Cecil committed Oct 9, 2018
1 parent 11054d8 commit ffec6c9
Show file tree
Hide file tree
Showing 6 changed files with 225 additions and 51 deletions.
20 changes: 15 additions & 5 deletions Tests/layout/l1.rb
Original file line number Diff line number Diff line change
@@ -1,13 +1,22 @@

class MyLayout
attr_accessor :pos_x, :pos_y
attr_accessor :pos_x, :pos_y, :w, :h
attr_accessor :contents

def initialize()
@pos_x = 25
@pos_y = 25
@contents = []
end

def add_widget(widget)
def setup(attr)
@w = attr[:width]
@h = attr[:height]
puts "setup #{@w} X #{@h}"
end

def add(widget)
@contents << widget
widget.move @pos_x, @pos_y
@pos_x += 25
@pos_y += 25
Expand All @@ -17,14 +26,15 @@ def add_widget(widget)
Shoes.app width: 350, height: 400, resizeable: true do
stack do
para "Before layout"
@ml = layout manager: MyLayout.new, width: 300, height: 300 do
@ml = MyLayout.new
layout manager: @ml, width: 300, height: 300 do
background yellow
p1 = para "First Para"
a = button "one"
b = button "two"
p2 = para "I am #{self}"
p2 = para "I am #{self.class}"
end
end
para "After layout"
para "@ml is #{@ml.inspect}"
para "@ml is #{@ml.class}"
end
77 changes: 77 additions & 0 deletions Tests/layout/l2.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@

class MyLayout
attr_accessor :pos_x, :pos_y, :w, :h
attr_accessor :incr_x, :incr_y

def initialize()
puts "initialized"
clear
end

def setup(canvas, attr)
@w = attr[:width]
@h = attr[:height]
puts "callback: setup #{@w} X #{@h}"
end

def add(canvas, widget)
puts "callback add: #{widget.inspect} #{canvas.contents.size}"
@pos_x += @incr_x
if @pos_x < 0
@pos_x = 0
@incr_x = 25
end
if @pos_x >= @w
@pos_x = @w
@incr_x = -25
end
@pos_y += @incr_y
if @pos_y <= 0
@pos_y = 0
@incr_y = +25
end
if @pos_y >= @h
@pos_y = @h - 25
@incr_y = -25
end
widget.move @pos_x, @pos_y
end

def clear
@pos_x = -20
@pos_y = -20
@incr_x = 25
@incr_y = 25
puts "callback: clear"
end

end

Shoes.app width: 350, height: 450, resizeable: true do
stack do
@p = para "Before layout"
@ml = MyLayout.new
@lay =layout manager: @ml, width: 340, height: 380 do
background yellow
p1 = para "First Para"
a = button "one"
b = button "two"
p2 = para "I am #{self.class}"
end
@p.text = @lay.inspect
@lay.finish
end
button "Append" do
@lay.append { para "appended" }
end
button "Clear" do
@lay.clear { background white }
end
button "Prepend" do
# problem here?
@lay.prepend { para "prepended" }
end
button "refresh" do
@lay.refresh
end
end
2 changes: 1 addition & 1 deletion make/linux/minlin/env.rb
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

APP['GDB'] = "true" # true => compile -g, don't strip symbols
if APP['GDB']
LINUX_CFLAGS = "-g -O0"
LINUX_CFLAGS = "-ggdb3 -O0"
else
LINUX_CFLAGS = "-O -Wall"
end
Expand Down
32 changes: 21 additions & 11 deletions shoes/canvas.c
Original file line number Diff line number Diff line change
Expand Up @@ -281,6 +281,10 @@ static void shoes_canvas_empty(shoes_canvas *canvas, int extras) {
canvas->stage = CANVAS_EMPTY;
shoes_ele_remove_all(canvas->contents);
if (extras) shoes_extras_remove_all(canvas);
if (! NIL_P(canvas->layout_mgr)) {
shoes_layout_clear(canvas);
}

canvas->stage = stage;
}

Expand Down Expand Up @@ -715,7 +719,7 @@ void shoes_canvas_compute(VALUE self) {
cairo_restore(cr);
}

static void shoes_canvas_insert(VALUE self, long i, VALUE ele, VALUE block) {
void shoes_canvas_insert(VALUE self, long i, VALUE ele, VALUE block) {
SETUP_CANVAS();

if (canvas->insertion != -2)
Expand All @@ -727,8 +731,15 @@ static void shoes_canvas_insert(VALUE self, long i, VALUE ele, VALUE block) {
canvas->insertion = i;
if (rb_respond_to(block, s_widget))
rb_funcall(block, s_widget, 1, self);
else
else {
if (! NIL_P(canvas->layout_mgr)) {
shoes_layout *lay;
Data_Get_Struct(canvas->layout_mgr, shoes_layout, lay);
fprintf(stderr, "Insert into Layout\n");

} else
shoes_canvas_memdraw(self, block);
}
canvas->insertion = -2;
shoes_canvas_repaint_all(self);
}
Expand Down Expand Up @@ -855,30 +866,29 @@ VALUE shoes_canvas_widget(int argc, VALUE *argv, VALUE self) {

VALUE shoes_canvas_layout(int argc, VALUE *argv, VALUE self) {
rb_arg_list args;
VALUE layout;
VALUE layout_canvas;
VALUE layout_obj;
SETUP_CANVAS();
fprintf(stderr, "canvas_layout: called\n");

rb_parse_args(argc, argv, "|h&", &args);
layout_obj = shoes_layout_new(args.a[0], self);
shoes_layout *self_t;
Data_Get_Struct(layout_obj, shoes_layout, self_t);
layout = self_t->canvas; // from shoes_slot_new()
shoes_layout *lay;
Data_Get_Struct(layout_obj, shoes_layout, lay);
layout_canvas = lay->canvas;
if (!NIL_P(args.a[1])) {
/* expand macro by hand
DRAW(layout, canvas->app, rb_funcall(args.a[1], s_call, 0));
*/
rb_ary_push(canvas->app->nesting, layout);
rb_ary_push(canvas->app->nesting, layout_canvas);
rb_funcall(args.a[1], s_call, 0); // this is the block arg
rb_ary_pop(canvas->app->nesting);
}
shoes_add_ele(canvas, layout);
shoes_add_ele(canvas, layout_canvas); // Shoes tracks the canvas

//shoes_canvas *self_t;
//Data_Get_Struct(layout, shoes_canvas, self_t);
// yes, we return the canvas, not the Layout Object
return layout;
//return layout_canvas;
return layout_obj;
}

void shoes_canvas_size(VALUE self, int w, int h) {
Expand Down
119 changes: 94 additions & 25 deletions shoes/types/layout.c
Original file line number Diff line number Diff line change
Expand Up @@ -13,17 +13,33 @@
#include "shoes/types/layout.h"
#include <math.h>
//
// Shoes::Layout needs to be a class so it can be subclassed
// Shoes::Layout needs to be a slot-like class - same api?
//
extern VALUE cButton, cBackground;

/* FUNC_M generate two functions here
* shoes_canvas_c_layout(int argc, VALUE *argv, VALUE self) { ..}
* + means call shoes_canvas_repaint_all() at end
* shoes_app_c_layout(int argc, VALUE *argv, VALUE self) {...}
*/
FUNC_M("+layout", layout, -1);

void shoes_layout_init() {
cLayout = rb_define_class_under(cTypes, "Layout", cNative);
rb_define_method(cLayout, "rule", CASTHOOK(shoes_layout_add_rule), 1);
rb_define_method(cLayout, "compute", CASTHOOK(shoes_layout_compute), 1);
cLayout = rb_define_class_under(cTypes, "Layout", cShoes);
//cLayout = rb_define_class_under(cFlow, "Layout", cShoes);
rb_define_method(cLayout, "append", CASTHOOK(shoes_layout_append), -1); // crash in shoes_canvas_memdraw
//rb_define_method(cLayout, "append", CASTHOOK(shoes_canvas_append), -1); // slot is being modified
rb_define_method(cLayout, "clear", CASTHOOK(shoes_canvas_clear_contents), -1);
rb_define_method(cLayout, "prepend", CASTHOOK(shoes_canvas_prepend), -1);
rb_define_method(cLayout, "before", CASTHOOK(shoes_canvas_before), -1);
rb_define_method(cLayout, "after", CASTHOOK(shoes_canvas_after), -1);
rb_define_method(cLayout, "rule", CASTHOOK(shoes_layout_add_rule), -1);
rb_define_method(cLayout, "finish", CASTHOOK(shoes_layout_compute), -1);

/* RUBY_M generates defines (allow Ruby to call the FUNC_M funtions
rb_define_method(cCanvas, "layout", CASTHOOK(shoes_canvas_c_layout), -1);
rb_define_method(cApp, "layout", CASTHOOK(shoes_app_c_layout), -1)
*/
RUBY_M("+layout", layout, -1);
}

Expand Down Expand Up @@ -54,7 +70,7 @@ VALUE shoes_layout_new(VALUE attr, VALUE parent) {
VALUE obj = shoes_layout_alloc(cLayout);
shoes_layout *ly;
Data_Get_Struct(obj, shoes_layout, ly);
// Most of shoes thinks its a Flow
// Most of shoes thinks its a Flow (cFlow or cLayout ?)
VALUE canvas = shoes_slot_new(cFlow, attr, parent);
ly->canvas = canvas;
shoes_canvas *cvs;
Expand All @@ -63,49 +79,102 @@ VALUE shoes_layout_new(VALUE attr, VALUE parent) {
VALUE mgr;
ID s_manager = rb_intern ("manager");
mgr = ATTR(attr, manager);
if (! NIL_P(mgr))
if (! NIL_P(mgr)) {
ly->delegate = mgr;
ID s_setup = rb_intern("setup");
if (rb_respond_to(mgr, s_setup))
rb_funcall(mgr, s_setup, 2, canvas, attr);
}
cvs->layout_mgr = obj; // me
//return cvs;
return obj;
}

// called from inside shoes (shoes_add_ele)
VALUE shoes_layout_append(int argc, VALUE *argv, VALUE self) {
shoes_layout *lay;
Data_Get_Struct(self, shoes_layout, lay);
VALUE canvas = lay->canvas;
rb_arg_list args;
rb_parse_args(argc, argv, "o,&", &args);
shoes_canvas_insert(canvas, -1, Qnil, args.a[0]);
return self;
}

VALUE shoes_layout_prepend(VALUE self, VALUE ele) {
shoes_layout *ly;
Data_Get_Struct(self, shoes_layout, ly);
shoes_canvas *canvas;
Data_Get_Struct(ly->canvas, shoes_canvas, canvas);
shoes_layout_add_ele(canvas, ele);
}

// called from shoes_add_ele (def in canvas.c) by widget creators
// The ele has already been added to canvas->contents
void shoes_layout_add_ele(shoes_canvas *canvas, VALUE ele) {
if (rb_obj_is_kind_of(ele, cBackground)) {
fprintf(stderr, "skipping background widget\n");
//fprintf(stderr, "skipping background widget\n");
return;
}
// Find a delegate or use the Toy ?
// Find a delegate or use the internal default?
if (canvas->layout_mgr != Qnil) {
shoes_layout *ly;
Data_Get_Struct(canvas->layout_mgr, shoes_layout, ly);
if (! NIL_P(ly->delegate)) {
fprintf(stderr,"Delegating\n");
//printf(stderr,"Delegating\n");
VALUE del = ly->delegate;
ID s_addw = rb_intern("add_widget");
ID s_addw = rb_intern("add");
if (rb_respond_to(del, s_addw))
rb_funcall(del, s_addw, 1, ele);
//return;
rb_funcall(del, s_addw, 2, ly->canvas, ele);
else {
rb_raise( rb_eArgError, "'add' not implment in Layout");
}
return;
}
}
if (rb_obj_is_kind_of(ele, cButton)) {
fprintf(stderr, "shoes_layout_add Button\n");
} else if (rb_obj_is_kind_of(ele, cPara)) {
fprintf(stderr,"shoes layout_add Para\n");
} else {
fprintf(stderr, "shoes_layout_add something\n");
}
}
// here if no delgate or no manager object
shoes_layout_default_add(canvas, ele);
return;
}

VALUE shoes_layout_delete_ele(shoes_canvas *canvas, VALUE ele) {
fprintf(stderr,"shoes_layout_delete called\n");
// called from inside shoes (shoes_canvas_clear)
void shoes_layout_clear(shoes_canvas *canvas) {
fprintf(stderr,"shoes_layout_clear called\n");
if (canvas->layout_mgr != Qnil) {
shoes_layout *ly;
Data_Get_Struct(canvas->layout_mgr, shoes_layout, ly);
if (! NIL_P(ly->delegate)) {
//printf(stderr,"Delegating\n");
VALUE del = ly->delegate;
ID s_clear = rb_intern("clear");
if (rb_respond_to(del, s_clear))
rb_funcall(del, s_clear, 0);
else {
rb_raise( rb_eArgError, "'clear' not implment in Layout");
}
return;
}
}
// here if no delgate or no manager object
shoes_layout_default_clear(canvas);
return;
}

/*
* Methods to call the default layout manager -
* Might be a cassawory variant? grid_bag? Something Gtk or Cocoa?
*/
void shoes_layout_default_add(shoes_canvas *canvas, VALUE ele) {
fprintf(stderr, "default layout add\n");
}

void shoes_layout_default_clear(shoes_canvas *canvas) {
fprintf(stderr, "default layout clear\n");
}

extern VALUE shoes_layout_add_rule(VALUE self, VALUE rule) {
VALUE shoes_layout_add_rule(VALUE self, VALUE rule) {
fprintf(stderr,"shoes_layout_add_rule called\n");
}

extern VALUE shoes_layout_compute(VALUE self) {
VALUE shoes_layout_compute(VALUE self) {
fprintf(stderr, "shoes_layout_compute called\n");
}
Loading

0 comments on commit ffec6c9

Please sign in to comment.