/*
* Copyright (C) 2013 Chen Hui <calmer91@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package master.flame.danmaku.danmaku.renderer.android;
import master.flame.danmaku.controller.DanmakuFilters;
import master.flame.danmaku.danmaku.model.BaseDanmaku;
import master.flame.danmaku.danmaku.model.DanmakuTimer;
import master.flame.danmaku.danmaku.model.IDanmakuIterator;
import master.flame.danmaku.danmaku.model.IDanmakus;
import master.flame.danmaku.danmaku.model.IDisplayer;
import master.flame.danmaku.danmaku.renderer.IRenderer;
import master.flame.danmaku.danmaku.renderer.Renderer;
public class DanmakuRenderer extends Renderer {
private final DanmakuTimer mStartTimer = new DanmakuTimer();
private final RenderingState mRenderingState = new RenderingState();
@Override
public void clear() {
DanmakusRetainer.clear();
DanmakuFilters.getDefault().clear();
}
@Override
public void release() {
DanmakusRetainer.release();
DanmakuFilters.getDefault().release();
}
@Override
public RenderingState draw(IDisplayer disp, IDanmakus danmakus, long startRenderTime) {
int lastTotalDanmakuCount = mRenderingState.totalDanmakuCount;
mRenderingState.reset();
IDanmakuIterator itr = danmakus.iterator();
int orderInScreen = 0;
mStartTimer.update(System.currentTimeMillis());
int sizeInScreen = danmakus.size();
BaseDanmaku drawItem = null;
while (itr.hasNext()) {
drawItem = itr.next();
if (drawItem.isLate()) {
break;
}
if (drawItem.time < startRenderTime
|| (drawItem.priority == 0 && DanmakuFilters.getDefault().filter(drawItem,
orderInScreen, sizeInScreen, mStartTimer, false))) {
continue;
}
if (drawItem.getType() == BaseDanmaku.TYPE_SCROLL_RL){
// 同屏弹幕密度只对滚动弹幕有效
orderInScreen++;
}
// measure
if (!drawItem.isMeasured()) {
drawItem.measure(disp);
}
// layout
DanmakusRetainer.fix(drawItem, disp);
// draw
if (!drawItem.isOutside() && drawItem.isShown()) {
if (drawItem.lines == null && drawItem.getBottom() > disp.getHeight()) {
continue; // skip bottom outside danmaku
}
int renderingType = drawItem.draw(disp);
if(renderingType == IRenderer.CACHE_RENDERING) {
mRenderingState.cacheHitCount++;
} else if(renderingType == IRenderer.TEXT_RENDERING) {
mRenderingState.cacheMissCount++;
}
mRenderingState.addCount(drawItem.getType(), 1);
mRenderingState.addTotalCount(1);
}
}
mRenderingState.nothingRendered = (mRenderingState.totalDanmakuCount == 0);
mRenderingState.endTime = drawItem != null ? drawItem.time : RenderingState.UNKNOWN_TIME;
if (mRenderingState.nothingRendered) {
mRenderingState.beginTime = RenderingState.UNKNOWN_TIME;
}
mRenderingState.incrementCount = mRenderingState.totalDanmakuCount - lastTotalDanmakuCount;
mRenderingState.consumingTime = mStartTimer.update(System.currentTimeMillis());
return mRenderingState;
}
}