aboutsummaryrefslogtreecommitdiff
path: root/apps/NotificationStudio/src/com/android/notificationstudio/NotificationStudioActivity.java
diff options
context:
space:
mode:
Diffstat (limited to 'apps/NotificationStudio/src/com/android/notificationstudio/NotificationStudioActivity.java')
-rw-r--r--apps/NotificationStudio/src/com/android/notificationstudio/NotificationStudioActivity.java249
1 files changed, 249 insertions, 0 deletions
diff --git a/apps/NotificationStudio/src/com/android/notificationstudio/NotificationStudioActivity.java b/apps/NotificationStudio/src/com/android/notificationstudio/NotificationStudioActivity.java
new file mode 100644
index 000000000..9c2e8119a
--- /dev/null
+++ b/apps/NotificationStudio/src/com/android/notificationstudio/NotificationStudioActivity.java
@@ -0,0 +1,249 @@
+/*
+ * Copyright 2012 The Android Open Source Project
+ *
+ * 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 com.android.notificationstudio;
+
+import android.animation.Animator;
+import android.animation.AnimatorListenerAdapter;
+import android.app.Activity;
+import android.app.Notification;
+import android.app.NotificationManager;
+import android.content.Context;
+import android.os.Build;
+import android.os.Bundle;
+import android.os.Handler;
+import android.util.DisplayMetrics;
+import android.util.Log;
+import android.view.Menu;
+import android.view.MenuInflater;
+import android.view.MenuItem;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.View.OnLayoutChangeListener;
+import android.view.ViewGroup;
+import android.view.inputmethod.InputMethodManager;
+import android.widget.EditText;
+import android.widget.FrameLayout;
+import android.widget.FrameLayout.LayoutParams;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.RemoteViews;
+import android.widget.TextView;
+
+import com.android.notificationstudio.action.ShareCodeAction;
+import com.android.notificationstudio.action.ShareMockupAction;
+import com.android.notificationstudio.editor.Editors;
+import com.android.notificationstudio.generator.NotificationGenerator;
+import com.android.notificationstudio.model.EditableItem;
+import com.android.notificationstudio.model.EditableItemConstants;
+
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+public class NotificationStudioActivity extends Activity implements EditableItemConstants{
+ private static final String TAG = NotificationStudioActivity.class.getSimpleName();
+ private static final int PREVIEW_NOTIFICATION = 1;
+ private static final int REFRESH_DELAY = 50;
+ private static final ExecutorService BACKGROUND = Executors.newSingleThreadExecutor();
+
+ private boolean mRefreshPending;
+
+ private final Handler mHandler = new Handler();
+ private final Runnable mRefreshNotificationInner = new Runnable() {
+ public void run() {
+ refreshNotificationInner();
+ }};
+
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ getWindow().setBackgroundDrawableResource(android.R.color.black);
+ setContentView(R.layout.studio);
+ initPreviewScroller();
+
+ EditableItem.initIfNecessary(this);
+
+ initEditors();
+ }
+
+ private void initPreviewScroller() {
+
+ MaxHeightScrollView preview = (MaxHeightScrollView) findViewById(R.id.preview_scroller);
+ if (preview == null)
+ return;
+ final int margin = ((ViewGroup.MarginLayoutParams) preview.getLayoutParams()).bottomMargin;
+ preview.addOnLayoutChangeListener(new OnLayoutChangeListener(){
+ public void onLayoutChange(View v, int left, int top, int right, int bottom,
+ int oldLeft, int oldTop, int oldRight, int oldBottom) {
+ // animate preview height changes
+ if (oldBottom != bottom) {
+ final View e = findViewById(R.id.editors);
+ final int y = bottom + margin;
+ e.animate()
+ .translationY(y - oldBottom)
+ .setListener(new AnimatorListenerAdapter() {
+ public void onAnimationEnd(Animator animation) {
+ FrameLayout.LayoutParams lp = (LayoutParams) e.getLayoutParams();
+ lp.topMargin = y;
+ e.setTranslationY(0);
+ e.setLayoutParams(lp);
+ }
+ });
+ }
+ }});
+
+ // limit the max height for preview, leave room for editors + soft keyboard
+ DisplayMetrics dm = new DisplayMetrics();
+ getWindowManager().getDefaultDisplay().getMetrics(dm);
+ float actualHeight = dm.heightPixels / dm.ydpi;
+ float pct = actualHeight < 3.5 ? .32f :
+ actualHeight < 4 ? .35f :
+ .38f;
+ preview.setMaxHeight((int)(dm.heightPixels * pct));
+ }
+
+ private void initEditors() {
+ LinearLayout items = (LinearLayout) findViewById(R.id.items);
+ items.removeAllViews();
+ String currentCategory = null;
+ for (EditableItem item : EditableItem.values()) {
+ String itemCategory = item.getCategory(this);
+ if (!itemCategory.equals(currentCategory)) {
+ View dividerView = getLayoutInflater().inflate(R.layout.divider, null);
+ ((TextView) dividerView.findViewById(R.id.divider_text)).setText(itemCategory);
+ items.addView(dividerView);
+ currentCategory = itemCategory;
+ }
+ View editorView = Editors.newEditor(this, items, item);
+ if (editorView != null)
+ items.addView(editorView);
+ }
+ refreshNotification();
+ }
+
+ @Override
+ protected void onRestoreInstanceState(Bundle savedInstanceState) {
+ // we'll take care of restoring state
+ }
+
+ public void refreshNotification() {
+ mRefreshPending = true;
+ mHandler.postDelayed(mRefreshNotificationInner, REFRESH_DELAY);
+ }
+
+ private void refreshNotificationInner() {
+ if (!mRefreshPending) {
+ return;
+ }
+ final Notification notification = NotificationGenerator.build(this);
+ ViewGroup oneU = (ViewGroup) findViewById(R.id.oneU);
+ ViewGroup fourU = (ViewGroup) findViewById(R.id.fourU);
+ View oneUView = refreshRemoteViews(oneU, notification.contentView);
+ if (Build.VERSION.SDK_INT >= 16)
+ refreshRemoteViews(fourU, notification.bigContentView);
+ else if (Build.VERSION.SDK_INT >= 11) {
+ ImageView largeIcon = (ImageView) findViewById(R.id.large_icon);
+ largeIcon.setVisibility(notification.largeIcon == null ? View.GONE : View.VISIBLE);
+ if (notification.largeIcon != null)
+ largeIcon.setImageBitmap(notification.largeIcon);
+ } else if (oneUView != null) {
+ oneUView.setBackgroundColor(getResources().getColor(R.color.gb_background));
+ oneUView.setMinimumHeight(100);
+ }
+ mRefreshPending = false;
+
+ // this can take a while, run on a background thread
+ BACKGROUND.submit(new Runnable() {
+ public void run() {
+ NotificationManager mgr =
+ (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
+ try {
+ mgr.notify(PREVIEW_NOTIFICATION, notification);
+ } catch (Throwable t) {
+ Log.w(TAG, "Error displaying notification", t);
+ }
+ }});
+ }
+
+ private View refreshRemoteViews(ViewGroup parent, RemoteViews remoteViews) {
+ parent.removeAllViews();
+ if (remoteViews != null) {
+ parent.setVisibility(View.VISIBLE);
+ try {
+ View v = remoteViews.apply(this, parent);
+ parent.addView(v);
+ return v;
+ } catch (Exception e) {
+ TextView exceptionView = new TextView(this);
+ exceptionView.setText(e.getClass().getSimpleName() + ": " + e.getMessage());
+ parent.addView(exceptionView);
+ return exceptionView;
+ }
+ } else {
+ parent.setVisibility(View.GONE);
+ return null;
+ }
+ }
+
+ // action bar setup
+ @Override
+ public boolean onCreateOptionsMenu(Menu menu) {
+ MenuInflater inflater = getMenuInflater();
+ inflater.inflate(R.menu.action_bar, menu);
+ return true;
+ }
+
+ @Override
+ public boolean onOptionsItemSelected(MenuItem item) {
+ switch (item.getItemId()) {
+ case R.id.action_share_code:
+ ShareCodeAction.launch(this, item.getTitle());
+ return true;
+ case R.id.action_share_mockup:
+ ShareMockupAction.launch(this, item.getTitle());
+ return true;
+ }
+ return false;
+ }
+
+ // hides the soft keyboard more aggressively when leaving text editors
+ @Override
+ public boolean dispatchTouchEvent(MotionEvent event) {
+ View v = getCurrentFocus();
+ boolean ret = super.dispatchTouchEvent(event);
+
+ if (v instanceof EditText) {
+ View currentFocus = getCurrentFocus();
+ int screenCoords[] = new int[2];
+ currentFocus.getLocationOnScreen(screenCoords);
+ float x = event.getRawX() + currentFocus.getLeft() - screenCoords[0];
+ float y = event.getRawY() + currentFocus.getTop() - screenCoords[1];
+
+ if (event.getAction() == MotionEvent.ACTION_UP
+ && (x < currentFocus.getLeft() ||
+ x >= currentFocus.getRight() ||
+ y < currentFocus.getTop() ||
+ y > currentFocus.getBottom())) {
+ InputMethodManager imm =
+ (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
+ imm.hideSoftInputFromWindow(getWindow().getCurrentFocus().getWindowToken(), 0);
+ }
+ }
+ return ret;
+ }
+
+}