diff --git a/src/lib/aqdiagram/draw/w_drawable.c b/src/lib/aqdiagram/draw/w_drawable.c index e3eef45..fbf5673 100644 --- a/src/lib/aqdiagram/draw/w_drawable.c +++ b/src/lib/aqdiagram/draw/w_drawable.c @@ -366,7 +366,7 @@ int AQDG_DrawableWidget_DrawChildren(AQDG_OBJECT *object) -int _drawFallback(AQDG_OBJECT *object) +void AQDG_DrawableWidget_DefaultDraw(AQDG_OBJECT *object) { AQDG_OBJECT_DRAWABLE *xo; @@ -375,14 +375,20 @@ int _drawFallback(AQDG_OBJECT *object) AQDG_DrawableWidget_DrawBackground(object); AQDG_DrawableWidget_DrawChildren(object); AQDG_Object_SubFlags(object, AQDG_OBJECT_FLAGS_DRAW); - return 1; } - return 0; } -void AQDG_DrawableWidget_UpdateTextContentDims(AQDG_OBJECT *object) +int _drawFallback(AQDG_OBJECT *object) +{ + AQDG_DrawableWidget_DefaultDraw(object); + return 1; +} + + + +int AQDG_DrawableWidget_GetTextDefaultWidth(AQDG_OBJECT *object) { if (object) { AQDG_OBJECT_DRAWABLE *xo; @@ -391,18 +397,35 @@ void AQDG_DrawableWidget_UpdateTextContentDims(AQDG_OBJECT *object) if (xo) { if (xo->text) { int w; - int h; w=AQDG_DrawableWidget_GetTextWidth(object); w+=AQDG_Object_GetBorderLeft(object)+AQDG_Object_GetBorderRight(object); - h=AQDG_DrawableWidget_GetTextHeight(object); - h+=AQDG_Object_GetBorderTop(object)+AQDG_Object_GetBorderBottom(object); - - AQDG_Object_SetContentWidth(object, w); - AQDG_Object_SetContentHeight(object, h); + return w; } } } + return 0; +} + + + +int AQDG_DrawableWidget_GetTextDefaultHeight(AQDG_OBJECT *object) +{ + if (object) { + AQDG_OBJECT_DRAWABLE *xo; + + xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_OBJECT_DRAWABLE, object); + if (xo) { + if (xo->text) { + int h; + + h=AQDG_DrawableWidget_GetTextHeight(object); + h+=AQDG_Object_GetBorderTop(object)+AQDG_Object_GetBorderBottom(object); + return h; + } + } + } + return 0; } diff --git a/src/lib/aqdiagram/draw/w_drawable.h b/src/lib/aqdiagram/draw/w_drawable.h index 36967c2..39c6bff 100644 --- a/src/lib/aqdiagram/draw/w_drawable.h +++ b/src/lib/aqdiagram/draw/w_drawable.h @@ -61,6 +61,7 @@ AQDG_API void AQDG_DrawableWidget_SetContentWidth(AQDG_OBJECT *object, int i); AQDG_API int AQDG_DrawableWidget_GetContentHeight(const AQDG_OBJECT *object); AQDG_API void AQDG_DrawableWidget_SetContentHeight(AQDG_OBJECT *object, int i); +AQDG_API void AQDG_DrawableWidget_DefaultDraw(AQDG_OBJECT *object); AQDG_API AQDG_WIDGET_DRAWABLE_DRAW_FN AQDG_DrawableWidget_SetDrawFn(AQDG_OBJECT *object, AQDG_WIDGET_DRAWABLE_DRAW_FN fn); @@ -71,8 +72,8 @@ AQDG_API int AQDG_DrawableWidget_DrawBackground(AQDG_OBJECT *object); AQDG_API int AQDG_DrawableWidget_DrawChildren(AQDG_OBJECT *object); AQDG_API void AQDG_DrawableWidget_DrawText(AQDG_OBJECT *object, int x, int y, const char *text); - -AQDG_API void AQDG_DrawableWidget_UpdateTextContentDims(AQDG_OBJECT *object); +AQDG_API int AQDG_DrawableWidget_GetTextDefaultWidth(AQDG_OBJECT *object); +AQDG_API int AQDG_DrawableWidget_GetTextDefaultHeight(AQDG_OBJECT *object); AQDG_API int AQDG_DrawableWidget_GetTextWidth(AQDG_OBJECT *object); AQDG_API int AQDG_DrawableWidget_GetTextHeight(AQDG_OBJECT *object); @@ -81,5 +82,6 @@ AQDG_API AQDG_OBJECT *AQDG_DrawableWidget_GetFirstVisibleChild(const AQDG_OBJECT AQDG_API AQDG_OBJECT *AQDG_DrawableWidget_GetNextVisibleWidget(AQDG_OBJECT *o); AQDG_API void AQDG_DrawableWidget_UnhideAllChildren(AQDG_OBJECT *o); + #endif diff --git a/src/lib/aqdiagram/draw/w_label.c b/src/lib/aqdiagram/draw/w_label.c index 00d6e07..ab4a2e1 100644 --- a/src/lib/aqdiagram/draw/w_label.c +++ b/src/lib/aqdiagram/draw/w_label.c @@ -24,7 +24,6 @@ */ static int _draw(AQDG_OBJECT *object); -static int _calcContentDims(AQDG_OBJECT *object); static int _calcXPos(AQDG_OBJECT *object, uint32_t opts, int tw); static int _calcYPos(AQDG_OBJECT *object, uint32_t opts, int th); @@ -44,7 +43,8 @@ AQDG_OBJECT *AQDG_LabelWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_DR object=AQDG_DrawableWidget_new(parent, options, drawContext); AQDG_Object_SetName(object, "LabelWidget"); AQDG_Object_SetOptions(object, options); - AQDG_Object_SetCalcContentDimsFn(object, _calcContentDims); + AQDG_Object_SetGetDefaultWidthFn(object, AQDG_DrawableWidget_GetTextDefaultWidth); + AQDG_Object_SetGetDefaultHeightFn(object, AQDG_DrawableWidget_GetTextDefaultHeight); AQDG_DrawableWidget_SetDrawFn(object, _draw); if (text) AQDG_DrawableWidget_SetText(object, text); @@ -53,16 +53,6 @@ AQDG_OBJECT *AQDG_LabelWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_DR -int _calcContentDims(AQDG_OBJECT *object) -{ - AQDG_DrawableWidget_UpdateTextContentDims(object); - return 1; -} - - - - - int _draw(AQDG_OBJECT *object) { if (object) { diff --git a/src/lib/aqdiagram/graph/w_axis.c b/src/lib/aqdiagram/graph/w_axis.c index b0c2ffe..6a57ddc 100644 --- a/src/lib/aqdiagram/graph/w_axis.c +++ b/src/lib/aqdiagram/graph/w_axis.c @@ -66,6 +66,10 @@ AQDG_OBJECT *AQDG_AxisWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_OBJ /* set defaults */ xo->scaleSize=AQDG_AXISWIDGET_SCALESIZE; + AQDG_DrawableWidget_SetBackgroundPenId(o, AQDG_GraphWidget_GetPen(graphObject, AQDG_GRAPHWIDGET_PEN_IDX_BACKGROUND)); + AQDG_DrawableWidget_SetForegroundPenId(o, AQDG_GraphWidget_GetPen(graphObject, AQDG_GRAPHWIDGET_PEN_IDX_AXISLINE)); + AQDG_DrawableWidget_SetFontId(o, AQDG_GraphWidget_GetFont(graphObject, AQDG_GRAPHWIDGET_FONT_IDX_AXISLABEL)); + _setupObjectTree(o); return o; @@ -257,6 +261,9 @@ void _createTickLabelsForLevel(AQDG_OBJECT *o, AQDG_GRAPH *graph, const AQDG_GRA oNew=AQDG_LabelWidget_new(o, opts, dc, s); AQDG_DrawableWidget_SetValue(oNew, AQDG_Graph_Tick_GetValue(tick)); + AQDG_DrawableWidget_SetBackgroundPenId(oNew, AQDG_GraphWidget_GetPen(xo->graphObject, AQDG_GRAPHWIDGET_PEN_IDX_BACKGROUND)); + AQDG_DrawableWidget_SetForegroundPenId(oNew, AQDG_GraphWidget_GetPen(xo->graphObject, AQDG_GRAPHWIDGET_PEN_IDX_AXISLABEL)); + AQDG_DrawableWidget_SetFontId(oNew, AQDG_GraphWidget_GetFont(xo->graphObject, AQDG_GRAPHWIDGET_FONT_IDX_AXISLABEL)); } } diff --git a/src/lib/aqdiagram/graph/w_graph.c b/src/lib/aqdiagram/graph/w_graph.c index 92f23bb..8716c61 100644 --- a/src/lib/aqdiagram/graph/w_graph.c +++ b/src/lib/aqdiagram/graph/w_graph.c @@ -32,7 +32,8 @@ static GWENHYWFAR_CB void _freeData(void *bp, void *p); static void _setupObjectTree(AQDG_OBJECT *o); static void _setupMatrix(AQDG_OBJECT *o); -static AQDG_OBJECT *_createLabel(AQDG_OBJECT *o, AQDG_OBJECT *parent, uint32_t options, const char *s, int penIdx, int fontIdx); +static AQDG_OBJECT *_createLabel(AQDG_OBJECT *o, AQDG_OBJECT *parent, const char *name, + uint32_t options, const char *s, int penIdx, int fontIdx); @@ -63,7 +64,7 @@ GWEN_INHERIT(AQDG_OBJECT, AQDG_WIDGET_GRAPH); -AQDG_OBJECT *AQDG_GraphWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_DRAW_CONTEXT *drawContext, AQDG_GRAPH *graph) +AQDG_OBJECT *AQDG_GraphWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_DRAW_CONTEXT *drawContext) { AQDG_OBJECT *o; AQDG_WIDGET_GRAPH *xo; @@ -73,10 +74,6 @@ AQDG_OBJECT *AQDG_GraphWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_DR GWEN_NEW_OBJECT(AQDG_WIDGET_GRAPH, xo); GWEN_INHERIT_SETDATA(AQDG_OBJECT, AQDG_WIDGET_GRAPH, o, xo, _freeData); - xo->graph=graph; - - _setupObjectTree(o); - return o; } @@ -93,6 +90,23 @@ GWENHYWFAR_CB void _freeData(void *bp, void *p) +void AQDG_GraphWidget_SetupForGraph(AQDG_OBJECT *o, AQDG_GRAPH *graph) +{ + if (o && graph) { + AQDG_WIDGET_GRAPH *xo; + + xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_WIDGET_GRAPH, o); + if (xo) { + xo->graph=graph; + AQDG_DrawableWidget_SetBackgroundPenId(o, xo->penArray[AQDG_GRAPHWIDGET_PEN_IDX_BACKGROUND]); + _setupObjectTree(o); + } + } +} + + + + void _setupObjectTree(AQDG_OBJECT *o) { AQDG_WIDGET_GRAPH *xo; @@ -103,8 +117,9 @@ void _setupObjectTree(AQDG_OBJECT *o) s=AQDG_Graph_GetTitle(xo->graph); if (s) _createLabel(o, - o, - AQDG_OBJECT_OPTIONS_STRETCHX | AQDG_OBJECT_OPTIONS_HALIGNCENTER, + o, + "titleLabel", + AQDG_OBJECT_OPTIONS_HALIGNCENTER, s, AQDG_GRAPHWIDGET_PEN_IDX_TITLE, AQDG_GRAPHWIDGET_FONT_IDX_TITLE); @@ -113,7 +128,8 @@ void _setupObjectTree(AQDG_OBJECT *o) if (s) _createLabel(o, o, - AQDG_OBJECT_OPTIONS_STRETCHX | AQDG_OBJECT_OPTIONS_HALIGNCENTER, + "subTitleLabel", + AQDG_OBJECT_OPTIONS_HALIGNCENTER, s, AQDG_GRAPHWIDGET_PEN_IDX_SUBTITLE, AQDG_GRAPHWIDGET_FONT_IDX_SUBTITLE); @@ -172,7 +188,8 @@ void _setupMatrix(AQDG_OBJECT *o) -AQDG_OBJECT *_createLabel(AQDG_OBJECT *o, AQDG_OBJECT *parent, uint32_t options, const char *s, int penIdx, int fontIdx) +AQDG_OBJECT *_createLabel(AQDG_OBJECT *o, AQDG_OBJECT *parent, const char *name, + uint32_t options, const char *s, int penIdx, int fontIdx) { AQDG_OBJECT *oLabel; int penId; @@ -181,6 +198,8 @@ AQDG_OBJECT *_createLabel(AQDG_OBJECT *o, AQDG_OBJECT *parent, uint32_t options, penId=AQDG_GraphWidget_GetPen(o, penIdx); fontId=AQDG_GraphWidget_GetFont(o, fontIdx); oLabel=AQDG_LabelWidget_new(o, options, AQDG_DrawableWidget_GetDrawContext(o), s); + if (name && *name) + AQDG_Object_SetName(oLabel, name); if (penId!=-1) AQDG_DrawableWidget_SetForegroundPenId(oLabel, penId); if (fontId!=-1) @@ -452,6 +471,71 @@ uint32_t AQDG_GraphWidget_GetStandardCurveColor(int idx, uint32_t defCol) +void AQDG_GraphWidget_SetupDefaultPens(AQDG_OBJECT *o) +{ + AQDG_WIDGET_GRAPH *xo; + + xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_WIDGET_GRAPH, o); + if (xo) { + AQDG_DRAW_CONTEXT *dc; + + dc=AQDG_DrawableWidget_GetDrawContext(o); +#define MKSOLIDPEN(penArrayIdx, penColour, penSize) \ + xo->penArray[penArrayIdx]=AQDG_Draw_Context_PenCreate(dc, penColour, penSize, AQDG_Dash_None); + + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_TITLE, AQDG_GRAPHWIDGET_COL_BLACK, 2); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_SUBTITLE, AQDG_GRAPHWIDGET_COL_BLACK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_AXISLINE, AQDG_GRAPHWIDGET_COL_BLACK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_AXISLABEL, AQDG_GRAPHWIDGET_COL_BLACK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_TICKLABELMAINLEVEL, AQDG_GRAPHWIDGET_COL_BLACK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_TICKLABELSUBLEVEL, AQDG_GRAPHWIDGET_COL_BLACK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_TICKMAINLEVEL, AQDG_GRAPHWIDGET_COL_BLACK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_TICKSUBLEVEL, AQDG_GRAPHWIDGET_COL_BLACK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_GRAPHBACKGROUND, AQDG_GRAPHWIDGET_COL_WHITESMOKE, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_GRID, AQDG_GRAPHWIDGET_COL_BLACK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_BACKGROUND, AQDG_GRAPHWIDGET_COL_GAINSBORO, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_CURVE0, AQDG_GRAPHWIDGET_COL_LIME, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_CURVE1, AQDG_GRAPHWIDGET_COL_BLUE, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_CURVE2, AQDG_GRAPHWIDGET_COL_CYAN, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_CURVE3, AQDG_GRAPHWIDGET_COL_MAGENTA, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_CURVE4, AQDG_GRAPHWIDGET_COL_GREEN, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_CURVE5, AQDG_GRAPHWIDGET_COL_TURQUOISE, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_CURVE6, AQDG_GRAPHWIDGET_COL_DEEPPINK, 1); + MKSOLIDPEN(AQDG_GRAPHWIDGET_PEN_IDX_CURVE7, AQDG_GRAPHWIDGET_COL_NAVY, 1); + +#undef MKSOLIDPEN + + } +} + + + +void AQDG_GraphWidget_SetupDefaultFonts(AQDG_OBJECT *o) +{ + AQDG_WIDGET_GRAPH *xo; + + xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_WIDGET_GRAPH, o); + if (xo) { + AQDG_DRAW_CONTEXT *dc; + + dc=AQDG_DrawableWidget_GetDrawContext(o); +#define MKNORMALFONT(fontArrayIdx, fontSize) \ + xo->fontArray[fontArrayIdx]=AQDG_Draw_Context_FontCreate(dc, "", fontSize, AQDG_Slant_None, AQDG_Weight_None); + + MKNORMALFONT(AQDG_GRAPHWIDGET_FONT_IDX_TITLE, 16); + MKNORMALFONT(AQDG_GRAPHWIDGET_FONT_IDX_SUBTITLE, 12); + MKNORMALFONT(AQDG_GRAPHWIDGET_FONT_IDX_AXISLABEL, 12); + MKNORMALFONT(AQDG_GRAPHWIDGET_FONT_IDX_TICKLABELMAINLEVEL, 12); + MKNORMALFONT(AQDG_GRAPHWIDGET_FONT_IDX_TICKLABELSUBLEVEL, 10); + +#undef MKNORMALFONT + } +} + + + + + diff --git a/src/lib/aqdiagram/graph/w_graph.h b/src/lib/aqdiagram/graph/w_graph.h index 7cb34a2..e555a42 100644 --- a/src/lib/aqdiagram/graph/w_graph.h +++ b/src/lib/aqdiagram/graph/w_graph.h @@ -81,7 +81,8 @@ enum { -AQDG_API AQDG_OBJECT *AQDG_GraphWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_DRAW_CONTEXT *drawContext, AQDG_GRAPH *graph); +AQDG_API AQDG_OBJECT *AQDG_GraphWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_DRAW_CONTEXT *drawContext); +AQDG_API void AQDG_GraphWidget_SetupForGraph(AQDG_OBJECT *o, AQDG_GRAPH *graph); AQDG_API AQDG_GRAPH *AQDG_GraphWidget_GetGraph(const AQDG_OBJECT *o); @@ -97,6 +98,10 @@ AQDG_API int AQDG_GraphWidget_CreatePenFromDb(AQDG_OBJECT *o, GWEN_DB_NODE *db, AQDG_API int AQDG_GraphWidget_CreateFontFromDb(AQDG_OBJECT *o, GWEN_DB_NODE *db, const char *name, int defaultFontSize); AQDG_API uint32_t AQDG_GraphWidget_GetStandardCurveColor(int idx, uint32_t defCol); +AQDG_API void AQDG_GraphWidget_SetupDefaultPens(AQDG_OBJECT *o); +AQDG_API void AQDG_GraphWidget_SetupDefaultFonts(AQDG_OBJECT *o); + + #endif diff --git a/src/lib/aqdiagram/graph/w_viewport.c b/src/lib/aqdiagram/graph/w_viewport.c index 20d98b4..527169d 100644 --- a/src/lib/aqdiagram/graph/w_viewport.c +++ b/src/lib/aqdiagram/graph/w_viewport.c @@ -47,6 +47,12 @@ AQDG_OBJECT *AQDG_ViewportWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG xo->graphObject=graphObject; + AQDG_DrawableWidget_SetBackgroundPenId(o, AQDG_GraphWidget_GetPen(graphObject, AQDG_GRAPHWIDGET_PEN_IDX_GRAPHBACKGROUND)); + AQDG_Object_SetBorderLeft(o, 0); + AQDG_Object_SetBorderRight(o, 0); + AQDG_Object_SetBorderTop(o, 0); + AQDG_Object_SetBorderBottom(o, 0); + return o; } @@ -64,4 +70,17 @@ GWENHYWFAR_CB void _freeData(void *bp, void *p) +int _calcHorizontalPos(double value, int contentSize, double minValue, double maxValue) +{ + return ((value-minValue)*(contentSize/(maxValue-minValue))); +} + + + +int _calcVerticalPos(double value, int contentSize, double minValue, double maxValue) +{ + return (contentSize-((value-minValue)*(contentSize/(maxValue-minValue)))); +} + + diff --git a/src/lib/aqdiagram/graph/w_xaxis.c b/src/lib/aqdiagram/graph/w_xaxis.c index bbe4f16..dd10540 100644 --- a/src/lib/aqdiagram/graph/w_xaxis.c +++ b/src/lib/aqdiagram/graph/w_xaxis.c @@ -14,6 +14,7 @@ #include "./w_axis.h" #include "aqdiagram/draw/w_drawable.h" #include "aqdiagram/draw/w_label.h" +#include "aqdiagram/placement/o_layout.h" #include @@ -24,9 +25,15 @@ * ------------------------------------------------------------------------------------------------ */ -static int _calcContentDims(AQDG_OBJECT *object); static int _layout(AQDG_OBJECT *object); -static int _calcHorizontalPos(double value, int contentSize, int borderSize, double minValue, double maxValue); +static int _draw(AQDG_OBJECT *object); +static void _drawTicks(AQDG_OBJECT *o, AQDG_DRAW_CONTEXT *dc, int absY); +static int _getDefaultWidth(AQDG_OBJECT *o); +static int _getDefaultHeight(AQDG_OBJECT *o); +static int _calcHorizontalPos(double value, int contentSize, double minValue, double maxValue); +static void _setChildrenRelXFromValue(AQDG_OBJECT *o); +static void _setChildrenRelY(AQDG_OBJECT *o); +static void _setChildrenSizes(AQDG_OBJECT *o); @@ -45,44 +52,140 @@ AQDG_OBJECT *AQDG_XAxisWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_OB AQDG_Object_SetName(o, "XAxisWidget"); AQDG_Object_SetLayoutFn(o, _layout); - AQDG_Object_SetCalcContentDimsFn(o, _calcContentDims); + AQDG_DrawableWidget_SetDrawFn(o, _draw); + AQDG_Object_SetGetDefaultWidthFn(o, _getDefaultWidth); + AQDG_Object_SetGetDefaultHeightFn(o, _getDefaultHeight); + AQDG_Object_SetBorderLeft(o, 0); + AQDG_Object_SetBorderRight(o, 0); return o; } -int _calcContentDims(AQDG_OBJECT *object) +int _layout(AQDG_OBJECT *o) { - /* TODO - * - get axis - * - get ticks - * - calc max height of tick labels - * - add size of axis line + tick lines + spacing - */ + _setChildrenSizes(o); + _setChildrenRelXFromValue(o); + _setChildrenRelY(o); + AQDG_DrawableWidget_UnhideAllChildren(o); + AQDG_AxisWidget_HideCollidingChildren(o); + AQDG_LayoutObject_LayoutChildren(o); return 1; } -int _layout(AQDG_OBJECT *object) +int _draw(AQDG_OBJECT *object) { - /* TODO */ + AQDG_DRAW_CONTEXT *dc; + int y; + int x1; + int x2; + int pen; + + AQDG_DrawableWidget_DefaultDraw(object); + + dc=AQDG_DrawableWidget_GetDrawContext(object); + y=AQDG_Object_GetAbsoluteY(object); + y+=AQDG_Object_GetBorderTop(object); + x1=AQDG_Object_GetAbsoluteX(object)+AQDG_Object_GetBorderLeft(object); + x2=AQDG_Object_GetAbsoluteX(object)+AQDG_Object_GetWidth(object)-AQDG_Object_GetBorderRight(object); + pen=AQDG_DrawableWidget_GetForegroundPenId(object); + AQDG_Draw_Context_DrawLine(dc, pen, x1, y, x2, y); + _drawTicks(object, dc, y); + return 1; } +void _drawTicks(AQDG_OBJECT *o, AQDG_DRAW_CONTEXT *dc, int absY) +{ + AQDG_OBJECT *graphObject; + AQDG_GRAPH *graph; + AQDG_GRAPH_AXIS *axis; + + graphObject=AQDG_AxisWidget_GetGraphObject(o); + graph=AQDG_GraphWidget_GetGraph(graphObject); + axis=AQDG_Graph_GetAxisByIndex(graph, AQDG_AxisWidget_GetAxisIndex(o)); + if (axis) { + const AQDG_GRAPH_TICK_LIST *tickList; + + tickList=AQDG_Graph_Axis_GetTickList(axis); + if (tickList) { + const AQDG_GRAPH_TICK *tick; + int contentSize; + int scaleSize; + double minValue; + double maxValue; + int absX; + int pen; + + contentSize=AQDG_Object_GetWidth(o)-AQDG_Object_GetBorderLeft(o)-AQDG_Object_GetBorderRight(o); + scaleSize=AQDG_AxisWidget_GetScaleSize(o); + absX=AQDG_Object_GetAbsoluteX(o); + minValue=AQDG_AxisWidget_GetMinValue(o); + maxValue=AQDG_AxisWidget_GetMaxValue(o); + pen=AQDG_DrawableWidget_GetForegroundPenId(o); + + tick=AQDG_Graph_Tick_List_First(tickList); + while(tick) { + if (AQDG_Graph_Tick_GetLevel(tick)==0) { + double value; + int xpos; + + value=AQDG_Graph_Tick_GetValue(tick); + xpos=_calcHorizontalPos(value, contentSize, minValue, maxValue); + xpos+=AQDG_Object_GetBorderLeft(o); + AQDG_Draw_Context_DrawLine(dc, pen, absX+xpos, absY-(scaleSize/2), absX+xpos, absY+(scaleSize/2)); + } + tick=AQDG_Graph_Tick_List_Next(tick); + } + } + } +} + + + +int _getDefaultWidth(AQDG_OBJECT *o) +{ + return 1; +} + + + +int _getDefaultHeight(AQDG_OBJECT *o) +{ + AQDG_OBJECT *child; + int h=0; + + /* get max label height */ + child=AQDG_Object_Tree2_GetFirstChild(o); + while(child) { + int i; + + i=AQDG_Object_GetDefaultHeight(child); + h=(i>h)?i:h; + child=AQDG_Object_Tree2_GetNext(child); + } + + /* add space for scale, top border and bottom border */ + h+=AQDG_AxisWidget_GetScaleSize(o); + h+=AQDG_Object_GetBorderTop(o)+AQDG_Object_GetBorderBottom(o); + return h; +} + + + void _setChildrenRelXFromValue(AQDG_OBJECT *o) { AQDG_OBJECT *child; int contentSize; - int borderSize; double minValue; double maxValue; - contentSize=AQDG_Object_GetContentWidth(o); - borderSize=AQDG_Object_GetBorderLeft(o); + contentSize=AQDG_Object_GetWidth(o); minValue=AQDG_AxisWidget_GetMinValue(o); maxValue=AQDG_AxisWidget_GetMaxValue(o); @@ -92,7 +195,9 @@ void _setChildrenRelXFromValue(AQDG_OBJECT *o) double value; value=AQDG_DrawableWidget_GetValue(child); - pos=_calcHorizontalPos(value, contentSize, borderSize, minValue, maxValue); + pos=_calcHorizontalPos(value, contentSize, minValue, maxValue); + pos+=AQDG_Object_GetBorderLeft(o); + pos-=AQDG_Object_GetWidth(child)/2; AQDG_Object_SetRelativeX(child, pos); /* TODO: take label size into account */ child=AQDG_Object_Tree2_GetNext(child); } @@ -104,13 +209,13 @@ void _setChildrenRelY(AQDG_OBJECT *o) { int contentSize; - contentSize=AQDG_Object_GetContentHeight(o); + contentSize=AQDG_Object_GetHeight(o); - if (AQDG_AxisWidget_GetAxisIndex(o)==AQDG_GRAPH_AXISPOS_BOTTOM) { + if (AQDG_AxisWidget_GetAxisIndex(o)==AQDG_GRAPH_AXISPOS_TOP) { AQDG_OBJECT *child; int borderSize; - borderSize=AQDG_Object_GetBorderTop(o)+AQDG_AxisWidget_GetScaleSize(o); + borderSize=AQDG_Object_GetBorderTop(o); /* align left */ child=AQDG_Object_Tree2_GetFirstChild(o); while(child) { @@ -123,7 +228,7 @@ void _setChildrenRelY(AQDG_OBJECT *o) int borderSize; /* align right */ - borderSize=AQDG_Object_GetBorderBottom(o)+AQDG_AxisWidget_GetScaleSize(o); + borderSize=AQDG_Object_GetBorderBottom(o); child=AQDG_Object_Tree2_GetFirstChild(o); while(child) { int pos; @@ -139,9 +244,23 @@ void _setChildrenRelY(AQDG_OBJECT *o) -int _calcHorizontalPos(double value, int contentSize, int borderSize, double minValue, double maxValue) +void _setChildrenSizes(AQDG_OBJECT *o) { - return borderSize+((value-minValue)*(contentSize/(maxValue-minValue))); + AQDG_OBJECT *child; + + child=AQDG_Object_Tree2_GetFirstChild(o); + while(child) { + AQDG_Object_SetWidth(child, AQDG_Object_GetDefaultWidth(child)); + AQDG_Object_SetHeight(child, AQDG_Object_GetDefaultHeight(child)); + child=AQDG_Object_Tree2_GetNext(child); + } +} + + + +int _calcHorizontalPos(double value, int contentSize, double minValue, double maxValue) +{ + return ((value-minValue)*(contentSize/(maxValue-minValue))); } diff --git a/src/lib/aqdiagram/graph/w_yaxis.c b/src/lib/aqdiagram/graph/w_yaxis.c index 31b2381..17f6f12 100644 --- a/src/lib/aqdiagram/graph/w_yaxis.c +++ b/src/lib/aqdiagram/graph/w_yaxis.c @@ -13,6 +13,7 @@ #include "./w_yaxis.h" #include "./w_axis.h" #include "aqdiagram/draw/w_drawable.h" +#include "aqdiagram/placement/o_layout.h" #include @@ -23,11 +24,15 @@ * ------------------------------------------------------------------------------------------------ */ -static int _calcContentDims(AQDG_OBJECT *object); +static int _getDefaultWidth(AQDG_OBJECT *o); +static int _getDefaultHeight(AQDG_OBJECT *o); static int _layout(AQDG_OBJECT *object); +static int _draw(AQDG_OBJECT *object); +static void _drawTicks(AQDG_OBJECT *o, AQDG_DRAW_CONTEXT *dc, int x); static void _setChildrenRelX(AQDG_OBJECT *o); static void _setChildrenRelYFromValue(AQDG_OBJECT *o); -static int _calcVerticalPos(double value, int contentSize, int borderSize, double minValue, double maxValue); +static void _setChildrenSizes(AQDG_OBJECT *o); +static int _calcVerticalPos(double value, int contentSize, double minValue, double maxValue); @@ -44,25 +49,28 @@ AQDG_OBJECT *AQDG_YAxisWidget_new(AQDG_OBJECT *parent, uint32_t options, AQDG_OB AQDG_Object_SetName(o, "YAxisWidget"); AQDG_Object_SetLayoutFn(o, _layout); - AQDG_Object_SetCalcContentDimsFn(o, _calcContentDims); + AQDG_DrawableWidget_SetDrawFn(o, _draw); + AQDG_Object_SetGetDefaultWidthFn(o, _getDefaultWidth); + AQDG_Object_SetGetDefaultHeightFn(o, _getDefaultHeight); + AQDG_Object_SetBorderTop(o, 0); + AQDG_Object_SetBorderBottom(o, 0); return o; } -int _calcContentDims(AQDG_OBJECT *o) +int _getDefaultWidth(AQDG_OBJECT *o) { AQDG_OBJECT *child; int w=0; - int h=1; /* get max label width */ child=AQDG_Object_Tree2_GetFirstChild(o); while(child) { int i; - i=AQDG_Object_GetWidth(child); + i=AQDG_Object_GetDefaultWidth(child); w=(i>w)?i:w; child=AQDG_Object_Tree2_GetNext(child); } @@ -70,10 +78,13 @@ int _calcContentDims(AQDG_OBJECT *o) /* add space for scale, left border and right border */ w+=AQDG_AxisWidget_GetScaleSize(o); w+=AQDG_Object_GetBorderLeft(o)+AQDG_Object_GetBorderRight(o); + return w; +} - AQDG_Object_SetContentWidth(o, w); - AQDG_Object_SetContentHeight(o, h); + +int _getDefaultHeight(AQDG_OBJECT *o) +{ return 1; } @@ -81,21 +92,94 @@ int _calcContentDims(AQDG_OBJECT *o) int _layout(AQDG_OBJECT *o) { + _setChildrenSizes(o); _setChildrenRelX(o); _setChildrenRelYFromValue(o); AQDG_DrawableWidget_UnhideAllChildren(o); AQDG_AxisWidget_HideCollidingChildren(o); + AQDG_LayoutObject_LayoutChildren(o); + return 1; +} + + + +int _draw(AQDG_OBJECT *object) +{ + AQDG_DRAW_CONTEXT *dc; + int x; + int y1; + int y2; + int pen; + + AQDG_DrawableWidget_DefaultDraw(object); + + dc=AQDG_DrawableWidget_GetDrawContext(object); + x=AQDG_Object_GetAbsoluteX(object); + x+=AQDG_Object_GetWidth(object)-AQDG_Object_GetBorderRight(object); + y1=AQDG_Object_GetAbsoluteY(object)+AQDG_Object_GetBorderTop(object); + y2=AQDG_Object_GetAbsoluteY(object)+AQDG_Object_GetHeight(object)-AQDG_Object_GetBorderBottom(object); + pen=AQDG_DrawableWidget_GetForegroundPenId(object); + AQDG_Draw_Context_DrawLine(dc, pen, x, y1, x, y2); + _drawTicks(object, dc, x); return 1; } +void _drawTicks(AQDG_OBJECT *o, AQDG_DRAW_CONTEXT *dc, int absX) +{ + AQDG_OBJECT *graphObject; + AQDG_GRAPH *graph; + AQDG_GRAPH_AXIS *axis; + + graphObject=AQDG_AxisWidget_GetGraphObject(o); + graph=AQDG_GraphWidget_GetGraph(graphObject); + axis=AQDG_Graph_GetAxisByIndex(graph, AQDG_AxisWidget_GetAxisIndex(o)); + if (axis) { + const AQDG_GRAPH_TICK_LIST *tickList; + + tickList=AQDG_Graph_Axis_GetTickList(axis); + if (tickList) { + const AQDG_GRAPH_TICK *tick; + int contentSize; + int scaleSize; + double minValue; + double maxValue; + int absY; + int pen; + + contentSize=AQDG_Object_GetHeight(o)-AQDG_Object_GetBorderTop(o)-AQDG_Object_GetBorderBottom(o); + scaleSize=AQDG_AxisWidget_GetScaleSize(o); + absY=AQDG_Object_GetAbsoluteY(o); + minValue=AQDG_AxisWidget_GetMinValue(o); + maxValue=AQDG_AxisWidget_GetMaxValue(o); + pen=AQDG_DrawableWidget_GetForegroundPenId(o); + + tick=AQDG_Graph_Tick_List_First(tickList); + while(tick) { + if (AQDG_Graph_Tick_GetLevel(tick)==0) { + double value; + int ypos; + + value=AQDG_Graph_Tick_GetValue(tick); + ypos=_calcVerticalPos(value, contentSize, minValue, maxValue); + ypos+=AQDG_Object_GetBorderTop(o); + AQDG_Draw_Context_DrawLine(dc, pen, absX-(scaleSize/2), absY+ypos, absX+(scaleSize/2), absY+ypos); + } + tick=AQDG_Graph_Tick_List_Next(tick); + } + } + } +} + + + void _setChildrenRelX(AQDG_OBJECT *o) { int contentSize; - contentSize=AQDG_Object_GetContentWidth(o); + contentSize=AQDG_Object_GetWidth(o); if (AQDG_AxisWidget_GetAxisIndex(o)==AQDG_GRAPH_AXISPOS_RIGHT) { AQDG_OBJECT *child; @@ -122,7 +206,7 @@ void _setChildrenRelX(AQDG_OBJECT *o) cwidth=AQDG_Object_GetWidth(child); pos=contentSize-cwidth-borderSize; - AQDG_Object_SetRelativeX(child, pos); /* TODO: take label size into account */ + AQDG_Object_SetRelativeX(child, pos); child=AQDG_Object_Tree2_GetNext(child); } } @@ -134,12 +218,10 @@ void _setChildrenRelYFromValue(AQDG_OBJECT *o) { AQDG_OBJECT *child; int contentSize; - int borderSize; double minValue; double maxValue; - contentSize=AQDG_Object_GetContentHeight(o); - borderSize=AQDG_Object_GetBorderTop(o); + contentSize=AQDG_Object_GetHeight(o)-AQDG_Object_GetBorderTop(o)-AQDG_Object_GetBorderBottom(o); minValue=AQDG_AxisWidget_GetMinValue(o); maxValue=AQDG_AxisWidget_GetMaxValue(o); @@ -149,7 +231,9 @@ void _setChildrenRelYFromValue(AQDG_OBJECT *o) double value; value=AQDG_DrawableWidget_GetValue(child); - pos=_calcVerticalPos(value, contentSize, borderSize, minValue, maxValue); + pos=_calcVerticalPos(value, contentSize, minValue, maxValue); + pos+=AQDG_Object_GetBorderTop(o); + pos-=AQDG_Object_GetHeight(child)/2; AQDG_Object_SetRelativeY(child, pos); /* TODO: take label size into account */ child=AQDG_Object_Tree2_GetNext(child); } @@ -157,12 +241,26 @@ void _setChildrenRelYFromValue(AQDG_OBJECT *o) +void _setChildrenSizes(AQDG_OBJECT *o) +{ + AQDG_OBJECT *child; + + child=AQDG_Object_Tree2_GetFirstChild(o); + while(child) { + AQDG_Object_SetWidth(child, AQDG_Object_GetDefaultWidth(child)); + AQDG_Object_SetHeight(child, AQDG_Object_GetDefaultHeight(child)); + child=AQDG_Object_Tree2_GetNext(child); + } +} + + + /** * special case because 0/0 is top left corner, so we need to flip contentSize */ -int _calcVerticalPos(double value, int contentSize, int borderSize, double minValue, double maxValue) +int _calcVerticalPos(double value, int contentSize, double minValue, double maxValue) { - return borderSize+(contentSize-((value-minValue)*(contentSize/(maxValue-minValue)))); + return (contentSize-((value-minValue)*(contentSize/(maxValue-minValue)))); } diff --git a/src/lib/aqdiagram/libtest.c b/src/lib/aqdiagram/libtest.c index c3c0570..0678724 100644 --- a/src/lib/aqdiagram/libtest.c +++ b/src/lib/aqdiagram/libtest.c @@ -20,6 +20,7 @@ #include #include #include +#include #include #include @@ -36,6 +37,7 @@ +static AQDG_GRAPH *_mkTestGraph(); static void _dumpTicks(const AQDG_GRAPH_TICK_LIST *tickList); @@ -123,6 +125,47 @@ int test1(int argc, char **argv) int test2(int argc, char **argv) +{ + AQDG_GRAPH *g; + + g=_mkTestGraph(); + AQDG_Graph_free(g); + return 0; +} + + + +int test3() +{ + AQDG_GRAPH *g; + AQDG_DRAW_CONTEXT *dc; + AQDG_OBJECT *graphObject; + + g=_mkTestGraph(); + dc=AQDG_Draw_ContextCairo_Png_new("/tmp/testgraph.png", 800, 600); + graphObject=AQDG_GraphWidget_new(NULL, AQDG_OBJECT_OPTIONS_STRETCHX | AQDG_OBJECT_OPTIONS_STRETCHY, dc); + AQDG_Object_SetWidth(graphObject, 800); + AQDG_Object_SetHeight(graphObject, 600); + + AQDG_GraphWidget_SetupDefaultPens(graphObject); + AQDG_GraphWidget_SetupDefaultFonts(graphObject); + AQDG_GraphWidget_SetupForGraph(graphObject, g); + + AQDG_Object_ModifyBranchFlagsDown(graphObject, AQDG_OBJECT_FLAGS_RECALC, AQDG_OBJECT_FLAGS_RECALC); + AQDG_Object_ModifyBranchFlagsDown(graphObject, AQDG_OBJECT_FLAGS_LAYOUT, AQDG_OBJECT_FLAGS_LAYOUT); + AQDG_Object_Layout(graphObject); + AQDG_Object_Tree2_CalculateAbsPositions(graphObject); + AQDG_Object_Dump(graphObject, 2); + + AQDG_DrawableWidget_Draw(graphObject); + AQDG_Draw_Context_Finish(dc); + + return 0; +} + + + +AQDG_GRAPH *_mkTestGraph() { AQDG_GRAPH *g; AQDG_GRAPH_AXIS *xAxis; @@ -134,7 +177,7 @@ int test2(int argc, char **argv) xAxis=AQDG_Graph_Axis_new(); AQDG_Graph_Axis_SetLabel(xAxis, "Label X"); - AQDG_Graph_Axis_SetMinValue(xAxis, -5.0); + AQDG_Graph_Axis_SetMinValue(xAxis, -23.0); AQDG_Graph_Axis_SetMaxValue(xAxis, 117.0); AQDG_Graph_Axis_SetPrecision(xAxis, 0); AQDG_Graph_SetAxis(g, AQDG_GRAPH_AXISPOS_BOTTOM, xAxis); @@ -147,9 +190,10 @@ int test2(int argc, char **argv) yAxis=AQDG_Graph_Axis_new(); AQDG_Graph_Axis_SetLabel(yAxis, "Label Y"); - AQDG_Graph_Axis_SetMinValue(yAxis, -27.0); + AQDG_Graph_Axis_SetMinValue(yAxis, -127.0); AQDG_Graph_Axis_SetMaxValue(yAxis, 1235.0); AQDG_Graph_Axis_SetPrecision(yAxis, 2); + AQDG_Graph_SetAxis(g, AQDG_GRAPH_AXISPOS_LEFT, yAxis); fprintf(stderr, "Generating ticks for Y-axis\n"); AQDG_Graph_Axis_GenLog10Ticks(yAxis); fprintf(stderr, "Ticks for Y-Axis (%f - %f)\n", @@ -157,9 +201,7 @@ int test2(int argc, char **argv) AQDG_Graph_Axis_GetMaxValue(yAxis)); _dumpTicks(AQDG_Graph_Axis_GetTickList(yAxis)); - AQDG_Graph_SetAxis(g, AQDG_GRAPH_AXISPOS_LEFT, yAxis); - - return 0; + return g; } @@ -226,8 +268,9 @@ int main(int argc, char **argv) GWEN_Logger_SetLevel(AQDG_LOGDOMAIN, GWEN_LoggerLevel_Info); GWEN_Logger_SetLevel(NULL, GWEN_LoggerLevel_Info); - rv=test1(argc, argv); - rv=test2(argc, argv); +// rv=test1(argc, argv); +// rv=test2(argc, argv); + rv=test3(); if (rv!=0){ DBG_ERROR(NULL, "here (%d)", rv); diff --git a/src/lib/aqdiagram/placement/o_hlayout-t.c b/src/lib/aqdiagram/placement/o_hlayout-t.c index 7f4603c..cd6112b 100644 --- a/src/lib/aqdiagram/placement/o_hlayout-t.c +++ b/src/lib/aqdiagram/placement/o_hlayout-t.c @@ -31,6 +31,8 @@ static int GWENHYWFAR_CB test1(GWEN_TEST_MODULE *mod); static AQDG_OBJECT *_createBox10x10(uint32_t opts); +static int _getDefaultWidth10(AQDG_OBJECT *o); +static int _getDefaultHeight10(AQDG_OBJECT *o); @@ -164,13 +166,25 @@ AQDG_OBJECT *_createBox10x10(uint32_t opts) box=AQDG_Object_new(); AQDG_Object_SetOptions(box, opts); - AQDG_Object_SetContentWidth(box, 10); - AQDG_Object_SetContentHeight(box, 10); + AQDG_Object_SetGetDefaultWidthFn(box, _getDefaultWidth10); + AQDG_Object_SetGetDefaultHeightFn(box, _getDefaultHeight10); return box; } +int _getDefaultWidth10(AQDG_OBJECT *o) +{ + return 10; +} + + +int _getDefaultHeight10(AQDG_OBJECT *o) +{ + return 10; +} + + #else int AQDG_HLayoutObject_AddTests(GWEN_TEST_MODULE *mod) diff --git a/src/lib/aqdiagram/placement/o_hlayout.c b/src/lib/aqdiagram/placement/o_hlayout.c index fa9ce5a..a618be7 100644 --- a/src/lib/aqdiagram/placement/o_hlayout.c +++ b/src/lib/aqdiagram/placement/o_hlayout.c @@ -22,7 +22,6 @@ */ static int _layout(AQDG_OBJECT *object); -static int _calcContentDims(AQDG_OBJECT *object); static int _calcContentWidth(AQDG_OBJECT *object); static int _calcContentHeight(AQDG_OBJECT *object); @@ -42,7 +41,8 @@ AQDG_OBJECT *AQDG_HLayoutObject_new(AQDG_OBJECT *parent, uint32_t options) AQDG_Object_SetOptions(object, options); AQDG_Object_SetLayoutFn(object, _layout); - AQDG_Object_SetCalcContentDimsFn(object, _calcContentDims); + AQDG_Object_SetGetDefaultWidthFn(object, _calcContentWidth); + AQDG_Object_SetGetDefaultHeightFn(object, _calcContentHeight); if (parent) AQDG_Object_Tree2_AddChild(parent, object); @@ -81,6 +81,7 @@ int _layout(AQDG_OBJECT *object) AQDG_LayoutObject_ChildrenFromElementsY(object, elements, num); free(elements); } + AQDG_LayoutObject_LayoutChildren(object); } return 0; @@ -88,14 +89,6 @@ int _layout(AQDG_OBJECT *object) -int _calcContentDims(AQDG_OBJECT *object) -{ - AQDG_Object_SetContentWidth(object, _calcContentWidth(object)); - AQDG_Object_SetContentHeight(object, _calcContentHeight(object)); - return 0; -} - - int _calcContentWidth(AQDG_OBJECT *object) { AQDG_OBJECT *child; diff --git a/src/lib/aqdiagram/placement/o_layout.c b/src/lib/aqdiagram/placement/o_layout.c index 05fc63c..f4ecbda 100644 --- a/src/lib/aqdiagram/placement/o_layout.c +++ b/src/lib/aqdiagram/placement/o_layout.c @@ -19,7 +19,7 @@ * ------------------------------------------------------------------------------------------------ */ -static void _setElementFromObjectX(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OBJECT *object); +static void _setElementFromObjectX(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, AQDG_OBJECT *object); static void _setElementFromObjectY(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OBJECT *object); static void _setObjectFromElementX(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr); static void _setObjectFromElementY(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr); @@ -57,7 +57,7 @@ AQDG_PLACEMENT_LAYOUT_ELEMENT *AQDG_LayoutObject_Children2ElementsX(const AQDG_O -AQDG_PLACEMENT_LAYOUT_ELEMENT *AQDG_LayoutObject_ObjectList2ElementsX(const AQDG_OBJECT *object, int num) +AQDG_PLACEMENT_LAYOUT_ELEMENT *AQDG_LayoutObject_ObjectList2ElementsX(AQDG_OBJECT *object, int num) { if (object && num) { AQDG_PLACEMENT_LAYOUT_ELEMENT *elements; @@ -194,13 +194,13 @@ void AQDG_LayoutObject_SetChildrenHeights(AQDG_OBJECT *object) -void _setElementFromObjectX(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OBJECT *object) +void _setElementFromObjectX(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, AQDG_OBJECT *object) { uint32_t opts; opts=AQDG_Object_GetOptions(object); eptr->pos=0; - eptr->length=AQDG_Object_GetWidth(object); + eptr->length=AQDG_Object_GetDefaultWidth(object); eptr->opts=(opts & AQDG_OBJECT_OPTIONS_STRETCHX)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_STRETCH:0; eptr->opts|=(opts & AQDG_OBJECT_OPTIONS_HALIGNCENTER)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_CENTER:0; eptr->opts|=(opts & AQDG_OBJECT_OPTIONS_HALIGNRIGHT)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_RIGHT:0; @@ -239,5 +239,17 @@ void _setObjectFromElementY(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELE +void AQDG_LayoutObject_LayoutChildren(AQDG_OBJECT *o) +{ + if (o) { + AQDG_OBJECT *child; + + child=AQDG_Object_Tree2_GetFirstChild(o); + while(child) { + AQDG_Object_Layout(child); + child=AQDG_Object_Tree2_GetNext(child); + } + } +} diff --git a/src/lib/aqdiagram/placement/o_layout.h b/src/lib/aqdiagram/placement/o_layout.h index 7abda35..5cdefe7 100644 --- a/src/lib/aqdiagram/placement/o_layout.h +++ b/src/lib/aqdiagram/placement/o_layout.h @@ -19,7 +19,7 @@ AQDG_API int AQDG_LayoutObject_CountDirectChildren(const AQDG_OBJECT *object); AQDG_API AQDG_PLACEMENT_LAYOUT_ELEMENT *AQDG_LayoutObject_Children2ElementsX(const AQDG_OBJECT *object, int num); -AQDG_API AQDG_PLACEMENT_LAYOUT_ELEMENT *AQDG_LayoutObject_ObjectList2ElementsX(const AQDG_OBJECT *object, int num); +AQDG_API AQDG_PLACEMENT_LAYOUT_ELEMENT *AQDG_LayoutObject_ObjectList2ElementsX(AQDG_OBJECT *object, int num); AQDG_API AQDG_PLACEMENT_LAYOUT_ELEMENT *AQDG_LayoutObject_Children2ElementsY(const AQDG_OBJECT *object, int num); AQDG_API AQDG_PLACEMENT_LAYOUT_ELEMENT *AQDG_LayoutObject_ObjectList2ElementsY(const AQDG_OBJECT *object, int num); @@ -33,6 +33,7 @@ AQDG_API void AQDG_LayoutObject_Elements2ObjectListY(AQDG_OBJECT *object, const AQDG_API void AQDG_LayoutObject_SetChildrenWidths(AQDG_OBJECT *object); AQDG_API void AQDG_LayoutObject_SetChildrenHeights(AQDG_OBJECT *object); +AQDG_API void AQDG_LayoutObject_LayoutChildren(AQDG_OBJECT *o); diff --git a/src/lib/aqdiagram/placement/o_mlayout.c b/src/lib/aqdiagram/placement/o_mlayout.c index 100d44a..1d317a0 100644 --- a/src/lib/aqdiagram/placement/o_mlayout.c +++ b/src/lib/aqdiagram/placement/o_mlayout.c @@ -13,6 +13,9 @@ #include "o_mlayout_p.h" #include "o_layout.h" +#include + + /* ------------------------------------------------------------------------------------------------ * forward declarations @@ -28,21 +31,26 @@ static void _layoutSecondaryY(AQDG_OBJECT *object, int numElements); static void _layoutSecondaryX(AQDG_OBJECT *object, int numElements); static AQDG_PLACEMENT_LAYOUT_ELEMENT *_mkEmptyElementList(int num); -static void _mergeObjectsIntoElementsX(const AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements); -static void _mergeObjectsIntoElementsY(const AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements); +static void _mergeObjectsIntoElementsByRowX(AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements); +static void _mergeObjectsIntoElementsByRowY(AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements); -static void _mergeObjectXIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OBJECT *object); -static void _mergeObjectYIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OBJECT *object); +static void _mergeObjectXIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, AQDG_OBJECT *object); +static void _mergeObjectYIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, AQDG_OBJECT *object); -static void _setChildrenFromElementsX(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *elements, int num); +static void _setChildrenFromElementsByRowX(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *elements, int num); +static void _setChildrenFromElementsByRowY(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *elements, int num); static void _setChildrenFromElementsY(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *elements, int num); static void _setObjectFromElementX(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr); static void _setObjectFromElementY(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr); -static int _calcDimsByRows(AQDG_OBJECT *object); -static int _calcDimsByColumns(AQDG_OBJECT *object); +static int _getDefaultWidthByRows(AQDG_OBJECT *object); +static int _getDefaultHeightByRows(AQDG_OBJECT *object); -static int _calcWidthByRows(const AQDG_OBJECT *object, int columns); +static int _getDefaultWidthByColumns(AQDG_OBJECT *object); +static int _getDefaultHeightByColumns(AQDG_OBJECT *object); + +static int _calcWidthByRows(AQDG_OBJECT *object, int columns); +static int _calcMaxColumnWidth(AQDG_OBJECT *object, int columns); static int _calcHeightByRows(const AQDG_OBJECT *object, int columns); static int _calcWidthByColumns(const AQDG_OBJECT *object, int rows); @@ -65,7 +73,8 @@ AQDG_OBJECT *AQDG_MatrixLayoutObjectByRows_new(AQDG_OBJECT *parent, uint32_t opt object=_matrixLayoutObject_new(parent, options, columns); AQDG_Object_SetLayoutFn(object, _layoutByRows); - AQDG_Object_SetCalcContentDimsFn(object, _calcDimsByRows); + AQDG_Object_SetGetDefaultWidthFn(object, _getDefaultWidthByRows); + AQDG_Object_SetGetDefaultHeightFn(object, _getDefaultHeightByRows); return object; } @@ -77,7 +86,8 @@ AQDG_OBJECT *AQDG_MatrixLayoutObjectByColumns_new(AQDG_OBJECT *parent, uint32_t object=_matrixLayoutObject_new(parent, options, rows); AQDG_Object_SetLayoutFn(object, _layoutByColumns); - AQDG_Object_SetCalcContentDimsFn(object, _calcDimsByColumns); + AQDG_Object_SetGetDefaultWidthFn(object, _getDefaultWidthByColumns); + AQDG_Object_SetGetDefaultHeightFn(object, _getDefaultHeightByColumns); return object; } @@ -121,23 +131,42 @@ int _layoutByRows(AQDG_OBJECT *object) xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_OBJECT_MLAYOUT, object); if (xo) { AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements; - int numElements; + int numColumns; + int numRows; + int numChildren; - numElements=xo->numRowsOrColumns; - ptrElements=_mkEmptyElementList(numElements); + numColumns=xo->numRowsOrColumns; + numChildren=AQDG_LayoutObject_CountDirectChildren(object); + numRows=(numChildren+numColumns)/numColumns; + + /* layout columns */ + ptrElements=_mkEmptyElementList(numColumns); if (ptrElements) { - _mergeObjectsIntoElementsX(object, ptrElements, numElements); - AQDG_Placement_LayoutAndStretch(ptrElements, numElements, + _mergeObjectsIntoElementsByRowX(object, ptrElements, numColumns); + AQDG_Placement_LayoutAndStretch(ptrElements, numColumns, AQDG_Object_GetWidth(object), AQDG_Object_GetBorderLeft(object), AQDG_Object_GetBorderRight(object), AQDG_Object_GetHSpacing(object)); - _setChildrenFromElementsX(object, ptrElements, numElements); + _setChildrenFromElementsByRowX(object, ptrElements, numColumns); + free(ptrElements); + } + + /* layout rows */ + ptrElements=_mkEmptyElementList(numRows); + if (ptrElements) { + _mergeObjectsIntoElementsByRowY(object, ptrElements, numColumns); + AQDG_Placement_LayoutAndStretch(ptrElements, numRows, + AQDG_Object_GetHeight(object), + AQDG_Object_GetBorderTop(object), + AQDG_Object_GetBorderBottom(object), + AQDG_Object_GetVSpacing(object)); + _setChildrenFromElementsByRowY(object, ptrElements, numColumns); free(ptrElements); - _layoutSecondaryY(object, numElements); } } + AQDG_LayoutObject_LayoutChildren(object); return 0; } @@ -145,8 +174,11 @@ int _layoutByRows(AQDG_OBJECT *object) int _layoutByColumns(AQDG_OBJECT *object) { +#warning "TODO" +#if 0 AQDG_OBJECT_MLAYOUT *xo; + DBG_ERROR(NULL, "%s: LayoutByColumns", AQDG_Object_GetName(object)); xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_OBJECT_MLAYOUT, object); if (xo) { AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements; @@ -155,7 +187,7 @@ int _layoutByColumns(AQDG_OBJECT *object) numElements=xo->numRowsOrColumns; ptrElements=_mkEmptyElementList(numElements); if (ptrElements) { - _mergeObjectsIntoElementsY(object, ptrElements, numElements); + _mergeObjectsIntoElementsByColumnY(object, ptrElements, numElements); AQDG_Placement_LayoutAndStretch(ptrElements, numElements, AQDG_Object_GetHeight(object), AQDG_Object_GetBorderTop(object), @@ -167,6 +199,8 @@ int _layoutByColumns(AQDG_OBJECT *object) _layoutSecondaryX(object, numElements); } } + AQDG_LayoutObject_LayoutChildren(object); +#endif return 0; } @@ -180,7 +214,7 @@ void _layoutSecondaryY(AQDG_OBJECT *object, int numElements) while(child) { AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements; int i; - + // TODO: only distribute across row, not full widget!! /* handle numElements */ ptrElements=AQDG_LayoutObject_ObjectList2ElementsY(child, numElements); AQDG_Placement_LayoutSecondaryAxis(ptrElements, numElements, @@ -245,9 +279,9 @@ AQDG_PLACEMENT_LAYOUT_ELEMENT *_mkEmptyElementList(int num) -void _mergeObjectsIntoElementsX(const AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements) +void _mergeObjectsIntoElementsByRowX(AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements) { - const AQDG_OBJECT *child; + AQDG_OBJECT *child; int i=0; child=AQDG_Object_Tree2_GetFirstChild(object); @@ -260,9 +294,29 @@ void _mergeObjectsIntoElementsX(const AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT -void _mergeObjectsIntoElementsY(const AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements) +void _mergeObjectsIntoElementsByRowY(AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements) { - const AQDG_OBJECT *child; + AQDG_OBJECT *child; + int r=0; + int i=0; + + child=AQDG_Object_Tree2_GetFirstChild(object); + while(child) { + _mergeObjectYIntoElement(&ptrElements[r], child); + i++; + if (i>=numElements) { + r++; + i=0; + } + child=AQDG_Object_Tree2_GetNext(child); + } +} + + + +void _mergeObjectsIntoColumnElementsY(AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT_ELEMENT *ptrElements, int numElements) +{ + AQDG_OBJECT *child; int i=0; child=AQDG_Object_Tree2_GetFirstChild(object); @@ -275,15 +329,15 @@ void _mergeObjectsIntoElementsY(const AQDG_OBJECT *object, AQDG_PLACEMENT_LAYOUT -void _mergeObjectXIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OBJECT *object) +void _mergeObjectXIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, AQDG_OBJECT *object) { uint32_t opts; int len; opts=AQDG_Object_GetOptions(object); eptr->pos=0; - len=AQDG_Object_GetWidth(object);; - eptr->length=(len>eptr->length)?len:(len>eptr->length); + len=AQDG_Object_GetDefaultWidth(object); + eptr->length=(len>eptr->length)?len:(eptr->length); eptr->opts=(opts & AQDG_OBJECT_OPTIONS_STRETCHX)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_STRETCH:0; eptr->opts|=(opts & AQDG_OBJECT_OPTIONS_HALIGNCENTER)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_CENTER:0; eptr->opts|=(opts & AQDG_OBJECT_OPTIONS_HALIGNRIGHT)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_RIGHT:0; @@ -291,15 +345,15 @@ void _mergeObjectXIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OB -void _mergeObjectYIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OBJECT *object) +void _mergeObjectYIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, AQDG_OBJECT *object) { uint32_t opts; int len; opts=AQDG_Object_GetOptions(object); eptr->pos=0; - len=AQDG_Object_GetHeight(object); - eptr->length=(len>eptr->length)?len:(len>eptr->length); + len=AQDG_Object_GetDefaultHeight(object); + eptr->length=(len>eptr->length)?len:(eptr->length); eptr->opts=(opts & AQDG_OBJECT_OPTIONS_STRETCHY)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_STRETCH:0; eptr->opts|=(opts & AQDG_OBJECT_OPTIONS_VALIGNCENTER)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_CENTER:0; eptr->opts|=(opts & AQDG_OBJECT_OPTIONS_VALIGNBOTTOM)?AQDG_PLACEMENT_LAYOUT_ELEMENT_OPTS_RIGHT:0; @@ -307,7 +361,7 @@ void _mergeObjectYIntoElement(AQDG_PLACEMENT_LAYOUT_ELEMENT *eptr, const AQDG_OB -void _setChildrenFromElementsX(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *elements, int num) +void _setChildrenFromElementsByRowX(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *elements, int num) { if (num && elements) { AQDG_OBJECT *child; @@ -324,6 +378,28 @@ void _setChildrenFromElementsX(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ +void _setChildrenFromElementsByRowY(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *elements, int num) +{ + if (num && elements) { + AQDG_OBJECT *child; + int i=0; + int r=0; + + child=AQDG_Object_Tree2_GetFirstChild(object); + while(child) { + _setObjectFromElementY(child, &elements[r]); + i++; + if (i>=num) { + r++; + i=0; + } + child=AQDG_Object_Tree2_GetNext(child); + } + } +} + + + void _setChildrenFromElementsY(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELEMENT *elements, int num) { if (num && elements) { @@ -357,69 +433,64 @@ void _setObjectFromElementY(AQDG_OBJECT *object, const AQDG_PLACEMENT_LAYOUT_ELE - -int _calcDimsByRows(AQDG_OBJECT *object) +int _getDefaultWidthByRows(AQDG_OBJECT *object) { AQDG_OBJECT_MLAYOUT *xo; xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_OBJECT_MLAYOUT, object); - if (xo) { - AQDG_Object_SetContentWidth(object, _calcWidthByRows(object, xo->numRowsOrColumns)); - AQDG_Object_SetContentHeight(object, _calcHeightByRows(object, xo->numRowsOrColumns)); - return 1; - } - return 0; + return xo?_calcWidthByRows(object, xo->numRowsOrColumns):0; } -int _calcDimsByColumns(AQDG_OBJECT *object) +int _getDefaultHeightByRows(AQDG_OBJECT *object) { AQDG_OBJECT_MLAYOUT *xo; xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_OBJECT_MLAYOUT, object); - if (xo) { - AQDG_Object_SetContentWidth(object, _calcWidthByColumns(object, xo->numRowsOrColumns)); - AQDG_Object_SetContentHeight(object, _calcHeightByColumns(object, xo->numRowsOrColumns)); - return 1; - } - return 0; + return xo?_calcHeightByRows(object, xo->numRowsOrColumns):0; } -int _calcWidthByRows(const AQDG_OBJECT *object, int columns) +int _getDefaultWidthByColumns(AQDG_OBJECT *object) +{ + AQDG_OBJECT_MLAYOUT *xo; + + xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_OBJECT_MLAYOUT, object); + return xo?_calcWidthByColumns(object, xo->numRowsOrColumns):0; +} + + + +int _getDefaultHeightByColumns(AQDG_OBJECT *object) +{ + AQDG_OBJECT_MLAYOUT *xo; + + xo=GWEN_INHERIT_GETDATA(AQDG_OBJECT, AQDG_OBJECT_MLAYOUT, object); + return xo?_calcHeightByColumns(object, xo->numRowsOrColumns):0; +} + + + +int _calcWidthByRows(AQDG_OBJECT *object, int columns) { AQDG_OBJECT *child; int i=0; - int cw=0; int w; w=AQDG_Object_GetBorderLeft(object); i=0; - cw=0; child=AQDG_Object_Tree2_GetFirstChild(object); while(child && icw)?k:cw; - while(n && jw)?cw:w; + //DBG_ERROR(NULL, "row %d: %d (%s)", row, cw, AQDG_Object_GetName(object)); + + while(object && i - - with_tree2 - with_tree2 - - $(api) int $(struct_prefix)_GetDefaultWidth($(struct_type) *object); - - - - - with_tree2 - with_tree2 - - int $(struct_prefix)_GetDefaultWidth($(struct_type) *object) \n - { \n - if (object) { \n - if (object->flags & AQDG_OBJECT_FLAGS_RECALC) { \n - $(struct_prefix)_CalcContentDims(object); \n - object->flags &=~AQDG_OBJECT_FLAGS_RECALC; \n - } \n - return object->contentWidth; \n - } \n - return 1; \n - } \n - - - - - - - $(api) int $(struct_prefix)_GetDefaultHeight($(struct_type) *object); - - - - - - int $(struct_prefix)_GetDefaultHeight($(struct_type) *object)\n - { \n - if (object) { \n - if (object->flags & AQDG_OBJECT_FLAGS_RECALC) { \n - $(struct_prefix)_CalcContentDims(object); \n - object->flags &=~AQDG_OBJECT_FLAGS_RECALC; \n - } \n - return object->contentHeight; \n - } \n - return 1; \n - } \n - - - - $(api) void $(struct_prefix)_Tree2_CalculateAbsPositions($(struct_type) *object); @@ -188,9 +138,8 @@ for(i=0; i<indent+2; i++) \n fprintf(stderr, " "); \n fprintf(stderr, \n - "hSpacing=%d, vSpacing=%d, contWidth=%d, contWidthHeight=%d\\n",\n - object->hSpacing, object->vSpacing, \n - object->contentWidth, object->contentHeight); \n + "hSpacing=%d, vSpacing=%d\\n", \n + object->hSpacing, object->vSpacing); \n \n child=$(struct_prefix)_Tree2_GetFirstChild(object); \n while(child) { \n @@ -330,20 +279,6 @@ - - 0 - 0 - public - - - - - 0 - 0 - public - - - 0 0 @@ -364,11 +299,19 @@ - + public - 0 + 1 + int + + + + + + public + 1 int