source: Dev/branches/rest-dojo-ui/client/dijit/layout/utils.js @ 256

Last change on this file since 256 was 256, checked in by hendrikvanantwerpen, 13 years ago

Reworked project structure based on REST interaction and Dojo library. As
soon as this is stable, the old jQueryUI branch can be removed (it's
kept for reference).

File size: 4.9 KB
Line 
1define([
2        "dojo/_base/array", // array.filter array.forEach
3        "dojo/dom-class", // domClass.add domClass.remove
4        "dojo/dom-geometry", // domGeometry.marginBox
5        "dojo/dom-style", // domStyle.getComputedStyle
6        "dojo/_base/lang", // lang.mixin
7        ".."    // for exporting symbols to dijit, remove in 2.0
8], function(array, domClass, domGeometry, domStyle, lang, dijit){
9
10        // module:
11        //              dijit/layout/utils
12        // summary:
13        //              marginBox2contentBox() and layoutChildren()
14
15        var layout = lang.getObject("layout", true, dijit);
16        /*===== layout = dijit.layout =====*/
17
18        layout.marginBox2contentBox = function(/*DomNode*/ node, /*Object*/ mb){
19                // summary:
20                //              Given the margin-box size of a node, return its content box size.
21                //              Functions like domGeometry.contentBox() but is more reliable since it doesn't have
22                //              to wait for the browser to compute sizes.
23                var cs = domStyle.getComputedStyle(node);
24                var me = domGeometry.getMarginExtents(node, cs);
25                var pb = domGeometry.getPadBorderExtents(node, cs);
26                return {
27                        l: domStyle.toPixelValue(node, cs.paddingLeft),
28                        t: domStyle.toPixelValue(node, cs.paddingTop),
29                        w: mb.w - (me.w + pb.w),
30                        h: mb.h - (me.h + pb.h)
31                };
32        };
33
34        function capitalize(word){
35                return word.substring(0,1).toUpperCase() + word.substring(1);
36        }
37
38        function size(widget, dim){
39                // size the child
40                var newSize = widget.resize ? widget.resize(dim) : domGeometry.setMarginBox(widget.domNode, dim);
41
42                // record child's size
43                if(newSize){
44                        // if the child returned it's new size then use that
45                        lang.mixin(widget, newSize);
46                }else{
47                        // otherwise, call getMarginBox(), but favor our own numbers when we have them.
48                        // the browser lies sometimes
49                        lang.mixin(widget, domGeometry.getMarginBox(widget.domNode));
50                        lang.mixin(widget, dim);
51                }
52        }
53
54        layout.layoutChildren = function(/*DomNode*/ container, /*Object*/ dim, /*Widget[]*/ children,
55                        /*String?*/ changedRegionId, /*Number?*/ changedRegionSize){
56                // summary:
57                //              Layout a bunch of child dom nodes within a parent dom node
58                // container:
59                //              parent node
60                // dim:
61                //              {l, t, w, h} object specifying dimensions of container into which to place children
62                // children:
63                //              an array of Widgets or at least objects containing:
64                //                      * domNode: pointer to DOM node to position
65                //                      * region or layoutAlign: position to place DOM node
66                //                      * resize(): (optional) method to set size of node
67                //                      * id: (optional) Id of widgets, referenced from resize object, below.
68                // changedRegionId:
69                //              If specified, the slider for the region with the specified id has been dragged, and thus
70                //              the region's height or width should be adjusted according to changedRegionSize
71                // changedRegionSize:
72                //              See changedRegionId.
73
74                // copy dim because we are going to modify it
75                dim = lang.mixin({}, dim);
76
77                domClass.add(container, "dijitLayoutContainer");
78
79                // Move "client" elements to the end of the array for layout.  a11y dictates that the author
80                // needs to be able to put them in the document in tab-order, but this algorithm requires that
81                // client be last.    TODO: move these lines to LayoutContainer?   Unneeded other places I think.
82                children = array.filter(children, function(item){ return item.region != "center" && item.layoutAlign != "client"; })
83                        .concat(array.filter(children, function(item){ return item.region == "center" || item.layoutAlign == "client"; }));
84
85                // set positions/sizes
86                array.forEach(children, function(child){
87                        var elm = child.domNode,
88                                pos = (child.region || child.layoutAlign);
89                        if(!pos){
90                                throw new Error("No region setting for " + child.id)
91                        }
92
93                        // set elem to upper left corner of unused space; may move it later
94                        var elmStyle = elm.style;
95                        elmStyle.left = dim.l+"px";
96                        elmStyle.top = dim.t+"px";
97                        elmStyle.position = "absolute";
98
99                        domClass.add(elm, "dijitAlign" + capitalize(pos));
100
101                        // Size adjustments to make to this child widget
102                        var sizeSetting = {};
103
104                        // Check for optional size adjustment due to splitter drag (height adjustment for top/bottom align
105                        // panes and width adjustment for left/right align panes.
106                        if(changedRegionId && changedRegionId == child.id){
107                                sizeSetting[child.region == "top" || child.region == "bottom" ? "h" : "w"] = changedRegionSize;
108                        }
109
110                        // set size && adjust record of remaining space.
111                        // note that setting the width of a <div> may affect its height.
112                        if(pos == "top" || pos == "bottom"){
113                                sizeSetting.w = dim.w;
114                                size(child, sizeSetting);
115                                dim.h -= child.h;
116                                if(pos == "top"){
117                                        dim.t += child.h;
118                                }else{
119                                        elmStyle.top = dim.t + dim.h + "px";
120                                }
121                        }else if(pos == "left" || pos == "right"){
122                                sizeSetting.h = dim.h;
123                                size(child, sizeSetting);
124                                dim.w -= child.w;
125                                if(pos == "left"){
126                                        dim.l += child.w;
127                                }else{
128                                        elmStyle.left = dim.l + dim.w + "px";
129                                }
130                        }else if(pos == "client" || pos == "center"){
131                                size(child, dim);
132                        }
133                });
134        };
135
136
137        return {
138                marginBox2contentBox: layout.marginBox2contentBox,
139                layoutChildren: layout.layoutChildren
140        };
141});
Note: See TracBrowser for help on using the repository browser.