diff --git a/app/build.gradle b/app/build.gradle
index 6243b3a..e7baa42 100644
--- a/app/build.gradle
+++ b/app/build.gradle
@@ -14,7 +14,6 @@ android {
buildTypes {
release {
minifyEnabled false
- proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}
@@ -30,4 +29,6 @@ dependencies {
//External libs
compile 'com.davemorrissey.labs:subsampling-scale-image-view:3.6.0'
+ compile 'com.jakewharton:butterknife:8.8.1'
+ annotationProcessor 'com.jakewharton:butterknife-compiler:8.8.1'
}
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index c15743d..efa46c1 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -3,6 +3,7 @@
package="de.trac.spherical">
+
fragments;
+ private Fragment currentFragment;
// Broadcast handling.
private BroadcastReceiver broadcastReceiver = new BroadcastReceiver() {
@@ -83,19 +93,22 @@ public class MainActivity extends AppCompatActivity {
public void onReceive(Context context, Intent intent) {
switch (BroadcastHelper.getBroadcastType(intent)) {
case PROGRESS_START:
+ fragmentManager.beginTransaction().add(R.id.container_fragment, fragments.get(FragmentType.PROGRESS)).commitAllowingStateLoss();
break;
case PROGRESS_FINISHED:
+ fragmentManager.beginTransaction().remove(fragments.get(FragmentType.PROGRESS)).commitAllowingStateLoss();
break;
default:
break;
}
}
- }
+ };
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
+ ButterKnife.bind(this);
setupUI();
// Init fragments.
@@ -122,25 +135,28 @@ public class MainActivity extends AppCompatActivity {
*/
private void setupUI() {
// Prepare UI
- toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
getSupportActionBar().setDisplayShowTitleEnabled(false);
+
+ // Dirty hacks
RelativeLayout.LayoutParams lp = (RelativeLayout.LayoutParams) toolbar.getLayoutParams();
lp.topMargin += getStatusBarHeight();
toolbar.bringToFront();
- actionButton = (FloatingActionButton) findViewById(R.id.fab);
- actionButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- sphereFragment.toggleUseTouchInput();
- setUIVisibility(false);
- }
- });
-
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
Window w = getWindow();
w.setFlags(WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS, WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS);
}
+
+ actionButton.setOnClickListener(new View.OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ PhotoSphereSurfaceView photoSphereSurfaceView =
+ ((SphereFragment)fragments.get(FragmentType.SPHERE)).getSurfaceView();
+ photoSphereSurfaceView.setUseTouchInput(!photoSphereSurfaceView.getUseTouchInput());
+ setUIVisibility(false);
+ }
+ });
+
// Detect gestures like single taps.
gestureDetector = new GestureDetectorCompat(this, new GestureDetector.SimpleOnGestureListener() {
@Override
@@ -157,7 +173,8 @@ public class MainActivity extends AppCompatActivity {
* @param intent incoming intent.
*/
private void handleIntent(Intent intent) {
- switch (intent.getAction()) {
+ String action = intent.getAction() != null ? intent.getAction() : "";
+ switch (action) {
//Image was sent into the app
case Intent.ACTION_SEND:
showFragment(FragmentType.SPHERE);
@@ -227,7 +244,8 @@ public class MainActivity extends AppCompatActivity {
}
// process image asynchronous.
- new LoadImageTask(this, getContentResolver(), imageUri).execute();
+ BroadcastHelper.broadcast(this, BroadcastHelper.BroadcastType.PROGRESS_START);
+ new LoadImageTask(getContentResolver(), imageUri, type, this).execute();
}
/**
@@ -249,7 +267,8 @@ public class MainActivity extends AppCompatActivity {
* @param type fragment to be shown
*/
private void showFragment(FragmentType type) {
- fragmentManager.beginTransaction().replace(R.id.container_fragment, fragments.get(type), type.tag).commit();
+ currentFragment = fragments.get(type);
+ fragmentManager.beginTransaction().replace(R.id.container_fragment, currentFragment, type.tag).commit();
}
@Override
@@ -271,27 +290,20 @@ public class MainActivity extends AppCompatActivity {
case R.id.menu_about:
Toast.makeText(this, R.string.toast_not_yet_implemented, Toast.LENGTH_SHORT).show();
return true;
+ case R.id.menu_force_sphere:
+ showFragment(FragmentType.SPHERE);
+ ((ImageFragment) currentFragment).updateBitmap(image.getBitmap());
+ return true;
+
+ case R.id.menu_force_flat:
+ showFragment(FragmentType.FLAT);
+ ((ImageFragment) currentFragment).updateBitmap(image.getBitmap());
+ return true;
}
return super.onOptionsItemSelected(item);
}
- /**
- * Display a photo sphere.
- */
- public void displayPhotoSphere() {
- showFragment(FragmentType.SPHERE);
- currentlyShownImageFragment.updateBitmap(bitmap);
- }
-
- /**
- * Display a flat bitmap.
- */
- public void displayFlatImage() {
- showFragment(FragmentType.FLAT);
- currentlyShownImageFragment.updateBitmap(bitmap);
- }
-
/**
* Convenience method because android sux.
* Returns the height of the status bar in dp.
@@ -310,59 +322,4 @@ public class MainActivity extends AppCompatActivity {
return gestureDetector;
}
- /**
- * Dedicated async tasks to load an image.
- * Takes a progress reporter and informs it about the changes.
- */
- private static class LoadImageTask extends AsyncTask {
-
- private ContentResolver contentResolver;
- private Uri uri;
-
- private Bitmap bitmap;
- private PhotoSphereMetadata metadata;
- private Context context;
-
- LoadImageTask(Context context, ContentResolver contentResolver, Uri uri) {
- this.context = context;
- this.contentResolver = contentResolver;
- this.uri = uri;
- }
-
- @Override
- protected void onPreExecute() {
- BroadcastHelper.broadcast(context, PROGRESS_START);
- }
-
- @Override
- protected Void doInBackground(Void... params) {
-
- try {
- bitmap = BitmapFactory.decodeStream(contentResolver.openInputStream(uri));
- metadata = PhotoSphereParser.parse(contentResolver.openInputStream(uri));
- } catch (IOException | OutOfMemoryError e) {
- e.printStackTrace();
- }
-
- return null;
- }
-
- @Override
- protected void onPostExecute(Void result) {
- BroadcastHelper.broadcast(context, PROGRESS_FINISHED);
- switch (type) {
- case MIME_PHOTO_SPHERE:
- showFragment(FragmentType.SPHERE);
- break;
-
- default:
- if (metadata != null) {
- displayPhotoSphere();
- } else {
- displayFlatImage();
- }
- break;
- }
- }
- }
}
diff --git a/app/src/main/java/de/trac/spherical/SphereFragment.java b/app/src/main/java/de/trac/spherical/SphereFragment.java
index 509ad9c..f0af724 100644
--- a/app/src/main/java/de/trac/spherical/SphereFragment.java
+++ b/app/src/main/java/de/trac/spherical/SphereFragment.java
@@ -2,6 +2,7 @@ package de.trac.spherical;
import android.graphics.Bitmap;
import android.os.Bundle;
+import android.support.v4.view.GestureDetectorCompat;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.Menu;
@@ -12,6 +13,8 @@ import android.view.View;
import android.view.ViewGroup;
import android.widget.FrameLayout;
+import butterknife.BindView;
+import butterknife.ButterKnife;
import de.trac.spherical.rendering.PhotoSphereSurfaceView;
/**
@@ -21,31 +24,37 @@ public class SphereFragment extends ImageFragment implements View.OnTouchListene
private static final String TAG = "SphericalSFrag";
+ @BindView(R.id.container_sphere)
+ FrameLayout frameLayout;
+
private PhotoSphereSurfaceView surfaceView;
+ private Bitmap bitmap;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup parent, Bundle savedInstanceState) {
- Log.d(TAG, "onCreateView");
- return inflater.inflate(R.layout.fragment_sphere, parent, false);
+ View view = inflater.inflate(R.layout.fragment_sphere, parent, false);
+ ButterKnife.bind(this, view);
+ return view;
}
@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
- Log.d(TAG, "onViewCreated");
setHasOptionsMenu(true);
- FrameLayout fragmentRoot = (FrameLayout) view.findViewById(R.id.container_sphere);
surfaceView = new PhotoSphereSurfaceView(getContext());
// Initialize renderer and setup surface view.
- fragmentRoot.addView(surfaceView);
-
+ frameLayout.addView(surfaceView);
surfaceView.setOnTouchListener(this);
- updateBitmap(getMainActivity().getBitmap());
+ updateBitmap(bitmap);
}
@Override
public boolean onTouch(View v, MotionEvent event) {
- return getMainActivity().getGestureDetector().onTouchEvent(event);
+ MainActivity activity = ((MainActivity)getActivity());
+ if (activity != null) {
+ return activity.getGestureDetector().onTouchEvent(event);
+ }
+ return false;
}
@Override
@@ -56,20 +65,15 @@ public class SphereFragment extends ImageFragment implements View.OnTouchListene
@Override
public boolean onOptionsItemSelected(MenuItem item) {
- switch (item.getItemId()) {
- case R.id.menu_force_flat:
- getMainActivity().displayFlatImage();
- return true;
- }
return super.onOptionsItemSelected(item);
}
@Override
public void updateBitmap(Bitmap bitmap) {
- if (surfaceView == null) {
- return;
+ this.bitmap = bitmap;
+ if (surfaceView != null && bitmap != null) {
+ surfaceView.setBitmap(bitmap);
}
- surfaceView.setBitmap(bitmap);
}
public PhotoSphereSurfaceView getSurfaceView() {
diff --git a/app/src/main/java/de/trac/spherical/rendering/PhotoSphereRenderer.java b/app/src/main/java/de/trac/spherical/rendering/PhotoSphereRenderer.java
index 53d8770..6084a97 100644
--- a/app/src/main/java/de/trac/spherical/rendering/PhotoSphereRenderer.java
+++ b/app/src/main/java/de/trac/spherical/rendering/PhotoSphereRenderer.java
@@ -203,12 +203,12 @@ public class PhotoSphereRenderer implements GLSurfaceView.Renderer {
// Tell the main activity we are going to do an expensive operation.
BroadcastHelper.broadcast(surfaceView.getContext(), BroadcastHelper.BroadcastType.PROGRESS_START);
- // Check if requestedBitmap needs to be downsampled.
+ // Check if requestedBitmap needs to be down-sampled.
int [] maxTextureSize = new int[1];
glGetIntegerv(GL_MAX_TEXTURE_SIZE, maxTextureSize, 0);
float maxSize = Math.max(requestedBitmap.getWidth(), requestedBitmap.getHeight());
if(maxSize > maxTextureSize[0]) { // TODO: implement tiling technique
- Log.w(TAG, "Image too big, exceeding " + maxTextureSize[0] + " : will be downsampled");
+ Log.w(TAG, "Image too big, exceeding " + maxTextureSize[0] + " : will be down-sampled");
int newWidth = (int) (requestedBitmap.getWidth() * maxTextureSize[0] / maxSize);
int newHeight = (int) (requestedBitmap.getHeight() * maxTextureSize[0] / maxSize);
requestedBitmap = Bitmap.createScaledBitmap(requestedBitmap, newWidth, newHeight, true);
diff --git a/app/src/main/java/de/trac/spherical/util/LoadImageTask.java b/app/src/main/java/de/trac/spherical/util/LoadImageTask.java
new file mode 100644
index 0000000..e829927
--- /dev/null
+++ b/app/src/main/java/de/trac/spherical/util/LoadImageTask.java
@@ -0,0 +1,76 @@
+package de.trac.spherical.util;
+
+import android.content.ContentResolver;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.net.Uri;
+import android.os.AsyncTask;
+
+import java.io.IOException;
+
+import de.trac.spherical.parser.PhotoSphereMetadata;
+import de.trac.spherical.parser.PhotoSphereParser;
+
+/**
+ * Dedicated async tasks to load an image.
+ * Takes a progress reporter and informs it about the changes.
+ */
+public class LoadImageTask extends AsyncTask {
+
+ private ContentResolver contentResolver;
+ private Uri uri;
+
+ private Bitmap bitmap;
+ private PhotoSphereMetadata metadata;
+ private final String type;
+ private final FinishedCallback callback;
+
+ public LoadImageTask(ContentResolver contentResolver, Uri uri, String type, FinishedCallback callback) {
+ this.callback = callback;
+ this.contentResolver = contentResolver;
+ this.uri = uri;
+ this.type = type;
+ }
+
+ @Override
+ protected Result doInBackground(Void... params) {
+
+ try {
+ bitmap = BitmapFactory.decodeStream(contentResolver.openInputStream(uri));
+ metadata = PhotoSphereParser.parse(contentResolver.openInputStream(uri));
+ return new Result(bitmap, metadata);
+ } catch (IOException | OutOfMemoryError e) {
+ e.printStackTrace();
+ }
+
+ return null;
+ }
+
+ @Override
+ protected void onPostExecute(Result result) {
+ callback.onImageLoadingFinished(result);
+ }
+
+ public interface FinishedCallback {
+ void onImageLoadingFinished(Result result);
+ }
+
+ public static class Result {
+
+ private Bitmap bitmap;
+ private PhotoSphereMetadata metadata;
+
+ public Result(Bitmap bitmap, PhotoSphereMetadata metadata) {
+ this.bitmap = bitmap;
+ this.metadata = metadata;
+ }
+
+ public Bitmap getBitmap() {
+ return bitmap;
+ }
+
+ public PhotoSphereMetadata getMetadata() {
+ return metadata;
+ }
+ }
+}