Composer
The Composer class hold a matrix of placed items. It allows to search for empty spaces
(with a defined or undefined size) and can place items on an area of grid positions.
The constructor attributes width and height defined the size of the internal
composer grid. The optional hotspots attribute defines a list of points [(x1,y1), (x2,y2), ...]
that work as ordered list of relevant points or as magnetic points to answer the most relevant free area.
If one of x or y values is None, then use the tuple as the indicator of a magnetic line.
Note that the name “elements” used in the source of the Composer class is not for instances of the Element database elements, just local generic elements to be placed in the matrix, spanning multiple cells that can expose themselves on a canvas.
Note that the name “elements” used in the source of the Composer class is not for instances of the Element database elements, just local generic elements to be placed in the matrix, spanning multiple cells that can expose themselves on a canvas.
Import
from xpyth.xierpa.imaging.composer import Composer
How to use the composer
c = Composer(10,8) c.printdump()

We can add elements to the place at a certain fixed position.
c = Composer(10,8)
c.place('aba', 4,2,4,4 )
c.printdump()

Then we can place another element on the composer, partly overlapping the previous element. Note that the cell numbers indicate that 2 elements are placed on that position. This happens because 'aba' and 'xyz' are differnt objects. Otherwise the cell count would not be incremented.
c = Composer(10,8)
c.place('aba', 4,2,4,4 )
c.place('xyz', 2,4,7,4 )
c.printdump()

This way manually elements can be placed on the matrix. Also it is possible to ask the composer for all free rectangles at a given position.
free = c.getfree(1,1)
But the composer also can be used to search for free spaces. The code
free = c.findfirstfree(3,3)
((0,0), [(10,2), (4,4), (2,8)]),
showing several options to accommodate a square of 2x2.
If the result free is None then no free space was found to accommodate the requested size.
@@@@ MORE MANUAL TO BE ADDED.
An overview
The Composer class contains the following methods:| Method | Attributes | Docstring or default value |
|---|---|---|
| AREA | 3 | |
| HORIZONTAL | 1 | |
| MAGNETIC | 5 | |
| RELEVANCE | 6 | |
| RESERVED | 'Reserved' | |
| SQUARE | 4 | |
| VERTICAL | 2 | |
| clear |
The clear does clear the current position and element content. Also the current hot element is cleared.
|
|
| copy |
The copy method answers a copy of self, including copies of self._matrix, self._elements
and self._elementsbyorder. The contained items are not copied, just another reference is made by the copy. This allows a page to replacing the original composer by the copy if placements turn out to be successful after a simulation of placements, while referring to the same items. |
|
| deflate |
The deflate method alternates between x and y while removing duplicate or empty rows and columns.
Each pass the matrix gets smaller until there is no change with the pre-pre-version.
The smallest definition of the matrix is then stored in the composer.
|
|
| dump |
The dump method answers a string showing the filled matrix.
|
|
| extendable | direction element x y |
The extendable method answers a list of tuples (the element may have multiple placements in the composer)
that indicates to what size the placed elements could be extended from the current position of the elememt.
(So including the current size of the element). If the element cannot be extended then answer an empty list. If there is no element
at the requested position or if the element is not placed then answer None. The optional attribute direction
defines the direction of the requested extension. It can hold one of the values [self.VERTICAL, self.HORIZONTAL].
The default value is self.VERTICAL. Note that extending the composer space does not have automatic influence on the size the element will expose. E.g. there is no reflow of placed proof text. The application needs to adjust the content of the element to fit the extended space. |
| finddistinctpositions | height width |
The finddistinctpositions method answers a dictionary of possible coordinates that can accommodate a requested width
and height rectangle. Key of the dictionary is the (x,y) and value is a list of all possible ((w1,h1), (w2,h2), ...)
free rectangles on that position, while selecting only distinct rectangles, omitting all rectangles that fit inside others. If not limited by width or height, then set these values to the at maximum possible size on the current position. |
| findfirstfree | height hotspots placement width |
The findfirstfree method answers the first topleft coordinate from the result list of findfree().
The placement can have the values self.RELEVANCE, Composer.MAGNETIC,
Composer.VERTICAL (default) and Composer.HORIZONTAL to indicate the searching direction.
The optional width and height attributes define a requested size to accommodate.
If the search is done by self.RELEVANCE, then the composer answers the first point in the hotspot list that
is not occupied. This technique allows to define a list of areas that will be filled in a particular order. Note that one
placement may occupy several hotspots at the time. If there are no free hostspot points available hotspots left, the
page is considered “filled” without searching of other free area’s. If the search is done by self.MAGNETIC, then the composer answers the free space closest to one of the hotspot points. If the attribute hotspots is None then the single magnetic point [(0,0)] is used. In general the format of the list is [(x1,y1), (x2,y2), ...]. If one of x or y values is None, then use the tuple as the indicator of a magnetic line. |
| findfree | height width |
The findfree method answers a dictionary of possible coordinates that can accommodate a requested width
and height. Key of the dictionary is the (x,y) and value is a list of possible ((w1,h1), (w2,h2), ...)
on that position.
|
| getelements |
The getelements method answers a dictionary with elements as keys and (((x, y), (w, h)), ...),
a list of position/size tuples as value. Note that this must be a list, since in theory the same object can be placed
on multiple positions on the page.
|
|
| getelementsbyorder |
The getelementsbyorder method answers a list of elements in the order that they where splaced.
|
|
| getfree | height width x y |
The getfree method answers a list of (w,h) tuples, combinations of free spaces for the (x,y) position
with a list of possible sizes ((w1,h1), (w2,h2), ...) on that position. If width or height is defined, then only answer rectangles that fit in the request measure. |
| getfreetotal |
The getfreetotal answers the number of free positions. This can be used as indicator
how much free space there is on the matrix.
|
|
| gethot |
The gethot method does answer the hot (element, x, y) tuple combination.
|
|
| getmatrix |
The getmatrix method answers a dictionary with coordinates as keys occupied cells as values.
|
|
| getorigin | element |
The getorigin method answers the origin of the element if it is placed.
If the element is not placed then answer None.
|
| gettotal |
The gettotal method answers the total of possible matrix positions, as result of
self.width * self.height.
|
|
| hotextendable | direction |
The hotextendable method answers a tuple of (element, (x, y), (w, h)). The (w, h) is the size
that the element can be expanded to. Depending on the value of the direction attribute, one of [self.VERTICAL, self.HORIZONTAL],
it contains respectively the vertical or horizontal grown size. The default direction is self.VERTiCAL.
If the element cannot be expanded, then the value is None. If the hot element was not set, then the methods answers
None instead of the described tuple. Note that the method does not change the element of the placed slice. The application needs to adjust the element up to the answered available size and then application has to call self.resizeelement(element, width, height) |
| isfree | height width x y |
The isfree method answers a boolean flag if there are any elements positioned on (x,y).
If width or height are defined (default value is 1), then check if all
cells of the defined rectangle are available.
|
| isreserved | x y |
The isreserved method answers the boolean if the position (x, y) is reserved. Note that explicite testing
is done on a special element type, the reservation status self.RESERVED The cell may have been filled by other content as well.
|
| largestfree | mode |
The largestfree method answers the largest free area. What “largest” means is defined by the mode
attribute. self.AREA will take the width * height as ordering value, self.SQUARE
will select the largest “squarish” area, self.HORIZONTAL orders on largest width and self.VERTICAL orders on height.
|
| magneticsort | coordinates hotspots |
The magneticsort method creates a internal list of all distances of the permuted combination of
the coordinates and defined hotspots. If one of x or y
values is None, then use the tuple as the indicator of a magnetic line. Then sort the distances
and answer the point that is closest to one of the defined magnetic points. If there a multiple points with the
same distance to a magnetic point, then order these points and answer the first one.
|
| place | element height hot width x y |
The place method does place the element in the grid positions
defined by width and height. Default value is 1.
This method is the only way elements should be placed in the composer grid to ensure that all entries are update correctly. The self.getelements() dictionary is updated with the element as key and a list of ((x,y),(width,height)) combinations as value. Empty elements (element.isempty() are ignored. If the optional hot attribute is True, then store the element as current hot selection. The default value for the hot attribute is False. |
| printdump |
The printdump method prints the content of the composition to standard output.
This is used for debugging when running this file in main mode.
|
|
| remove | element x y |
The remove method removes the element from the position if is there. Note that
a new list of cells in created at the matrix position. Avoid direct references to the cell lists.
If the element is not in the matrix or not on that position, then nothing changes.
If this is the only placement of the element, then remove all references in the elements set.
|
| reserve | height width x y |
The reserve method does reserve the space of this (x,y) position and size (width,height)
without actually placing a special element self.RESERVED in the matrix. Default size is 1. In combination with the unreserve method reserve can also be used to temporaly reserve a space (e.g. for a table of content), that will be used/filled in a later stage. |
| resizeelement | element height width |
The resizeelement method resizes the placement of the element to the width as defined by the optional width
attribute and the height as defined by the optional height attribute. If the attributes are omitted, then the
original width and height of the element is used. Note that the method does not check if the extended area is already occupied. If both width and height are defined, the complete expansion of the width first before resizing the height. Testing on the available space without overlap can be done by self.extendable(element, direction). |
| set | element x y |
The set method makes sure that the x and y attributes
are integers and inserts the element on that position. Only position in the range
of the matrix are inserted to make sure that the getfreetotal answers an accurate
number.
|
| sethot | element x y |
The sethot method stores the optional hot element (with the specific (x,y) location)
that the application may want to add content to. If the element attribute is omitted, then the hot element reference is cleared.
|
| unreserve | height width x y |
The unreserve method unreserves that space as the defined coordinate. Note that it
only will remove any existing special element self.RESERVED (also if it the space was not reserved before).
Any other placed elements are unaffected. This method can be used in combination with the self.reserve
method to temporary remove an area from the free space (e.g. for a table of content that will be filled
in the later stage of composing) or other fixed areas in a page that should not be filled.
|
