package org.ebookdroid.core; import org.ebookdroid.common.settings.AppSettings; import org.ebookdroid.common.settings.books.BookSettings; import org.ebookdroid.common.settings.types.DocumentViewMode; import org.ebookdroid.common.settings.types.PageAlign; import org.ebookdroid.core.models.DocumentModel.PageIterator; import org.ebookdroid.ui.viewer.IActivityController; import android.graphics.Rect; import android.graphics.RectF; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.List; public class HScrollController extends AbstractScrollController { public HScrollController(final IActivityController base) { super(base, DocumentViewMode.HORIZONTAL_SCROLL); } /** * {@inheritDoc} * * @see org.ebookdroid.ui.viewer.IViewController#calculateCurrentPage(org.ebookdroid.core.ViewState) */ @Override public final int calculateCurrentPage(final ViewState viewState, final int firstVisible, final int lastVisible) { int result = 0; long bestDistance = Long.MAX_VALUE; final int viewX = Math.round(viewState.viewRect.centerX()); final PageIterator pages = firstVisible != -1 ? viewState.model.getPages(firstVisible, lastVisible + 1) : viewState.model.getPages(0); try { final RectF bounds = new RectF(); for (final Page page : pages) { viewState.getBounds(page, bounds); final int pageX = Math.round(bounds.centerX()); final long dist = Math.abs(pageX - viewX); if (dist < bestDistance) { bestDistance = dist; result = page.index.viewIndex; } } } finally { pages.release(); } return result; } /** * {@inheritDoc} * * @see org.ebookdroid.ui.viewer.IViewController#verticalConfigScroll(int) */ @Override public final void verticalConfigScroll(final int direction) { final AppSettings app = AppSettings.current(); final int dx = (int) (direction * getWidth() * (app.scrollHeight / 100.0)); if (app.animateScrolling) { getView().startPageScroll(dx, 0); } else { getView().scrollBy(dx, 0); } } private boolean isRightToLeft() { final BookSettings bs = base.getBookSettings(); return bs.rtl; } /** * {@inheritDoc} * * @see org.ebookdroid.ui.viewer.IViewController#getScrollLimits() */ @Override public final Rect getScrollLimits() { final int width = getWidth(); final int height = getHeight(); final Page lpo = isRightToLeft() ? model.getPageObject(0) : model.getLastPageObject(); final float zoom = getBase().getZoomModel().getZoom(); final int right = lpo != null ? (int) lpo.getBounds(zoom).right - width : 0; final int bottom = (int) (height * zoom) - height; return new Rect(0, 0, right, bottom); } /** * {@inheritDoc} * * @see org.ebookdroid.ui.viewer.IViewController#invalidatePageSizes(org.ebookdroid.ui.viewer.IViewController.InvalidateSizeReason, * org.ebookdroid.core.Page) */ @Override public synchronized final void invalidatePageSizes(final InvalidateSizeReason reason, final Page changedPage) { if (!isInitialized) { return; } if (reason == InvalidateSizeReason.PAGE_ALIGN) { return; } final int height = getHeight(); final int width = getWidth(); final BookSettings bookSettings = base.getBookSettings(); final PageAlign pageAlign = DocumentViewMode.getPageAlign(bookSettings); if (changedPage == null || isRightToLeft()) { float widthAccum = 0; List<Page> pages = new ArrayList<Page>(Arrays.asList(model.getPages())); if (isRightToLeft()) { Collections.reverse(pages); } for (final Page page : pages) { final RectF pageBounds = calcPageBounds(pageAlign, page.getAspectRatio(), width, height); pageBounds.offset(widthAccum, 0); page.setBounds(pageBounds); widthAccum += pageBounds.width() + 3; } } else { // TODO: Implement this for the isRightToLeft() case float widthAccum = changedPage.getBounds(1.0f).left; List<Page> pages = model.getPageList(changedPage.index.viewIndex, model.getPageCount()); for (final Page page : pages) { final RectF pageBounds = calcPageBounds(pageAlign, page.getAspectRatio(), width, height); pageBounds.offset(widthAccum, 0); page.setBounds(pageBounds); widthAccum += pageBounds.width() + 3; } } } @Override public RectF calcPageBounds(final PageAlign pageAlign, final float pageAspectRatio, final int width, final int height) { return new RectF(0, 0, height * pageAspectRatio, height); } }