use of maspack.util.Rectangle in project artisynth_core by artisynth.
the class TextImageStore method upload.
/**
* Attempts to store a glyph into the backing image store, returning the
* storage information. If the glyph is already stored, then the existing
* backing store is returned. Otherwise, the {@link RectanglePacker} will
* attempt to place the glyph in the backing store.
*
* @param glyph
* glyph to try to upload to the backing store (if not already present)
* @return the resulting storage information, or null if it doesn't fit
*/
public GlyphStore upload(Glyph glyph) {
GlyphStore store = get(glyph);
if (store != null) {
return store;
}
// new single glyph vector
Font glyphFont = glyph.getFont();
GlyphVector vec = glyphFont.createGlyphVector(graphics.getFontRenderContext(), new int[] { glyph.getGlyphCode() });
// determine required glyph size
GlyphMetrics metrics = vec.getGlyphMetrics(0);
Rectangle2D rect = adjustBounds(metrics.getBounds2D(), GLYPH_BORDER);
// pack glyph into backing store
Rectangle packed = packer.pack((int) rect.getWidth(), (int) rect.getHeight());
if (packed == null) {
// didn't fit
return null;
}
// determine layout in image
int left = packed.x();
int top = image.getHeight() - packed.y() - packed.height();
int bottom = image.getHeight() - packed.y() - 1;
int width = packed.width();
int height = packed.height();
// draw to image
// Clear out the area we're going to draw into
// graphics.clearRect (left, top, width, height);
graphics.drawGlyphVector(vec, (float) (left - rect.getMinX()), (float) (bottom + rect.getMinY()));
markDirty(packed);
storageModified = true;
// debugging, draw border
if (DEBUG) {
Color pen = graphics.getColor();
graphics.setColor(Color.CYAN);
graphics.drawRect(left, top, width - 1, height - 1);
graphics.setColor(pen);
}
// store and return glyph location in image
GlyphLoc loc = new GlyphLoc(packed, -rect.getMinX(), -rect.getMinY());
glyphMap.put(glyph.getId(), loc);
store = new GlyphStore(glyph, storageId, loc);
if (DEBUG) {
debugFrame.repaint();
}
return store;
}
use of maspack.util.Rectangle in project artisynth_core by artisynth.
the class TextureTextRenderer method flush.
/**
* Draw characters to screen now
*/
public void flush() {
queue = draw(queue);
// now try to upload any that were missing
while (queue.size() > 0) {
// upload as many as we can before we start drawing
for (GlyphQueue gq : queue) {
int s = gq.remaining;
Glyph[] glyphs = gq.glyphqueue;
for (int i = 0; i < s; ++i) {
textstore.upload(glyphs[i]);
}
}
// update texture
if (textureUploaded) {
Rectangle dirty = textstore.getDirty();
ByteBuffer buff = BufferUtilities.newNativeByteBuffer(dirty.area() * 4);
textstore.getData(dirty, buff);
buff.flip();
replaceSubTexture(dirty.x(), dirty.y(), dirty.width(), dirty.height(), buff);
textstore.markClean();
buff = BufferUtilities.freeDirectBuffer(buff);
} else {
ByteBuffer buff = BufferUtilities.newNativeByteBuffer(textstore.getWidth() * textstore.getHeight() * 4);
textstore.getData(buff);
buff.flip();
replaceTexture(textstore.getWidth(), textstore.getHeight(), buff);
textstore.markClean();
buff = BufferUtilities.freeDirectBuffer(buff);
textureUploaded = true;
}
// draw
queue = draw(queue);
// again
if (queue.size() > 0) {
setPreferredSize(textstore.getWidth() * 2, textstore.getHeight() * 2);
textstore.clear();
}
}
}
use of maspack.util.Rectangle in project artisynth_core by artisynth.
the class DicomTextureContent method updateBackingBuffer.
/**
* Uploads dicom pixels to backing buffer
* @param plane plane index
*/
protected void updateBackingBuffer(int plane) {
Rectangle rect = rects[plane];
int psize = getPixelSize();
int scanline = psize * textureWidth;
synchronized (textureImage) {
textureImage.limit(textureImage.capacity());
textureImage.position(rect.y() * scanline + psize * rect.x());
switch(plane) {
case COL_ROW_PLANE:
image.getPixels(0, 0, slice, 1, 1, 1, rect.width(), rect.height(), 1, time, internalStorage, scanline, 0, window, textureImage);
break;
case COL_SLICE_PLANE:
image.getPixels(0, row, 0, 1, 1, 1, rect.width(), 1, rect.height(), time, internalStorage, 0, scanline, window, textureImage);
break;
case ROW_SLICE_PLANE:
image.getPixels(col, 0, 0, 1, 1, 1, 1, rect.width(), rect.height(), time, internalStorage, 0, scanline, window, textureImage);
break;
}
valid[plane] = true;
}
}
use of maspack.util.Rectangle in project artisynth_core by artisynth.
the class DicomTextureContent method packRects.
protected Rectangle[] packRects(int nrows, int ncols, int nslices) {
// pack three textures into one
// rows x cols, rows x slices, cols x slices
List<Pair<Integer, Rectangle>> planes = new ArrayList<Pair<Integer, Rectangle>>(3);
planes.add(new Pair<Integer, Rectangle>(COL_ROW_PLANE, new Rectangle(0, 0, ncols, nrows)));
planes.add(new Pair<Integer, Rectangle>(COL_SLICE_PLANE, new Rectangle(0, 0, ncols, nslices)));
planes.add(new Pair<Integer, Rectangle>(ROW_SLICE_PLANE, new Rectangle(0, 0, nrows, nslices)));
// sort by area descending
Collections.sort(planes, new Comparator<Pair<Integer, Rectangle>>() {
@Override
public int compare(Pair<Integer, Rectangle> o1, Pair<Integer, Rectangle> o2) {
int a1 = o1.second().area();
int a2 = o2.second().area();
if (a1 > a2) {
return -1;
} else if (a1 < a2) {
return 1;
}
return 0;
}
});
int totalwidth = 2 * ncols + nrows;
int totalheight = nrows + 2 * nslices;
int maxdim = Math.max(totalwidth, totalheight);
Rectangle[] out = new Rectangle[3];
// tightly pack into rectangle
BinaryTreeRectanglePacker packer = new BinaryTreeRectanglePacker(maxdim, maxdim);
for (int i = 0; i < 3; ++i) {
out[planes.get(i).first] = packer.pack(planes.get(i).second);
}
return out;
}
Aggregations