📄 logicalpageimpl.java
字号:
{
return;
}
replaySpool(operations);
}
/**
* Replays a previously recorded spool. The spool is a collection of PhysicalOperations.
*
* @param operations the operations.
*/
public void replaySpool(final Spool operations)
{
final PhysicalOperation[] ops = operations.getOperations();
for (int i = 0; i < ops.length; i++)
{
getPhysicalPage(0, 0).addOperation(ops[i]);
}
}
/**
* Creates a spool made up of the contents generated from the given Band. The band
* is printed at the location and with the dimensions specified in <code>bounds</code>.
* <p>
* Spooling is the process of creating operations suitable for the physical pages.
* <p>
* ToDo: Support distribution over multiple pages ...
*
* @param bounds the bounds that define where to print the given band on this logical page
* @param band the band that should be spooled/printed
* @return the generated spool for the given band
*
* @throws OutputTargetException if there is a problem with the output target.
*/
public Spool spoolBand(final Rectangle2D bounds, final Band band) throws OutputTargetException
{
if (isOpen() == false)
{
throw new IllegalStateException("Band already closed");
}
final Spool spool = new Spool();
spoolBand(bounds, band, spool);
return spool;
}
/**
* Creates a spool made up of the contents generated from the given Band. The band
* is printed at the location and with the dimensions specified in <code>bounds</code>.
* <p>
* Spooling is the process of creating operations suitable for the physical pages.
* The generated operations are added to the given spool.
* <p>
* ToDo: Support distribution over multiple pages ...
*
* @param bounds the bounds that define where to print the given band on this logical page
* @param band the band that should be spooled/printed
* @param spool the spool which collects the generated operations.
*
* @throws OutputTargetException if there is a problem with the output target.
*/
protected void spoolBand(final Rectangle2D bounds, final Band band, final Spool spool)
throws OutputTargetException
{
// do nothing if the band is invisble
if (band.isVisible() == false)
{
return;
}
// do nothing if the band has a height of 0 (also invisible)
if (bounds.getHeight() == 0)
{
return;
}
final PageFormat pf = getPageFormat();
final Rectangle2D logicalPageBounds = new Rectangle2D.Float(0, 0,
(float) pf.getImageableWidth(),
(float) pf.getImageableHeight());
final Rectangle2D ibounds = logicalPageBounds.createIntersection(bounds);
if (addOperationComments)
{
spool.addOperation(new PhysicalOperation.AddComment(
new Log.SimpleMessage("Begin Band: ", band.getClass(), " -> ", band.getName())));
}
// process all elements
final Element[] elements = band.getElementArray();
for (int i = 0; i < elements.length; i++)
{
final Element e = elements[i];
if (e instanceof Band)
{
final Rectangle2D bbounds = (Rectangle2D)
e.getStyle().getStyleProperty(ElementStyleSheet.BOUNDS);
spoolBand(translateSubRect(bounds, bbounds), (Band) e, spool);
}
else
{
addElement(ibounds, e, spool);
}
}
}
/**
* Converts an inner rectangle to the coordinate space of the outer rectangle.
* The inner rectangle's origin (0,0) is mapped to the outer rectangles upper
* left corner.
*
* @param outer the outer rectangle in the global coordinate space
* @param inner the inner rectangle in the local coordinate space
* @return the translated sub rectangle.
*/
private Rectangle2D translateSubRect(final Rectangle2D outer, final Rectangle2D inner)
{
final float w =
(float) Math.min(outer.getX() + outer.getWidth() - inner.getX(), inner.getWidth());
final float h =
(float) Math.min(outer.getY() + outer.getHeight() - inner.getY(), inner.getHeight());
final Rectangle2D rc = new Rectangle2D.Float(
(float) (outer.getX() + inner.getX()),
(float) (outer.getY() + inner.getY()),
Math.max(0, w),
Math.max(0, h));
return rc;
}
/**
* Add the specified element to the logical page. Create content from the values
* contained in the element and format the content by using the element's attributes.
* <p>
* @param bounds the element bounds.
* @param e the element.
* @param operations the operations.
*
* @throws OutputTargetException if there was content that could not be handled
* @throws NullPointerException if the element has no valid layout (no BOUNDS defined).
* Bounds are usually defined by the BandLayoutManager.
*/
private void addElement(final Rectangle2D bounds, final Element e, final Spool operations)
throws OutputTargetException
{
if (e.isVisible() == false)
{
return;
}
final ContentFactory factory = outputTarget.getContentFactory();
if (factory.canHandleContent(e.getContentType()) == false)
{
// the output target does not support this kind of content, ignore it...
return;
}
final Rectangle2D elementBounds = (Rectangle2D)
e.getStyle().getStyleProperty(ElementStyleSheet.BOUNDS);
if (elementBounds == null)
{
throw new NullPointerException("No layout for element");
}
final Rectangle2D drawBounds = translateSubRect(bounds, elementBounds);
if (addOperationComments)
{
operations.addOperation(new PhysicalOperation.AddComment("Begin Element: " + e.getClass()
+ " -> " + e.getName()));
operations.addOperation(new PhysicalOperation.AddComment(" ... Element: " + drawBounds));
}
final ElementLayoutInformation eli = new ElementLayoutInformation(drawBounds);
try
{
final Content content = factory.createContentForElement(e, eli, getOutputTarget());
if (content == null)
{
return;
}
// split the elements contents, then write ..
getOperationFactory().createOperations(operations, e, content, drawBounds);
}
catch (ContentCreationException ce)
{
throw new OutputTargetException("Unable to create content", ce);
}
}
/**
* Close this logical page and all physical pages. Write the content to the
* OutputTarget.
*
* todo how to handle multiple physical pages? How to specify which page should be printed ...
*/
public void close()
{
for (int i = 0; i < physicalPage.length; i++)
{
try
{
physicalPage[i].write(getOutputTarget());
}
catch (Exception e)
{
Log.error("On CloseLogicalPage", e);
}
physicalPage[i].flush();
}
closed = true;
}
/**
* Test whether is logical page is opened and bands can be added to the page.
*
* @return true if the page is open, false otherwise
*/
public boolean isOpen()
{
return closed == false;
}
/**
* Opens the logical page. Prepare everything to get bands added.
*/
public void open()
{
closed = false;
}
/**
* Test whether this page is empty. A logical page is empty, when all
* physical pages are empty (no operations were executed there).
*
* @return true, if the page is empty and nothing was printed, false otherwise.
*/
public boolean isEmpty()
{
for (int i = 0; i < physicalPage.length; i++)
{
if (physicalPage[i].isEmpty() == false)
{
return false;
}
}
return true;
}
/**
* Get the width of this logical page. Logical pages start at coordinate (0,0)
* and have no borders. Borders should be handled by the Physical Pages.
*
* @return the defined width of this logical page.
*/
public float getWidth()
{
return (float) getPageFormat().getImageableWidth();
}
/**
* Get the height of this logical page. Logical pages start at coordinate (0,0)
* and have no borders. Borders should be handled by the Physical Pages.
*
* @return the defined height of this logical page.
*/
public float getHeight()
{
return (float) getPageFormat().getImageableHeight();
}
/**
* Returns a new instance of this logical page, fully initialized as this page,
* but without this pages state cloned.
*
* @return a new instance of this LogicalPage
*/
public LogicalPage newInstance()
{
return new LogicalPageImpl(getPageFormat(), getPhysicalPageFormat());
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -