Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Stickers #1958

Open
wants to merge 6 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,6 @@ void onDrawEye(int eye) {
mRenderBundle.getPostEffectRenderTextureB());
captureRightEye(renderTarget,false);
}
captureFinish();
}

void setCameraRig(GVRCameraRig cameraRig) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -196,8 +196,6 @@ void onDrawEye(int eye, int swapChainIndex, boolean use_multiview) {
captureRightEye(renderTarget, true);
captureLeftEye(renderTarget, true);

captureFinish();

if (DEBUG_STATS) {
mTracerDrawEyes1.leave();
mTracerDrawEyes2.leave();
Expand All @@ -217,7 +215,6 @@ void onDrawEye(int eye, int swapChainIndex, boolean use_multiview) {
mRenderBundle.getPostEffectRenderTextureB());
captureRightEye(renderTarget, false);

captureFinish();
if (DEBUG_STATS) {
mTracerDrawEyes1.leave();
mTracerDrawEyes.leave();
Expand All @@ -236,6 +233,7 @@ void onDrawEye(int eye, int swapChainIndex, boolean use_multiview) {

renderTarget.cullFromCamera(mMainScene, mainCameraRig.getCenterCamera(), mRenderBundle.getShaderManager());
captureCenterEye(renderTarget, false);
captureSticker();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What about other backend adapters?

renderTarget.render(mMainScene, leftCamera, mRenderBundle.getShaderManager(), mRenderBundle.getPostEffectRenderTextureA(), mRenderBundle.getPostEffectRenderTextureB());

captureLeftEye(renderTarget, false);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -584,6 +584,8 @@ protected synchronized static void resetOnRestart() {
*/
public abstract void captureScreenCenter(GVRScreenshotCallback callback);

abstract boolean captureSticker(GVRScreenshotCallback callback, int pboIndex);

/**
* Capture a 2D screenshot from the position of left eye.
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,10 @@ public void captureScreenCenter(GVRScreenshotCallback callback) {
mContext.get().captureScreenCenter(callback);
}

public boolean captureSticker(GVRScreenshotCallback callback, int pboIndex) {
return mContext.get().captureSticker(callback, pboIndex);
}

public void captureScreenLeft(GVRScreenshotCallback callback) {
mContext.get().captureScreenLeft(callback);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@ class GVRRenderBundle {
private GVRRenderTexture mPostEffectRenderTextureA = null;
private GVRRenderTexture mPostEffectRenderTextureB = null;
private GVRRenderTarget mEyeCaptureRenderTarget = null;
// Three render targets for sticker generation
private GVRRenderTarget mStickerRenderTarget[] = {null, null, null};

protected int mSampleCount;
protected int mWidth, mHeight;
Expand Down Expand Up @@ -92,6 +94,15 @@ public GVRRenderTarget getEyeCaptureRenderTarget() {
}
return mEyeCaptureRenderTarget;
}

public GVRRenderTarget getStickerRenderTarget(int index) {
if(mStickerRenderTarget[index] == null){
mStickerRenderTarget[index] = new GVRRenderTarget(new GVRRenderTexture(mGVRContext, mWidth, mHeight, mSampleCount), mGVRContext.getMainScene());
mStickerRenderTarget[index].setCamera(mGVRContext.getMainScene().getMainCameraRig().getCenterCamera());
}
return mStickerRenderTarget[index];
}

void beginRendering(int bufferIdx, GVRViewManager.EYE eye) {
getRenderTexture(bufferIdx,eye).beginRendering();
}
Expand Down
150 changes: 150 additions & 0 deletions GVRf/Framework/framework/src/main/java/org/gearvrf/GVRSticker.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,150 @@
/* Copyright 2015 Samsung Electronics Co., LTD
*
* 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 org.gearvrf;

import android.graphics.Bitmap;
import android.os.Environment;
import android.util.Log;

import org.gearvrf.utility.Threads;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/**
* This class takes screenshots at a specified interval and writes the output PNG files to GearVRFScreenshots directory.
* The capturing can be stopped by calling {@link GVRSticker#stop()}
* The images can be used to create Stickers (a GIF animation)
*/

public class GVRSticker {
private final GVRContext mGVRContext;
private final String mTag;
private final String mDirectory;
private final long mInterval;
private boolean mCaptureFlag = true;
private final static String TAG = "GVRSticker";

/**
* Constructor takes the following parameters
* @param gvrContext
* @param tag
* Name for outputting PNG's to the SD Card along with appended frame ID
* @param interval
* Time in milliseconds to take screenshot at that interval
*/
public GVRSticker(GVRContext gvrContext, String tag, long interval){
mGVRContext = gvrContext;
mTag = tag;
mInterval = interval;

File sdcard = Environment.getExternalStorageDirectory();
mDirectory = sdcard.getAbsolutePath() + "/GearVRFScreenshots/";
File d = new File(mDirectory);
d.mkdirs();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Probably the fact that WRITE_EXTERNAL_STORAGE is required should be mentioned. Also I'd recommend checking the return value of mkdirs and throwing an exception immediately if needed.

}

private boolean lastScreenshotFinished[] = {true, true, true};
private int pboIndex = 0;

/**
* Initiate's the screenshot capturing
* Captures images every {@link GVRSticker#mInterval} milliseconds
*/
public void startCapturing()
{
mCaptureFlag = true;
Threads.spawn(new Runnable()
{
public void run()
{
int frame = 0;
boolean lastStickerCall;
while(mCaptureFlag) {
if (lastScreenshotFinished[pboIndex]) {
lastStickerCall = mGVRContext
.captureSticker(newScreenshotCallback(frame, pboIndex), pboIndex);
if(lastStickerCall) {
lastScreenshotFinished[pboIndex] = false;
pboIndex = (pboIndex + 1) % 3;
frame++;
}
}
else{
Log.e(TAG, "Sticker skipped since previous read is not completed");
}
try {
Thread.sleep(mInterval);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
});
}

/**
* Stop's the screenshot thread
*/
public void stopCapturing(){
mCaptureFlag = false;
}

private GVRScreenshotCallback newScreenshotCallback(final int frame, final int currentPboIndex)
{
return new GVRScreenshotCallback()
{
@Override
public void onScreenCaptured(Bitmap bitmap)
{
if (bitmap != null)
{
File file = new File(mDirectory + mTag +"_"+ frame +"_" + ".png");
FileOutputStream outputStream = null;
try
{
outputStream = new FileOutputStream(file);
bitmap.compress(Bitmap.CompressFormat.PNG, 100, outputStream);
}
catch (FileNotFoundException e)
{
e.printStackTrace();
}
finally
{
try
{
outputStream.close();
}
catch (IOException e)
{
e.printStackTrace();
}
}
}
else
{
Log.e(TAG, "Returned Bitmap is null for frame " + frame);
}

// enable next screenshot
lastScreenshotFinished[currentPboIndex] = true;
}
};
}
}
Loading