Kaydet (Commit) 25ad5279 authored tarafından Tomaž Vajngerl's avatar Tomaž Vajngerl

LOAndroid3: tile loading and invalidation

Change-Id: I6e0157efc52d8cd0eabf650e14559697139d8e7e
üst 019cf5e8
package org.libreoffice;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Rect;
import android.util.JsonWriter;
import android.graphics.RectF;
import android.util.Log;
import org.mozilla.gecko.gfx.FloatSize;
import org.mozilla.gecko.gfx.SubTile;
import org.mozilla.gecko.gfx.ViewportMetrics;
import java.io.IOException;
import java.io.StringWriter;
import java.nio.ByteBuffer;
import java.util.Random;
import java.util.ArrayList;
import java.util.concurrent.ConcurrentLinkedQueue;
public class LOKitThread extends Thread {
private static final String LOGTAG = LOKitThread.class.getSimpleName();
private static final int TILE_SIZE = 256;
public ConcurrentLinkedQueue<LOEvent> mEvents = new ConcurrentLinkedQueue<LOEvent>();
private LibreOfficeMainActivity mApplication;
private TileProvider mTileProvider;
public ConcurrentLinkedQueue<LOEvent> gEvents = new ConcurrentLinkedQueue<LOEvent>();
private ViewportMetrics mViewportMetrics;
LOKitThread() {
......@@ -38,14 +30,53 @@ public class LOKitThread extends Thread {
mViewportMetrics = new ViewportMetrics();
mViewportMetrics.setPageSize(new FloatSize(pageWidth, pageHeight));
RectF viewport = mApplication.getLayerController().getViewportMetrics().getClampedViewport();
float zoomFactor = mApplication.getLayerController().getViewportMetrics().getZoomFactor();
boolean shouldContinue = mApplication.getLayerClient().beginDrawing(mViewportMetrics);
if (!shouldContinue) {
return false;
}
for (SubTile tile : mTileProvider.getTileIterator()) {
mApplication.getLayerClient().addTile(tile);
int minX = ((int) viewport.left / TILE_SIZE) * TILE_SIZE;
int minY = ((int) viewport.top / TILE_SIZE) * TILE_SIZE;
int maxX = (((int) viewport.right / TILE_SIZE) + 1) * TILE_SIZE;
int maxY = (((int) viewport.bottom / TILE_SIZE) + 1) * TILE_SIZE;
Rect rect = new Rect(
Math.round(minX / zoomFactor),
Math.round(minY / zoomFactor),
Math.round(maxX / zoomFactor),
Math.round(maxY / zoomFactor));
ArrayList<SubTile> removeTiles = new ArrayList<SubTile>();
for (SubTile tile : mApplication.getLayerClient().getTiles()) {
if (!rect.intersects(tile.x, tile.y, tile.x + TILE_SIZE, tile.y + TILE_SIZE)) {
removeTiles.add(tile);
}
}
mApplication.getLayerClient().getTiles().removeAll(removeTiles);
for (int y = minY; y <= maxY; y+=TILE_SIZE) {
for (int x = minX; x <= maxX; x+=TILE_SIZE) {
if (x > pageWidth) {
continue;
}
if (y > pageHeight) {
continue;
}
boolean contains = false;
for (SubTile tile : mApplication.getLayerClient().getTiles()) {
if (tile.x == x && tile.y == y) {
contains = true;
}
}
if (!contains) {
SubTile tile = mTileProvider.createTile(x, y);
mApplication.getLayerClient().addTile(tile);
}
}
}
mApplication.getLayerClient().endDrawing();
......@@ -63,14 +94,10 @@ public class LOKitThread extends Thread {
try {
boolean drawn = false;
while (true) {
if (!gEvents.isEmpty()) {
processEvent(gEvents.poll());
} else {
if (!drawn) {
drawn = draw();
}
Thread.sleep(100L);
if (!mEvents.isEmpty()) {
processEvent(mEvents.poll());
}
Thread.sleep(100L);
}
} catch (InterruptedException ex) {
}
......@@ -80,6 +107,7 @@ public class LOKitThread extends Thread {
switch (event.mType) {
case LOEvent.VIEWPORT:
mViewportMetrics = event.getViewport();
draw();
break;
case LOEvent.DRAW:
draw();
......@@ -89,5 +117,8 @@ public class LOKitThread extends Thread {
}
}
public void queueEvent(LOEvent event) {
Log.i(LOGTAG, "Event: " + event.getTypeString());
mEvents.add(event);
}
}
package org.libreoffice;
import android.graphics.Bitmap;
import android.util.Log;
import org.libreoffice.kit.Document;
import org.libreoffice.kit.LibreOfficeKit;
import org.libreoffice.kit.Office;
import org.mozilla.gecko.gfx.BufferedCairoImage;
import org.mozilla.gecko.gfx.CairoImage;
import org.mozilla.gecko.gfx.LayerController;
import org.mozilla.gecko.gfx.SubTile;
import java.nio.ByteBuffer;
import java.util.Iterator;
import org.libreoffice.kit.LibreOfficeKit;
import org.libreoffice.kit.Office;
import org.libreoffice.kit.Document;
import org.mozilla.gecko.gfx.SubTile;
public class LOKitTileProvider implements TileProvider {
private final LayerController mLayerController;
public static int TILE_SIZE = 256;
private final double mTileWidth;
private final double mTileHeight;
public final Office mOffice;
public final Document mDocument;
......@@ -42,6 +42,9 @@ public class LOKitTileProvider implements TileProvider {
mOffice = new Office(LibreOfficeKit.getLibreOfficeKitHandle());
String input = "/assets/test1.odt";
mDocument = mOffice.documentLoad(input);
mTileWidth = pixelToTwip(TILE_SIZE, mDPI);
mTileHeight = pixelToTwip(TILE_SIZE, mDPI);
}
@Override
......@@ -54,71 +57,17 @@ public class LOKitTileProvider implements TileProvider {
return (int) twipToPixel(mDocument.getDocumentHeight(), mDPI);
}
public TileIterator getTileIterator() {
return new LoKitTileIterator();
}
public class LoKitTileIterator implements TileIterator, Iterator<SubTile> {
private final double mTileWidth;
private final double mTileHeight;
private double mPositionWidth = 0;
private double mPositionHeight = 0;
private int mX = 0;
private int mY = 0;
private double mPageWidth;
private double mPageHeight;
public LoKitTileIterator() {
mTileWidth = pixelToTwip(TILE_SIZE, mDPI);
mTileHeight = pixelToTwip(TILE_SIZE, mDPI);
mPageWidth = mDocument.getDocumentWidth();
mPageHeight = mDocument.getDocumentHeight();
}
@Override
public boolean hasNext() {
return mPositionHeight <= mPageHeight;
}
@Override
public SubTile next() {
ByteBuffer buffer = ByteBuffer.allocateDirect(TILE_SIZE * TILE_SIZE * 4);
Bitmap bitmap = Bitmap.createBitmap(TILE_SIZE, TILE_SIZE, Bitmap.Config.ARGB_8888);
mDocument.paintTile(buffer, TILE_SIZE, TILE_SIZE,
(int) Math.round(mPositionWidth), (int) Math.round(mPositionHeight), (int) Math.round(mTileWidth + pixelToTwip(1, mDPI)), (int) Math.round(mTileHeight+ pixelToTwip(1, mDPI)));
bitmap.copyPixelsFromBuffer(buffer);
CairoImage image = new BufferedCairoImage(bitmap);
SubTile tile = new SubTile(image, mX, mY);
tile.beginTransaction();
mPositionWidth += mTileWidth;
mX += TILE_SIZE;
if (mPositionWidth > mPageWidth) {
mPositionHeight += mTileHeight;
mY += TILE_SIZE;
mPositionWidth = 0;
mX = 0;
}
public SubTile createTile(int x, int y) {
ByteBuffer buffer = ByteBuffer.allocateDirect(TILE_SIZE * TILE_SIZE * 4);
Bitmap bitmap = Bitmap.createBitmap(TILE_SIZE, TILE_SIZE, Bitmap.Config.ARGB_8888);
return tile;
}
mDocument.paintTile(buffer, TILE_SIZE, TILE_SIZE, (int) pixelToTwip(x, mDPI), (int) pixelToTwip(y, mDPI), (int)mTileWidth, (int)mTileHeight);
@Override
public void remove() {
throw new UnsupportedOperationException();
}
bitmap.copyPixelsFromBuffer(buffer);
@Override
public Iterator<SubTile> iterator() {
return this;
}
CairoImage image = new BufferedCairoImage(bitmap);
SubTile tile = new SubTile(image, x, y);
tile.beginTransaction();
return tile;
}
}
......@@ -2,15 +2,11 @@ package org.libreoffice;
import android.graphics.Bitmap;
import org.apache.http.MethodNotSupportedException;
import org.mozilla.gecko.gfx.BufferedCairoImage;
import org.mozilla.gecko.gfx.CairoImage;
import org.mozilla.gecko.gfx.LayerController;
import org.mozilla.gecko.gfx.SubTile;
import java.util.Iterator;
import java.util.List;
public class MockTileProvider implements TileProvider {
private final LayerController layerController;
private static final int TILE_SIZE = 256;
......@@ -26,58 +22,23 @@ public class MockTileProvider implements TileProvider {
@Override
public int getPageHeight() {
return 630;
}
public TileIterator getTileIterator() {
return new MockTileIterator(layerController);
return 630*5;
}
public class MockTileIterator implements TileIterator, Iterator<SubTile> {
private final LayerController layerController;
private int tileNumber = 1;
private int x = 0;
private int y = 0;
public MockTileIterator(LayerController layerController) {
this.layerController = layerController;
}
@Override
public boolean hasNext() {
return tileNumber <= 9;
}
@Override
public SubTile next() {
String imageName = "d" + tileNumber;
tileNumber++;
Bitmap bitmap = layerController.getDrawable(imageName);
CairoImage image = new BufferedCairoImage(bitmap);
SubTile tile = new SubTile(image, x, y);
tile.beginTransaction();
x += TILE_SIZE;
if (x > getPageWidth()) {
x = 0;
y += TILE_SIZE;
}
@Override
public SubTile createTile(int x, int y) {
int tiles = (getPageWidth() / TILE_SIZE) + 1;
int tileNumber = (y / TILE_SIZE) * tiles + (x / TILE_SIZE);
tileNumber %= 9;
tileNumber += 1; // 0 to 1 based numbering
return tile;
}
String imageName = "d" + tileNumber;
Bitmap bitmap = layerController.getDrawable(imageName);
@Override
public void remove() {
throw new UnsupportedOperationException();
}
CairoImage image = new BufferedCairoImage(bitmap);
SubTile tile = new SubTile(image, x, y);
tile.beginTransaction();
@Override
public Iterator<SubTile> iterator() {
return this;
}
return tile;
}
}
package org.libreoffice;
import org.mozilla.gecko.gfx.SubTile;
public interface TileIterator extends Iterable<SubTile> {
}
package org.libreoffice;
import org.mozilla.gecko.gfx.SubTile;
public interface TileProvider {
int getPageWidth();
int getPageHeight();
TileIterator getTileIterator();
SubTile createTile(int x, int y);
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment